Skip to content
This repository was archived by the owner on Oct 23, 2024. It is now read-only.

Commit d26b35e

Browse files
authored
Fix stream API issues (#1313)
1 parent 1246a33 commit d26b35e

23 files changed

+559
-207
lines changed

doc/servermd/StreamAPI.md

Lines changed: 147 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ Because it's REST, management clients can be implemented by different programmin
1919
To enable stream API, add experimental targets `stream-service` and `customized-agent` during packing. `stream-service` is the module that provide stream related API. `customized-agent` is the module that provide server side customization for stream related API.
2020

2121
After packing, the stream API configuration is in stream_service/service.toml.
22-
Edit portal/portal.toml, set `stream_engine_name` to the same value of stream API configuration.
22+
Edit portal/portal.toml, set `stream_engine_name` to the same value of stream API configuration(`service.name` or `scheduler.name` in stream_service/service.toml).
2323
Edit management_api/management_api.toml, set `stream_engine` and `control_agent` to the same values of stream API configuration.
2424

2525
Start OWT service with updated configuration, stream API should be enabled.
@@ -236,7 +236,9 @@ request body:
236236

237237
object(ListQuery):
238238
{
239-
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
239+
query: {
240+
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
241+
}
240242
}
241243

242244
response body:
@@ -273,7 +275,9 @@ request body:
273275
type: string(publishType), // E.g, "streaming", "video", ...
274276
participant: string(participantId), // Or use domain name as participant ID.
275277
media: object(MediaTrack) | object(MediaInfo),
276-
info: object(TypeSpecificInfo)
278+
info: object(TypeSpecificInfo),
279+
connection: object(ConnectionInfo) | undefined, // For "streaming"
280+
processor: string(processorId) | undefined, // For "audio", "video"
277281
}
278282
object(MediaTrack) { // For WebRTC publications
279283
tracks: [ object(TrackInfo) ],
@@ -287,6 +291,11 @@ request body:
287291
parameters: object(VideoParameters)
288292
}
289293
}
294+
object(ConnectionInfo) { // For streaming publications
295+
url: string(streamingUrl),
296+
transportProtocol: "tcp" | "udp",
297+
bufferSize: number(bufferSize),
298+
},
290299

291300
For *object(TrackInfo)*, refers to [tracks in MediaOptions](../Client-Portal%20Protocol.md#331-participant-joins-a-room).
292301
For *format* and *parameters*, refers to [REST API](RESTAPI.md#53-streams-StreamAPIsection53).
@@ -367,7 +376,9 @@ request body:
367376

368377
object(ListQuery):
369378
{
370-
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
379+
query: {
380+
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
381+
}
371382
}
372383

373384
response body:
@@ -404,7 +415,9 @@ request body:
404415
type: string(subscribeType), // E.g, "streaming", "video", ...
405416
participant: string(participantId), // Or use domain name as participant ID.
406417
media: object(MediaTrack) | object(MediaInfo),
407-
info: object(TypeSpecificInfo)
418+
info: object(TypeSpecificInfo),
419+
connection: object(ConnectionInfo) | undefined, // For "streaming", "recording"
420+
processor: string(processorId) | undefined, // For "audio", "video", "analytics"
408421
}
409422
object(MediaTrack) { // For WebRTC subscriptions
410423
tracks: [ object(TrackInfo) ],
@@ -413,12 +426,21 @@ request body:
413426
audio: {
414427
from: string(sourceAudioId), // Could be publication ID or source track ID
415428
format: object(AudioFormat),
416-
},
429+
} | boolean(enable),
417430
video: {
418431
from: string(sourceVideoId), // Could be publication ID or source track ID
419432
format: object(VideoFormat),
420433
parameters: object(VideoParameters)
421-
}
434+
} | boolean(enable)
435+
}
436+
object(ConnectionInfo) {
437+
container: "mkv" | "mp4" | undefined, // For "recording"
438+
url: string(url) | undefined, // For "streaming"
439+
algorithm: string(algorithmName) | undefined, // For "analytics"
440+
video: { // For "analytics"
441+
format: object(VideoFormat), // Analytics output video format
442+
parameters: object(VideoParameters), // Analytics output video parameters
443+
} | undefined,
422444
}
423445

424446
For *object(TrackInfo)*, refers to [tracks in MediaOptions](../Client-Portal%20Protocol.md#331-participant-joins-a-room).
@@ -497,7 +519,9 @@ request body:
497519

498520
object(ListQuery):
499521
{
500-
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
522+
query: {
523+
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
524+
}
501525
}
502526

503527
response body:
@@ -577,6 +601,14 @@ request body:
577601
id: string(analyticsId)
578602
}
579603

604+
// For "sip" type processor
605+
sip: {
606+
server: string(serverHost),
607+
user: string(sipUser),
608+
password: string(sipPasswd)
609+
},
610+
stream: string(outgoingSipStream)
611+
580612
For *object(Region)*, refers to [REST API](RESTAPI.md#51-rooms-StreamAPIsection51).
581613

582614
response body:
@@ -605,7 +637,109 @@ response body:
605637

606638
**Empty**
607639

608-
## 5.5 Nodes {#StreamAPIsection5_5}
640+
## 5.5 Participants {#StreamAPIsection5_5}
641+
Description:<br>
642+
Participants represents owner of publications and subscriptions in OWT server.<br>
643+
644+
Resources:
645+
646+
- /v1.1/stream-engine/participants
647+
- /v1.1/stream-engine/participants/{participantId}
648+
649+
Data Model:
650+
651+
Object(Participant) {
652+
id: string(ParticipantID),
653+
domain: string(domainName), // For example, room ID
654+
portal: string(portalId),
655+
notifying: boolean(notifyOthers), // Notify other participants about join/leave.
656+
}
657+
658+
### List Participants {#StreamAPIsection5_5_1}
659+
**GET ${host}/v1.1/stream-engine/participants**
660+
**GET ${host}/v1.1/stream-engine/participants/{participantId}**
661+
662+
Description:<br>
663+
List participants in stream engine.<br>
664+
665+
request body:
666+
667+
| type | content |
668+
|:-------------|:-------|
669+
| json | object(ListQuery) |
670+
671+
**Note**: Definition of *ListQuery*.<br>
672+
673+
object(ListQuery):
674+
{
675+
query: {
676+
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
677+
}
678+
}
679+
680+
response body:
681+
682+
| type | content |
683+
|:-------------|:-------|
684+
| json | Object(ListResult) |
685+
686+
**Note**: Definition of *ListResult*.<br>
687+
688+
object(ListResult):
689+
{
690+
total: number(ListSize),
691+
start: number(offsetInList),
692+
data: [ object(Participant) ]
693+
}
694+
695+
### Create Participant {#StreamAPIsection5_5_2}
696+
**POST ${host}/v1.1/stream-engine/participants**
697+
698+
Description:<br>
699+
Create a participant with configuration.<br>
700+
701+
request body:
702+
703+
| type | content |
704+
|:-------------|:-------|
705+
| json | object(ParticipantRequest) |
706+
707+
**Note**: Definition of *ParticipantRequest*.<br>
708+
709+
Object(ParticipantRequest) {
710+
id: string(ParticipantID),
711+
domain: string(domainName),
712+
notifying: boolean(notifyOthers), // Notify other participants about join/leave.
713+
}
714+
715+
response body:
716+
717+
| type | content |
718+
|:-------------|:-------|
719+
| json | object(IdObject) |
720+
721+
**Note**: Definition of *IdObject*.<br>
722+
723+
Object(IdObject) {
724+
id: string(createdParticipantId)
725+
}
726+
727+
### Delete Participant {#StreamAPIsection5_5_3}
728+
**DELETE ${host}/v1.1/stream-engine/participants/{participantId}**
729+
730+
Description:<br>
731+
Drop the specified participant, all related publications and subscriptions will be stopped as well.<br>
732+
733+
request body:
734+
735+
**Empty**
736+
737+
response body:
738+
739+
**Empty**
740+
741+
742+
## 5.6 Nodes {#StreamAPIsection5_6}
609743
Description:<br>
610744
Node represents working process in stream engine.<br>
611745

@@ -624,7 +758,7 @@ Data Model:
624758
streamAddr: {ip: string(host), port: number(port)}
625759
}
626760

627-
### List Nodes {#StreamAPIsection5_5_1}
761+
### List Nodes {#StreamAPIsection5_6_1}
628762
**GET ${host}/v1.1/stream-engine/nodes**
629763

630764
Description:<br>
@@ -640,7 +774,9 @@ request body:
640774

641775
object(ListQuery):
642776
{
643-
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
777+
query: {
778+
KEY: VALUE // Specified key-value pair for query result, such as `{name: "default"}`
779+
}
644780
}
645781

646782
response body:

source/agent/analytics/index.js

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,9 @@ module.exports = function (rpcClient, rpcId, agentId, clusterIp) {
210210

211211
this.connectionclose = () => {
212212
destroyStream(options.controller, newStreamId);
213+
// Notify stream engine if needed
214+
const data = {id: newStreamId};
215+
notifyStatus(options.controller, connectionId, 'onStreamRemoved', data);
213216
}
214217
inputs[connectionId] = true;
215218

@@ -259,11 +262,10 @@ module.exports = function (rpcClient, rpcId, agentId, clusterIp) {
259262
}
260263
}
261264

262-
// For Stream Engine, onSessionProgress(id, name, data)
265+
generateStream(options.controller, newStreamId, streamInfo);
266+
// Notify stream engine if needed
263267
streamInfo.id = newStreamId;
264-
notifyStatus(controller, connectionId, 'onNewStream', streamInfo);
265-
266-
// generateStream(options.controller, newStreamId, streamInfo);
268+
notifyStatus(controller, connectionId, 'onStreamAdded', streamInfo);
267269
} catch (e) {
268270
log.error("Parse stream added data with error:", e);
269271
}

source/agent/conference/rpcRequest.js

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -574,10 +574,12 @@ const RpcRequest = function(rpcChannel, listener) {
574574
};
575575

576576
that.addSipNode = function (workerNode) {
577-
grpcNode[workerNode] = grpcTools.startClient(
578-
'sip',
579-
workerNode
580-
);
577+
if (enableGrpc) {
578+
grpcNode[workerNode] = grpcTools.startClient(
579+
'sip',
580+
workerNode
581+
);
582+
}
581583
}
582584

583585
return that;

0 commit comments

Comments
 (0)