Skip to content
This repository was archived by the owner on Jul 18, 2025. It is now read-only.

Commit 1e141b3

Browse files
committed
Merge pull request #67 from dmcgowan/copy_updates
Fix copying
2 parents a9af616 + a4c7a6e commit 1e141b3

2 files changed

Lines changed: 122 additions & 8 deletions

File tree

inmem.go

Lines changed: 58 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -300,17 +300,26 @@ func (w *pipeSender) copyValue(v interface{}) (interface{}, error) {
300300
}
301301
case io.ReadWriteCloser:
302302
return w.copyByteStream(val)
303+
case io.ReadCloser:
304+
return w.copyByteReadStream(val)
305+
case io.WriteCloser:
306+
return w.copyByteWriteStream(val)
303307
case Sender:
304308
return w.copySender(val)
305309
case Receiver:
306310
return w.copyReceiver(val)
307311
case map[string]interface{}:
308312
return w.copyChannelMessage(val)
309-
case struct{}:
310-
return w.copyStructure(v)
311-
case *struct{}:
312-
return w.copyStructure(v)
313+
case map[interface{}]interface{}:
314+
return w.copyChannelInterfaceMessage(val)
313315
default:
316+
if rv := reflect.ValueOf(v); rv.Kind() == reflect.Ptr {
317+
if rv.Elem().Kind() == reflect.Struct {
318+
return w.copyStructValue(rv.Elem())
319+
}
320+
} else if rv.Kind() == reflect.Struct {
321+
return w.copyStructValue(rv)
322+
}
314323
}
315324
return v, nil
316325
}
@@ -355,6 +364,31 @@ func (w *pipeSender) copyByteStream(stream io.ReadWriteCloser) (io.ReadWriteClos
355364
return streamCopy, nil
356365
}
357366

367+
func (w *pipeSender) copyByteReadStream(stream io.ReadCloser) (io.ReadCloser, error) {
368+
streamCopy, err := w.session.newByteStream()
369+
if err != nil {
370+
return nil, err
371+
}
372+
go func() {
373+
io.Copy(streamCopy, stream)
374+
streamCopy.Close()
375+
stream.Close()
376+
}()
377+
return streamCopy, nil
378+
}
379+
380+
func (w *pipeSender) copyByteWriteStream(stream io.WriteCloser) (io.WriteCloser, error) {
381+
streamCopy, err := w.session.newByteStream()
382+
if err != nil {
383+
return nil, err
384+
}
385+
go func() {
386+
io.Copy(stream, streamCopy)
387+
stream.Close()
388+
}()
389+
return streamCopy, nil
390+
}
391+
358392
func (w *pipeSender) copyChannelMessage(m map[string]interface{}) (interface{}, error) {
359393
mCopy := make(map[string]interface{})
360394
for k, v := range m {
@@ -368,6 +402,22 @@ func (w *pipeSender) copyChannelMessage(m map[string]interface{}) (interface{},
368402
return mCopy, nil
369403
}
370404

405+
func (w *pipeSender) copyChannelInterfaceMessage(m map[interface{}]interface{}) (interface{}, error) {
406+
mCopy := make(map[string]interface{})
407+
for k, v := range m {
408+
vCopy, vErr := w.copyValue(v)
409+
if vErr != nil {
410+
return nil, vErr
411+
}
412+
keyStr, ok := k.(string)
413+
if !ok {
414+
return nil, errors.New("invalid non string key")
415+
}
416+
mCopy[keyStr] = vCopy
417+
}
418+
419+
return mCopy, nil
420+
}
371421
func (w *pipeSender) copyStructure(m interface{}) (interface{}, error) {
372422
v := reflect.ValueOf(m)
373423
if v.Kind() == reflect.Ptr {
@@ -376,6 +426,10 @@ func (w *pipeSender) copyStructure(m interface{}) (interface{}, error) {
376426
if v.Kind() != reflect.Struct {
377427
return nil, errors.New("invalid non struct type")
378428
}
429+
return w.copyStructValue(v)
430+
}
431+
432+
func (w *pipeSender) copyStructValue(v reflect.Value) (interface{}, error) {
379433
mCopy := make(map[string]interface{})
380434
t := v.Type()
381435
for i := 0; i < v.NumField(); i++ {

spdy/copy.go

Lines changed: 64 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -32,23 +32,37 @@ func (c *channel) copyValue(v interface{}) (interface{}, error) {
3232
}
3333
return c.copySender(val)
3434
}
35+
case *channelWrapper:
36+
if val.direction == inbound {
37+
return c.copyReceiver(val)
38+
}
39+
return c.copySender(val)
3540
case *net.TCPConn:
3641
// Do nothing until socket support is added
3742
case *net.UDPConn:
3843
// Do nothing until socket support is added
3944
case io.ReadWriteCloser:
4045
return c.copyByteStream(val)
46+
case io.ReadCloser:
47+
return c.copyByteReadStream(val)
48+
case io.WriteCloser:
49+
return c.copyByteWriteStream(val)
4150
case libchan.Sender:
4251
return c.copySender(val)
4352
case libchan.Receiver:
4453
return c.copyReceiver(val)
4554
case map[string]interface{}:
4655
return c.copyChannelMessage(val)
47-
case struct{}:
48-
return c.copyStructure(v)
49-
case *struct{}:
50-
return c.copyStructure(v)
56+
case map[interface{}]interface{}:
57+
return c.copyChannelInterfaceMessage(val)
5158
default:
59+
if rv := reflect.ValueOf(v); rv.Kind() == reflect.Ptr {
60+
if rv.Elem().Kind() == reflect.Struct {
61+
return c.copyStructValue(rv.Elem())
62+
}
63+
} else if rv.Kind() == reflect.Struct {
64+
return c.copyStructValue(rv)
65+
}
5266
}
5367
return v, nil
5468
}
@@ -93,6 +107,31 @@ func (c *channel) copyByteStream(stream io.ReadWriteCloser) (io.ReadWriteCloser,
93107
return streamCopy, nil
94108
}
95109

110+
func (c *channel) copyByteReadStream(stream io.ReadCloser) (io.ReadCloser, error) {
111+
streamCopy, err := c.session.createByteStream()
112+
if err != nil {
113+
return nil, err
114+
}
115+
go func() {
116+
io.Copy(streamCopy, stream)
117+
streamCopy.Close()
118+
stream.Close()
119+
}()
120+
return streamCopy, nil
121+
}
122+
123+
func (c *channel) copyByteWriteStream(stream io.WriteCloser) (io.WriteCloser, error) {
124+
streamCopy, err := c.session.createByteStream()
125+
if err != nil {
126+
return nil, err
127+
}
128+
go func() {
129+
io.Copy(stream, streamCopy)
130+
stream.Close()
131+
}()
132+
return streamCopy, nil
133+
}
134+
96135
func (c *channel) copyChannelMessage(m map[string]interface{}) (interface{}, error) {
97136
mCopy := make(map[string]interface{})
98137
for k, v := range m {
@@ -106,6 +145,23 @@ func (c *channel) copyChannelMessage(m map[string]interface{}) (interface{}, err
106145
return mCopy, nil
107146
}
108147

148+
func (c *channel) copyChannelInterfaceMessage(m map[interface{}]interface{}) (interface{}, error) {
149+
mCopy := make(map[string]interface{})
150+
for k, v := range m {
151+
vCopy, vErr := c.copyValue(v)
152+
if vErr != nil {
153+
return nil, vErr
154+
}
155+
keyStr, ok := k.(string)
156+
if !ok {
157+
return nil, errors.New("invalid non string key")
158+
}
159+
mCopy[keyStr] = vCopy
160+
}
161+
162+
return mCopy, nil
163+
}
164+
109165
func (c *channel) copyStructure(m interface{}) (interface{}, error) {
110166
v := reflect.ValueOf(m)
111167
if v.Kind() == reflect.Ptr {
@@ -114,6 +170,10 @@ func (c *channel) copyStructure(m interface{}) (interface{}, error) {
114170
if v.Kind() != reflect.Struct {
115171
return nil, errors.New("invalid non struct type")
116172
}
173+
return c.copyStructValue(v)
174+
}
175+
176+
func (c *channel) copyStructValue(v reflect.Value) (interface{}, error) {
117177
mCopy := make(map[string]interface{})
118178
t := v.Type()
119179
for i := 0; i < v.NumField(); i++ {

0 commit comments

Comments
 (0)