diff --git a/datachannel.go b/datachannel.go index 0050185..606444b 100644 --- a/datachannel.go +++ b/datachannel.go @@ -118,12 +118,7 @@ func Client(stream *sctp.Stream, config *Config) (*DataChannel, error) { return nil, fmt.Errorf("failed to send ChannelOpen %w", err) } } - dc := newDataChannel(stream, config) - - if err := dc.commitReliabilityParams(); err != nil { - return nil, err - } - return dc, nil + return newDataChannel(stream, config), nil } // Accept is used to accept incoming data channels over SCTP @@ -285,6 +280,9 @@ func (c *DataChannel) handleDCEP(data []byte) error { switch msg := msg.(type) { case *channelAck: + if err := c.commitReliabilityParams(); err != nil { + return err + } c.onOpenComplete() default: return fmt.Errorf("%w, wanted ACK got %v", ErrUnexpectedDataChannelType, msg) diff --git a/datachannel_test.go b/datachannel_test.go index 9c4965f..0df30d6 100644 --- a/datachannel_test.go +++ b/datachannel_test.go @@ -384,8 +384,34 @@ func TestDataChannel(t *testing.T) { assert.True(t, reflect.DeepEqual(dc0.Config, *cfg), "local config should match") assert.True(t, reflect.DeepEqual(dc1.Config, *cfg), "remote config should match") + // reliability parameters are committed after data channel open ACK is received on client side, + // wait for open to be completed + openCompleted := make(chan bool) + dc0.OnOpen(func() { + close(openCompleted) + }) + var n int + // write a message as ReadChannel loops till user data is read + bridgeProcessAtLeastOne(br) + binary.BigEndian.PutUint32(sbuf, 10) + n, err = dc1.WriteDataChannel(sbuf, true) + assert.Nil(t, err, "Write() should succeed") + assert.Equal(t, len(sbuf), n, "data length should match") + + // read data channel open ACK and the user message sent above + bridgeProcessAtLeastOne(br) + _, _, err = dc0.ReadDataChannel(rbuf) + assert.NoError(t, err) + + select { + case <-time.After(time.Second * 10): + assert.FailNow(t, "OnOpen() failed to fire 10s") + case <-openCompleted: + } + + // test unordered messages binary.BigEndian.PutUint32(sbuf, 1) n, err = dc0.WriteDataChannel(sbuf, true) assert.Nil(t, err, "Write() should succeed")