|
|
@@ -1,6 +1,9 @@ |
|
|
package io2 |
|
|
package io2 |
|
|
|
|
|
|
|
|
import "io" |
|
|
|
|
|
|
|
|
import ( |
|
|
|
|
|
"io" |
|
|
|
|
|
"sync" |
|
|
|
|
|
) |
|
|
|
|
|
|
|
|
type PromiseWriteCloser[T any] interface { |
|
|
type PromiseWriteCloser[T any] interface { |
|
|
io.Writer |
|
|
io.Writer |
|
|
@@ -35,6 +38,7 @@ type readCloserHook struct { |
|
|
callback func(closer io.ReadCloser) |
|
|
callback func(closer io.ReadCloser) |
|
|
once int |
|
|
once int |
|
|
isBefore bool // callback调用时机,true则在closer的Close之前调用 |
|
|
isBefore bool // callback调用时机,true则在closer的Close之前调用 |
|
|
|
|
|
lock *sync.Mutex |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
func (hook *readCloserHook) Read(buf []byte) (n int, err error) { |
|
|
func (hook *readCloserHook) Read(buf []byte) (n int, err error) { |
|
|
@@ -42,6 +46,9 @@ func (hook *readCloserHook) Read(buf []byte) (n int, err error) { |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
func (hook *readCloserHook) Close() error { |
|
|
func (hook *readCloserHook) Close() error { |
|
|
|
|
|
hook.lock.Lock() |
|
|
|
|
|
defer hook.lock.Unlock() |
|
|
|
|
|
|
|
|
if hook.once == onceDone { |
|
|
if hook.once == onceDone { |
|
|
return hook.readCloser.Close() |
|
|
return hook.readCloser.Close() |
|
|
} |
|
|
} |
|
|
@@ -69,6 +76,7 @@ func BeforeReadClosing(closer io.ReadCloser, callback func(closer io.ReadCloser) |
|
|
callback: callback, |
|
|
callback: callback, |
|
|
once: onceDisabled, |
|
|
once: onceDisabled, |
|
|
isBefore: true, |
|
|
isBefore: true, |
|
|
|
|
|
lock: &sync.Mutex{}, |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
@@ -78,6 +86,7 @@ func AfterReadClosed(closer io.ReadCloser, callback func(closer io.ReadCloser)) |
|
|
callback: callback, |
|
|
callback: callback, |
|
|
once: onceDisabled, |
|
|
once: onceDisabled, |
|
|
isBefore: false, |
|
|
isBefore: false, |
|
|
|
|
|
lock: &sync.Mutex{}, |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
@@ -87,16 +96,22 @@ func AfterReadClosedOnce(closer io.ReadCloser, callback func(closer io.ReadClose |
|
|
callback: callback, |
|
|
callback: callback, |
|
|
once: onceEnabled, |
|
|
once: onceEnabled, |
|
|
isBefore: false, |
|
|
isBefore: false, |
|
|
|
|
|
lock: &sync.Mutex{}, |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
type afterEOF struct { |
|
|
type afterEOF struct { |
|
|
inner io.ReadCloser |
|
|
inner io.ReadCloser |
|
|
callback func(str io.ReadCloser, err error) |
|
|
callback func(str io.ReadCloser, err error) |
|
|
|
|
|
lock *sync.Mutex |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
func (hook *afterEOF) Read(buf []byte) (n int, err error) { |
|
|
func (hook *afterEOF) Read(buf []byte) (n int, err error) { |
|
|
n, err = hook.inner.Read(buf) |
|
|
n, err = hook.inner.Read(buf) |
|
|
|
|
|
|
|
|
|
|
|
hook.lock.Lock() |
|
|
|
|
|
defer hook.lock.Unlock() |
|
|
|
|
|
|
|
|
if hook.callback != nil { |
|
|
if hook.callback != nil { |
|
|
if err == io.EOF { |
|
|
if err == io.EOF { |
|
|
hook.callback(hook.inner, nil) |
|
|
hook.callback(hook.inner, nil) |
|
|
@@ -111,6 +126,10 @@ func (hook *afterEOF) Read(buf []byte) (n int, err error) { |
|
|
|
|
|
|
|
|
func (hook *afterEOF) Close() error { |
|
|
func (hook *afterEOF) Close() error { |
|
|
err := hook.inner.Close() |
|
|
err := hook.inner.Close() |
|
|
|
|
|
|
|
|
|
|
|
hook.lock.Lock() |
|
|
|
|
|
defer hook.lock.Unlock() |
|
|
|
|
|
|
|
|
if hook.callback != nil { |
|
|
if hook.callback != nil { |
|
|
hook.callback(hook.inner, io.ErrClosedPipe) |
|
|
hook.callback(hook.inner, io.ErrClosedPipe) |
|
|
hook.callback = nil |
|
|
hook.callback = nil |
|
|
@@ -122,6 +141,7 @@ func AfterEOF(str io.ReadCloser, callback func(str io.ReadCloser, err error)) io |
|
|
return &afterEOF{ |
|
|
return &afterEOF{ |
|
|
inner: str, |
|
|
inner: str, |
|
|
callback: callback, |
|
|
callback: callback, |
|
|
|
|
|
lock: &sync.Mutex{}, |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|