@tomgiee/tsdp 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (171) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +124 -0
  3. package/dist/src/builder/media-builder.d.ts +221 -0
  4. package/dist/src/builder/media-builder.d.ts.map +1 -0
  5. package/dist/src/builder/media-builder.js +385 -0
  6. package/dist/src/builder/session-builder.d.ts +195 -0
  7. package/dist/src/builder/session-builder.d.ts.map +1 -0
  8. package/dist/src/builder/session-builder.js +366 -0
  9. package/dist/src/index.d.ts +67 -0
  10. package/dist/src/index.d.ts.map +1 -0
  11. package/dist/src/index.js +250 -0
  12. package/dist/src/parser/attribute-parser.d.ts +100 -0
  13. package/dist/src/parser/attribute-parser.d.ts.map +1 -0
  14. package/dist/src/parser/attribute-parser.js +217 -0
  15. package/dist/src/parser/field-parser.d.ts +124 -0
  16. package/dist/src/parser/field-parser.d.ts.map +1 -0
  17. package/dist/src/parser/field-parser.js +335 -0
  18. package/dist/src/parser/media-parser.d.ts +45 -0
  19. package/dist/src/parser/media-parser.d.ts.map +1 -0
  20. package/dist/src/parser/media-parser.js +157 -0
  21. package/dist/src/parser/primitive-parser.d.ts +138 -0
  22. package/dist/src/parser/primitive-parser.d.ts.map +1 -0
  23. package/dist/src/parser/primitive-parser.js +316 -0
  24. package/dist/src/parser/scanner.d.ts +142 -0
  25. package/dist/src/parser/scanner.d.ts.map +1 -0
  26. package/dist/src/parser/scanner.js +284 -0
  27. package/dist/src/parser/session-parser.d.ts +35 -0
  28. package/dist/src/parser/session-parser.d.ts.map +1 -0
  29. package/dist/src/parser/session-parser.js +207 -0
  30. package/dist/src/parser/time-parser.d.ts +74 -0
  31. package/dist/src/parser/time-parser.d.ts.map +1 -0
  32. package/dist/src/parser/time-parser.js +168 -0
  33. package/dist/src/serializer/attribute-serializer.d.ts +18 -0
  34. package/dist/src/serializer/attribute-serializer.d.ts.map +1 -0
  35. package/dist/src/serializer/attribute-serializer.js +34 -0
  36. package/dist/src/serializer/field-serializer.d.ts +112 -0
  37. package/dist/src/serializer/field-serializer.d.ts.map +1 -0
  38. package/dist/src/serializer/field-serializer.js +212 -0
  39. package/dist/src/serializer/media-serializer.d.ts +31 -0
  40. package/dist/src/serializer/media-serializer.d.ts.map +1 -0
  41. package/dist/src/serializer/media-serializer.js +83 -0
  42. package/dist/src/serializer/session-serializer.d.ts +29 -0
  43. package/dist/src/serializer/session-serializer.d.ts.map +1 -0
  44. package/dist/src/serializer/session-serializer.js +99 -0
  45. package/dist/src/serializer/time-serializer.d.ts +46 -0
  46. package/dist/src/serializer/time-serializer.d.ts.map +1 -0
  47. package/dist/src/serializer/time-serializer.js +86 -0
  48. package/dist/src/types/attributes.d.ts +318 -0
  49. package/dist/src/types/attributes.d.ts.map +1 -0
  50. package/dist/src/types/attributes.js +225 -0
  51. package/dist/src/types/errors.d.ts +129 -0
  52. package/dist/src/types/errors.d.ts.map +1 -0
  53. package/dist/src/types/errors.js +186 -0
  54. package/dist/src/types/fields.d.ts +100 -0
  55. package/dist/src/types/fields.d.ts.map +1 -0
  56. package/dist/src/types/fields.js +48 -0
  57. package/dist/src/types/media.d.ts +148 -0
  58. package/dist/src/types/media.d.ts.map +1 -0
  59. package/dist/src/types/media.js +137 -0
  60. package/dist/src/types/network.d.ts +136 -0
  61. package/dist/src/types/network.d.ts.map +1 -0
  62. package/dist/src/types/network.js +130 -0
  63. package/dist/src/types/primitives.d.ts +193 -0
  64. package/dist/src/types/primitives.d.ts.map +1 -0
  65. package/dist/src/types/primitives.js +195 -0
  66. package/dist/src/types/session.d.ts +122 -0
  67. package/dist/src/types/session.d.ts.map +1 -0
  68. package/dist/src/types/session.js +81 -0
  69. package/dist/src/types/time.d.ts +129 -0
  70. package/dist/src/types/time.d.ts.map +1 -0
  71. package/dist/src/types/time.js +84 -0
  72. package/dist/src/utils/address-parser.d.ts +100 -0
  73. package/dist/src/utils/address-parser.d.ts.map +1 -0
  74. package/dist/src/utils/address-parser.js +338 -0
  75. package/dist/src/utils/format-validators.d.ts +77 -0
  76. package/dist/src/utils/format-validators.d.ts.map +1 -0
  77. package/dist/src/utils/format-validators.js +504 -0
  78. package/dist/src/utils/line-reader.d.ts +84 -0
  79. package/dist/src/utils/line-reader.d.ts.map +1 -0
  80. package/dist/src/utils/line-reader.js +169 -0
  81. package/dist/src/utils/time-converter.d.ts +99 -0
  82. package/dist/src/utils/time-converter.d.ts.map +1 -0
  83. package/dist/src/utils/time-converter.js +195 -0
  84. package/dist/src/validator/media-validator.d.ts +27 -0
  85. package/dist/src/validator/media-validator.d.ts.map +1 -0
  86. package/dist/src/validator/media-validator.js +241 -0
  87. package/dist/src/validator/semantic-validator.d.ts +47 -0
  88. package/dist/src/validator/semantic-validator.d.ts.map +1 -0
  89. package/dist/src/validator/semantic-validator.js +207 -0
  90. package/dist/src/validator/session-validator.d.ts +36 -0
  91. package/dist/src/validator/session-validator.d.ts.map +1 -0
  92. package/dist/src/validator/session-validator.js +280 -0
  93. package/dist/tests/integration/round-trip.test.d.ts +5 -0
  94. package/dist/tests/integration/round-trip.test.d.ts.map +1 -0
  95. package/dist/tests/integration/round-trip.test.js +320 -0
  96. package/dist/tests/integration/voip-examples.test.d.ts +5 -0
  97. package/dist/tests/integration/voip-examples.test.d.ts.map +1 -0
  98. package/dist/tests/integration/voip-examples.test.js +361 -0
  99. package/dist/tests/unit/builder/media-builder.test.d.ts +5 -0
  100. package/dist/tests/unit/builder/media-builder.test.d.ts.map +1 -0
  101. package/dist/tests/unit/builder/media-builder.test.js +524 -0
  102. package/dist/tests/unit/builder/session-builder.test.d.ts +5 -0
  103. package/dist/tests/unit/builder/session-builder.test.d.ts.map +1 -0
  104. package/dist/tests/unit/builder/session-builder.test.js +367 -0
  105. package/dist/tests/unit/parser/attribute-parser.test.d.ts +5 -0
  106. package/dist/tests/unit/parser/attribute-parser.test.d.ts.map +1 -0
  107. package/dist/tests/unit/parser/attribute-parser.test.js +319 -0
  108. package/dist/tests/unit/parser/field-parser.test.d.ts +5 -0
  109. package/dist/tests/unit/parser/field-parser.test.d.ts.map +1 -0
  110. package/dist/tests/unit/parser/field-parser.test.js +355 -0
  111. package/dist/tests/unit/parser/media-parser.test.d.ts +5 -0
  112. package/dist/tests/unit/parser/media-parser.test.d.ts.map +1 -0
  113. package/dist/tests/unit/parser/media-parser.test.js +241 -0
  114. package/dist/tests/unit/parser/primitive-parser.test.d.ts +5 -0
  115. package/dist/tests/unit/parser/primitive-parser.test.d.ts.map +1 -0
  116. package/dist/tests/unit/parser/primitive-parser.test.js +261 -0
  117. package/dist/tests/unit/parser/scanner.test.d.ts +5 -0
  118. package/dist/tests/unit/parser/scanner.test.d.ts.map +1 -0
  119. package/dist/tests/unit/parser/scanner.test.js +241 -0
  120. package/dist/tests/unit/parser/session-parser.test.d.ts +5 -0
  121. package/dist/tests/unit/parser/session-parser.test.d.ts.map +1 -0
  122. package/dist/tests/unit/parser/session-parser.test.js +346 -0
  123. package/dist/tests/unit/parser/time-parser.test.d.ts +5 -0
  124. package/dist/tests/unit/parser/time-parser.test.d.ts.map +1 -0
  125. package/dist/tests/unit/parser/time-parser.test.js +173 -0
  126. package/dist/tests/unit/serializer/attribute-serializer.test.d.ts +5 -0
  127. package/dist/tests/unit/serializer/attribute-serializer.test.d.ts.map +1 -0
  128. package/dist/tests/unit/serializer/attribute-serializer.test.js +78 -0
  129. package/dist/tests/unit/serializer/field-serializer.test.d.ts +5 -0
  130. package/dist/tests/unit/serializer/field-serializer.test.d.ts.map +1 -0
  131. package/dist/tests/unit/serializer/field-serializer.test.js +159 -0
  132. package/dist/tests/unit/serializer/media-serializer.test.d.ts +5 -0
  133. package/dist/tests/unit/serializer/media-serializer.test.d.ts.map +1 -0
  134. package/dist/tests/unit/serializer/media-serializer.test.js +155 -0
  135. package/dist/tests/unit/serializer/session-serializer.test.d.ts +5 -0
  136. package/dist/tests/unit/serializer/session-serializer.test.d.ts.map +1 -0
  137. package/dist/tests/unit/serializer/session-serializer.test.js +317 -0
  138. package/dist/tests/unit/serializer/time-serializer.test.d.ts +5 -0
  139. package/dist/tests/unit/serializer/time-serializer.test.d.ts.map +1 -0
  140. package/dist/tests/unit/serializer/time-serializer.test.js +115 -0
  141. package/dist/tests/unit/types/errors.test.d.ts +5 -0
  142. package/dist/tests/unit/types/errors.test.d.ts.map +1 -0
  143. package/dist/tests/unit/types/errors.test.js +127 -0
  144. package/dist/tests/unit/types/network.test.d.ts +5 -0
  145. package/dist/tests/unit/types/network.test.d.ts.map +1 -0
  146. package/dist/tests/unit/types/network.test.js +132 -0
  147. package/dist/tests/unit/types/primitives.test.d.ts +5 -0
  148. package/dist/tests/unit/types/primitives.test.d.ts.map +1 -0
  149. package/dist/tests/unit/types/primitives.test.js +108 -0
  150. package/dist/tests/unit/utils/address-parser.test.d.ts +5 -0
  151. package/dist/tests/unit/utils/address-parser.test.d.ts.map +1 -0
  152. package/dist/tests/unit/utils/address-parser.test.js +203 -0
  153. package/dist/tests/unit/utils/format-validators.test.d.ts +5 -0
  154. package/dist/tests/unit/utils/format-validators.test.d.ts.map +1 -0
  155. package/dist/tests/unit/utils/format-validators.test.js +224 -0
  156. package/dist/tests/unit/utils/line-reader.test.d.ts +5 -0
  157. package/dist/tests/unit/utils/line-reader.test.d.ts.map +1 -0
  158. package/dist/tests/unit/utils/line-reader.test.js +157 -0
  159. package/dist/tests/unit/utils/time-converter.test.d.ts +5 -0
  160. package/dist/tests/unit/utils/time-converter.test.d.ts.map +1 -0
  161. package/dist/tests/unit/utils/time-converter.test.js +190 -0
  162. package/dist/tests/unit/validator/media-validator.test.d.ts +5 -0
  163. package/dist/tests/unit/validator/media-validator.test.d.ts.map +1 -0
  164. package/dist/tests/unit/validator/media-validator.test.js +313 -0
  165. package/dist/tests/unit/validator/semantic-validator.test.d.ts +5 -0
  166. package/dist/tests/unit/validator/semantic-validator.test.d.ts.map +1 -0
  167. package/dist/tests/unit/validator/semantic-validator.test.js +262 -0
  168. package/dist/tests/unit/validator/session-validator.test.d.ts +5 -0
  169. package/dist/tests/unit/validator/session-validator.test.d.ts.map +1 -0
  170. package/dist/tests/unit/validator/session-validator.test.js +447 -0
  171. package/package.json +50 -0
@@ -0,0 +1,367 @@
1
+ "use strict";
2
+ /**
3
+ * Tests for session-builder.ts
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ const session_builder_1 = require("../../../src/builder/session-builder");
7
+ const media_builder_1 = require("../../../src/builder/media-builder");
8
+ const errors_1 = require("../../../src/types/errors");
9
+ const time_1 = require("../../../src/types/time");
10
+ describe('session-builder', () => {
11
+ describe('SessionBuilder', () => {
12
+ describe('required fields', () => {
13
+ it('should throw when origin is missing', () => {
14
+ const builder = new session_builder_1.SessionBuilder()
15
+ .sessionName('Test Session');
16
+ expect(() => builder.build()).toThrow(errors_1.BuilderError);
17
+ expect(() => builder.build()).toThrow('origin');
18
+ });
19
+ it('should throw when session name is missing', () => {
20
+ const builder = new session_builder_1.SessionBuilder()
21
+ .origin('alice', '123', '456', '192.168.1.1');
22
+ expect(() => builder.build()).toThrow(errors_1.BuilderError);
23
+ expect(() => builder.build()).toThrow('sessionName');
24
+ });
25
+ it('should throw for empty session name', () => {
26
+ const builder = new session_builder_1.SessionBuilder()
27
+ .origin('alice', '123', '456', '192.168.1.1');
28
+ expect(() => builder.sessionName('')).toThrow(errors_1.BuilderError);
29
+ });
30
+ });
31
+ describe('minimal session', () => {
32
+ it('should build minimal session with auto timing', () => {
33
+ const sdp = new session_builder_1.SessionBuilder()
34
+ .origin('alice', '123', '456', '192.168.1.1')
35
+ .sessionName('Test')
36
+ .build();
37
+ expect(sdp.version).toBe(0);
38
+ expect(sdp.origin.username).toBe('alice');
39
+ expect(sdp.sessionName).toBe('Test');
40
+ expect(sdp.timeDescriptions).toHaveLength(1);
41
+ expect(sdp.timeDescriptions[0].timing.startTime).toBe(0);
42
+ expect(sdp.timeDescriptions[0].timing.stopTime).toBe(0);
43
+ });
44
+ it('should build session with explicit timing', () => {
45
+ const sdp = new session_builder_1.SessionBuilder()
46
+ .origin('alice', '123', '456', '192.168.1.1')
47
+ .sessionName('Test')
48
+ .addTiming(2873397496, 2873404696)
49
+ .build();
50
+ expect(sdp.timeDescriptions).toHaveLength(1);
51
+ expect(sdp.timeDescriptions[0].timing.startTime).toBe(2873397496);
52
+ expect(sdp.timeDescriptions[0].timing.stopTime).toBe(2873404696);
53
+ });
54
+ it('should build session with permanent timing', () => {
55
+ const sdp = new session_builder_1.SessionBuilder()
56
+ .origin('alice', '123', '456', '192.168.1.1')
57
+ .sessionName('Test')
58
+ .permanentTiming()
59
+ .build();
60
+ expect(sdp.timeDescriptions[0].timing.startTime).toBe(0);
61
+ expect(sdp.timeDescriptions[0].timing.stopTime).toBe(0);
62
+ });
63
+ });
64
+ describe('origin field', () => {
65
+ it('should detect IPv4 address type', () => {
66
+ const sdp = new session_builder_1.SessionBuilder()
67
+ .origin('alice', '123', '456', '192.168.1.1')
68
+ .sessionName('Test')
69
+ .build();
70
+ expect(sdp.origin.addrType).toBe('IP4');
71
+ });
72
+ it('should detect IPv6 address type', () => {
73
+ const sdp = new session_builder_1.SessionBuilder()
74
+ .origin('alice', '123', '456', '2001:db8::1')
75
+ .sessionName('Test')
76
+ .build();
77
+ expect(sdp.origin.addrType).toBe('IP6');
78
+ });
79
+ it('should allow explicit address type override', () => {
80
+ const sdp = new session_builder_1.SessionBuilder()
81
+ .origin('alice', '123', '456', '2001:db8::1', 'IP6')
82
+ .sessionName('Test')
83
+ .build();
84
+ expect(sdp.origin.addrType).toBe('IP6');
85
+ });
86
+ it('should support originAuto for auto-generated session ID', () => {
87
+ const sdp = new session_builder_1.SessionBuilder()
88
+ .originAuto('alice', '192.168.1.1')
89
+ .sessionName('Test')
90
+ .build();
91
+ expect(sdp.origin.username).toBe('alice');
92
+ expect(sdp.origin.sessId).toBeTruthy();
93
+ expect(sdp.origin.sessVersion).toBeTruthy();
94
+ });
95
+ });
96
+ describe('optional fields', () => {
97
+ it('should add session information', () => {
98
+ const sdp = new session_builder_1.SessionBuilder()
99
+ .origin('alice', '123', '456', '192.168.1.1')
100
+ .sessionName('Test')
101
+ .sessionInformation('A test session')
102
+ .build();
103
+ expect(sdp.sessionInformation).toBe('A test session');
104
+ });
105
+ it('should add URI', () => {
106
+ const sdp = new session_builder_1.SessionBuilder()
107
+ .origin('alice', '123', '456', '192.168.1.1')
108
+ .sessionName('Test')
109
+ .uri('https://example.com/session')
110
+ .build();
111
+ expect(sdp.uri).toBe('https://example.com/session');
112
+ });
113
+ it('should add emails', () => {
114
+ const sdp = new session_builder_1.SessionBuilder()
115
+ .origin('alice', '123', '456', '192.168.1.1')
116
+ .sessionName('Test')
117
+ .addEmail('alice@example.com')
118
+ .addEmail('bob@example.com')
119
+ .build();
120
+ expect(sdp.emails).toHaveLength(2);
121
+ expect(sdp.emails[0]).toBe('alice@example.com');
122
+ expect(sdp.emails[1]).toBe('bob@example.com');
123
+ });
124
+ it('should add phones', () => {
125
+ const sdp = new session_builder_1.SessionBuilder()
126
+ .origin('alice', '123', '456', '192.168.1.1')
127
+ .sessionName('Test')
128
+ .addPhone('+1-555-1234')
129
+ .build();
130
+ expect(sdp.phones).toHaveLength(1);
131
+ expect(sdp.phones[0]).toBe('+1-555-1234');
132
+ });
133
+ it('should add key (deprecated)', () => {
134
+ const sdp = new session_builder_1.SessionBuilder()
135
+ .origin('alice', '123', '456', '192.168.1.1')
136
+ .sessionName('Test')
137
+ .key('clear:testkey')
138
+ .build();
139
+ expect(sdp.key).toBe('clear:testkey');
140
+ });
141
+ });
142
+ describe('connection field', () => {
143
+ it('should add session-level connection', () => {
144
+ const sdp = new session_builder_1.SessionBuilder()
145
+ .origin('alice', '123', '456', '192.168.1.1')
146
+ .sessionName('Test')
147
+ .connection('192.168.1.100')
148
+ .build();
149
+ expect(sdp.connection).toBeDefined();
150
+ expect(sdp.connection.addrType).toBe('IP4');
151
+ });
152
+ it('should add IPv6 connection', () => {
153
+ const sdp = new session_builder_1.SessionBuilder()
154
+ .origin('alice', '123', '456', '192.168.1.1')
155
+ .sessionName('Test')
156
+ .connection('2001:db8::1')
157
+ .build();
158
+ expect(sdp.connection.addrType).toBe('IP6');
159
+ });
160
+ });
161
+ describe('bandwidth', () => {
162
+ it('should add CT bandwidth', () => {
163
+ const sdp = new session_builder_1.SessionBuilder()
164
+ .origin('alice', '123', '456', '192.168.1.1')
165
+ .sessionName('Test')
166
+ .addBandwidth('CT', 1000)
167
+ .build();
168
+ expect(sdp.bandwidths).toHaveLength(1);
169
+ expect(sdp.bandwidths[0].type).toBe('CT');
170
+ expect(sdp.bandwidths[0].value).toBe(1000);
171
+ });
172
+ it('should add AS bandwidth', () => {
173
+ const sdp = new session_builder_1.SessionBuilder()
174
+ .origin('alice', '123', '456', '192.168.1.1')
175
+ .sessionName('Test')
176
+ .addBandwidth('AS', 512)
177
+ .build();
178
+ expect(sdp.bandwidths[0].type).toBe('AS');
179
+ expect(sdp.bandwidths[0].value).toBe(512);
180
+ });
181
+ });
182
+ describe('time descriptions', () => {
183
+ it('should add time description object', () => {
184
+ const td = (0, time_1.createTimeDescription)((0, time_1.createTiming)(1000, 2000));
185
+ const sdp = new session_builder_1.SessionBuilder()
186
+ .origin('alice', '123', '456', '192.168.1.1')
187
+ .sessionName('Test')
188
+ .addTimeDescription(td)
189
+ .build();
190
+ expect(sdp.timeDescriptions).toHaveLength(1);
191
+ expect(sdp.timeDescriptions[0].timing.startTime).toBe(1000);
192
+ });
193
+ it('should add multiple time descriptions', () => {
194
+ const sdp = new session_builder_1.SessionBuilder()
195
+ .origin('alice', '123', '456', '192.168.1.1')
196
+ .sessionName('Test')
197
+ .addTiming(1000, 2000)
198
+ .addTiming(3000, 4000)
199
+ .build();
200
+ expect(sdp.timeDescriptions).toHaveLength(2);
201
+ });
202
+ });
203
+ describe('attributes', () => {
204
+ it('should add direction attributes', () => {
205
+ const sdp = new session_builder_1.SessionBuilder()
206
+ .origin('alice', '123', '456', '192.168.1.1')
207
+ .sessionName('Test')
208
+ .sendrecv()
209
+ .build();
210
+ expect(sdp.attributes).toHaveLength(1);
211
+ expect(sdp.attributes[0]).toEqual({ kind: 'property', name: 'sendrecv' });
212
+ });
213
+ it('should add recvonly attribute', () => {
214
+ const sdp = new session_builder_1.SessionBuilder()
215
+ .origin('alice', '123', '456', '192.168.1.1')
216
+ .sessionName('Test')
217
+ .recvonly()
218
+ .build();
219
+ expect(sdp.attributes[0].name).toBe('recvonly');
220
+ });
221
+ it('should add sendonly attribute', () => {
222
+ const sdp = new session_builder_1.SessionBuilder()
223
+ .origin('alice', '123', '456', '192.168.1.1')
224
+ .sessionName('Test')
225
+ .sendonly()
226
+ .build();
227
+ expect(sdp.attributes[0].name).toBe('sendonly');
228
+ });
229
+ it('should add inactive attribute', () => {
230
+ const sdp = new session_builder_1.SessionBuilder()
231
+ .origin('alice', '123', '456', '192.168.1.1')
232
+ .sessionName('Test')
233
+ .inactive()
234
+ .build();
235
+ expect(sdp.attributes[0].name).toBe('inactive');
236
+ });
237
+ it('should add category attribute', () => {
238
+ const sdp = new session_builder_1.SessionBuilder()
239
+ .origin('alice', '123', '456', '192.168.1.1')
240
+ .sessionName('Test')
241
+ .category('conference')
242
+ .build();
243
+ expect(sdp.attributes[0]).toEqual({ kind: 'value', name: 'cat', value: 'conference' });
244
+ });
245
+ it('should add keywords attribute', () => {
246
+ const sdp = new session_builder_1.SessionBuilder()
247
+ .origin('alice', '123', '456', '192.168.1.1')
248
+ .sessionName('Test')
249
+ .keywords('voip,sip')
250
+ .build();
251
+ expect(sdp.attributes[0]).toEqual({ kind: 'value', name: 'keywds', value: 'voip,sip' });
252
+ });
253
+ it('should add tool attribute', () => {
254
+ const sdp = new session_builder_1.SessionBuilder()
255
+ .origin('alice', '123', '456', '192.168.1.1')
256
+ .sessionName('Test')
257
+ .tool('tsdp/1.0')
258
+ .build();
259
+ expect(sdp.attributes[0]).toEqual({ kind: 'value', name: 'tool', value: 'tsdp/1.0' });
260
+ });
261
+ it('should add charset attribute', () => {
262
+ const sdp = new session_builder_1.SessionBuilder()
263
+ .origin('alice', '123', '456', '192.168.1.1')
264
+ .sessionName('Test')
265
+ .charset('UTF-8')
266
+ .build();
267
+ expect(sdp.attributes[0]).toEqual({ kind: 'value', name: 'charset', value: 'UTF-8' });
268
+ });
269
+ it('should add custom property attribute', () => {
270
+ const sdp = new session_builder_1.SessionBuilder()
271
+ .origin('alice', '123', '456', '192.168.1.1')
272
+ .sessionName('Test')
273
+ .addPropertyAttribute('ice-lite')
274
+ .build();
275
+ expect(sdp.attributes[0]).toEqual({ kind: 'property', name: 'ice-lite' });
276
+ });
277
+ it('should add custom value attribute', () => {
278
+ const sdp = new session_builder_1.SessionBuilder()
279
+ .origin('alice', '123', '456', '192.168.1.1')
280
+ .sessionName('Test')
281
+ .addValueAttribute('group', 'BUNDLE audio video')
282
+ .build();
283
+ expect(sdp.attributes[0]).toEqual({ kind: 'value', name: 'group', value: 'BUNDLE audio video' });
284
+ });
285
+ });
286
+ describe('media descriptions', () => {
287
+ it('should add media description directly', () => {
288
+ const media = new media_builder_1.MediaBuilder()
289
+ .type('audio')
290
+ .port(49170)
291
+ .protocol('RTP/AVP')
292
+ .formats(['0'])
293
+ .build();
294
+ const sdp = new session_builder_1.SessionBuilder()
295
+ .origin('alice', '123', '456', '192.168.1.1')
296
+ .sessionName('Test')
297
+ .connection('192.168.1.100')
298
+ .addMedia(media)
299
+ .build();
300
+ expect(sdp.mediaDescriptions).toHaveLength(1);
301
+ expect(sdp.mediaDescriptions[0].media.type).toBe('audio');
302
+ });
303
+ it('should add media description via builder function', () => {
304
+ const sdp = new session_builder_1.SessionBuilder()
305
+ .origin('alice', '123', '456', '192.168.1.1')
306
+ .sessionName('Test')
307
+ .connection('192.168.1.100')
308
+ .addMediaBuilder((b) => b.type('audio').port(49170).protocol('RTP/AVP').formats(['0']))
309
+ .build();
310
+ expect(sdp.mediaDescriptions).toHaveLength(1);
311
+ expect(sdp.mediaDescriptions[0].media.type).toBe('audio');
312
+ });
313
+ it('should add audio media shorthand', () => {
314
+ const sdp = new session_builder_1.SessionBuilder()
315
+ .origin('alice', '123', '456', '192.168.1.1')
316
+ .sessionName('Test')
317
+ .connection('192.168.1.100')
318
+ .addAudioMedia(49170, 'RTP/AVP', ['0', '8'])
319
+ .build();
320
+ expect(sdp.mediaDescriptions[0].media.type).toBe('audio');
321
+ expect(sdp.mediaDescriptions[0].media.formats).toEqual(['0', '8']);
322
+ });
323
+ it('should add video media shorthand', () => {
324
+ const sdp = new session_builder_1.SessionBuilder()
325
+ .origin('alice', '123', '456', '192.168.1.1')
326
+ .sessionName('Test')
327
+ .connection('192.168.1.100')
328
+ .addVideoMedia(51372, 'RTP/AVP', ['96'])
329
+ .build();
330
+ expect(sdp.mediaDescriptions[0].media.type).toBe('video');
331
+ });
332
+ });
333
+ describe('connection coverage validation', () => {
334
+ it('should require connection when media has no connection', () => {
335
+ const builder = new session_builder_1.SessionBuilder()
336
+ .origin('alice', '123', '456', '192.168.1.1')
337
+ .sessionName('Test')
338
+ .addAudioMedia(49170, 'RTP/AVP', ['0']);
339
+ expect(() => builder.build()).toThrow(errors_1.BuilderError);
340
+ expect(() => builder.build()).toThrow('Connection information required');
341
+ });
342
+ it('should allow media without connection when session has connection', () => {
343
+ const sdp = new session_builder_1.SessionBuilder()
344
+ .origin('alice', '123', '456', '192.168.1.1')
345
+ .sessionName('Test')
346
+ .connection('192.168.1.100')
347
+ .addAudioMedia(49170, 'RTP/AVP', ['0'])
348
+ .build();
349
+ expect(sdp.mediaDescriptions).toHaveLength(1);
350
+ });
351
+ it('should allow media with own connection when session has no connection', () => {
352
+ const sdp = new session_builder_1.SessionBuilder()
353
+ .origin('alice', '123', '456', '192.168.1.1')
354
+ .sessionName('Test')
355
+ .addMediaBuilder((b) => b.type('audio').port(49170).protocol('RTP/AVP').formats(['0']).connection('192.168.1.100'))
356
+ .build();
357
+ expect(sdp.mediaDescriptions).toHaveLength(1);
358
+ });
359
+ });
360
+ });
361
+ describe('sessionBuilder factory', () => {
362
+ it('should create a new SessionBuilder', () => {
363
+ const builder = (0, session_builder_1.sessionBuilder)();
364
+ expect(builder).toBeInstanceOf(session_builder_1.SessionBuilder);
365
+ });
366
+ });
367
+ });
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Tests for attribute-parser.ts
3
+ */
4
+ export {};
5
+ //# sourceMappingURL=attribute-parser.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"attribute-parser.test.d.ts","sourceRoot":"","sources":["../../../../tests/unit/parser/attribute-parser.test.ts"],"names":[],"mappings":"AAAA;;GAEG"}