@@ -430,7 +430,7 @@ func (dc *DuplexConnection) killCallback(sid uint32) {
430430}
431431
432432// RequestChannel start a request of RequestChannel.
433- func (dc * DuplexConnection ) RequestChannel (sending flux.Flux ) (ret flux.Flux ) {
433+ func (dc * DuplexConnection ) RequestChannel (request payload. Payload , sending flux.Flux ) (ret flux.Flux ) {
434434 if dc .closed .Load () {
435435 ret = flux .Error (errSocketClosed )
436436 return
@@ -481,9 +481,56 @@ func (dc *DuplexConnection) RequestChannel(sending flux.Flux) (ret flux.Flux) {
481481 return
482482 }
483483
484+ // First request - send the initial REQUEST_CHANNEL frame with the request payload,
485+ // then subscribe to the sending flux for subsequent payloads.
486+ releasable , isReleasable := request .(common.Releasable )
487+
488+ if isReleasable {
489+ releasable .IncRef ()
490+ }
491+
492+ data := request .Data ()
493+ metadata , _ := request .Metadata ()
494+
495+ size := framing .CalcPayloadFrameSize (data , metadata ) + 4
496+ if ! dc .shouldSplit (size ) {
497+ toBeSent := framing .NewWriteableRequestChannelFrame (sid , n , data , metadata , core .FlagNext )
498+
499+ if isReleasable {
500+ toBeSent .HandleDone (func () {
501+ releasable .Release ()
502+ })
503+ }
504+
505+ if ok := dc .sendFrame (toBeSent ); ! ok {
506+ dc .killCallback (sid )
507+ return
508+ }
509+ } else {
510+ dc .doSplitSkip (4 , data , metadata , func (index int , result fragmentation.SplitResult ) {
511+ var toBeSent core.WriteableFrame
512+ if index == 0 {
513+ toBeSent = framing .NewWriteableRequestChannelFrame (sid , n , result .Data , result .Metadata , result .Flag | core .FlagNext )
514+ } else {
515+ toBeSent = framing .NewWriteablePayloadFrame (sid , result .Data , result .Metadata , result .Flag | core .FlagNext )
516+ }
517+
518+ // Add release hook at last frame.
519+ if ! result .Flag .Check (core .FlagFollow ) && isReleasable {
520+ toBeSent .HandleDone (func () {
521+ releasable .Release ()
522+ })
523+ }
524+
525+ if ok := dc .sendFrame (toBeSent ); ! ok {
526+ dc .killCallback (sid )
527+ }
528+ })
529+ }
530+
531+ // Subscribe to sending flux for subsequent payloads
484532 sub := & requestChannelSubscriber {
485533 sid : sid ,
486- n : n ,
487534 dc : dc ,
488535 rcv : receiving ,
489536 }
@@ -613,7 +660,7 @@ func (dc *DuplexConnection) respondRequestChannel(req fragmentation.HeaderAndPay
613660 }
614661 logger .Errorf ("handle request-channel failed: %+v\n " , err )
615662 }()
616- resp = dc .responder .RequestChannel (receiving )
663+ resp = dc .responder .RequestChannel (req , receiving )
617664 if resp == nil {
618665 err = framing .NewWriteableErrorFrame (sid , core .ErrorCodeApplicationError , unsupportedRequestChannel )
619666 }
@@ -643,8 +690,6 @@ func (dc *DuplexConnection) respondRequestChannel(req fragmentation.HeaderAndPay
643690 sending .SubscribeWith (dc .ctx , sub )
644691 })
645692
646- receivingProcessor .Next (req )
647-
648693 <- subscribed
649694
650695 return nil
0 commit comments