music-metadata 7.11.6 → 7.11.7

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 (152) hide show
  1. package/README.md +432 -432
  2. package/lib/ParserFactory.d.ts +49 -49
  3. package/lib/ParserFactory.js +251 -251
  4. package/lib/aiff/AiffParser.d.ts +15 -15
  5. package/lib/aiff/AiffParser.js +85 -85
  6. package/lib/aiff/AiffToken.d.ts +22 -22
  7. package/lib/aiff/AiffToken.js +43 -43
  8. package/lib/apev2/APEv2Parser.d.ts +30 -30
  9. package/lib/apev2/APEv2Parser.js +162 -162
  10. package/lib/apev2/APEv2TagMapper.d.ts +4 -4
  11. package/lib/apev2/APEv2TagMapper.js +86 -86
  12. package/lib/apev2/APEv2Token.d.ts +100 -100
  13. package/lib/apev2/APEv2Token.js +126 -126
  14. package/lib/asf/AsfObject.d.ts +319 -319
  15. package/lib/asf/AsfObject.js +384 -384
  16. package/lib/asf/AsfParser.d.ts +17 -17
  17. package/lib/asf/AsfParser.js +135 -135
  18. package/lib/asf/AsfTagMapper.d.ts +7 -7
  19. package/lib/asf/AsfTagMapper.js +95 -95
  20. package/lib/asf/AsfUtil.d.ts +13 -13
  21. package/lib/asf/AsfUtil.js +40 -40
  22. package/lib/asf/GUID.d.ts +86 -86
  23. package/lib/asf/GUID.js +123 -123
  24. package/lib/common/BasicParser.d.ts +17 -17
  25. package/lib/common/BasicParser.js +18 -18
  26. package/lib/common/CaseInsensitiveTagMap.d.ts +10 -10
  27. package/lib/common/CaseInsensitiveTagMap.js +21 -21
  28. package/lib/common/CombinedTagMapper.d.ts +19 -19
  29. package/lib/common/CombinedTagMapper.js +51 -51
  30. package/lib/common/FourCC.d.ts +6 -6
  31. package/lib/common/FourCC.js +28 -28
  32. package/lib/common/GenericTagMapper.d.ts +51 -51
  33. package/lib/common/GenericTagMapper.js +55 -55
  34. package/lib/common/GenericTagTypes.d.ts +33 -33
  35. package/lib/common/GenericTagTypes.js +131 -131
  36. package/lib/common/MetadataCollector.d.ts +76 -76
  37. package/lib/common/MetadataCollector.js +275 -275
  38. package/lib/common/RandomFileReader.d.ts +20 -20
  39. package/lib/common/RandomFileReader.js +37 -37
  40. package/lib/common/RandomUint8ArrayReader.d.ts +18 -18
  41. package/lib/common/RandomUint8ArrayReader.js +25 -25
  42. package/lib/common/Util.d.ts +58 -57
  43. package/lib/common/Util.js +162 -169
  44. package/lib/core.d.ts +48 -48
  45. package/lib/core.js +90 -90
  46. package/lib/dsdiff/DsdiffParser.d.ts +14 -14
  47. package/lib/dsdiff/DsdiffParser.js +143 -143
  48. package/lib/dsdiff/DsdiffToken.d.ts +9 -9
  49. package/lib/dsdiff/DsdiffToken.js +21 -21
  50. package/lib/dsf/DsfChunk.d.ts +86 -86
  51. package/lib/dsf/DsfChunk.js +54 -54
  52. package/lib/dsf/DsfParser.d.ts +9 -9
  53. package/lib/dsf/DsfParser.js +56 -56
  54. package/lib/flac/FlacParser.d.ts +28 -28
  55. package/lib/flac/FlacParser.js +175 -175
  56. package/lib/id3v1/ID3v1Parser.d.ts +13 -13
  57. package/lib/id3v1/ID3v1Parser.js +134 -134
  58. package/lib/id3v1/ID3v1TagMap.d.ts +4 -4
  59. package/lib/id3v1/ID3v1TagMap.js +22 -22
  60. package/lib/id3v2/AbstractID3Parser.d.ts +17 -17
  61. package/lib/id3v2/AbstractID3Parser.js +60 -60
  62. package/lib/id3v2/FrameParser.d.ts +32 -32
  63. package/lib/id3v2/FrameParser.js +329 -323
  64. package/lib/id3v2/ID3v22TagMapper.d.ts +9 -9
  65. package/lib/id3v2/ID3v22TagMapper.js +55 -55
  66. package/lib/id3v2/ID3v24TagMapper.d.ts +14 -14
  67. package/lib/id3v2/ID3v24TagMapper.js +193 -193
  68. package/lib/id3v2/ID3v2Parser.d.ts +29 -29
  69. package/lib/id3v2/ID3v2Parser.js +194 -194
  70. package/lib/id3v2/ID3v2Token.d.ts +73 -73
  71. package/lib/id3v2/ID3v2Token.js +106 -106
  72. package/lib/iff/index.d.ts +33 -33
  73. package/lib/iff/index.js +19 -19
  74. package/lib/index.d.ts +45 -45
  75. package/lib/index.js +74 -74
  76. package/lib/lyrics3/Lyrics3.d.ts +3 -3
  77. package/lib/lyrics3/Lyrics3.js +17 -17
  78. package/lib/matroska/MatroskaDtd.d.ts +8 -8
  79. package/lib/matroska/MatroskaDtd.js +279 -279
  80. package/lib/matroska/MatroskaParser.d.ts +37 -37
  81. package/lib/matroska/MatroskaParser.js +235 -235
  82. package/lib/matroska/MatroskaTagMapper.d.ts +4 -4
  83. package/lib/matroska/MatroskaTagMapper.js +35 -35
  84. package/lib/matroska/types.d.ts +175 -175
  85. package/lib/matroska/types.js +32 -32
  86. package/lib/mp4/Atom.d.ts +16 -16
  87. package/lib/mp4/Atom.js +70 -70
  88. package/lib/mp4/AtomToken.d.ts +395 -395
  89. package/lib/mp4/AtomToken.js +406 -406
  90. package/lib/mp4/MP4Parser.d.ts +30 -30
  91. package/lib/mp4/MP4Parser.js +511 -511
  92. package/lib/mp4/MP4TagMapper.d.ts +5 -5
  93. package/lib/mp4/MP4TagMapper.js +115 -115
  94. package/lib/mpeg/ExtendedLameHeader.d.ts +27 -27
  95. package/lib/mpeg/ExtendedLameHeader.js +31 -31
  96. package/lib/mpeg/MpegParser.d.ts +49 -49
  97. package/lib/mpeg/MpegParser.js +529 -529
  98. package/lib/mpeg/ReplayGainDataFormat.d.ts +55 -55
  99. package/lib/mpeg/ReplayGainDataFormat.js +69 -69
  100. package/lib/mpeg/XingTag.d.ts +45 -45
  101. package/lib/mpeg/XingTag.js +69 -69
  102. package/lib/musepack/index.d.ts +5 -5
  103. package/lib/musepack/index.js +32 -32
  104. package/lib/musepack/sv7/BitReader.d.ts +13 -13
  105. package/lib/musepack/sv7/BitReader.js +54 -54
  106. package/lib/musepack/sv7/MpcSv7Parser.d.ts +8 -8
  107. package/lib/musepack/sv7/MpcSv7Parser.js +46 -46
  108. package/lib/musepack/sv7/StreamVersion7.d.ts +28 -28
  109. package/lib/musepack/sv7/StreamVersion7.js +41 -41
  110. package/lib/musepack/sv8/MpcSv8Parser.d.ts +6 -6
  111. package/lib/musepack/sv8/MpcSv8Parser.js +55 -55
  112. package/lib/musepack/sv8/StreamVersion8.d.ts +40 -40
  113. package/lib/musepack/sv8/StreamVersion8.js +80 -80
  114. package/lib/ogg/Ogg.d.ts +72 -72
  115. package/lib/ogg/Ogg.js +2 -2
  116. package/lib/ogg/OggParser.d.ts +23 -23
  117. package/lib/ogg/OggParser.js +126 -126
  118. package/lib/ogg/opus/Opus.d.ts +48 -48
  119. package/lib/ogg/opus/Opus.js +28 -28
  120. package/lib/ogg/opus/OpusParser.d.ts +25 -25
  121. package/lib/ogg/opus/OpusParser.js +56 -56
  122. package/lib/ogg/speex/Speex.d.ts +36 -36
  123. package/lib/ogg/speex/Speex.js +31 -31
  124. package/lib/ogg/speex/SpeexParser.d.ts +22 -22
  125. package/lib/ogg/speex/SpeexParser.js +35 -35
  126. package/lib/ogg/theora/Theora.d.ts +20 -20
  127. package/lib/ogg/theora/Theora.js +23 -23
  128. package/lib/ogg/theora/TheoraParser.d.ts +28 -28
  129. package/lib/ogg/theora/TheoraParser.js +44 -44
  130. package/lib/ogg/vorbis/Vorbis.d.ts +79 -79
  131. package/lib/ogg/vorbis/Vorbis.js +78 -78
  132. package/lib/ogg/vorbis/VorbisDecoder.d.ts +12 -12
  133. package/lib/ogg/vorbis/VorbisDecoder.js +32 -32
  134. package/lib/ogg/vorbis/VorbisParser.d.ts +36 -36
  135. package/lib/ogg/vorbis/VorbisParser.js +128 -128
  136. package/lib/ogg/vorbis/VorbisTagMapper.d.ts +7 -7
  137. package/lib/ogg/vorbis/VorbisTagMapper.js +132 -132
  138. package/lib/riff/RiffChunk.d.ts +16 -16
  139. package/lib/riff/RiffChunk.js +32 -32
  140. package/lib/riff/RiffInfoTagMap.d.ts +10 -10
  141. package/lib/riff/RiffInfoTagMap.js +37 -37
  142. package/lib/type.d.ts +599 -599
  143. package/lib/type.js +13 -13
  144. package/lib/wav/WaveChunk.d.ts +64 -64
  145. package/lib/wav/WaveChunk.js +65 -65
  146. package/lib/wav/WaveParser.d.ts +24 -24
  147. package/lib/wav/WaveParser.js +144 -144
  148. package/lib/wavpack/WavPackParser.d.ts +14 -14
  149. package/lib/wavpack/WavPackParser.js +105 -105
  150. package/lib/wavpack/WavPackToken.d.ts +64 -64
  151. package/lib/wavpack/WavPackToken.js +76 -76
  152. package/package.json +142 -142
@@ -1,406 +1,406 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.ChapterText = exports.StcoAtom = exports.StszAtom = exports.StscAtom = exports.SampleToChunkToken = exports.SttsAtom = exports.TimeToSampleToken = exports.SoundSampleDescriptionV0 = exports.SoundSampleDescriptionVersion = exports.StsdAtom = exports.TrackHeaderAtom = exports.NameAtom = exports.DataAtom = exports.MvhdAtom = exports.MdhdAtom = exports.FixedLengthAtom = exports.mhdr = exports.tkhd = exports.ftyp = exports.ExtendedSize = exports.Header = void 0;
4
- const Token = require("token-types");
5
- const initDebug = require("debug");
6
- const FourCC_1 = require("../common/FourCC");
7
- const debug = initDebug('music-metadata:parser:MP4:atom');
8
- exports.Header = {
9
- len: 8,
10
- get: (buf, off) => {
11
- const length = Token.UINT32_BE.get(buf, off);
12
- if (length < 0)
13
- throw new Error('Invalid atom header length');
14
- return {
15
- length: BigInt(length),
16
- name: new Token.StringType(4, 'binary').get(buf, off + 4)
17
- };
18
- },
19
- put: (buf, off, hdr) => {
20
- Token.UINT32_BE.put(buf, off, Number(hdr.length));
21
- return FourCC_1.FourCcToken.put(buf, off + 4, hdr.name);
22
- }
23
- };
24
- /**
25
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap1/qtff1.html#//apple_ref/doc/uid/TP40000939-CH203-38190
26
- */
27
- exports.ExtendedSize = Token.UINT64_BE;
28
- exports.ftyp = {
29
- len: 4,
30
- get: (buf, off) => {
31
- return {
32
- type: new Token.StringType(4, 'ascii').get(buf, off)
33
- };
34
- }
35
- };
36
- exports.tkhd = {
37
- len: 4,
38
- get: (buf, off) => {
39
- return {
40
- type: new Token.StringType(4, 'ascii').get(buf, off)
41
- };
42
- }
43
- };
44
- /**
45
- * Token: Movie Header Atom
46
- */
47
- exports.mhdr = {
48
- len: 8,
49
- get: (buf, off) => {
50
- return {
51
- version: Token.UINT8.get(buf, off),
52
- flags: Token.UINT24_BE.get(buf, off + 1),
53
- nextItemID: Token.UINT32_BE.get(buf, off + 4)
54
- };
55
- }
56
- };
57
- /**
58
- * Base class for 'fixed' length atoms.
59
- * In some cases these atoms are longer then the sum of the described fields.
60
- * Issue: https://github.com/Borewit/music-metadata/issues/120
61
- */
62
- class FixedLengthAtom {
63
- /**
64
- *
65
- * @param {number} len Length as specified in the size field
66
- * @param {number} expLen Total length of sum of specified fields in the standard
67
- */
68
- constructor(len, expLen, atomId) {
69
- this.len = len;
70
- if (len < expLen) {
71
- throw new Error(`Atom ${atomId} expected to be ${expLen}, but specifies ${len} bytes long.`);
72
- }
73
- else if (len > expLen) {
74
- debug(`Warning: atom ${atomId} expected to be ${expLen}, but was actually ${len} bytes long.`);
75
- }
76
- }
77
- }
78
- exports.FixedLengthAtom = FixedLengthAtom;
79
- /**
80
- * Timestamp stored in seconds since Mac Epoch (1 January 1904)
81
- */
82
- const SecondsSinceMacEpoch = {
83
- len: 4,
84
- get: (buf, off) => {
85
- const secondsSinceUnixEpoch = Token.UINT32_BE.get(buf, off) - 2082844800;
86
- return new Date(secondsSinceUnixEpoch * 1000);
87
- }
88
- };
89
- /**
90
- * Token: Media Header Atom
91
- * Ref:
92
- * https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-SW34
93
- * https://wiki.multimedia.cx/index.php/QuickTime_container#mdhd
94
- */
95
- class MdhdAtom extends FixedLengthAtom {
96
- constructor(len) {
97
- super(len, 24, 'mdhd');
98
- this.len = len;
99
- }
100
- get(buf, off) {
101
- return {
102
- version: Token.UINT8.get(buf, off + 0),
103
- flags: Token.UINT24_BE.get(buf, off + 1),
104
- creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
105
- modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
106
- timeScale: Token.UINT32_BE.get(buf, off + 12),
107
- duration: Token.UINT32_BE.get(buf, off + 16),
108
- language: Token.UINT16_BE.get(buf, off + 20),
109
- quality: Token.UINT16_BE.get(buf, off + 22)
110
- };
111
- }
112
- }
113
- exports.MdhdAtom = MdhdAtom;
114
- /**
115
- * Token: Movie Header Atom
116
- */
117
- class MvhdAtom extends FixedLengthAtom {
118
- constructor(len) {
119
- super(len, 100, 'mvhd');
120
- this.len = len;
121
- }
122
- get(buf, off) {
123
- return {
124
- version: Token.UINT8.get(buf, off),
125
- flags: Token.UINT24_BE.get(buf, off + 1),
126
- creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
127
- modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
128
- timeScale: Token.UINT32_BE.get(buf, off + 12),
129
- duration: Token.UINT32_BE.get(buf, off + 16),
130
- preferredRate: Token.UINT32_BE.get(buf, off + 20),
131
- preferredVolume: Token.UINT16_BE.get(buf, off + 24),
132
- // ignore reserver: 10 bytes
133
- // ignore matrix structure: 36 bytes
134
- previewTime: Token.UINT32_BE.get(buf, off + 72),
135
- previewDuration: Token.UINT32_BE.get(buf, off + 76),
136
- posterTime: Token.UINT32_BE.get(buf, off + 80),
137
- selectionTime: Token.UINT32_BE.get(buf, off + 84),
138
- selectionDuration: Token.UINT32_BE.get(buf, off + 88),
139
- currentTime: Token.UINT32_BE.get(buf, off + 92),
140
- nextTrackID: Token.UINT32_BE.get(buf, off + 96)
141
- };
142
- }
143
- }
144
- exports.MvhdAtom = MvhdAtom;
145
- /**
146
- * Data Atom Structure
147
- */
148
- class DataAtom {
149
- constructor(len) {
150
- this.len = len;
151
- }
152
- get(buf, off) {
153
- return {
154
- type: {
155
- set: Token.UINT8.get(buf, off + 0),
156
- type: Token.UINT24_BE.get(buf, off + 1)
157
- },
158
- locale: Token.UINT24_BE.get(buf, off + 4),
159
- value: Buffer.from(new Token.Uint8ArrayType(this.len - 8).get(buf, off + 8))
160
- };
161
- }
162
- }
163
- exports.DataAtom = DataAtom;
164
- /**
165
- * Data Atom Structure
166
- * Ref: https://developer.apple.com/library/content/documentation/QuickTime/QTFF/Metadata/Metadata.html#//apple_ref/doc/uid/TP40000939-CH1-SW31
167
- */
168
- class NameAtom {
169
- constructor(len) {
170
- this.len = len;
171
- }
172
- get(buf, off) {
173
- return {
174
- version: Token.UINT8.get(buf, off),
175
- flags: Token.UINT24_BE.get(buf, off + 1),
176
- name: new Token.StringType(this.len - 4, 'utf-8').get(buf, off + 4)
177
- };
178
- }
179
- }
180
- exports.NameAtom = NameAtom;
181
- /**
182
- * Track Header Atoms structure
183
- * Ref: https://developer.apple.com/library/content/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25550
184
- */
185
- class TrackHeaderAtom {
186
- constructor(len) {
187
- this.len = len;
188
- }
189
- get(buf, off) {
190
- return {
191
- version: Token.UINT8.get(buf, off),
192
- flags: Token.UINT24_BE.get(buf, off + 1),
193
- creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
194
- modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
195
- trackId: Token.UINT32_BE.get(buf, off + 12),
196
- // reserved 4 bytes
197
- duration: Token.UINT32_BE.get(buf, off + 20),
198
- layer: Token.UINT16_BE.get(buf, off + 24),
199
- alternateGroup: Token.UINT16_BE.get(buf, off + 26),
200
- volume: Token.UINT16_BE.get(buf, off + 28) // ToDo: fixed point
201
- // ToDo: add remaining fields
202
- };
203
- }
204
- }
205
- exports.TrackHeaderAtom = TrackHeaderAtom;
206
- /**
207
- * Atom: Sample Description Atom ('stsd')
208
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
209
- */
210
- const stsdHeader = {
211
- len: 8,
212
- get: (buf, off) => {
213
- return {
214
- version: Token.UINT8.get(buf, off),
215
- flags: Token.UINT24_BE.get(buf, off + 1),
216
- numberOfEntries: Token.UINT32_BE.get(buf, off + 4)
217
- };
218
- }
219
- };
220
- /**
221
- * Atom: Sample Description Atom ('stsd')
222
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
223
- */
224
- class SampleDescriptionTable {
225
- constructor(len) {
226
- this.len = len;
227
- }
228
- get(buf, off) {
229
- return {
230
- dataFormat: FourCC_1.FourCcToken.get(buf, off),
231
- dataReferenceIndex: Token.UINT16_BE.get(buf, off + 10),
232
- description: new Token.Uint8ArrayType(this.len - 12).get(buf, off + 12)
233
- };
234
- }
235
- }
236
- /**
237
- * Atom: Sample-description Atom ('stsd')
238
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
239
- */
240
- class StsdAtom {
241
- constructor(len) {
242
- this.len = len;
243
- }
244
- get(buf, off) {
245
- const header = stsdHeader.get(buf, off);
246
- off += stsdHeader.len;
247
- const table = [];
248
- for (let n = 0; n < header.numberOfEntries; ++n) {
249
- const size = Token.UINT32_BE.get(buf, off); // Sample description size
250
- off += Token.UINT32_BE.len;
251
- table.push(new SampleDescriptionTable(size).get(buf, off));
252
- off += size;
253
- }
254
- return {
255
- header,
256
- table
257
- };
258
- }
259
- }
260
- exports.StsdAtom = StsdAtom;
261
- /**
262
- * Common Sound Sample Description (version & revision)
263
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap3/qtff3.html#//apple_ref/doc/uid/TP40000939-CH205-57317
264
- */
265
- exports.SoundSampleDescriptionVersion = {
266
- len: 8,
267
- get(buf, off) {
268
- return {
269
- version: Token.INT16_BE.get(buf, off),
270
- revision: Token.INT16_BE.get(buf, off + 2),
271
- vendor: Token.INT32_BE.get(buf, off + 4)
272
- };
273
- }
274
- };
275
- /**
276
- * Sound Sample Description (Version 0)
277
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap3/qtff3.html#//apple_ref/doc/uid/TP40000939-CH205-130736
278
- */
279
- exports.SoundSampleDescriptionV0 = {
280
- len: 12,
281
- get(buf, off) {
282
- return {
283
- numAudioChannels: Token.INT16_BE.get(buf, off + 0),
284
- sampleSize: Token.INT16_BE.get(buf, off + 2),
285
- compressionId: Token.INT16_BE.get(buf, off + 4),
286
- packetSize: Token.INT16_BE.get(buf, off + 6),
287
- sampleRate: Token.UINT16_BE.get(buf, off + 8) + Token.UINT16_BE.get(buf, off + 10) / 10000
288
- };
289
- }
290
- };
291
- class SimpleTableAtom {
292
- constructor(len, token) {
293
- this.len = len;
294
- this.token = token;
295
- }
296
- get(buf, off) {
297
- const nrOfEntries = Token.INT32_BE.get(buf, off + 4);
298
- return {
299
- version: Token.INT8.get(buf, off + 0),
300
- flags: Token.INT24_BE.get(buf, off + 1),
301
- numberOfEntries: nrOfEntries,
302
- entries: readTokenTable(buf, this.token, off + 8, this.len - 8, nrOfEntries)
303
- };
304
- }
305
- }
306
- exports.TimeToSampleToken = {
307
- len: 8,
308
- get(buf, off) {
309
- return {
310
- count: Token.INT32_BE.get(buf, off + 0),
311
- duration: Token.INT32_BE.get(buf, off + 4)
312
- };
313
- }
314
- };
315
- /**
316
- * Time-to-sample('stts') atom.
317
- * Store duration information for a media’s samples.
318
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25696
319
- */
320
- class SttsAtom extends SimpleTableAtom {
321
- constructor(len) {
322
- super(len, exports.TimeToSampleToken);
323
- this.len = len;
324
- }
325
- }
326
- exports.SttsAtom = SttsAtom;
327
- exports.SampleToChunkToken = {
328
- len: 12,
329
- get(buf, off) {
330
- return {
331
- firstChunk: Token.INT32_BE.get(buf, off),
332
- samplesPerChunk: Token.INT32_BE.get(buf, off + 4),
333
- sampleDescriptionId: Token.INT32_BE.get(buf, off + 8)
334
- };
335
- }
336
- };
337
- /**
338
- * Sample-to-Chunk ('stsc') atom interface
339
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25706
340
- */
341
- class StscAtom extends SimpleTableAtom {
342
- constructor(len) {
343
- super(len, exports.SampleToChunkToken);
344
- this.len = len;
345
- }
346
- }
347
- exports.StscAtom = StscAtom;
348
- /**
349
- * Sample-size ('stsz') atom
350
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25710
351
- */
352
- class StszAtom {
353
- constructor(len) {
354
- this.len = len;
355
- }
356
- get(buf, off) {
357
- const nrOfEntries = Token.INT32_BE.get(buf, off + 8);
358
- return {
359
- version: Token.INT8.get(buf, off),
360
- flags: Token.INT24_BE.get(buf, off + 1),
361
- sampleSize: Token.INT32_BE.get(buf, off + 4),
362
- numberOfEntries: nrOfEntries,
363
- entries: readTokenTable(buf, Token.INT32_BE, off + 12, this.len - 12, nrOfEntries)
364
- };
365
- }
366
- }
367
- exports.StszAtom = StszAtom;
368
- /**
369
- * Chunk offset atom, 'stco'
370
- * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25715
371
- */
372
- class StcoAtom extends SimpleTableAtom {
373
- constructor(len) {
374
- super(len, Token.INT32_BE);
375
- this.len = len;
376
- }
377
- }
378
- exports.StcoAtom = StcoAtom;
379
- /**
380
- * Token used to decode text-track from 'mdat' atom (raw data stream)
381
- */
382
- class ChapterText {
383
- constructor(len) {
384
- this.len = len;
385
- }
386
- get(buf, off) {
387
- const titleLen = Token.INT16_BE.get(buf, off + 0);
388
- const str = new Token.StringType(titleLen, 'utf-8');
389
- return str.get(buf, off + 2);
390
- }
391
- }
392
- exports.ChapterText = ChapterText;
393
- function readTokenTable(buf, token, off, remainingLen, numberOfEntries) {
394
- debug(`remainingLen=${remainingLen}, numberOfEntries=${numberOfEntries} * token-len=${token.len}`);
395
- if (remainingLen === 0)
396
- return [];
397
- if (remainingLen !== numberOfEntries * token.len)
398
- throw new Error('mismatch number-of-entries with remaining atom-length');
399
- const entries = [];
400
- // parse offset-table
401
- for (let n = 0; n < numberOfEntries; ++n) {
402
- entries.push(token.get(buf, off));
403
- off += token.len;
404
- }
405
- return entries;
406
- }
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ChapterText = exports.StcoAtom = exports.StszAtom = exports.StscAtom = exports.SampleToChunkToken = exports.SttsAtom = exports.TimeToSampleToken = exports.SoundSampleDescriptionV0 = exports.SoundSampleDescriptionVersion = exports.StsdAtom = exports.TrackHeaderAtom = exports.NameAtom = exports.DataAtom = exports.MvhdAtom = exports.MdhdAtom = exports.FixedLengthAtom = exports.mhdr = exports.tkhd = exports.ftyp = exports.ExtendedSize = exports.Header = void 0;
4
+ const Token = require("token-types");
5
+ const initDebug = require("debug");
6
+ const FourCC_1 = require("../common/FourCC");
7
+ const debug = initDebug('music-metadata:parser:MP4:atom');
8
+ exports.Header = {
9
+ len: 8,
10
+ get: (buf, off) => {
11
+ const length = Token.UINT32_BE.get(buf, off);
12
+ if (length < 0)
13
+ throw new Error('Invalid atom header length');
14
+ return {
15
+ length: BigInt(length),
16
+ name: new Token.StringType(4, 'binary').get(buf, off + 4)
17
+ };
18
+ },
19
+ put: (buf, off, hdr) => {
20
+ Token.UINT32_BE.put(buf, off, Number(hdr.length));
21
+ return FourCC_1.FourCcToken.put(buf, off + 4, hdr.name);
22
+ }
23
+ };
24
+ /**
25
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap1/qtff1.html#//apple_ref/doc/uid/TP40000939-CH203-38190
26
+ */
27
+ exports.ExtendedSize = Token.UINT64_BE;
28
+ exports.ftyp = {
29
+ len: 4,
30
+ get: (buf, off) => {
31
+ return {
32
+ type: new Token.StringType(4, 'ascii').get(buf, off)
33
+ };
34
+ }
35
+ };
36
+ exports.tkhd = {
37
+ len: 4,
38
+ get: (buf, off) => {
39
+ return {
40
+ type: new Token.StringType(4, 'ascii').get(buf, off)
41
+ };
42
+ }
43
+ };
44
+ /**
45
+ * Token: Movie Header Atom
46
+ */
47
+ exports.mhdr = {
48
+ len: 8,
49
+ get: (buf, off) => {
50
+ return {
51
+ version: Token.UINT8.get(buf, off),
52
+ flags: Token.UINT24_BE.get(buf, off + 1),
53
+ nextItemID: Token.UINT32_BE.get(buf, off + 4)
54
+ };
55
+ }
56
+ };
57
+ /**
58
+ * Base class for 'fixed' length atoms.
59
+ * In some cases these atoms are longer then the sum of the described fields.
60
+ * Issue: https://github.com/Borewit/music-metadata/issues/120
61
+ */
62
+ class FixedLengthAtom {
63
+ /**
64
+ *
65
+ * @param {number} len Length as specified in the size field
66
+ * @param {number} expLen Total length of sum of specified fields in the standard
67
+ */
68
+ constructor(len, expLen, atomId) {
69
+ this.len = len;
70
+ if (len < expLen) {
71
+ throw new Error(`Atom ${atomId} expected to be ${expLen}, but specifies ${len} bytes long.`);
72
+ }
73
+ else if (len > expLen) {
74
+ debug(`Warning: atom ${atomId} expected to be ${expLen}, but was actually ${len} bytes long.`);
75
+ }
76
+ }
77
+ }
78
+ exports.FixedLengthAtom = FixedLengthAtom;
79
+ /**
80
+ * Timestamp stored in seconds since Mac Epoch (1 January 1904)
81
+ */
82
+ const SecondsSinceMacEpoch = {
83
+ len: 4,
84
+ get: (buf, off) => {
85
+ const secondsSinceUnixEpoch = Token.UINT32_BE.get(buf, off) - 2082844800;
86
+ return new Date(secondsSinceUnixEpoch * 1000);
87
+ }
88
+ };
89
+ /**
90
+ * Token: Media Header Atom
91
+ * Ref:
92
+ * https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-SW34
93
+ * https://wiki.multimedia.cx/index.php/QuickTime_container#mdhd
94
+ */
95
+ class MdhdAtom extends FixedLengthAtom {
96
+ constructor(len) {
97
+ super(len, 24, 'mdhd');
98
+ this.len = len;
99
+ }
100
+ get(buf, off) {
101
+ return {
102
+ version: Token.UINT8.get(buf, off + 0),
103
+ flags: Token.UINT24_BE.get(buf, off + 1),
104
+ creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
105
+ modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
106
+ timeScale: Token.UINT32_BE.get(buf, off + 12),
107
+ duration: Token.UINT32_BE.get(buf, off + 16),
108
+ language: Token.UINT16_BE.get(buf, off + 20),
109
+ quality: Token.UINT16_BE.get(buf, off + 22)
110
+ };
111
+ }
112
+ }
113
+ exports.MdhdAtom = MdhdAtom;
114
+ /**
115
+ * Token: Movie Header Atom
116
+ */
117
+ class MvhdAtom extends FixedLengthAtom {
118
+ constructor(len) {
119
+ super(len, 100, 'mvhd');
120
+ this.len = len;
121
+ }
122
+ get(buf, off) {
123
+ return {
124
+ version: Token.UINT8.get(buf, off),
125
+ flags: Token.UINT24_BE.get(buf, off + 1),
126
+ creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
127
+ modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
128
+ timeScale: Token.UINT32_BE.get(buf, off + 12),
129
+ duration: Token.UINT32_BE.get(buf, off + 16),
130
+ preferredRate: Token.UINT32_BE.get(buf, off + 20),
131
+ preferredVolume: Token.UINT16_BE.get(buf, off + 24),
132
+ // ignore reserver: 10 bytes
133
+ // ignore matrix structure: 36 bytes
134
+ previewTime: Token.UINT32_BE.get(buf, off + 72),
135
+ previewDuration: Token.UINT32_BE.get(buf, off + 76),
136
+ posterTime: Token.UINT32_BE.get(buf, off + 80),
137
+ selectionTime: Token.UINT32_BE.get(buf, off + 84),
138
+ selectionDuration: Token.UINT32_BE.get(buf, off + 88),
139
+ currentTime: Token.UINT32_BE.get(buf, off + 92),
140
+ nextTrackID: Token.UINT32_BE.get(buf, off + 96)
141
+ };
142
+ }
143
+ }
144
+ exports.MvhdAtom = MvhdAtom;
145
+ /**
146
+ * Data Atom Structure
147
+ */
148
+ class DataAtom {
149
+ constructor(len) {
150
+ this.len = len;
151
+ }
152
+ get(buf, off) {
153
+ return {
154
+ type: {
155
+ set: Token.UINT8.get(buf, off + 0),
156
+ type: Token.UINT24_BE.get(buf, off + 1)
157
+ },
158
+ locale: Token.UINT24_BE.get(buf, off + 4),
159
+ value: Buffer.from(new Token.Uint8ArrayType(this.len - 8).get(buf, off + 8))
160
+ };
161
+ }
162
+ }
163
+ exports.DataAtom = DataAtom;
164
+ /**
165
+ * Data Atom Structure
166
+ * Ref: https://developer.apple.com/library/content/documentation/QuickTime/QTFF/Metadata/Metadata.html#//apple_ref/doc/uid/TP40000939-CH1-SW31
167
+ */
168
+ class NameAtom {
169
+ constructor(len) {
170
+ this.len = len;
171
+ }
172
+ get(buf, off) {
173
+ return {
174
+ version: Token.UINT8.get(buf, off),
175
+ flags: Token.UINT24_BE.get(buf, off + 1),
176
+ name: new Token.StringType(this.len - 4, 'utf-8').get(buf, off + 4)
177
+ };
178
+ }
179
+ }
180
+ exports.NameAtom = NameAtom;
181
+ /**
182
+ * Track Header Atoms structure
183
+ * Ref: https://developer.apple.com/library/content/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25550
184
+ */
185
+ class TrackHeaderAtom {
186
+ constructor(len) {
187
+ this.len = len;
188
+ }
189
+ get(buf, off) {
190
+ return {
191
+ version: Token.UINT8.get(buf, off),
192
+ flags: Token.UINT24_BE.get(buf, off + 1),
193
+ creationTime: SecondsSinceMacEpoch.get(buf, off + 4),
194
+ modificationTime: SecondsSinceMacEpoch.get(buf, off + 8),
195
+ trackId: Token.UINT32_BE.get(buf, off + 12),
196
+ // reserved 4 bytes
197
+ duration: Token.UINT32_BE.get(buf, off + 20),
198
+ layer: Token.UINT16_BE.get(buf, off + 24),
199
+ alternateGroup: Token.UINT16_BE.get(buf, off + 26),
200
+ volume: Token.UINT16_BE.get(buf, off + 28) // ToDo: fixed point
201
+ // ToDo: add remaining fields
202
+ };
203
+ }
204
+ }
205
+ exports.TrackHeaderAtom = TrackHeaderAtom;
206
+ /**
207
+ * Atom: Sample Description Atom ('stsd')
208
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
209
+ */
210
+ const stsdHeader = {
211
+ len: 8,
212
+ get: (buf, off) => {
213
+ return {
214
+ version: Token.UINT8.get(buf, off),
215
+ flags: Token.UINT24_BE.get(buf, off + 1),
216
+ numberOfEntries: Token.UINT32_BE.get(buf, off + 4)
217
+ };
218
+ }
219
+ };
220
+ /**
221
+ * Atom: Sample Description Atom ('stsd')
222
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
223
+ */
224
+ class SampleDescriptionTable {
225
+ constructor(len) {
226
+ this.len = len;
227
+ }
228
+ get(buf, off) {
229
+ return {
230
+ dataFormat: FourCC_1.FourCcToken.get(buf, off),
231
+ dataReferenceIndex: Token.UINT16_BE.get(buf, off + 10),
232
+ description: new Token.Uint8ArrayType(this.len - 12).get(buf, off + 12)
233
+ };
234
+ }
235
+ }
236
+ /**
237
+ * Atom: Sample-description Atom ('stsd')
238
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25691
239
+ */
240
+ class StsdAtom {
241
+ constructor(len) {
242
+ this.len = len;
243
+ }
244
+ get(buf, off) {
245
+ const header = stsdHeader.get(buf, off);
246
+ off += stsdHeader.len;
247
+ const table = [];
248
+ for (let n = 0; n < header.numberOfEntries; ++n) {
249
+ const size = Token.UINT32_BE.get(buf, off); // Sample description size
250
+ off += Token.UINT32_BE.len;
251
+ table.push(new SampleDescriptionTable(size).get(buf, off));
252
+ off += size;
253
+ }
254
+ return {
255
+ header,
256
+ table
257
+ };
258
+ }
259
+ }
260
+ exports.StsdAtom = StsdAtom;
261
+ /**
262
+ * Common Sound Sample Description (version & revision)
263
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap3/qtff3.html#//apple_ref/doc/uid/TP40000939-CH205-57317
264
+ */
265
+ exports.SoundSampleDescriptionVersion = {
266
+ len: 8,
267
+ get(buf, off) {
268
+ return {
269
+ version: Token.INT16_BE.get(buf, off),
270
+ revision: Token.INT16_BE.get(buf, off + 2),
271
+ vendor: Token.INT32_BE.get(buf, off + 4)
272
+ };
273
+ }
274
+ };
275
+ /**
276
+ * Sound Sample Description (Version 0)
277
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap3/qtff3.html#//apple_ref/doc/uid/TP40000939-CH205-130736
278
+ */
279
+ exports.SoundSampleDescriptionV0 = {
280
+ len: 12,
281
+ get(buf, off) {
282
+ return {
283
+ numAudioChannels: Token.INT16_BE.get(buf, off + 0),
284
+ sampleSize: Token.INT16_BE.get(buf, off + 2),
285
+ compressionId: Token.INT16_BE.get(buf, off + 4),
286
+ packetSize: Token.INT16_BE.get(buf, off + 6),
287
+ sampleRate: Token.UINT16_BE.get(buf, off + 8) + Token.UINT16_BE.get(buf, off + 10) / 10000
288
+ };
289
+ }
290
+ };
291
+ class SimpleTableAtom {
292
+ constructor(len, token) {
293
+ this.len = len;
294
+ this.token = token;
295
+ }
296
+ get(buf, off) {
297
+ const nrOfEntries = Token.INT32_BE.get(buf, off + 4);
298
+ return {
299
+ version: Token.INT8.get(buf, off + 0),
300
+ flags: Token.INT24_BE.get(buf, off + 1),
301
+ numberOfEntries: nrOfEntries,
302
+ entries: readTokenTable(buf, this.token, off + 8, this.len - 8, nrOfEntries)
303
+ };
304
+ }
305
+ }
306
+ exports.TimeToSampleToken = {
307
+ len: 8,
308
+ get(buf, off) {
309
+ return {
310
+ count: Token.INT32_BE.get(buf, off + 0),
311
+ duration: Token.INT32_BE.get(buf, off + 4)
312
+ };
313
+ }
314
+ };
315
+ /**
316
+ * Time-to-sample('stts') atom.
317
+ * Store duration information for a media’s samples.
318
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25696
319
+ */
320
+ class SttsAtom extends SimpleTableAtom {
321
+ constructor(len) {
322
+ super(len, exports.TimeToSampleToken);
323
+ this.len = len;
324
+ }
325
+ }
326
+ exports.SttsAtom = SttsAtom;
327
+ exports.SampleToChunkToken = {
328
+ len: 12,
329
+ get(buf, off) {
330
+ return {
331
+ firstChunk: Token.INT32_BE.get(buf, off),
332
+ samplesPerChunk: Token.INT32_BE.get(buf, off + 4),
333
+ sampleDescriptionId: Token.INT32_BE.get(buf, off + 8)
334
+ };
335
+ }
336
+ };
337
+ /**
338
+ * Sample-to-Chunk ('stsc') atom interface
339
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25706
340
+ */
341
+ class StscAtom extends SimpleTableAtom {
342
+ constructor(len) {
343
+ super(len, exports.SampleToChunkToken);
344
+ this.len = len;
345
+ }
346
+ }
347
+ exports.StscAtom = StscAtom;
348
+ /**
349
+ * Sample-size ('stsz') atom
350
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25710
351
+ */
352
+ class StszAtom {
353
+ constructor(len) {
354
+ this.len = len;
355
+ }
356
+ get(buf, off) {
357
+ const nrOfEntries = Token.INT32_BE.get(buf, off + 8);
358
+ return {
359
+ version: Token.INT8.get(buf, off),
360
+ flags: Token.INT24_BE.get(buf, off + 1),
361
+ sampleSize: Token.INT32_BE.get(buf, off + 4),
362
+ numberOfEntries: nrOfEntries,
363
+ entries: readTokenTable(buf, Token.INT32_BE, off + 12, this.len - 12, nrOfEntries)
364
+ };
365
+ }
366
+ }
367
+ exports.StszAtom = StszAtom;
368
+ /**
369
+ * Chunk offset atom, 'stco'
370
+ * Ref: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/QTFFChap2/qtff2.html#//apple_ref/doc/uid/TP40000939-CH204-25715
371
+ */
372
+ class StcoAtom extends SimpleTableAtom {
373
+ constructor(len) {
374
+ super(len, Token.INT32_BE);
375
+ this.len = len;
376
+ }
377
+ }
378
+ exports.StcoAtom = StcoAtom;
379
+ /**
380
+ * Token used to decode text-track from 'mdat' atom (raw data stream)
381
+ */
382
+ class ChapterText {
383
+ constructor(len) {
384
+ this.len = len;
385
+ }
386
+ get(buf, off) {
387
+ const titleLen = Token.INT16_BE.get(buf, off + 0);
388
+ const str = new Token.StringType(titleLen, 'utf-8');
389
+ return str.get(buf, off + 2);
390
+ }
391
+ }
392
+ exports.ChapterText = ChapterText;
393
+ function readTokenTable(buf, token, off, remainingLen, numberOfEntries) {
394
+ debug(`remainingLen=${remainingLen}, numberOfEntries=${numberOfEntries} * token-len=${token.len}`);
395
+ if (remainingLen === 0)
396
+ return [];
397
+ if (remainingLen !== numberOfEntries * token.len)
398
+ throw new Error('mismatch number-of-entries with remaining atom-length');
399
+ const entries = [];
400
+ // parse offset-table
401
+ for (let n = 0; n < numberOfEntries; ++n) {
402
+ entries.push(token.get(buf, off));
403
+ off += token.len;
404
+ }
405
+ return entries;
406
+ }