You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

SDP.spec.js 67KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422
  1. import { $iq } from 'strophe.js';
  2. import FeatureFlags from '../flags/FeatureFlags';
  3. import { expandSourcesFromJson } from '../xmpp/JingleHelperFunctions';
  4. import $ from '../util/XMLParser';
  5. import SDP from './SDP';
  6. /* eslint-disable max-len */
  7. /**
  8. * @param {string} xml - raw xml of the stanza
  9. */
  10. function createStanzaElement(xml) {
  11. return new DOMParser().parseFromString(xml, 'text/xml').documentElement;
  12. }
  13. describe('SDP', () => {
  14. afterEach(() => {
  15. FeatureFlags.init({ });
  16. });
  17. describe('toJingle', () => {
  18. const testSdp = [
  19. 'v=0\r\n',
  20. 'o=thisisadapterortc 2719486166053431 0 IN IP4 127.0.0.1\r\n',
  21. 's=-\r\n',
  22. 't=0 0\r\n',
  23. 'a=group:BUNDLE audio video\r\n',
  24. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  25. 'c=IN IP4 0.0.0.0\r\n',
  26. 'a=rtpmap:111 opus/48000/2\r\n',
  27. 'a=rtpmap:126 telephone-event/8000\r\n',
  28. 'a=fmtp:126 0-15\r\n',
  29. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  30. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  31. 'a=setup:active\r\n',
  32. 'a=mid:audio\r\n',
  33. 'a=msid:26D16D51-503A-420B-8274-3DD1174E498F 8205D1FC-50B4-407C-87D5-9C45F1B779F0\r\n',
  34. 'a=sendrecv\r\n',
  35. 'a=ice-ufrag:tOQd\r\n',
  36. 'a=ice-pwd:3sAozs7hw6+2O6DBp2pt9fvY\r\n',
  37. 'a=fingerprint:sha-256 A9:00:CC:F9:81:33:EA:E9:E3:B4:01:E9:9E:18:B3:9B:F8:49:25:A0:5D:12:20:70:D5:6F:34:5A:2A:39:19:0A\r\n',
  38. 'a=ssrc:2002 msid:26D16D51-503A-420B-8274-3DD1174E498F 8205D1FC-50B4-407C-87D5-9C45F1B779F0\r\n',
  39. 'a=ssrc:2002 cname:juejgy8a01\r\n',
  40. 'a=ssrc:2002 name:a8f7g30-a0\r\n',
  41. 'a=rtcp-mux\r\n',
  42. 'a=extmap-allow-mixed\r\n',
  43. 'm=video 9 UDP/TLS/RTP/SAVPF 107 100 99 96\r\n',
  44. 'c=IN IP4 0.0.0.0\r\n',
  45. 'a=rtpmap:107 h264/90000\r\n',
  46. 'a=rtpmap:100 VP8/90000\r\n',
  47. 'a=rtpmap:99 rtx/90000\r\n',
  48. 'a=rtpmap:96 rtx/90000\r\n',
  49. 'a=fmtp:99 apt=107\r\n',
  50. 'a=fmtp:96 apt=100\r\n',
  51. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  52. 'a=rtcp-fb:107 nack\r\n',
  53. 'a=rtcp-fb:107 nack pli\r\n',
  54. 'a=rtcp-fb:107 goog-remb\r\n',
  55. 'a=rtcp-fb:100 nack\r\n',
  56. 'a=rtcp-fb:100 nack pli\r\n',
  57. 'a=rtcp-fb:100 goog-remb\r\n',
  58. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  59. 'a=extmap-allow-mixed\r\n',
  60. 'a=setup:active\r\n',
  61. 'a=mid:video\r\n',
  62. 'a=msid:7C0035E5-2DA1-4AEA-804A-9E75BF9B3768 225E9CDA-0384-4C92-92DD-E74C1153EC68\r\n',
  63. 'a=sendrecv\r\n',
  64. 'a=ice-ufrag:tOQd\r\n',
  65. 'a=ice-pwd:3sAozs7hw6+2O6DBp2pt9fvY\r\n',
  66. 'a=fingerprint:sha-256 A9:00:CC:F9:81:33:EA:E9:E3:B4:01:E9:9E:18:B3:9B:F8:49:25:A0:5D:12:20:70:D5:6F:34:5A:2A:39:19:0A\r\n',
  67. 'a=ssrc:4004 msid:7C0035E5-2DA1-4AEA-804A-9E75BF9B3768 225E9CDA-0384-4C92-92DD-E74C1153EC68\r\n',
  68. 'a=ssrc:4005 msid:7C0035E5-2DA1-4AEA-804A-9E75BF9B3768 225E9CDA-0384-4C92-92DD-E74C1153EC68\r\n',
  69. 'a=ssrc:4004 cname:juejgy8a01\r\n',
  70. 'a=ssrc:4005 cname:juejgy8a01\r\n',
  71. 'a=ssrc:4004 name:a8f7g30-v0\r\n',
  72. 'a=ssrc:4005 name:a8f7g30-v0\r\n',
  73. 'a=ssrc-group:FID 4004 4005\r\n',
  74. 'a=rtcp-mux\r\n'
  75. ].join('');
  76. it('correctly groups ssrcs lines that are not in order', () => {
  77. const sdp = new SDP(testSdp);
  78. const accept = $iq({
  79. to: 'peerjid',
  80. type: 'set'
  81. })
  82. .c('jingle', {
  83. xmlns: 'urn:xmpp:jingle:1',
  84. action: 'session-accept',
  85. initiator: false,
  86. responder: true,
  87. sid: 'temp-sid'
  88. });
  89. sdp.toJingle(accept, 'responder');
  90. const { nodeTree } = accept;
  91. const videoSources = nodeTree.querySelectorAll('description[media=\'video\']>source');
  92. expect(videoSources.length).toBe(2);
  93. });
  94. it('put source names as source element attributes', () => {
  95. FeatureFlags.init({ });
  96. const sdp = new SDP(testSdp);
  97. const accept = $iq({
  98. to: 'peerjid',
  99. type: 'set'
  100. })
  101. .c('jingle', {
  102. xmlns: 'urn:xmpp:jingle:1',
  103. action: 'session-accept',
  104. initiator: false,
  105. responder: true,
  106. sid: 'temp-sid'
  107. });
  108. sdp.toJingle(accept, 'responder');
  109. const { nodeTree } = accept;
  110. const audioSources = nodeTree.querySelectorAll('description[media=\'audio\']>source');
  111. const videoSources = nodeTree.querySelectorAll('description[media=\'video\']>source');
  112. for (const source of audioSources) {
  113. expect(source.getAttribute('name')).toBe('a8f7g30-a0');
  114. }
  115. for (const source of videoSources) {
  116. expect(source.getAttribute('name')).toBe('a8f7g30-v0');
  117. }
  118. });
  119. });
  120. describe('toJingle for multiple m-lines', () => {
  121. const testSdp = [
  122. 'v=0\r\n',
  123. 'o=- 6251210045590020951 2 IN IP4 127.0.0.1\r\n',
  124. 's=-\r\n',
  125. 't=0 0\r\n',
  126. 'a=msid-semantic: WMS\r\n',
  127. 'a=group:BUNDLE 0 1 2\r\n',
  128. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  129. 'c=IN IP4 0.0.0.0\r\n',
  130. 'a=rtpmap:111 opus/48000/2\r\n',
  131. 'a=rtpmap:126 telephone-event/8000\r\n',
  132. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  133. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  134. 'a=rtcp-fb:111 transport-cc\r\n',
  135. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  136. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  137. 'a=setup:active\r\n',
  138. 'a=mid:0\r\n',
  139. 'a=msid:- 5caf9eeb-f846-43cf-8868-78ed2e0fea74\r\n',
  140. 'a=sendrecv\r\n',
  141. 'a=ice-ufrag:gi+W\r\n',
  142. 'a=ice-pwd:NmFZJ6NWoC2gjagIudLFWI8Q\r\n',
  143. 'a=fingerprint:sha-256 41:1D:49:50:40:0D:68:9F:C6:AB:B2:14:98:67:E7:06:70:F0:B2:4A:5C:AB:03:F3:89:AF:B0:11:AF:05:2D:D6\r\n',
  144. 'a=ice-options:trickle\r\n',
  145. 'a=ssrc:3134174615 cname:Ypjacq/wapOqDJKy\r\n',
  146. 'a=rtcp-mux\r\n',
  147. 'a=extmap-allow-mixed\r\n',
  148. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  149. 'c=IN IP4 0.0.0.0\r\n',
  150. 'a=rtpmap:101 VP9/90000\r\n',
  151. 'a=rtpmap:97 rtx/90000\r\n',
  152. 'a=rtpmap:100 VP8/90000\r\n',
  153. 'a=rtpmap:96 rtx/90000\r\n',
  154. 'a=rtpmap:107 H264/90000\r\n',
  155. 'a=rtpmap:99 rtx/90000\r\n',
  156. 'a=rtpmap:41 AV1/90000\r\n',
  157. 'a=rtpmap:42 rtx/90000\r\n',
  158. 'a=fmtp:101 profile-id=0\r\n',
  159. 'a=fmtp:97 apt=101\r\n',
  160. 'a=fmtp:96 apt=100\r\n',
  161. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  162. 'a=fmtp:99 apt=107\r\n',
  163. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  164. 'a=fmtp:42 apt=41\r\n',
  165. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  166. 'a=rtcp-fb:101 ccm fir\r\n',
  167. 'a=rtcp-fb:101 nack\r\n',
  168. 'a=rtcp-fb:101 nack pli\r\n',
  169. 'a=rtcp-fb:101 transport-cc\r\n',
  170. 'a=rtcp-fb:97 ccm fir\r\n',
  171. 'a=rtcp-fb:97 nack\r\n',
  172. 'a=rtcp-fb:97 nack pli\r\n',
  173. 'a=rtcp-fb:100 ccm fir\r\n',
  174. 'a=rtcp-fb:100 nack\r\n',
  175. 'a=rtcp-fb:100 nack pli\r\n',
  176. 'a=rtcp-fb:100 transport-cc\r\n',
  177. 'a=rtcp-fb:96 ccm fir\r\n',
  178. 'a=rtcp-fb:96 nack\r\n',
  179. 'a=rtcp-fb:96 nack pli\r\n',
  180. 'a=rtcp-fb:107 ccm fir\r\n',
  181. 'a=rtcp-fb:107 nack\r\n',
  182. 'a=rtcp-fb:107 nack pli\r\n',
  183. 'a=rtcp-fb:107 transport-cc\r\n',
  184. 'a=rtcp-fb:41 ccm fir\r\n',
  185. 'a=rtcp-fb:41 nack\r\n',
  186. 'a=rtcp-fb:41 nack pli\r\n',
  187. 'a=rtcp-fb:41 transport-cc\r\n',
  188. 'a=rtcp-fb:42 ccm fir\r\n',
  189. 'a=rtcp-fb:42 nack\r\n',
  190. 'a=rtcp-fb:42 nack pli\r\n',
  191. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  192. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  193. 'a=setup:active\r\n',
  194. 'a=mid:1\r\n',
  195. 'a=msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  196. 'a=sendrecv\r\n',
  197. 'a=ice-ufrag:gi+W\r\n',
  198. 'a=ice-pwd:NmFZJ6NWoC2gjagIudLFWI8Q\r\n',
  199. 'a=fingerprint:sha-256 41:1D:49:50:40:0D:68:9F:C6:AB:B2:14:98:67:E7:06:70:F0:B2:4A:5C:AB:03:F3:89:AF:B0:11:AF:05:2D:D6\r\n',
  200. 'a=ice-options:trickle\r\n',
  201. 'a=ssrc:691901703 cname:Ypjacq/wapOqDJKy\r\n',
  202. 'a=ssrc:3967743536 cname:Ypjacq/wapOqDJKy\r\n',
  203. 'a=ssrc:691901703 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  204. 'a=ssrc:3967743536 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  205. 'a=ssrc:4098097822 cname:Ypjacq/wapOqDJKy\r\n',
  206. 'a=ssrc:4098097822 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  207. 'a=ssrc:731566086 cname:Ypjacq/wapOqDJKy\r\n',
  208. 'a=ssrc:731566086 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  209. 'a=ssrc:2374965413 cname:Ypjacq/wapOqDJKy\r\n',
  210. 'a=ssrc:2374965413 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  211. 'a=ssrc:3680614139 cname:Ypjacq/wapOqDJKy\r\n',
  212. 'a=ssrc:3680614139 msid:- 84615c77-2441-4d1f-801d-591a4bc1beaa\r\n',
  213. 'a=ssrc-group:FID 691901703 3967743536\r\n',
  214. 'a=ssrc-group:SIM 691901703 4098097822 731566086\r\n',
  215. 'a=ssrc-group:FID 4098097822 2374965413\r\n',
  216. 'a=ssrc-group:FID 731566086 3680614139\r\n',
  217. 'a=rtcp-mux\r\n',
  218. 'a=extmap-allow-mixed\r\n',
  219. 'm=application 9 UDP/DTLS/SCTP webrtc-datachannel\r\n',
  220. 'c=IN IP4 0.0.0.0\r\n',
  221. 'a=setup:active\r\n',
  222. 'a=mid:2\r\n',
  223. 'a=ice-ufrag:gi+W\r\n',
  224. 'a=ice-pwd:NmFZJ6NWoC2gjagIudLFWI8Q\r\n',
  225. 'a=fingerprint:sha-256 41:1D:49:50:40:0D:68:9F:C6:AB:B2:14:98:67:E7:06:70:F0:B2:4A:5C:AB:03:F3:89:AF:B0:11:AF:05:2D:D6\r\n',
  226. 'a=ice-options:trickle\r\n',
  227. 'a=sctp-port:5000\r\n',
  228. 'a=max-message-size:262144\r\n'
  229. ].join('');
  230. it('correctly groups ssrcs lines', () => {
  231. const sdp = new SDP(testSdp);
  232. const accept = $iq({
  233. to: 'peerjid',
  234. type: 'set'
  235. })
  236. .c('jingle', {
  237. xmlns: 'urn:xmpp:jingle:1',
  238. action: 'session-accept',
  239. initiator: false,
  240. responder: true,
  241. sid: 'temp-sid'
  242. });
  243. sdp.toJingle(accept, 'responder');
  244. const { nodeTree } = accept;
  245. const content = nodeTree.querySelectorAll('jingle>content');
  246. expect(content.length).toBe(3);
  247. const videoSources = nodeTree.querySelectorAll('description[media=\'video\']>source');
  248. expect(videoSources.length).toBe(6);
  249. const audioSources = nodeTree.querySelectorAll('description[media=\'audio\']>source');
  250. expect(audioSources.length).toBe(1);
  251. const videoSourceGroups = nodeTree.querySelectorAll('description[media=\'video\']>ssrc-group');
  252. expect(videoSourceGroups.length).toBe(4);
  253. const data = nodeTree.querySelectorAll('jingle>content[name=\'data\']');
  254. expect(data.length).toBe(1);
  255. });
  256. });
  257. describe('toJingle for multiple m-lines with recv-only', () => {
  258. const testSdp = [
  259. 'v=0\r\n',
  260. 'o=- 8014175770430016012 6 IN IP4 127.0.0.1\r\n',
  261. 's=-\r\n',
  262. 't=0 0\r\n',
  263. 'a=msid-semantic: WMS\r\n',
  264. 'a=group:BUNDLE 0 1 2 3 4 5 6 7\r\n',
  265. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  266. 'c=IN IP4 0.0.0.0\r\n',
  267. 'a=rtpmap:111 opus/48000/2\r\n',
  268. 'a=rtpmap:126 telephone-event/8000\r\n',
  269. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  270. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  271. 'a=rtcp-fb:111 transport-cc\r\n',
  272. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  273. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  274. 'a=setup:active\r\n',
  275. 'a=mid:0\r\n',
  276. 'a=msid:- 836692af-4ea9-432f-811c-fef6ec7ee612\r\n',
  277. 'a=sendrecv\r\n',
  278. 'a=ice-ufrag:/5Yo\r\n',
  279. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  280. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  281. 'a=candidate:4240059272 1 UDP 2122260223 x.x.x.x 54192 typ host\r\n',
  282. 'a=ice-options:trickle\r\n',
  283. 'a=ssrc:2833013218 cname:0T+Z3AzTbva5NoHF\r\n',
  284. 'a=ssrc:2833013218 msid:- 836692af-4ea9-432f-811c-fef6ec7ee612\r\n',
  285. 'a=ssrc:2833013218 name:abcd-a0\r\n',
  286. 'a=rtcp-mux\r\n',
  287. 'a=extmap-allow-mixed\r\n',
  288. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  289. 'c=IN IP4 0.0.0.0\r\n',
  290. 'a=rtpmap:101 VP9/90000\r\n',
  291. 'a=rtpmap:97 rtx/90000\r\n',
  292. 'a=rtpmap:100 VP8/90000\r\n',
  293. 'a=rtpmap:96 rtx/90000\r\n',
  294. 'a=rtpmap:107 H264/90000\r\n',
  295. 'a=rtpmap:99 rtx/90000\r\n',
  296. 'a=rtpmap:41 AV1/90000\r\n',
  297. 'a=rtpmap:42 rtx/90000\r\n',
  298. 'a=fmtp:101 profile-id=0\r\n',
  299. 'a=fmtp:97 apt=101\r\n',
  300. 'a=fmtp:96 apt=100\r\n',
  301. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  302. 'a=fmtp:99 apt=107\r\n',
  303. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  304. 'a=fmtp:42 apt=41\r\n',
  305. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  306. 'a=rtcp-fb:101 ccm fir\r\n',
  307. 'a=rtcp-fb:101 nack\r\n',
  308. 'a=rtcp-fb:101 nack pli\r\n',
  309. 'a=rtcp-fb:101 transport-cc\r\n',
  310. 'a=rtcp-fb:97 ccm fir\r\n',
  311. 'a=rtcp-fb:97 nack\r\n',
  312. 'a=rtcp-fb:97 nack pli\r\n',
  313. 'a=rtcp-fb:100 ccm fir\r\n',
  314. 'a=rtcp-fb:100 nack\r\n',
  315. 'a=rtcp-fb:100 nack pli\r\n',
  316. 'a=rtcp-fb:100 transport-cc\r\n',
  317. 'a=rtcp-fb:96 ccm fir\r\n',
  318. 'a=rtcp-fb:96 nack\r\n',
  319. 'a=rtcp-fb:96 nack pli\r\n',
  320. 'a=rtcp-fb:107 ccm fir\r\n',
  321. 'a=rtcp-fb:107 nack\r\n',
  322. 'a=rtcp-fb:107 nack pli\r\n',
  323. 'a=rtcp-fb:107 transport-cc\r\n',
  324. 'a=rtcp-fb:41 ccm fir\r\n',
  325. 'a=rtcp-fb:41 nack\r\n',
  326. 'a=rtcp-fb:41 nack pli\r\n',
  327. 'a=rtcp-fb:41 transport-cc\r\n',
  328. 'a=rtcp-fb:42 ccm fir\r\n',
  329. 'a=rtcp-fb:42 nack\r\n',
  330. 'a=rtcp-fb:42 nack pli\r\n',
  331. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  332. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  333. 'a=setup:active\r\n',
  334. 'a=mid:1\r\n',
  335. 'a=msid:- 72254a21-ae73-4c0e-bd47-e84a2d3b9474\r\n',
  336. 'a=sendrecv\r\n',
  337. 'a=ice-ufrag:/5Yo\r\n',
  338. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  339. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  340. 'a=ice-options:trickle\r\n',
  341. 'a=ssrc:1261622218 cname:0T+Z3AzTbva5NoHF\r\n',
  342. 'a=ssrc:1261622218 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  343. 'a=ssrc:1261622218 videoType:camera\r\n',
  344. 'a=ssrc:1261622218 name:abcd-v0\r\n',
  345. 'a=ssrc:2809057491 cname:0T+Z3AzTbva5NoHF\r\n',
  346. 'a=ssrc:2809057491 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  347. 'a=ssrc:2809057491 videoType:camera\r\n',
  348. 'a=ssrc:2809057491 name:abcd-v0\r\n',
  349. 'a=ssrc:4223705690 cname:0T+Z3AzTbva5NoHF\r\n',
  350. 'a=ssrc:4223705690 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  351. 'a=ssrc:4223705690 videoType:camera\r\n',
  352. 'a=ssrc:4223705690 name:abcd-v0\r\n',
  353. 'a=ssrc:44482421 cname:0T+Z3AzTbva5NoHF\r\n',
  354. 'a=ssrc:44482421 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  355. 'a=ssrc:44482421 videoType:camera\r\n',
  356. 'a=ssrc:44482421 name:abcd-v0\r\n',
  357. 'a=ssrc:1408200021 cname:0T+Z3AzTbva5NoHF\r\n',
  358. 'a=ssrc:1408200021 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  359. 'a=ssrc:1408200021 videoType:camera\r\n',
  360. 'a=ssrc:1408200021 name:abcd-v0\r\n',
  361. 'a=ssrc:712505591 cname:0T+Z3AzTbva5NoHF\r\n',
  362. 'a=ssrc:712505591 msid:- 7c3aee52-697e-446e-a898-9ea470a19b27\r\n',
  363. 'a=ssrc:712505591 videoType:camera\r\n',
  364. 'a=ssrc:712505591 name:abcd-v0\r\n',
  365. 'a=ssrc-group:FID 1261622218 2809057491\r\n',
  366. 'a=ssrc-group:SIM 1261622218 4223705690 44482421\r\n',
  367. 'a=ssrc-group:FID 4223705690 1408200021\r\n',
  368. 'a=ssrc-group:FID 44482421 712505591\r\n',
  369. 'a=rtcp-mux\r\n',
  370. 'a=extmap-allow-mixed\r\n',
  371. 'm=application 9 UDP/DTLS/SCTP webrtc-datachannel\r\n',
  372. 'c=IN IP4 0.0.0.0\r\n',
  373. 'a=setup:active\r\n',
  374. 'a=mid:2\r\n',
  375. 'a=ice-ufrag:/5Yo\r\n',
  376. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  377. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  378. 'a=ice-options:trickle\r\n',
  379. 'a=sctp-port:5000\r\n',
  380. 'a=max-message-size:262144\r\n',
  381. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  382. 'c=IN IP4 0.0.0.0\r\n',
  383. 'a=rtpmap:101 VP9/90000\r\n',
  384. 'a=rtpmap:97 rtx/90000\r\n',
  385. 'a=rtpmap:100 VP8/90000\r\n',
  386. 'a=rtpmap:96 rtx/90000\r\n',
  387. 'a=rtpmap:107 H264/90000\r\n',
  388. 'a=rtpmap:99 rtx/90000\r\n',
  389. 'a=rtpmap:41 AV1/90000\r\n',
  390. 'a=rtpmap:42 rtx/90000\r\n',
  391. 'a=fmtp:101 profile-id=0\r\n',
  392. 'a=fmtp:97 apt=101\r\n',
  393. 'a=fmtp:96 apt=100\r\n',
  394. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  395. 'a=fmtp:99 apt=107\r\n',
  396. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  397. 'a=fmtp:42 apt=41\r\n',
  398. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  399. 'a=rtcp-fb:101 ccm fir\r\n',
  400. 'a=rtcp-fb:101 nack\r\n',
  401. 'a=rtcp-fb:101 nack pli\r\n',
  402. 'a=rtcp-fb:101 transport-cc\r\n',
  403. 'a=rtcp-fb:97 ccm fir\r\n',
  404. 'a=rtcp-fb:97 nack\r\n',
  405. 'a=rtcp-fb:97 nack pli\r\n',
  406. 'a=rtcp-fb:100 ccm fir\r\n',
  407. 'a=rtcp-fb:100 nack\r\n',
  408. 'a=rtcp-fb:100 nack pli\r\n',
  409. 'a=rtcp-fb:100 transport-cc\r\n',
  410. 'a=rtcp-fb:96 ccm fir\r\n',
  411. 'a=rtcp-fb:96 nack\r\n',
  412. 'a=rtcp-fb:96 nack pli\r\n',
  413. 'a=rtcp-fb:107 ccm fir\r\n',
  414. 'a=rtcp-fb:107 nack\r\n',
  415. 'a=rtcp-fb:107 nack pli\r\n',
  416. 'a=rtcp-fb:107 transport-cc\r\n',
  417. 'a=rtcp-fb:41 ccm fir\r\n',
  418. 'a=rtcp-fb:41 nack\r\n',
  419. 'a=rtcp-fb:41 nack pli\r\n',
  420. 'a=rtcp-fb:41 transport-cc\r\n',
  421. 'a=rtcp-fb:42 ccm fir\r\n',
  422. 'a=rtcp-fb:42 nack\r\n',
  423. 'a=rtcp-fb:42 nack pli\r\n',
  424. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  425. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  426. 'a=extmap:11 https://aomediacodec.github.io/av1-rtp-spec/#dependency-descriptor-rtp-header-extension\r\n',
  427. 'a=setup:active\r\n',
  428. 'a=mid:3\r\n',
  429. 'a=recvonly\r\n',
  430. 'a=ice-ufrag:/5Yo\r\n',
  431. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  432. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  433. 'a=ice-options:trickle\r\n',
  434. 'a=rtcp-mux\r\n',
  435. 'a=extmap-allow-mixed\r\n',
  436. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  437. 'c=IN IP4 0.0.0.0\r\n',
  438. 'a=rtpmap:101 VP9/90000\r\n',
  439. 'a=rtpmap:97 rtx/90000\r\n',
  440. 'a=rtpmap:100 VP8/90000\r\n',
  441. 'a=rtpmap:96 rtx/90000\r\n',
  442. 'a=rtpmap:107 H264/90000\r\n',
  443. 'a=rtpmap:99 rtx/90000\r\n',
  444. 'a=rtpmap:41 AV1/90000\r\n',
  445. 'a=rtpmap:42 rtx/90000\r\n',
  446. 'a=fmtp:101 profile-id=0\r\n',
  447. 'a=fmtp:97 apt=101\r\n',
  448. 'a=fmtp:96 apt=100\r\n',
  449. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  450. 'a=fmtp:99 apt=107\r\n',
  451. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  452. 'a=fmtp:42 apt=41\r\n',
  453. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  454. 'a=rtcp-fb:101 ccm fir\r\n',
  455. 'a=rtcp-fb:101 nack\r\n',
  456. 'a=rtcp-fb:101 nack pli\r\n',
  457. 'a=rtcp-fb:101 transport-cc\r\n',
  458. 'a=rtcp-fb:97 ccm fir\r\n',
  459. 'a=rtcp-fb:97 nack\r\n',
  460. 'a=rtcp-fb:97 nack pli\r\n',
  461. 'a=rtcp-fb:100 ccm fir\r\n',
  462. 'a=rtcp-fb:100 nack\r\n',
  463. 'a=rtcp-fb:100 nack pli\r\n',
  464. 'a=rtcp-fb:100 transport-cc\r\n',
  465. 'a=rtcp-fb:96 ccm fir\r\n',
  466. 'a=rtcp-fb:96 nack\r\n',
  467. 'a=rtcp-fb:96 nack pli\r\n',
  468. 'a=rtcp-fb:107 ccm fir\r\n',
  469. 'a=rtcp-fb:107 nack\r\n',
  470. 'a=rtcp-fb:107 nack pli\r\n',
  471. 'a=rtcp-fb:107 transport-cc\r\n',
  472. 'a=rtcp-fb:41 ccm fir\r\n',
  473. 'a=rtcp-fb:41 nack\r\n',
  474. 'a=rtcp-fb:41 nack pli\r\n',
  475. 'a=rtcp-fb:41 transport-cc\r\n',
  476. 'a=rtcp-fb:42 ccm fir\r\n',
  477. 'a=rtcp-fb:42 nack\r\n',
  478. 'a=rtcp-fb:42 nack pli\r\n',
  479. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  480. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  481. 'a=extmap:11 https://aomediacodec.github.io/av1-rtp-spec/#dependency-descriptor-rtp-header-extension\r\n',
  482. 'a=setup:active\r\n',
  483. 'a=mid:4\r\n',
  484. 'a=recvonly\r\n',
  485. 'a=ice-ufrag:/5Yo\r\n',
  486. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  487. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  488. 'a=ice-options:trickle\r\n',
  489. 'a=rtcp-mux\r\n',
  490. 'a=extmap-allow-mixed\r\n',
  491. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  492. 'c=IN IP4 0.0.0.0\r\n',
  493. 'a=rtpmap:111 opus/48000/2\r\n',
  494. 'a=rtpmap:126 telephone-event/8000\r\n',
  495. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  496. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  497. 'a=rtcp-fb:111 transport-cc\r\n',
  498. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  499. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  500. 'a=setup:active\r\n',
  501. 'a=mid:5\r\n',
  502. 'a=recvonly\r\n',
  503. 'a=ice-ufrag:/5Yo\r\n',
  504. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  505. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  506. 'a=ice-options:trickle\r\n',
  507. 'a=rtcp-mux\r\n',
  508. 'a=extmap-allow-mixed\r\n',
  509. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  510. 'c=IN IP4 0.0.0.0\r\n',
  511. 'a=rtpmap:111 opus/48000/2\r\n',
  512. 'a=rtpmap:126 telephone-event/8000\r\n',
  513. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  514. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  515. 'a=rtcp-fb:111 transport-cc\r\n',
  516. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  517. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  518. 'a=setup:active\r\n',
  519. 'a=mid:6\r\n',
  520. 'a=recvonly\r\n',
  521. 'a=ice-ufrag:/5Yo\r\n',
  522. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  523. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  524. 'a=ice-options:trickle\r\n',
  525. 'a=rtcp-mux\r\n',
  526. 'a=extmap-allow-mixed\r\n',
  527. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  528. 'c=IN IP4 0.0.0.0\r\n',
  529. 'a=rtpmap:101 VP9/90000\r\n',
  530. 'a=rtpmap:97 rtx/90000\r\n',
  531. 'a=rtpmap:100 VP8/90000\r\n',
  532. 'a=rtpmap:96 rtx/90000\r\n',
  533. 'a=rtpmap:107 H264/90000\r\n',
  534. 'a=rtpmap:99 rtx/90000\r\n',
  535. 'a=rtpmap:41 AV1/90000\r\n',
  536. 'a=rtpmap:42 rtx/90000\r\n',
  537. 'a=fmtp:101 profile-id=0\r\n',
  538. 'a=fmtp:97 apt=101\r\n',
  539. 'a=fmtp:96 apt=100\r\n',
  540. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  541. 'a=fmtp:99 apt=107\r\n',
  542. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  543. 'a=fmtp:42 apt=41\r\n',
  544. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  545. 'a=rtcp-fb:101 ccm fir\r\n',
  546. 'a=rtcp-fb:101 nack\r\n',
  547. 'a=rtcp-fb:101 nack pli\r\n',
  548. 'a=rtcp-fb:101 transport-cc\r\n',
  549. 'a=rtcp-fb:97 ccm fir\r\n',
  550. 'a=rtcp-fb:97 nack\r\n',
  551. 'a=rtcp-fb:97 nack pli\r\n',
  552. 'a=rtcp-fb:100 ccm fir\r\n',
  553. 'a=rtcp-fb:100 nack\r\n',
  554. 'a=rtcp-fb:100 nack pli\r\n',
  555. 'a=rtcp-fb:100 transport-cc\r\n',
  556. 'a=rtcp-fb:96 ccm fir\r\n',
  557. 'a=rtcp-fb:96 nack\r\n',
  558. 'a=rtcp-fb:96 nack pli\r\n',
  559. 'a=rtcp-fb:107 ccm fir\r\n',
  560. 'a=rtcp-fb:107 nack\r\n',
  561. 'a=rtcp-fb:107 nack pli\r\n',
  562. 'a=rtcp-fb:107 transport-cc\r\n',
  563. 'a=rtcp-fb:41 ccm fir\r\n',
  564. 'a=rtcp-fb:41 nack\r\n',
  565. 'a=rtcp-fb:41 nack pli\r\n',
  566. 'a=rtcp-fb:41 transport-cc\r\n',
  567. 'a=rtcp-fb:42 ccm fir\r\n',
  568. 'a=rtcp-fb:42 nack\r\n',
  569. 'a=rtcp-fb:42 nack pli\r\n',
  570. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  571. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  572. 'a=setup:active\r\n',
  573. 'a=mid:7\r\n',
  574. 'a=msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  575. 'a=sendonly\r\n',
  576. 'a=ice-ufrag:/5Yo\r\n',
  577. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  578. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  579. 'a=ice-options:trickle\r\n',
  580. 'a=ssrc:4074534577 cname:0T+Z3AzTbva5NoHF\r\n',
  581. 'a=ssrc:4074534577 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  582. 'a=ssrc:4074534577 videoType:desktop\r\n',
  583. 'a=ssrc:4074534577 name:abcd-v1\r\n',
  584. 'a=ssrc:3122913012 cname:0T+Z3AzTbva5NoHF\r\n',
  585. 'a=ssrc:3122913012 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  586. 'a=ssrc:3122913012 videoType:desktop\r\n',
  587. 'a=ssrc:3122913012 name:abcd-v1\r\n',
  588. 'a=ssrc:3145321104 cname:0T+Z3AzTbva5NoHF\r\n',
  589. 'a=ssrc:3145321104 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  590. 'a=ssrc:3145321104 videoType:desktop\r\n',
  591. 'a=ssrc:3145321104 name:abcd-v1\r\n',
  592. 'a=ssrc:2686550307 cname:0T+Z3AzTbva5NoHF\r\n',
  593. 'a=ssrc:2686550307 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  594. 'a=ssrc:2686550307 videoType:desktop\r\n',
  595. 'a=ssrc:2686550307 name:abcd-v1\r\n',
  596. 'a=ssrc:2960588630 cname:0T+Z3AzTbva5NoHF\r\n',
  597. 'a=ssrc:2960588630 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  598. 'a=ssrc:2960588630 videoType:desktop\r\n',
  599. 'a=ssrc:2960588630 name:abcd-v1\r\n',
  600. 'a=ssrc:3495860096 cname:0T+Z3AzTbva5NoHF\r\n',
  601. 'a=ssrc:3495860096 msid:- 7c3aee52-697e-446e-a898-9ea470a19b26\r\n',
  602. 'a=ssrc:3495860096 videoType:desktop\r\n',
  603. 'a=ssrc:3495860096 name:abcd-v1\r\n',
  604. 'a=ssrc-group:FID 4074534577 3122913012\r\n',
  605. 'a=ssrc-group:SIM 4074534577 3145321104 2686550307\r\n',
  606. 'a=ssrc-group:FID 3145321104 2960588630\r\n',
  607. 'a=ssrc-group:FID 2686550307 3495860096\r\n',
  608. 'a=rtcp-mux\r\n',
  609. 'a=extmap-allow-mixed\r\n'
  610. ].join('');
  611. it('correctly groups ssrcs lines', () => {
  612. const sdp = new SDP(testSdp);
  613. const accept = $iq({
  614. to: 'peerjid',
  615. type: 'set'
  616. })
  617. .c('jingle', {
  618. xmlns: 'urn:xmpp:jingle:1',
  619. action: 'session-accept',
  620. initiator: false,
  621. responder: true,
  622. sid: 'temp-sid'
  623. });
  624. sdp.toJingle(accept, 'responder');
  625. const { nodeTree } = accept;
  626. const content = nodeTree.querySelectorAll('jingle>content');
  627. expect(content.length).toBe(3);
  628. const videoSources = nodeTree.querySelectorAll('description[media=\'video\']>source');
  629. expect(videoSources.length).toBe(12);
  630. const audioSources = nodeTree.querySelectorAll('description[media=\'audio\']>source');
  631. expect(audioSources.length).toBe(1);
  632. const videoSourceGroups = nodeTree.querySelectorAll('description[media=\'video\']>ssrc-group');
  633. expect(videoSourceGroups.length).toBe(8);
  634. const data = nodeTree.querySelectorAll('jingle>content[name=\'data\']');
  635. expect(data.length).toBe(1);
  636. });
  637. });
  638. describe('toJingle for multiple m-lines with only recv-only', () => {
  639. const testSdp = [
  640. 'v=0\r\n',
  641. 'o=- 8014175770430016012 6 IN IP4 127.0.0.1\r\n',
  642. 's=-\r\n',
  643. 't=0 0\r\n',
  644. 'a=msid-semantic: WMS\r\n',
  645. 'a=group:BUNDLE 0 1 2 3 4 5 6 7\r\n',
  646. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  647. 'c=IN IP4 0.0.0.0\r\n',
  648. 'a=rtpmap:111 opus/48000/2\r\n',
  649. 'a=rtpmap:126 telephone-event/8000\r\n',
  650. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  651. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  652. 'a=rtcp-fb:111 transport-cc\r\n',
  653. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  654. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  655. 'a=setup:active\r\n',
  656. 'a=mid:0\r\n',
  657. 'a=msid:- 836692af-4ea9-432f-811c-fef6ec7ee612\r\n',
  658. 'a=recvonly\r\n',
  659. 'a=ice-ufrag:/5Yo\r\n',
  660. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  661. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  662. 'a=candidate:4240059272 1 UDP 2122260223 x.x.x.x 54192 typ host\r\n',
  663. 'a=ice-options:trickle\r\n',
  664. 'a=rtcp-mux\r\n',
  665. 'a=extmap-allow-mixed\r\n',
  666. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  667. 'c=IN IP4 0.0.0.0\r\n',
  668. 'a=rtpmap:101 VP9/90000\r\n',
  669. 'a=rtpmap:97 rtx/90000\r\n',
  670. 'a=rtpmap:100 VP8/90000\r\n',
  671. 'a=rtpmap:96 rtx/90000\r\n',
  672. 'a=rtpmap:107 H264/90000\r\n',
  673. 'a=rtpmap:99 rtx/90000\r\n',
  674. 'a=rtpmap:41 AV1/90000\r\n',
  675. 'a=rtpmap:42 rtx/90000\r\n',
  676. 'a=fmtp:101 profile-id=0\r\n',
  677. 'a=fmtp:97 apt=101\r\n',
  678. 'a=fmtp:96 apt=100\r\n',
  679. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  680. 'a=fmtp:99 apt=107\r\n',
  681. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  682. 'a=fmtp:42 apt=41\r\n',
  683. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  684. 'a=rtcp-fb:101 ccm fir\r\n',
  685. 'a=rtcp-fb:101 nack\r\n',
  686. 'a=rtcp-fb:101 nack pli\r\n',
  687. 'a=rtcp-fb:101 transport-cc\r\n',
  688. 'a=rtcp-fb:97 ccm fir\r\n',
  689. 'a=rtcp-fb:97 nack\r\n',
  690. 'a=rtcp-fb:97 nack pli\r\n',
  691. 'a=rtcp-fb:100 ccm fir\r\n',
  692. 'a=rtcp-fb:100 nack\r\n',
  693. 'a=rtcp-fb:100 nack pli\r\n',
  694. 'a=rtcp-fb:100 transport-cc\r\n',
  695. 'a=rtcp-fb:96 ccm fir\r\n',
  696. 'a=rtcp-fb:96 nack\r\n',
  697. 'a=rtcp-fb:96 nack pli\r\n',
  698. 'a=rtcp-fb:107 ccm fir\r\n',
  699. 'a=rtcp-fb:107 nack\r\n',
  700. 'a=rtcp-fb:107 nack pli\r\n',
  701. 'a=rtcp-fb:107 transport-cc\r\n',
  702. 'a=rtcp-fb:41 ccm fir\r\n',
  703. 'a=rtcp-fb:41 nack\r\n',
  704. 'a=rtcp-fb:41 nack pli\r\n',
  705. 'a=rtcp-fb:41 transport-cc\r\n',
  706. 'a=rtcp-fb:42 ccm fir\r\n',
  707. 'a=rtcp-fb:42 nack\r\n',
  708. 'a=rtcp-fb:42 nack pli\r\n',
  709. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  710. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  711. 'a=setup:active\r\n',
  712. 'a=mid:1\r\n',
  713. 'a=recvonly\r\n',
  714. 'a=ice-ufrag:/5Yo\r\n',
  715. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  716. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  717. 'a=ice-options:trickle\r\n',
  718. 'a=rtcp-mux\r\n',
  719. 'a=extmap-allow-mixed\r\n',
  720. 'm=application 9 UDP/DTLS/SCTP webrtc-datachannel\r\n',
  721. 'c=IN IP4 0.0.0.0\r\n',
  722. 'a=setup:active\r\n',
  723. 'a=mid:2\r\n',
  724. 'a=ice-ufrag:/5Yo\r\n',
  725. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  726. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  727. 'a=ice-options:trickle\r\n',
  728. 'a=sctp-port:5000\r\n',
  729. 'a=max-message-size:262144\r\n',
  730. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  731. 'c=IN IP4 0.0.0.0\r\n',
  732. 'a=rtpmap:101 VP9/90000\r\n',
  733. 'a=rtpmap:97 rtx/90000\r\n',
  734. 'a=rtpmap:100 VP8/90000\r\n',
  735. 'a=rtpmap:96 rtx/90000\r\n',
  736. 'a=rtpmap:107 H264/90000\r\n',
  737. 'a=rtpmap:99 rtx/90000\r\n',
  738. 'a=rtpmap:41 AV1/90000\r\n',
  739. 'a=rtpmap:42 rtx/90000\r\n',
  740. 'a=fmtp:101 profile-id=0\r\n',
  741. 'a=fmtp:97 apt=101\r\n',
  742. 'a=fmtp:96 apt=100\r\n',
  743. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  744. 'a=fmtp:99 apt=107\r\n',
  745. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  746. 'a=fmtp:42 apt=41\r\n',
  747. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  748. 'a=rtcp-fb:101 ccm fir\r\n',
  749. 'a=rtcp-fb:101 nack\r\n',
  750. 'a=rtcp-fb:101 nack pli\r\n',
  751. 'a=rtcp-fb:101 transport-cc\r\n',
  752. 'a=rtcp-fb:97 ccm fir\r\n',
  753. 'a=rtcp-fb:97 nack\r\n',
  754. 'a=rtcp-fb:97 nack pli\r\n',
  755. 'a=rtcp-fb:100 ccm fir\r\n',
  756. 'a=rtcp-fb:100 nack\r\n',
  757. 'a=rtcp-fb:100 nack pli\r\n',
  758. 'a=rtcp-fb:100 transport-cc\r\n',
  759. 'a=rtcp-fb:96 ccm fir\r\n',
  760. 'a=rtcp-fb:96 nack\r\n',
  761. 'a=rtcp-fb:96 nack pli\r\n',
  762. 'a=rtcp-fb:107 ccm fir\r\n',
  763. 'a=rtcp-fb:107 nack\r\n',
  764. 'a=rtcp-fb:107 nack pli\r\n',
  765. 'a=rtcp-fb:107 transport-cc\r\n',
  766. 'a=rtcp-fb:41 ccm fir\r\n',
  767. 'a=rtcp-fb:41 nack\r\n',
  768. 'a=rtcp-fb:41 nack pli\r\n',
  769. 'a=rtcp-fb:41 transport-cc\r\n',
  770. 'a=rtcp-fb:42 ccm fir\r\n',
  771. 'a=rtcp-fb:42 nack\r\n',
  772. 'a=rtcp-fb:42 nack pli\r\n',
  773. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  774. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  775. 'a=extmap:11 https://aomediacodec.github.io/av1-rtp-spec/#dependency-descriptor-rtp-header-extension\r\n',
  776. 'a=setup:active\r\n',
  777. 'a=mid:3\r\n',
  778. 'a=recvonly\r\n',
  779. 'a=ice-ufrag:/5Yo\r\n',
  780. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  781. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  782. 'a=ice-options:trickle\r\n',
  783. 'a=rtcp-mux\r\n',
  784. 'a=extmap-allow-mixed\r\n',
  785. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  786. 'c=IN IP4 0.0.0.0\r\n',
  787. 'a=rtpmap:101 VP9/90000\r\n',
  788. 'a=rtpmap:97 rtx/90000\r\n',
  789. 'a=rtpmap:100 VP8/90000\r\n',
  790. 'a=rtpmap:96 rtx/90000\r\n',
  791. 'a=rtpmap:107 H264/90000\r\n',
  792. 'a=rtpmap:99 rtx/90000\r\n',
  793. 'a=rtpmap:41 AV1/90000\r\n',
  794. 'a=rtpmap:42 rtx/90000\r\n',
  795. 'a=fmtp:101 profile-id=0\r\n',
  796. 'a=fmtp:97 apt=101\r\n',
  797. 'a=fmtp:96 apt=100\r\n',
  798. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  799. 'a=fmtp:99 apt=107\r\n',
  800. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  801. 'a=fmtp:42 apt=41\r\n',
  802. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  803. 'a=rtcp-fb:101 ccm fir\r\n',
  804. 'a=rtcp-fb:101 nack\r\n',
  805. 'a=rtcp-fb:101 nack pli\r\n',
  806. 'a=rtcp-fb:101 transport-cc\r\n',
  807. 'a=rtcp-fb:97 ccm fir\r\n',
  808. 'a=rtcp-fb:97 nack\r\n',
  809. 'a=rtcp-fb:97 nack pli\r\n',
  810. 'a=rtcp-fb:100 ccm fir\r\n',
  811. 'a=rtcp-fb:100 nack\r\n',
  812. 'a=rtcp-fb:100 nack pli\r\n',
  813. 'a=rtcp-fb:100 transport-cc\r\n',
  814. 'a=rtcp-fb:96 ccm fir\r\n',
  815. 'a=rtcp-fb:96 nack\r\n',
  816. 'a=rtcp-fb:96 nack pli\r\n',
  817. 'a=rtcp-fb:107 ccm fir\r\n',
  818. 'a=rtcp-fb:107 nack\r\n',
  819. 'a=rtcp-fb:107 nack pli\r\n',
  820. 'a=rtcp-fb:107 transport-cc\r\n',
  821. 'a=rtcp-fb:41 ccm fir\r\n',
  822. 'a=rtcp-fb:41 nack\r\n',
  823. 'a=rtcp-fb:41 nack pli\r\n',
  824. 'a=rtcp-fb:41 transport-cc\r\n',
  825. 'a=rtcp-fb:42 ccm fir\r\n',
  826. 'a=rtcp-fb:42 nack\r\n',
  827. 'a=rtcp-fb:42 nack pli\r\n',
  828. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  829. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  830. 'a=extmap:11 https://aomediacodec.github.io/av1-rtp-spec/#dependency-descriptor-rtp-header-extension\r\n',
  831. 'a=setup:active\r\n',
  832. 'a=mid:4\r\n',
  833. 'a=recvonly\r\n',
  834. 'a=ice-ufrag:/5Yo\r\n',
  835. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  836. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  837. 'a=ice-options:trickle\r\n',
  838. 'a=rtcp-mux\r\n',
  839. 'a=extmap-allow-mixed\r\n',
  840. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  841. 'c=IN IP4 0.0.0.0\r\n',
  842. 'a=rtpmap:111 opus/48000/2\r\n',
  843. 'a=rtpmap:126 telephone-event/8000\r\n',
  844. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  845. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  846. 'a=rtcp-fb:111 transport-cc\r\n',
  847. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  848. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  849. 'a=setup:active\r\n',
  850. 'a=mid:5\r\n',
  851. 'a=recvonly\r\n',
  852. 'a=ice-ufrag:/5Yo\r\n',
  853. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  854. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  855. 'a=ice-options:trickle\r\n',
  856. 'a=rtcp-mux\r\n',
  857. 'a=extmap-allow-mixed\r\n',
  858. 'm=audio 9 UDP/TLS/RTP/SAVPF 111 126\r\n',
  859. 'c=IN IP4 0.0.0.0\r\n',
  860. 'a=rtpmap:111 opus/48000/2\r\n',
  861. 'a=rtpmap:126 telephone-event/8000\r\n',
  862. 'a=fmtp:111 minptime=10;useinbandfec=1\r\n',
  863. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  864. 'a=rtcp-fb:111 transport-cc\r\n',
  865. 'a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level\r\n',
  866. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  867. 'a=setup:active\r\n',
  868. 'a=mid:6\r\n',
  869. 'a=recvonly\r\n',
  870. 'a=ice-ufrag:/5Yo\r\n',
  871. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  872. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  873. 'a=ice-options:trickle\r\n',
  874. 'a=rtcp-mux\r\n',
  875. 'a=extmap-allow-mixed\r\n',
  876. 'm=video 9 UDP/TLS/RTP/SAVPF 101 97 100 96 107 99 41 42\r\n',
  877. 'c=IN IP4 0.0.0.0\r\n',
  878. 'a=rtpmap:101 VP9/90000\r\n',
  879. 'a=rtpmap:97 rtx/90000\r\n',
  880. 'a=rtpmap:100 VP8/90000\r\n',
  881. 'a=rtpmap:96 rtx/90000\r\n',
  882. 'a=rtpmap:107 H264/90000\r\n',
  883. 'a=rtpmap:99 rtx/90000\r\n',
  884. 'a=rtpmap:41 AV1/90000\r\n',
  885. 'a=rtpmap:42 rtx/90000\r\n',
  886. 'a=fmtp:101 profile-id=0\r\n',
  887. 'a=fmtp:97 apt=101\r\n',
  888. 'a=fmtp:96 apt=100\r\n',
  889. 'a=fmtp:107 ;level-asymmetry-allowed=1;packetization-mode=1;profile-level-id=42e01f\r\n',
  890. 'a=fmtp:99 apt=107\r\n',
  891. 'a=fmtp:41 level-idx=5;profile=0;tier=0\r\n',
  892. 'a=fmtp:42 apt=41\r\n',
  893. 'a=rtcp:9 IN IP4 0.0.0.0\r\n',
  894. 'a=rtcp-fb:101 ccm fir\r\n',
  895. 'a=rtcp-fb:101 nack\r\n',
  896. 'a=rtcp-fb:101 nack pli\r\n',
  897. 'a=rtcp-fb:101 transport-cc\r\n',
  898. 'a=rtcp-fb:97 ccm fir\r\n',
  899. 'a=rtcp-fb:97 nack\r\n',
  900. 'a=rtcp-fb:97 nack pli\r\n',
  901. 'a=rtcp-fb:100 ccm fir\r\n',
  902. 'a=rtcp-fb:100 nack\r\n',
  903. 'a=rtcp-fb:100 nack pli\r\n',
  904. 'a=rtcp-fb:100 transport-cc\r\n',
  905. 'a=rtcp-fb:96 ccm fir\r\n',
  906. 'a=rtcp-fb:96 nack\r\n',
  907. 'a=rtcp-fb:96 nack pli\r\n',
  908. 'a=rtcp-fb:107 ccm fir\r\n',
  909. 'a=rtcp-fb:107 nack\r\n',
  910. 'a=rtcp-fb:107 nack pli\r\n',
  911. 'a=rtcp-fb:107 transport-cc\r\n',
  912. 'a=rtcp-fb:41 ccm fir\r\n',
  913. 'a=rtcp-fb:41 nack\r\n',
  914. 'a=rtcp-fb:41 nack pli\r\n',
  915. 'a=rtcp-fb:41 transport-cc\r\n',
  916. 'a=rtcp-fb:42 ccm fir\r\n',
  917. 'a=rtcp-fb:42 nack\r\n',
  918. 'a=rtcp-fb:42 nack pli\r\n',
  919. 'a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time\r\n',
  920. 'a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01\r\n',
  921. 'a=setup:active\r\n',
  922. 'a=mid:7\r\n',
  923. 'a=recvonly\r\n',
  924. 'a=ice-ufrag:/5Yo\r\n',
  925. 'a=ice-pwd:Bn+13yvssP5vicDc0mUO7Aiu\r\n',
  926. 'a=fingerprint:sha-256 54:99:99:D2:C9:FE:63:B2:12:A5:D6:BA:BD:FA:F0:46:7E:E4:18:F8:9C:DF:25:55:94:DA:21:AE:19:19:56:AB\r\n',
  927. 'a=ice-options:trickle\r\n',
  928. 'a=rtcp-mux\r\n',
  929. 'a=extmap-allow-mixed\r\n'
  930. ].join('');
  931. it('correctly groups ssrcs lines', () => {
  932. const sdp = new SDP(testSdp);
  933. const accept = $iq({
  934. to: 'peerjid',
  935. type: 'set'
  936. })
  937. .c('jingle', {
  938. xmlns: 'urn:xmpp:jingle:1',
  939. action: 'session-accept',
  940. initiator: false,
  941. responder: true,
  942. sid: 'temp-sid'
  943. });
  944. sdp.toJingle(accept, 'responder');
  945. const { nodeTree } = accept;
  946. const content = nodeTree.querySelectorAll('jingle>content');
  947. expect(content.length).toBe(3);
  948. const videoSources = nodeTree.querySelectorAll('description[media=\'video\']>source');
  949. expect(videoSources.length).toBe(0);
  950. const audioSources = nodeTree.querySelectorAll('description[media=\'audio\']>source');
  951. expect(audioSources.length).toBe(0);
  952. const videoSourceGroups = nodeTree.querySelectorAll('description[media=\'video\']>ssrc-group');
  953. expect(videoSourceGroups.length).toBe(0);
  954. const data = nodeTree.querySelectorAll('jingle>content[name=\'data\']');
  955. expect(data.length).toBe(1);
  956. });
  957. });
  958. describe('fromJingle', () => {
  959. let sdp;
  960. beforeEach(() => {
  961. sdp = new SDP('');
  962. });
  963. it('should handle no sources', () => {
  964. const jingle = $(
  965. `<jingle xmlns='urn:xmpp:jingle:1'>
  966. <content name='audio'>
  967. <description xmlns='urn:xmpp:jingle:apps:rtp:1' media='audio'/>
  968. </content>
  969. </jingle>`
  970. );
  971. sdp.fromJingle(jingle);
  972. expect(sdp.raw).toContain('m=audio');
  973. });
  974. it('gets converted to SDP', () => {
  975. const stanza = `<iq>
  976. <jingle action='session-initiate' initiator='focus' sid='123' xmlns='urn:xmpp:jingle:1'>
  977. <content creator='initiator' name='audio' senders='both'>
  978. <description media='audio' maxptime='60' xmlns='urn:xmpp:jingle:apps:rtp:1'>
  979. <payload-type channels='2' clockrate='48000' name='opus' id='111'>
  980. <parameter name='minptime' value='10'/>
  981. <parameter name='useinbandfec' value='1'/>
  982. <rtcp-fb type='transport-cc' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  983. </payload-type>
  984. <payload-type clockrate='16000' name='ISAC' id='103'/>
  985. <payload-type clockrate='32000' name='ISAC' id='104'/>
  986. <payload-type clockrate='8000' name='telephone-event' id='126'>
  987. <parameter name="" value="0-15"/>
  988. </payload-type>
  989. <rtp-hdrext uri='urn:ietf:params:rtp-hdrext:ssrc-audio-level' id='1' xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  990. <rtp-hdrext uri='http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01' id='5' xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  991. <extmap-allow-mixed xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  992. <rtcp-mux/>
  993. <source ssrc='4039389863' xmlns='urn:xmpp:jingle:apps:rtp:ssma:0'>
  994. <parameter name='cname' value='mixed'/>
  995. <parameter name='label' value='mixedlabelaudio0'/>
  996. <parameter name='msid' value='mixedmslabel mixedlabelaudio0'/>
  997. <parameter name='mslabel' value='mixedmslabel'/>
  998. </source>
  999. </description>
  1000. <transport ufrag='someufrag' pwd='somepwd' xmlns='urn:xmpp:jingle:transports:ice-udp:1'>
  1001. <fingerprint hash='sha-256' required='false' setup='actpass' xmlns='urn:xmpp:jingle:apps:dtls:0'>09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7</fingerprint>
  1002. <candidate foundation='1' id='3cbe5aea5bde0c1401a60bbc2' network='0' protocol='udp' generation='0' port='10000' priority='2130706431' type='host' ip='10.0.0.1' component='1'/>
  1003. <candidate rel-addr='10.0.0.1' network='0' foundation='2' id='dfcfd075bde0c140ffffffff927646ba' port='10000' protocol='udp' generation='0' rel-port='10000' priority='1694498815' type='srflx' ip='10.0.0.2' component='1'/>
  1004. </transport>
  1005. </content>
  1006. <content creator='initiator' name='video' senders='both'>
  1007. <description media='video' xmlns='urn:xmpp:jingle:apps:rtp:1'>
  1008. <payload-type clockrate='90000' name='VP8' id='100'>
  1009. <rtcp-fb subtype='fir' type='ccm' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1010. <rtcp-fb type='nack' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1011. <rtcp-fb subtype='pli' type='nack' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1012. <rtcp-fb type='goog-remb' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1013. <rtcp-fb type='transport-cc' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1014. </payload-type>
  1015. <payload-type clockrate='90000' name='rtx' id='96'>
  1016. <rtcp-fb subtype='fir' type='ccm' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1017. <rtcp-fb type='nack' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1018. <rtcp-fb subtype='pli' type='nack' xmlns='urn:xmpp:jingle:apps:rtp:rtcp-fb:0'/>
  1019. <parameter name='apt' value='100'/>
  1020. </payload-type>
  1021. <rtp-hdrext uri='http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time' id='3' xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  1022. <rtp-hdrext uri='http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01' id='5' xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  1023. <extmap-allow-mixed xmlns='urn:xmpp:jingle:apps:rtp:rtp-hdrext:0'/>
  1024. <rtcp-mux/>
  1025. <source ssrc='3758540092' xmlns='urn:xmpp:jingle:apps:rtp:ssma:0'>
  1026. <parameter name='cname' value='mixed'/>
  1027. <parameter name='label' value='mixedlabelvideo0'/>
  1028. <parameter name='msid' value='mixedmslabel mixedlabelvideo0'/>
  1029. <parameter name='mslabel' value='mixedmslabel'/>
  1030. </source>
  1031. </description>
  1032. <transport ufrag='someufrag' pwd='somepwd' xmlns='urn:xmpp:jingle:transports:ice-udp:1'>
  1033. <fingerprint hash='sha-256' required='false' setup='actpass' xmlns='urn:xmpp:jingle:apps:dtls:0'>09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7</fingerprint>
  1034. <candidate foundation='1' id='3cbe5aea5bde0c1401a60bbc2' network='0' protocol='udp' generation='0' port='10000' priority='2130706431' type='host' ip='10.0.0.1' component='1'/>
  1035. <candidate rel-addr='10.0.0.1' network='0' foundation='2' id='dfcfd075bde0c140ffffffff927646ba' port='10000' protocol='udp' generation='0' rel-port='10000' priority='1694498815' type='srflx' ip='10.0.0.2' component='1'/>
  1036. </transport>
  1037. </content>
  1038. <group semantics='BUNDLE' xmlns='urn:xmpp:jingle:apps:grouping:0'>
  1039. <content name='audio'/>
  1040. <content name='video'/>
  1041. </group>
  1042. </jingle></iq>`;
  1043. const expectedSDP = `v=0
  1044. o=- 123 3 IN IP4 0.0.0.0
  1045. s=-
  1046. t=0 0
  1047. a=msid-semantic: WMS *
  1048. a=group:BUNDLE 0 1
  1049. m=audio 9 UDP/TLS/RTP/SAVPF 111 103 104 126
  1050. c=IN IP4 0.0.0.0
  1051. a=rtpmap:111 opus/48000/2
  1052. a=rtpmap:103 ISAC/16000
  1053. a=rtpmap:104 ISAC/32000
  1054. a=rtpmap:126 telephone-event/8000
  1055. a=fmtp:111 minptime=10;useinbandfec=1
  1056. a=fmtp:126 0-15
  1057. a=rtcp:1 IN IP4 0.0.0.0
  1058. a=rtcp-fb:111 transport-cc
  1059. a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level
  1060. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1061. a=setup:actpass
  1062. a=mid:0
  1063. a=sendrecv
  1064. a=ice-ufrag:someufrag
  1065. a=ice-pwd:somepwd
  1066. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1067. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1068. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1069. a=ssrc:4039389863 cname:mixed
  1070. a=rtcp-mux
  1071. a=extmap-allow-mixed
  1072. m=video 9 UDP/TLS/RTP/SAVPF 100 96
  1073. c=IN IP4 0.0.0.0
  1074. a=rtpmap:100 VP8/90000
  1075. a=rtpmap:96 rtx/90000
  1076. a=fmtp:96 apt=100
  1077. a=rtcp:1 IN IP4 0.0.0.0
  1078. a=rtcp-fb:100 ccm fir
  1079. a=rtcp-fb:100 nack
  1080. a=rtcp-fb:100 nack pli
  1081. a=rtcp-fb:100 goog-remb
  1082. a=rtcp-fb:100 transport-cc
  1083. a=rtcp-fb:96 ccm fir
  1084. a=rtcp-fb:96 nack
  1085. a=rtcp-fb:96 nack pli
  1086. a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
  1087. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1088. a=setup:actpass
  1089. a=mid:1
  1090. a=sendrecv
  1091. a=ice-ufrag:someufrag
  1092. a=ice-pwd:somepwd
  1093. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1094. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1095. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1096. a=ssrc:3758540092 cname:mixed
  1097. a=rtcp-mux
  1098. a=extmap-allow-mixed
  1099. `.split('\n').join('\r\n');
  1100. const offer = createStanzaElement(stanza);
  1101. sdp.fromJingle($(offer).find('>jingle'));
  1102. const rawSDP = sdp.raw.replace(/o=- \d+/, 'o=- 123'); // replace generated o= timestamp.
  1103. expect(rawSDP).toEqual(expectedSDP);
  1104. });
  1105. it('fromJingleWithJSONFormat gets converted to SDP', () => {
  1106. const stanza = `
  1107. <iq>
  1108. <jingle xmlns="urn:xmpp:jingle:1" action="session-initiate" initiator="focus" sid="123">
  1109. <content name="audio" creator="initiator" senders="both">
  1110. <description xmlns="urn:xmpp:jingle:apps:rtp:1" maxptime="60" media="audio">
  1111. <payload-type name="opus" clockrate="48000" id="111" channels="2">
  1112. <parameter value="10" name="minptime"/>
  1113. <parameter value="1" name="useinbandfec"/>
  1114. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" type="transport-cc"/>
  1115. </payload-type>
  1116. <payload-type name="ISAC" clockrate="16000" id="103"/>
  1117. <payload-type name="ISAC" clockrate="32000" id="104"/>
  1118. <payload-type name="telephone-event" clockrate="8000" id="126"/>
  1119. <rtp-hdrext xmlns="urn:xmpp:jingle:apps:rtp:rtp-hdrext:0" id="1" uri="urn:ietf:params:rtp-hdrext:ssrc-audio-level"/>
  1120. <rtp-hdrext xmlns="urn:xmpp:jingle:apps:rtp:rtp-hdrext:0" id="5" uri="http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01"/>
  1121. <rtcp-mux/>
  1122. </description>
  1123. <transport ufrag='someufrag' pwd='somepwd' xmlns='urn:xmpp:jingle:transports:ice-udp:1'>
  1124. <fingerprint hash='sha-256' required='false' setup='actpass' xmlns='urn:xmpp:jingle:apps:dtls:0'>09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7</fingerprint>
  1125. <candidate foundation='1' id='3cbe5aea5bde0c1401a60bbc2' network='0' protocol='udp' generation='0' port='10000' priority='2130706431' type='host' ip='10.0.0.1' component='1'/>
  1126. <candidate rel-addr='10.0.0.1' network='0' foundation='2' id='dfcfd075bde0c140ffffffff927646ba' port='10000' protocol='udp' generation='0' rel-port='10000' priority='1694498815' type='srflx' ip='10.0.0.2' component='1'/>
  1127. </transport>
  1128. </content>
  1129. <content name="video" creator="initiator" senders="both">
  1130. <description xmlns="urn:xmpp:jingle:apps:rtp:1" media="video">
  1131. <payload-type name="VP8" clockrate="90000" id="100">
  1132. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" subtype="fir" type="ccm"/>
  1133. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" type="nack"/>
  1134. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" subtype="pli" type="nack"/>
  1135. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" type="transport-cc"/>
  1136. </payload-type>
  1137. <payload-type name="rtx" clockrate="90000" id="96">
  1138. <parameter value="100" name="apt"/>
  1139. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" subtype="fir" type="ccm"/>
  1140. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" type="nack"/>
  1141. <rtcp-fb xmlns="urn:xmpp:jingle:apps:rtp:rtcp-fb:0" subtype="pli" type="nack"/>
  1142. </payload-type>
  1143. <rtp-hdrext xmlns="urn:xmpp:jingle:apps:rtp:rtp-hdrext:0" id="3" uri="http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time"/>
  1144. <rtp-hdrext xmlns="urn:xmpp:jingle:apps:rtp:rtp-hdrext:0" id="5" uri="http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01"/>
  1145. <rtcp-mux/>
  1146. </description>
  1147. <transport ufrag='someufrag' pwd='somepwd' xmlns='urn:xmpp:jingle:transports:ice-udp:1'>
  1148. <fingerprint hash='sha-256' required='false' setup='actpass' xmlns='urn:xmpp:jingle:apps:dtls:0'>09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7</fingerprint>
  1149. <candidate foundation='1' id='3cbe5aea5bde0c1401a60bbc2' network='0' protocol='udp' generation='0' port='10000' priority='2130706431' type='host' ip='10.0.0.1' component='1'/>
  1150. <candidate rel-addr='10.0.0.1' network='0' foundation='2' id='dfcfd075bde0c140ffffffff927646ba' port='10000' protocol='udp' generation='0' rel-port='10000' priority='1694498815' type='srflx' ip='10.0.0.2' component='1'/>
  1151. </transport>
  1152. </content>
  1153. <group xmlns="urn:xmpp:jingle:apps:grouping:0" semantics="BUNDLE">
  1154. <content name="audio"/>
  1155. <content name="video"/>
  1156. </group>
  1157. <json-message xmlns="http://jitsi.org/jitmeet">{"sources":{"831de82b":[[{"s":257838819,"m":"831de82b-video-1 9bb949d4-5abd-4498-98e9-2be1222b8d3e-1"},{"s":865670341,"m":"831de82b-video-1 9bb949d4-5abd-4498-98e9-2be1222b8d3e-1"}],[["f",257838819,865670341]],[]],"07af8d49":[[{"s":110279275,"m":"07af8d49-video-2 f685aa25-0318-442e-bd00-cd2a911236da-2"},{"s":3873826414,"m":"07af8d49-video-2 f685aa25-0318-442e-bd00-cd2a911236da-2"}],[["f",3873826414,110279275]],[]],"95edea8d":[[{"s":620660772,"m":"95edea8d-video-1 0c5d94d1-1902-4fb7-bf6a-76517d065d02-1"},{"s":2306112481,"m":"95edea8d-video-1 0c5d94d1-1902-4fb7-bf6a-76517d065d02-1"}],[["f",2306112481,620660772]],[]],"jvb":[[{"s":1427774514,"m":"mixedmslabel mixedlabelvideo0","c":"mixed"}],[],[{"s":3659539811,"m":"mixedmslabel mixedlabelaudio0","c":"mixed"}]]}}</json-message>
  1158. </jingle>
  1159. </iq>`;
  1160. const expectedSDP = `v=0
  1161. o=- 123 3 IN IP4 0.0.0.0
  1162. s=-
  1163. t=0 0
  1164. a=msid-semantic: WMS *
  1165. a=group:BUNDLE 0 1 2 3 4
  1166. m=audio 9 UDP/TLS/RTP/SAVPF 111 103 104 126
  1167. c=IN IP4 0.0.0.0
  1168. a=rtpmap:111 opus/48000/2
  1169. a=rtpmap:103 ISAC/16000
  1170. a=rtpmap:104 ISAC/32000
  1171. a=rtpmap:126 telephone-event/8000
  1172. a=fmtp:111 minptime=10;useinbandfec=1
  1173. a=rtcp:1 IN IP4 0.0.0.0
  1174. a=rtcp-fb:111 transport-cc
  1175. a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level
  1176. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1177. a=setup:actpass
  1178. a=mid:0
  1179. a=sendrecv
  1180. a=ice-ufrag:someufrag
  1181. a=ice-pwd:somepwd
  1182. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1183. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1184. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1185. a=ssrc:3659539811 msid:mixedmslabel mixedlabelaudio0
  1186. a=rtcp-mux
  1187. m=video 9 UDP/TLS/RTP/SAVPF 100 96
  1188. c=IN IP4 0.0.0.0
  1189. a=rtpmap:100 VP8/90000
  1190. a=rtpmap:96 rtx/90000
  1191. a=fmtp:96 apt=100
  1192. a=rtcp:1 IN IP4 0.0.0.0
  1193. a=rtcp-fb:100 ccm fir
  1194. a=rtcp-fb:100 nack
  1195. a=rtcp-fb:100 nack pli
  1196. a=rtcp-fb:100 transport-cc
  1197. a=rtcp-fb:96 ccm fir
  1198. a=rtcp-fb:96 nack
  1199. a=rtcp-fb:96 nack pli
  1200. a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
  1201. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1202. a=setup:actpass
  1203. a=mid:1
  1204. a=sendrecv
  1205. a=ice-ufrag:someufrag
  1206. a=ice-pwd:somepwd
  1207. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1208. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1209. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1210. a=ssrc:1427774514 msid:mixedmslabel mixedlabelvideo0
  1211. a=rtcp-mux
  1212. m=video 9 UDP/TLS/RTP/SAVPF 100 96
  1213. c=IN IP4 0.0.0.0
  1214. a=rtpmap:100 VP8/90000
  1215. a=rtpmap:96 rtx/90000
  1216. a=fmtp:96 apt=100
  1217. a=rtcp:1 IN IP4 0.0.0.0
  1218. a=rtcp-fb:100 ccm fir
  1219. a=rtcp-fb:100 nack
  1220. a=rtcp-fb:100 nack pli
  1221. a=rtcp-fb:100 transport-cc
  1222. a=rtcp-fb:96 ccm fir
  1223. a=rtcp-fb:96 nack
  1224. a=rtcp-fb:96 nack pli
  1225. a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
  1226. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1227. a=setup:actpass
  1228. a=mid:2
  1229. a=sendonly
  1230. a=ice-ufrag:someufrag
  1231. a=ice-pwd:somepwd
  1232. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1233. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1234. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1235. a=ssrc:257838819 msid:831de82b-video-1 9bb949d4-5abd-4498-98e9-2be1222b8d3e-1
  1236. a=ssrc:865670341 msid:831de82b-video-1 9bb949d4-5abd-4498-98e9-2be1222b8d3e-1
  1237. a=ssrc-group:FID 257838819 865670341
  1238. a=rtcp-mux
  1239. m=video 9 UDP/TLS/RTP/SAVPF 100 96
  1240. c=IN IP4 0.0.0.0
  1241. a=rtpmap:100 VP8/90000
  1242. a=rtpmap:96 rtx/90000
  1243. a=fmtp:96 apt=100
  1244. a=rtcp:1 IN IP4 0.0.0.0
  1245. a=rtcp-fb:100 ccm fir
  1246. a=rtcp-fb:100 nack
  1247. a=rtcp-fb:100 nack pli
  1248. a=rtcp-fb:100 transport-cc
  1249. a=rtcp-fb:96 ccm fir
  1250. a=rtcp-fb:96 nack
  1251. a=rtcp-fb:96 nack pli
  1252. a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
  1253. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1254. a=setup:actpass
  1255. a=mid:3
  1256. a=sendonly
  1257. a=ice-ufrag:someufrag
  1258. a=ice-pwd:somepwd
  1259. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1260. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1261. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1262. a=ssrc:110279275 msid:07af8d49-video-2 f685aa25-0318-442e-bd00-cd2a911236da-2
  1263. a=ssrc:3873826414 msid:07af8d49-video-2 f685aa25-0318-442e-bd00-cd2a911236da-2
  1264. a=ssrc-group:FID 3873826414 110279275
  1265. a=rtcp-mux
  1266. m=video 9 UDP/TLS/RTP/SAVPF 100 96
  1267. c=IN IP4 0.0.0.0
  1268. a=rtpmap:100 VP8/90000
  1269. a=rtpmap:96 rtx/90000
  1270. a=fmtp:96 apt=100
  1271. a=rtcp:1 IN IP4 0.0.0.0
  1272. a=rtcp-fb:100 ccm fir
  1273. a=rtcp-fb:100 nack
  1274. a=rtcp-fb:100 nack pli
  1275. a=rtcp-fb:100 transport-cc
  1276. a=rtcp-fb:96 ccm fir
  1277. a=rtcp-fb:96 nack
  1278. a=rtcp-fb:96 nack pli
  1279. a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
  1280. a=extmap:5 http://www.ietf.org/id/draft-holmer-rmcat-transport-wide-cc-extensions-01
  1281. a=setup:actpass
  1282. a=mid:4
  1283. a=sendonly
  1284. a=ice-ufrag:someufrag
  1285. a=ice-pwd:somepwd
  1286. a=fingerprint:sha-256 09:B1:51:0F:85:4C:80:19:A1:AF:81:73:47:EE:ED:3D:00:3A:84:C7:76:C1:4E:34:BE:56:F6:42:AD:15:D5:D7
  1287. a=candidate:1 1 udp 2130706431 10.0.0.1 10000 typ host generation 0
  1288. a=candidate:2 1 udp 1694498815 10.0.0.2 10000 typ srflx raddr 10.0.0.1 rport 10000 generation 0
  1289. a=ssrc:620660772 msid:95edea8d-video-1 0c5d94d1-1902-4fb7-bf6a-76517d065d02-1
  1290. a=ssrc:2306112481 msid:95edea8d-video-1 0c5d94d1-1902-4fb7-bf6a-76517d065d02-1
  1291. a=ssrc-group:FID 2306112481 620660772
  1292. a=rtcp-mux
  1293. `.split('\n').join('\r\n');
  1294. const offer = createStanzaElement(stanza);
  1295. const jsonMessages = $(offer).find('jingle>json-message');
  1296. for (let i = 0; i < jsonMessages.length; i++) {
  1297. expandSourcesFromJson(offer, jsonMessages[i]);
  1298. }
  1299. sdp.fromJingle($(offer).find('>jingle'));
  1300. const rawSDP = sdp.raw.replace(/o=- \d+/, 'o=- 123'); // replace generated o= timestamp.
  1301. expect(rawSDP).toEqual(expectedSDP);
  1302. });
  1303. });
  1304. /* eslint-disable max-len */
  1305. describe('jingle2media', () => {
  1306. it('should convert basic Jingle content to SDP', () => {
  1307. const jingleContent = createStanzaElement(`
  1308. <content name="audio">
  1309. <description media="audio" xmlns="urn:xmpp:jingle:apps:rtp:1">
  1310. <payload-type id="111" name="opus" clockrate="48000" channels="2"/>
  1311. </description>
  1312. <transport xmlns="urn:xmpp:jingle:transports:ice-udp:1">
  1313. <candidate foundation="1" component="1" protocol="udp" priority="2130706431" ip="192.168.1.1" port="10000" type="host"/>
  1314. </transport>
  1315. </content>
  1316. `);
  1317. const sdp = new SDP('');
  1318. const media = sdp.jingle2media($(jingleContent));
  1319. expect(media).toContain('m=audio 9 UDP/TLS/RTP/SAVPF 111');
  1320. expect(media).toContain('a=rtpmap:111 opus/48000/2');
  1321. expect(media).toContain('c=IN IP4 0.0.0.0');
  1322. expect(media).toContain('a=candidate:1 1 udp 2130706431 192.168.1.1 10000 typ host');
  1323. });
  1324. it('should convert Jingle content with multiple payload types to SDP', () => {
  1325. const jingleContent = createStanzaElement(`
  1326. <content name="video">
  1327. <description media="video" xmlns="urn:xmpp:jingle:apps:rtp:1">
  1328. <payload-type id="100" name="VP8" clockrate="90000"/>
  1329. <payload-type id="101" name="VP9" clockrate="90000"/>
  1330. </description>
  1331. <transport xmlns="urn:xmpp:jingle:transports:ice-udp:1">
  1332. <candidate foundation="1" component="1" protocol="udp" priority="2130706431" ip="192.168.1.1" port="10000" type="host"/>
  1333. </transport>
  1334. </content>
  1335. `);
  1336. const sdp = new SDP('');
  1337. const media = sdp.jingle2media($(jingleContent));
  1338. expect(media).toContain('m=video 9 UDP/TLS/RTP/SAVPF 100 101');
  1339. expect(media).toContain('a=rtpmap:100 VP8/90000');
  1340. expect(media).toContain('a=rtpmap:101 VP9/90000');
  1341. expect(media).toContain('c=IN IP4 0.0.0.0');
  1342. expect(media).toContain('a=candidate:1 1 udp 2130706431 192.168.1.1 10000 typ host');
  1343. });
  1344. it('should convert Jingle content with ICE candidates to SDP', () => {
  1345. const jingleContent = createStanzaElement(`
  1346. <content name="audio">
  1347. <description media="audio" xmlns="urn:xmpp:jingle:apps:rtp:1">
  1348. <payload-type id="111" name="opus" clockrate="48000" channels="2"/>
  1349. </description>
  1350. <transport xmlns="urn:xmpp:jingle:transports:ice-udp:1">
  1351. <candidate foundation="1" component="1" protocol="udp" priority="2130706431" ip="192.168.1.1" port="10000" type="host"/>
  1352. <candidate foundation="2" component="1" protocol="tcp" priority="2130706430" ip="192.168.1.2" port="10001" type="host"/>
  1353. </transport>
  1354. </content>
  1355. `);
  1356. const sdp = new SDP('');
  1357. const media = sdp.jingle2media($(jingleContent));
  1358. expect(media).toContain('a=candidate:1 1 udp 2130706431 192.168.1.1 10000 typ host');
  1359. expect(media).toContain('a=candidate:2 1 tcp 2130706430 192.168.1.2 10001 typ host');
  1360. });
  1361. });
  1362. });