protobufjs 8.6.2 → 8.6.3

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 (105) hide show
  1. package/LICENSE +39 -39
  2. package/README.md +441 -441
  3. package/dist/light/protobuf.js +8575 -8454
  4. package/dist/light/protobuf.js.map +1 -1
  5. package/dist/light/protobuf.min.js +3 -3
  6. package/dist/light/protobuf.min.js.map +1 -1
  7. package/dist/minimal/protobuf.js +3064 -2999
  8. package/dist/minimal/protobuf.js.map +1 -1
  9. package/dist/minimal/protobuf.min.js +3 -3
  10. package/dist/minimal/protobuf.min.js.map +1 -1
  11. package/dist/protobuf.js +10479 -10358
  12. package/dist/protobuf.js.map +1 -1
  13. package/dist/protobuf.min.js +3 -3
  14. package/dist/protobuf.min.js.map +1 -1
  15. package/ext/README.md +70 -70
  16. package/ext/debug/README.md +4 -4
  17. package/ext/debug/index.js +71 -71
  18. package/ext/descriptor/README.md +5 -5
  19. package/ext/descriptor/index.d.ts +2 -2
  20. package/ext/descriptor/index.js +2 -2
  21. package/ext/descriptor.d.ts +87 -87
  22. package/ext/descriptor.js +1354 -1354
  23. package/ext/protojson.LICENSE +201 -201
  24. package/ext/protojson.d.ts +20 -20
  25. package/ext/protojson.js +925 -925
  26. package/ext/textformat.d.ts +19 -19
  27. package/ext/textformat.js +1256 -1256
  28. package/google/LICENSE +27 -27
  29. package/google/README.md +1 -1
  30. package/google/api/annotations.json +82 -82
  31. package/google/api/annotations.proto +10 -10
  32. package/google/api/http.json +85 -85
  33. package/google/api/http.proto +30 -30
  34. package/google/protobuf/api.json +117 -117
  35. package/google/protobuf/api.proto +33 -33
  36. package/google/protobuf/compiler/plugin.json +126 -126
  37. package/google/protobuf/compiler/plugin.proto +47 -47
  38. package/google/protobuf/descriptor.json +1381 -1381
  39. package/google/protobuf/descriptor.proto +534 -534
  40. package/google/protobuf/source_context.json +19 -19
  41. package/google/protobuf/source_context.proto +7 -7
  42. package/google/protobuf/type.json +201 -201
  43. package/google/protobuf/type.proto +89 -89
  44. package/index.d.ts +30 -0
  45. package/index.js +4 -4
  46. package/light.d.ts +2 -2
  47. package/light.js +3 -3
  48. package/minimal.d.ts +2 -2
  49. package/minimal.js +4 -4
  50. package/package.json +93 -93
  51. package/src/common.js +399 -399
  52. package/src/converter.js +344 -344
  53. package/src/decoder.js +214 -208
  54. package/src/encoder.js +111 -111
  55. package/src/enum.js +231 -231
  56. package/src/field.js +497 -497
  57. package/src/index-light.js +104 -104
  58. package/src/index-minimal.js +35 -36
  59. package/src/index.js +12 -12
  60. package/src/mapfield.js +136 -136
  61. package/src/message.js +137 -137
  62. package/src/method.js +175 -175
  63. package/src/namespace.js +566 -565
  64. package/src/object.js +382 -382
  65. package/src/oneof.js +225 -225
  66. package/src/parse.js +1068 -1068
  67. package/src/reader.js +558 -543
  68. package/src/reader_buffer.js +72 -72
  69. package/src/root.js +416 -416
  70. package/src/roots.js +18 -18
  71. package/src/rpc/service.js +148 -148
  72. package/src/rpc.js +36 -36
  73. package/src/service.js +198 -198
  74. package/src/tokenize.js +421 -421
  75. package/src/type.js +654 -655
  76. package/src/types.js +196 -196
  77. package/src/typescript.js +25 -25
  78. package/src/util/aspromise.d.ts +13 -13
  79. package/src/util/aspromise.js +52 -52
  80. package/src/util/base64.d.ts +32 -32
  81. package/src/util/base64.js +146 -146
  82. package/src/util/codegen.d.ts +31 -31
  83. package/src/util/codegen.js +113 -113
  84. package/src/util/eventemitter.d.ts +45 -45
  85. package/src/util/eventemitter.js +86 -86
  86. package/src/util/fetch.d.ts +56 -56
  87. package/src/util/fetch.js +112 -112
  88. package/src/util/float.d.ts +83 -83
  89. package/src/util/float.js +335 -335
  90. package/src/util/fs.js +11 -11
  91. package/src/util/longbits.js +200 -200
  92. package/src/util/minimal.js +515 -515
  93. package/src/util/path.d.ts +22 -22
  94. package/src/util/path.js +100 -72
  95. package/src/util/patterns.js +7 -7
  96. package/src/util/pool.d.ts +32 -32
  97. package/src/util/pool.js +48 -48
  98. package/src/util/utf8.d.ts +24 -24
  99. package/src/util/utf8.js +181 -130
  100. package/src/util.js +264 -242
  101. package/src/verifier.js +180 -180
  102. package/src/wrappers.js +106 -106
  103. package/src/writer.js +495 -495
  104. package/src/writer_buffer.js +102 -102
  105. package/tsconfig.json +6 -6
package/ext/textformat.js CHANGED
@@ -1,1256 +1,1256 @@
1
- "use strict";
2
- var protobuf = require("../light");
3
-
4
- var Type = protobuf.Type,
5
- Enum = protobuf.Enum,
6
- Field = protobuf.Field,
7
- Reader = protobuf.Reader,
8
- types = protobuf.types,
9
- util = protobuf.util;
10
-
11
- var textformat = protobuf.textformat = module.exports = {};
12
-
13
- /**
14
- * Maximum recursion depth for formatting length-delimited unknown fields.
15
- * @name unknownRecursionLimit
16
- * @type {number}
17
- */
18
- textformat.unknownRecursionLimit = 10;
19
-
20
- var punct = {
21
- "{": true,
22
- "}": true,
23
- "<": true,
24
- ">": true,
25
- ":": true,
26
- "[": true,
27
- "]": true,
28
- ",": true,
29
- ";": true,
30
- "-": true
31
- };
32
-
33
- var identRe = /^[A-Za-z_][A-Za-z0-9_]*$/,
34
- numberStartRe = /[0-9]/,
35
- wordCharRe = /[A-Za-z0-9_]/,
36
- hexRe = /^[0-9A-Fa-f]$/,
37
- octRe = /^[0-7]$/,
38
- floatRe = /^(?:[0-9]+\.[0-9]*(?:[eE][+-]?[0-9]+)?[fF]?|\.[0-9]+(?:[eE][+-]?[0-9]+)?[fF]?|[0-9]+[eE][+-]?[0-9]+[fF]?|[0-9]+[fF])/,
39
- hexIntRe = /^0[xX][0-9A-Fa-f]+/,
40
- octIntRe = /^0[0-7]+/,
41
- decIntRe = /^(?:0|[1-9][0-9]*)/;
42
-
43
- /**
44
- * Parses protobuf text format using the specified reflected message type.
45
- * @param {Type} type Reflected message type
46
- * @param {string} text Text format input
47
- * @returns {Message<{}>} Message instance
48
- * @private
49
- */
50
- function parseText(type, text) {
51
- if (!(type instanceof Type))
52
- throw TypeError("type must be a Type");
53
- type.root.resolveAll();
54
- var parser = new Parser(String(text));
55
- var object = parser.parseMessage(type, null, 0);
56
- parser.expectEnd();
57
- var err = verifyTextMessage(type, object),
58
- message;
59
- if (err)
60
- throw Error(err);
61
- message = type.create(object);
62
- return message;
63
- }
64
-
65
- /**
66
- * Text format options.
67
- * @interface ITextFormatOptions
68
- * @property {boolean} [unknowns=false] Also includes and formats unknown fields.
69
- */
70
-
71
- /**
72
- * Parses a message from protobuf text format using the specified reflected type.
73
- * @function fromText
74
- * @name fromText
75
- * @param {$protobuf.Type} type Reflected message type
76
- * @param {string} text Text format input
77
- * @returns {$protobuf.Message<{}>} Message instance
78
- */
79
- textformat.fromText = function fromText(type, text) {
80
- return parseText(type, text);
81
- };
82
-
83
- /**
84
- * Formats a message as protobuf text format using the specified reflected type.
85
- * @function toText
86
- * @name toText
87
- * @param {$protobuf.Type} type Reflected message type
88
- * @param {$protobuf.Message<{}>|Object.<string,*>} message Message instance or plain object
89
- * @param {ITextFormatOptions} [options] Text format options
90
- * @returns {string} Text format output
91
- */
92
- textformat.toText = function toText(type, message, options) {
93
- if (!(type instanceof Type))
94
- throw TypeError("type must be a Type");
95
- type.root.resolveAll();
96
- var lines = [];
97
- writeMessage(type, message, lines, 0, options || {}, 0);
98
- return lines.join("\n");
99
- };
100
-
101
- /**
102
- * Installs reflected {@link Type} convenience methods.
103
- * @function install
104
- * @name install
105
- * @returns {undefined}
106
- */
107
- textformat.install = function install() {
108
- /**
109
- * Parses a message of this type from protobuf text format. Convenience for {@link textformat.fromText}.
110
- * @param {string} text Text format input
111
- * @returns {Message<{}>} Message instance
112
- */
113
- Type.prototype.fromText = function fromText(text) {
114
- return textformat.fromText(this, text);
115
- };
116
-
117
- /**
118
- * Formats a message of this type as protobuf text format. Convenience for {@link textformat.toText}.
119
- * @param {Message<{}>|Object.<string,*>} message Message instance or plain object
120
- * @param {ITextFormatOptions} [options] Text format options
121
- * @returns {string} Text format output
122
- */
123
- Type.prototype.toText = function toText(message, options) {
124
- return textformat.toText(this, message, options);
125
- };
126
- };
127
-
128
- function Tokenizer(source) {
129
- this.source = source;
130
- this.pos = 0;
131
- this.len = source.length;
132
- this.line = 1;
133
- this.stack = [];
134
- }
135
-
136
- Tokenizer.prototype.error = function error(message) {
137
- return Error(message + " (line " + this.line + ")");
138
- };
139
-
140
- Tokenizer.prototype.peek = function peek() {
141
- var token = this.next();
142
- this.push(token);
143
- return token;
144
- };
145
-
146
- Tokenizer.prototype.push = function push(token) {
147
- if (token)
148
- this.stack.unshift(token);
149
- };
150
-
151
- Tokenizer.prototype.next = function next() {
152
- if (this.stack.length)
153
- return this.stack.shift();
154
- this.skipSpace();
155
- if (this.pos >= this.len)
156
- return null;
157
-
158
- var ch = this.source.charAt(this.pos);
159
- if (ch === "\"" || ch === "'")
160
- return this.readString(ch);
161
- if (ch === "." && numberStartRe.test(this.source.charAt(this.pos + 1)) || numberStartRe.test(ch))
162
- return this.readNumber();
163
- if (punct[ch]) {
164
- ++this.pos;
165
- return { type: "punct", value: ch, raw: ch, line: this.line };
166
- }
167
- return this.readWord();
168
- };
169
-
170
- Tokenizer.prototype.expect = function expect(value) {
171
- var token = this.next();
172
- if (!token || token.value !== value)
173
- throw this.error("expected '" + value + "'");
174
- return token;
175
- };
176
-
177
- Tokenizer.prototype.skip = function skip(value) {
178
- var token = this.next();
179
- if (token && token.value === value)
180
- return true;
181
- this.push(token);
182
- return false;
183
- };
184
-
185
- Tokenizer.prototype.skipSpace = function skipSpace() {
186
- var ch;
187
- while (this.pos < this.len) {
188
- ch = this.source.charAt(this.pos);
189
- if (ch === "#") {
190
- while (this.pos < this.len && this.source.charAt(this.pos) !== "\n")
191
- ++this.pos;
192
- } else if (ch === " " || ch === "\t" || ch === "\v" || ch === "\f" || ch === "\r") {
193
- ++this.pos;
194
- } else if (ch === "\n") {
195
- ++this.pos;
196
- ++this.line;
197
- } else
198
- break;
199
- }
200
- };
201
-
202
- Tokenizer.prototype.readWord = function readWord() {
203
- var start = this.pos,
204
- ch;
205
- while (this.pos < this.len) {
206
- ch = this.source.charAt(this.pos);
207
- if (ch === "#" || ch === "\"" || ch === "'" || punct[ch] || /\s/.test(ch))
208
- break;
209
- ++this.pos;
210
- }
211
- if (start === this.pos)
212
- throw this.error("illegal character '" + this.source.charAt(this.pos) + "'");
213
- var raw = this.source.substring(start, this.pos);
214
- return { type: "word", value: raw, raw: raw, line: this.line };
215
- };
216
-
217
- Tokenizer.prototype.readNumber = function readNumber() {
218
- var rest = this.source.substring(this.pos),
219
- matches = [
220
- floatRe.exec(rest),
221
- hexIntRe.exec(rest),
222
- octIntRe.exec(rest),
223
- decIntRe.exec(rest)
224
- ],
225
- raw = null;
226
- for (var i = 0; i < matches.length; ++i)
227
- if (matches[i] && (!raw || matches[i][0].length > raw.length))
228
- raw = matches[i][0];
229
- if (!raw)
230
- throw this.error("illegal number");
231
- this.pos += raw.length;
232
- if (this.pos < this.len && wordCharRe.test(this.source.charAt(this.pos)))
233
- throw this.error("illegal number '" + raw + this.source.charAt(this.pos) + "'");
234
- return { type: "number", value: raw, raw: raw, line: this.line };
235
- };
236
-
237
- Tokenizer.prototype.readString = function readString(quote) {
238
- var bytes = [],
239
- ch,
240
- code;
241
- ++this.pos;
242
- while (this.pos < this.len) {
243
- ch = this.source.charAt(this.pos++);
244
- if (ch === quote)
245
- return { type: "string", value: bytes, raw: quote, line: this.line };
246
- if (ch === "\n")
247
- throw this.error("illegal string");
248
- if (ch !== "\\") {
249
- code = ch.charCodeAt(0);
250
- if ((code & 0xFC00) === 0xD800 && this.pos < this.len) {
251
- var next = this.source.charCodeAt(this.pos);
252
- if ((next & 0xFC00) === 0xDC00) {
253
- ++this.pos;
254
- code = 0x10000 + ((code & 0x03FF) << 10) + (next & 0x03FF);
255
- }
256
- }
257
- pushUtf8(bytes, code);
258
- continue;
259
- }
260
- if (this.pos >= this.len)
261
- throw this.error("illegal string escape");
262
- ch = this.source.charAt(this.pos++);
263
- switch (ch) {
264
- case "a": bytes.push(7); break;
265
- case "b": bytes.push(8); break;
266
- case "f": bytes.push(12); break;
267
- case "n": bytes.push(10); break;
268
- case "r": bytes.push(13); break;
269
- case "t": bytes.push(9); break;
270
- case "v": bytes.push(11); break;
271
- case "?": bytes.push(63); break;
272
- case "\\": bytes.push(92); break;
273
- case "'": bytes.push(39); break;
274
- case "\"": bytes.push(34); break;
275
- case "x":
276
- case "X":
277
- bytes.push(this.readHexEscape());
278
- break;
279
- case "u":
280
- pushUtf8(bytes, this.readCodePoint(4));
281
- break;
282
- case "U":
283
- pushUtf8(bytes, this.readCodePoint(8));
284
- break;
285
- default:
286
- if (octRe.test(ch)) {
287
- bytes.push(this.readOctEscape(ch));
288
- break;
289
- }
290
- throw this.error("illegal string escape '\\" + ch + "'");
291
- }
292
- }
293
- throw this.error("unterminated string");
294
- };
295
-
296
- Tokenizer.prototype.readHexEscape = function readHexEscape() {
297
- var value = 0,
298
- count = 0,
299
- ch;
300
- while (count < 2 && this.pos < this.len && hexRe.test(ch = this.source.charAt(this.pos))) {
301
- value = value * 16 + parseInt(ch, 16);
302
- ++this.pos;
303
- ++count;
304
- }
305
- if (!count)
306
- throw this.error("illegal hex escape");
307
- return value;
308
- };
309
-
310
- Tokenizer.prototype.readOctEscape = function readOctEscape(first) {
311
- var value = parseInt(first, 8),
312
- count = 1,
313
- ch;
314
- while (count < 3 && this.pos < this.len && octRe.test(ch = this.source.charAt(this.pos))) {
315
- value = value * 8 + parseInt(ch, 8);
316
- ++this.pos;
317
- ++count;
318
- }
319
- return value & 255;
320
- };
321
-
322
- Tokenizer.prototype.readCodePoint = function readCodePoint(size) {
323
- var raw = this.source.substring(this.pos, this.pos + size);
324
- if (raw.length !== size || !/^[0-9A-Fa-f]+$/.test(raw))
325
- throw this.error("illegal unicode escape");
326
- this.pos += size;
327
- var code = parseInt(raw, 16);
328
- if (code > 0x10FFFF || code >= 0xD800 && code <= 0xDFFF)
329
- throw this.error("illegal unicode escape");
330
- return code;
331
- };
332
-
333
- function Parser(source) {
334
- this.tn = new Tokenizer(source);
335
- }
336
-
337
- Parser.prototype.error = function error(message) {
338
- throw this.tn.error(message);
339
- };
340
-
341
- Parser.prototype.expectEnd = function expectEnd() {
342
- var token = this.tn.next();
343
- if (token)
344
- this.error("unexpected token '" + token.value + "'");
345
- };
346
-
347
- Parser.prototype.parseMessage = function parseMessage(type, end, depth) {
348
- if (depth > util.recursionLimit)
349
- this.error("max depth exceeded");
350
- var object = {},
351
- seen = {};
352
- for (;;) {
353
- var token = this.tn.peek();
354
- if (!token) {
355
- if (end)
356
- this.error("expected '" + end + "'");
357
- return object;
358
- }
359
- if (end && token.value === end) {
360
- this.tn.next();
361
- return object;
362
- }
363
- if (isSeparator(token))
364
- this.error("unexpected separator");
365
- this.parseField(type, object, seen, depth);
366
- token = this.tn.peek();
367
- if (token && isSeparator(token)) {
368
- this.tn.next();
369
- token = this.tn.peek();
370
- if (token && isSeparator(token))
371
- this.error("unexpected separator");
372
- }
373
- }
374
- };
375
-
376
- Parser.prototype.parseField = function parseField(type, object, seen, depth) {
377
- var info = this.readFieldName(type);
378
- if (info.any) {
379
- this.parseAny(type, info.name, object, seen, depth);
380
- return;
381
- }
382
- if (!info.field) {
383
- this.skipReservedValue(depth);
384
- return;
385
- }
386
-
387
- var field = info.field.resolve();
388
- if (field.map) {
389
- this.parseMessageFieldDelimiter();
390
- this.parseMapField(field, object, depth);
391
- } else if (field.resolvedType instanceof Type) {
392
- this.parseMessageFieldDelimiter();
393
- if (this.tn.skip("[")) {
394
- if (!field.repeated)
395
- this.error(field.fullName + ": list value specified for singular field");
396
- if (!this.tn.skip("]")) {
397
- do {
398
- addField(object, seen, field, this.parseMessageValue(field.resolvedType, depth));
399
- } while (this.tn.skip(","));
400
- this.tn.expect("]");
401
- }
402
- } else
403
- addField(object, seen, field, this.parseMessageValue(field.resolvedType, depth));
404
- } else {
405
- this.tn.expect(":");
406
- if (this.tn.skip("[")) {
407
- if (!field.repeated)
408
- this.error(field.fullName + ": list value specified for singular field");
409
- if (!this.tn.skip("]")) {
410
- do {
411
- addField(object, seen, field, this.parseScalar(field));
412
- } while (this.tn.skip(","));
413
- this.tn.expect("]");
414
- }
415
- } else
416
- addField(object, seen, field, this.parseScalar(field));
417
- }
418
- };
419
-
420
- Parser.prototype.readFieldName = function readFieldName(type) {
421
- var token = this.tn.next();
422
- if (!token)
423
- this.error("expected field name");
424
- if (token.value === "[") {
425
- var bracketName = this.readBracketName();
426
- if (type.fullName === ".google.protobuf.Any" && bracketName.indexOf("/") >= 0)
427
- return { any: true, name: bracketName };
428
- return { field: lookupExtension(type, bracketName), name: bracketName };
429
- }
430
- if (token.type !== "word" || !identRe.test(token.value))
431
- this.error("illegal field name '" + token.value + "'");
432
-
433
- var field = lookupField(type, token.value);
434
- if (!field) {
435
- if (type.isReservedName(token.value))
436
- return { name: token.value };
437
- this.error(type.fullName + ": unknown field '" + token.value + "'");
438
- }
439
- return { field: field, name: token.value };
440
- };
441
-
442
- Parser.prototype.readBracketName = function readBracketName() {
443
- var parts = [],
444
- token;
445
- while (token = this.tn.next()) {
446
- if (token.value === "]")
447
- return parts.join("");
448
- parts.push(token.raw || token.value);
449
- }
450
- this.error("unterminated bracketed field name");
451
- return null;
452
- };
453
-
454
- Parser.prototype.parseAny = function parseAny(type, typeUrl, object, seen, depth) {
455
- this.parseMessageFieldDelimiter();
456
- validateTypeUrl(typeUrl);
457
- var typeName = typeUrl.substring(typeUrl.lastIndexOf("/") + 1),
458
- embeddedType = type.root.lookupType(typeName.charAt(0) === "." ? typeName : "." + typeName),
459
- embedded = this.parseMessageValue(embeddedType, depth),
460
- typeUrlField = lookupField(type, "type_url") || lookupField(type, "typeUrl"),
461
- valueField = lookupField(type, "value");
462
- addField(object, seen, typeUrlField, typeUrl);
463
- addField(object, seen, valueField, embeddedType.encode(embedded).finish());
464
- };
465
-
466
- Parser.prototype.parseMapField = function parseMapField(field, object, depth) {
467
- if (!object[field.name])
468
- object[field.name] = {};
469
- if (this.tn.skip("[")) {
470
- if (!this.tn.skip("]")) {
471
- do {
472
- addMapEntry(field, object[field.name], this.parseMapEntry(field, depth + 1));
473
- } while (this.tn.skip(","));
474
- this.tn.expect("]");
475
- }
476
- } else
477
- addMapEntry(field, object[field.name], this.parseMapEntry(field, depth + 1));
478
- };
479
-
480
- Parser.prototype.parseMessageFieldDelimiter = function parseMessageFieldDelimiter() {
481
- this.tn.skip(":");
482
- };
483
-
484
- Parser.prototype.parseMapEntry = function parseMapEntry(field, depth) {
485
- if (depth > util.recursionLimit)
486
- this.error("max depth exceeded");
487
- var end;
488
- if (this.tn.skip("{"))
489
- end = "}";
490
- else if (this.tn.skip("<"))
491
- end = ">";
492
- else
493
- this.error("expected map entry");
494
-
495
- var entry = {},
496
- token,
497
- valueField = mapValueField(field),
498
- keyField = mapKeyField(field);
499
- for (;;) {
500
- token = this.tn.peek();
501
- if (!token)
502
- this.error("expected '" + end + "'");
503
- if (token.value === end) {
504
- this.tn.next();
505
- return entry;
506
- }
507
- if (isSeparator(token))
508
- this.error("unexpected separator");
509
- token = this.tn.next();
510
- if (token.type !== "word")
511
- this.error("expected map field name");
512
- if (token.value === "key") {
513
- this.tn.expect(":");
514
- entry.key = this.parseScalar(keyField);
515
- } else if (token.value === "value") {
516
- if (valueField.resolvedType instanceof Type) {
517
- this.parseMessageFieldDelimiter();
518
- entry.value = this.parseMessageValue(valueField.resolvedType, depth);
519
- } else {
520
- this.tn.expect(":");
521
- entry.value = this.parseScalar(valueField);
522
- }
523
- } else
524
- this.error("unknown map field '" + token.value + "'");
525
- token = this.tn.peek();
526
- if (token && isSeparator(token)) {
527
- this.tn.next();
528
- token = this.tn.peek();
529
- if (token && isSeparator(token))
530
- this.error("unexpected separator");
531
- }
532
- }
533
- };
534
-
535
- Parser.prototype.parseMessageValue = function parseMessageValue(type, depth) {
536
- var end;
537
- if (this.tn.skip("{"))
538
- end = "}";
539
- else if (this.tn.skip("<"))
540
- end = ">";
541
- else
542
- this.error("expected message value");
543
- return this.parseMessage(type, end, depth + 1);
544
- };
545
-
546
- Parser.prototype.parseScalar = function parseScalar(field) {
547
- if (field.type === "string" || field.type === "bytes") {
548
- var bytes = this.readStringBytes();
549
- return field.type === "bytes" ? util.newBuffer(bytes) : utf8Read(bytes, true);
550
- }
551
-
552
- var sign = 1;
553
- if (this.tn.skip("-"))
554
- sign = -1;
555
-
556
- var token = this.tn.next();
557
- if (!token)
558
- this.error("expected value");
559
-
560
- if (field.resolvedType instanceof Enum)
561
- return parseEnum(field, token, sign);
562
-
563
- switch (field.type) {
564
- case "double":
565
- case "float":
566
- return parseFloatValue(token, sign);
567
- case "bool":
568
- return parseBool(token, sign);
569
- case "int32":
570
- case "sint32":
571
- case "sfixed32":
572
- return parseInteger(token, sign, false, 32);
573
- case "uint32":
574
- case "fixed32":
575
- return parseInteger(token, sign, true, 32);
576
- case "int64":
577
- case "sint64":
578
- case "sfixed64":
579
- return parseInteger(token, sign, false, 64);
580
- case "uint64":
581
- case "fixed64":
582
- return parseInteger(token, sign, true, 64);
583
- default:
584
- this.error(field.fullName + ": unsupported scalar type");
585
- }
586
- return undefined;
587
- };
588
-
589
- Parser.prototype.readStringBytes = function readStringBytes() {
590
- var token = this.tn.next(),
591
- bytes = [];
592
- if (!token || token.type !== "string")
593
- this.error("expected string");
594
- Array.prototype.push.apply(bytes, token.value);
595
- while ((token = this.tn.peek()) && token.type === "string") {
596
- token = this.tn.next();
597
- Array.prototype.push.apply(bytes, token.value);
598
- }
599
- return bytes;
600
- };
601
-
602
- Parser.prototype.skipReservedValue = function skipReservedValue(depth) {
603
- this.tn.skip(":");
604
- var token = this.tn.peek();
605
- if (!token)
606
- return;
607
- if (token.value === "{") {
608
- this.skipBalanced("{", "}", depth);
609
- } else if (token.value === "<") {
610
- this.skipBalanced("<", ">", depth);
611
- } else if (token.value === "[") {
612
- this.skipBalanced("[", "]", depth);
613
- } else if (token.type === "string") {
614
- this.readStringBytes();
615
- } else {
616
- if (token.value === "-")
617
- this.tn.next();
618
- this.tn.next();
619
- }
620
- };
621
-
622
- Parser.prototype.skipBalanced = function skipBalanced(open, close, depth) {
623
- var balance = 0,
624
- token;
625
- do {
626
- token = this.tn.next();
627
- if (!token)
628
- this.error("expected '" + close + "'");
629
- if (token.value === open) {
630
- if (depth + ++balance > util.recursionLimit)
631
- this.error("max depth exceeded");
632
- }
633
- else if (token.value === close)
634
- --balance;
635
- } while (balance);
636
- };
637
-
638
- function addField(object, seen, field, value) {
639
- if (field.repeated) {
640
- (object[field.name] || (object[field.name] = [])).push(value);
641
- return;
642
- }
643
- if (Object.prototype.hasOwnProperty.call(seen, field.name))
644
- throw Error(field.fullName + ": multiple values");
645
- if (field.partOf) {
646
- var oneofName = "$oneof:" + field.partOf.name;
647
- if (seen[oneofName])
648
- throw Error(field.partOf.name + ": multiple values");
649
- seen[oneofName] = true;
650
- }
651
- seen[field.name] = true;
652
- object[field.name] = value;
653
- }
654
-
655
- function addMapEntry(field, map, entry) {
656
- var keyField = mapKeyField(field),
657
- valueField = mapValueField(field),
658
- key = Object.prototype.hasOwnProperty.call(entry, "key")
659
- ? entry.key
660
- : defaultScalarValue(keyField),
661
- value = Object.prototype.hasOwnProperty.call(entry, "value")
662
- ? entry.value
663
- : defaultMapValue(valueField);
664
- map[mapKey(keyField, key)] = value;
665
- }
666
-
667
- function defaultMapValue(field) {
668
- if (field.resolvedType instanceof Type)
669
- return field.resolvedType.create();
670
- if (field.resolvedType instanceof Enum)
671
- return field.typeDefault;
672
- return defaultScalarValue(field);
673
- }
674
-
675
- function defaultScalarValue(field) {
676
- if (field.type === "string")
677
- return "";
678
- if (field.type === "bytes")
679
- return util.newBuffer([]);
680
- if (field.type === "bool")
681
- return false;
682
- return field.defaultValue;
683
- }
684
-
685
- function mapKeyField(field) {
686
- return {
687
- name: "key",
688
- fullName: field.fullName + ".key",
689
- type: field.keyType,
690
- resolvedType: null,
691
- defaultValue: field.keyType === "bool" ? false : field.keyType === "string" ? "" : 0
692
- };
693
- }
694
-
695
- function mapValueField(field) {
696
- return {
697
- name: "value",
698
- fullName: field.fullName + ".value",
699
- type: field.type,
700
- resolvedType: field.resolvedType,
701
- defaultValue: field.resolvedType instanceof Enum ? field.resolvedType.values[Object.keys(field.resolvedType.values)[0]] : field.typeDefault
702
- };
703
- }
704
-
705
- function mapKey(field, value) {
706
- if (types.long[field.type] !== undefined)
707
- return String(value);
708
- if (field.type === "bool")
709
- return value ? "true" : "false";
710
- return String(value);
711
- }
712
-
713
- function lookupField(type, name) {
714
- var fields = type.fieldsArray;
715
- for (var i = 0; i < fields.length; ++i) {
716
- var field = fields[i].resolve();
717
- if (field.name === name || underScore(field.name) === name)
718
- return field;
719
- if (field.delimited && field.resolvedType instanceof Type) {
720
- var groupName = field.resolvedType.name,
721
- lowerName = name.toLowerCase(),
722
- compactName = compact(name);
723
- if (groupName === name || underScore(groupName) === name
724
- || field.name.toLowerCase() === lowerName
725
- || groupName.toLowerCase() === lowerName
726
- || compact(field.name) === compactName
727
- || compact(groupName) === compactName)
728
- return field;
729
- }
730
- }
731
- return null;
732
- }
733
-
734
- function lookupExtension(type, name) {
735
- var fullName = name.charAt(0) === "." ? name : "." + name,
736
- camelName = camelCaseLastPath(fullName),
737
- field = type.get(fullName) || type.root.lookup(fullName, Field)
738
- || type.get(camelName) || type.root.lookup(camelName, Field);
739
- if (!field)
740
- field = lookupExtensionField(type, fullName);
741
- if (field && field.extend !== undefined && field.extensionField)
742
- field = field.extensionField;
743
- if (!field || field.parent !== type)
744
- throw Error(type.fullName + ": unknown extension '" + name + "'");
745
- return field;
746
- }
747
-
748
- function camelCaseLastPath(name) {
749
- var dot = name.lastIndexOf(".");
750
- return name.substring(0, dot + 1) + util.camelCase(name.substring(dot + 1));
751
- }
752
-
753
- function parseEnum(field, token, sign) {
754
- if (sign < 0) {
755
- if (token.type !== "number")
756
- throw Error(field.fullName + ": enum value expected");
757
- return checkEnumValue(field, parseInteger(token, sign, false, 32));
758
- }
759
- if (token.type === "word") {
760
- var value = field.resolvedType.values[token.value];
761
- if (value === undefined)
762
- throw Error(field.fullName + ": enum value expected");
763
- return value;
764
- }
765
- return checkEnumValue(field, parseInteger(token, sign, false, 32));
766
- }
767
-
768
- function parseBool(token, sign) {
769
- if (sign < 0)
770
- throw Error("bool value expected");
771
- if (token.type === "word") {
772
- switch (token.value) {
773
- case "true":
774
- case "True":
775
- case "t":
776
- return true;
777
- case "false":
778
- case "False":
779
- case "f":
780
- return false;
781
- }
782
- } else if (token.type === "number") {
783
- var value = parseInteger(token, 1, true, 32);
784
- if (value === 0)
785
- return false;
786
- if (value === 1)
787
- return true;
788
- }
789
- throw Error("bool value expected");
790
- }
791
-
792
- function parseFloatValue(token, sign) {
793
- if (token.type === "word") {
794
- switch (token.value.toLowerCase()) {
795
- case "inf":
796
- case "infinity":
797
- return sign * Infinity;
798
- case "nan":
799
- return NaN;
800
- }
801
- throw Error("float value expected");
802
- }
803
- if (token.type !== "number")
804
- throw Error("float value expected");
805
- var raw = token.value;
806
- if (/^0[xX]/.test(raw) || /^0[0-7]/.test(raw) && raw.length > 1)
807
- throw Error("float value expected");
808
- if (/[fF]$/.test(raw))
809
- raw = raw.substring(0, raw.length - 1);
810
- return sign * Number(raw);
811
- }
812
-
813
- function parseInteger(token, sign, unsigned, bits) {
814
- if (token.type !== "number")
815
- throw Error("integer value expected");
816
- if (sign < 0 && unsigned)
817
- throw Error("unsigned integer value expected");
818
-
819
- var raw = token.value,
820
- radix = 10,
821
- digits = raw;
822
- if (/^0[xX]/.test(raw)) {
823
- radix = 16;
824
- digits = raw.substring(2);
825
- } else if (/^0[0-7]/.test(raw) && raw.length > 1) {
826
- radix = 8;
827
- digits = raw.substring(1);
828
- } else if (!/^(?:0|[1-9][0-9]*)$/.test(raw))
829
- throw Error("integer value expected");
830
-
831
- if (typeof util.global.BigInt === "function")
832
- return parseIntegerBigInt(digits, radix, sign, unsigned, bits);
833
-
834
- var value = parseInt(digits, radix) * sign;
835
- if (bits === 64 && util.Long)
836
- return util.Long.fromString(String(value), unsigned);
837
- return value;
838
- }
839
-
840
- function parseIntegerBigInt(digits, radix, sign, unsigned, bits) {
841
- var value,
842
- BigInt = util.global.BigInt;
843
- if (radix === 16)
844
- value = BigInt("0x" + digits);
845
- else if (radix === 8)
846
- value = BigInt("0o" + digits);
847
- else
848
- value = BigInt(digits);
849
- if (sign < 0)
850
- value = -value;
851
-
852
- var min,
853
- max;
854
- if (bits === 32) {
855
- min = unsigned ? BigInt(0) : -BigInt(2147483648);
856
- max = unsigned ? BigInt(4294967295) : BigInt(2147483647);
857
- } else {
858
- min = unsigned ? BigInt(0) : -BigInt("9223372036854775808");
859
- max = unsigned ? BigInt("18446744073709551615") : BigInt("9223372036854775807");
860
- }
861
- if (value < min || value > max)
862
- throw Error((unsigned ? "unsigned " : "") + "integer value out of range");
863
- if (bits === 64 && util.Long)
864
- return util.Long.fromString(value.toString(), unsigned, 10);
865
- return Number(value);
866
- }
867
-
868
- function writeMessage(type, message, lines, indent, options, depth) {
869
- if (depth > util.recursionLimit)
870
- throw Error("max depth exceeded");
871
- var fields = type.fieldsArray.slice().sort(util.compareFieldsById);
872
- for (var i = 0; i < fields.length; ++i) {
873
- var field = fields[i].resolve(),
874
- value = message[field.name];
875
- if (value == null || !Object.prototype.hasOwnProperty.call(message, field.name))
876
- continue;
877
- if (field.map)
878
- writeMapField(field, value, lines, indent, options, depth);
879
- else if (field.repeated)
880
- for (var j = 0; j < value.length; ++j)
881
- writeField(field, value[j], lines, indent, options, depth);
882
- else
883
- writeField(field, value, lines, indent, options, depth);
884
- }
885
- if (options.unknowns && message.$unknowns != null && Object.prototype.hasOwnProperty.call(message, "$unknowns"))
886
- writeUnknowns(message.$unknowns, lines, indent);
887
- }
888
-
889
- function writeMapField(field, map, lines, indent, options, depth) {
890
- var keys = Object.keys(map).sort(),
891
- keyField = mapKeyField(field),
892
- valueField = mapValueField(field),
893
- name = formatFieldName(field),
894
- sp = spaces(indent);
895
- for (var i = 0; i < keys.length; ++i) {
896
- if (depth + 1 > util.recursionLimit)
897
- throw Error("max depth exceeded");
898
- var key = keyField.long ? util.longFromKey(keys[i], keyField.type === "uint64" || keyField.type === "fixed64") : keys[i];
899
- if (keyField.type === "bool")
900
- key = util.boolFromKey(keys[i]);
901
- lines.push(sp + name + " {");
902
- lines.push(spaces(indent + 2) + "key: " + formatScalar(keyField, key));
903
- if (valueField.resolvedType instanceof Type) {
904
- lines.push(spaces(indent + 2) + "value {");
905
- writeMessage(valueField.resolvedType, map[keys[i]], lines, indent + 4, options, depth + 2);
906
- lines.push(spaces(indent + 2) + "}");
907
- } else
908
- lines.push(spaces(indent + 2) + "value: " + formatScalar(valueField, map[keys[i]]));
909
- lines.push(sp + "}");
910
- }
911
- }
912
-
913
- function writeField(field, value, lines, indent, options, depth) {
914
- var name = formatFieldName(field),
915
- sp = spaces(indent);
916
- if (field.resolvedType instanceof Type) {
917
- lines.push(sp + name + " {");
918
- writeMessage(field.resolvedType, value, lines, indent + 2, options, depth + 1);
919
- lines.push(sp + "}");
920
- } else
921
- lines.push(sp + name + ": " + formatScalar(field, value));
922
- }
923
-
924
- function writeUnknowns(unknowns, lines, indent) {
925
- for (var i = 0; i < unknowns.length; ++i) {
926
- var reader = Reader.create(unknowns[i]);
927
- writeUnknownFieldSet(reader, lines, indent, undefined, textformat.unknownRecursionLimit);
928
- if (reader.pos !== reader.len)
929
- throw Error("invalid unknown field data");
930
- }
931
- }
932
-
933
- function writeUnknownFieldSet(reader, lines, indent, endGroup, recursionBudget) {
934
- if (recursionBudget < 0)
935
- throw Error("max depth exceeded");
936
- while (reader.pos < reader.len) {
937
- var tag = reader.tag(),
938
- fieldNumber = tag >>> 3,
939
- wireType = tag & 7;
940
- if (!fieldNumber)
941
- throw Error("illegal tag: field number 0");
942
- if (wireType === 4) {
943
- if (fieldNumber !== endGroup)
944
- throw Error("invalid end group tag");
945
- return;
946
- }
947
- writeUnknownField(reader, fieldNumber, wireType, lines, indent, recursionBudget);
948
- }
949
- if (endGroup !== undefined)
950
- throw Error("missing end group tag");
951
- }
952
-
953
- function writeUnknownField(reader, fieldNumber, wireType, lines, indent, recursionBudget) {
954
- var sp = spaces(indent),
955
- lo;
956
- switch (wireType) {
957
- case 0:
958
- lines.push(sp + fieldNumber + ": " + readUnknownVarint(reader));
959
- break;
960
- case 1:
961
- lo = reader.fixed32();
962
- lines.push(sp + fieldNumber + ": 0x" + hexPad(reader.fixed32(), 8) + hexPad(lo, 8));
963
- break;
964
- case 2:
965
- writeUnknownLengthDelimited(reader, fieldNumber, lines, indent, recursionBudget);
966
- break;
967
- case 3:
968
- lines.push(sp + fieldNumber + " {");
969
- writeUnknownFieldSet(reader, lines, indent + 2, fieldNumber, recursionBudget - 1);
970
- lines.push(sp + "}");
971
- break;
972
- case 5:
973
- lines.push(sp + fieldNumber + ": 0x" + hexPad(reader.fixed32(), 8));
974
- break;
975
- default:
976
- throw Error("invalid wire type " + wireType);
977
- }
978
- }
979
-
980
- function writeUnknownLengthDelimited(reader, fieldNumber, lines, indent, recursionBudget) {
981
- var value = reader.bytes(),
982
- nested = value.length && recursionBudget > 0
983
- ? tryFormatUnknownMessage(value, indent + 2, recursionBudget - 1)
984
- : null,
985
- sp = spaces(indent);
986
- if (nested) {
987
- lines.push(sp + fieldNumber + " {");
988
- for (var i = 0; i < nested.length; ++i)
989
- lines.push(nested[i]);
990
- lines.push(sp + "}");
991
- } else
992
- lines.push(sp + fieldNumber + ": " + quoteBytes(value));
993
- }
994
-
995
- function tryFormatUnknownMessage(bytes, indent, recursionBudget) {
996
- var reader = Reader.create(bytes),
997
- lines = [];
998
- try {
999
- writeUnknownFieldSet(reader, lines, indent, undefined, recursionBudget);
1000
- return reader.pos === reader.len ? lines : null;
1001
- } catch (e) {
1002
- return null;
1003
- }
1004
- }
1005
-
1006
- function readUnknownVarint(reader) {
1007
- var BigInt = util.global.BigInt;
1008
- if (typeof BigInt !== "function")
1009
- return String(reader.uint64());
1010
-
1011
- var value = BigInt(0),
1012
- shift = BigInt(0),
1013
- b;
1014
- for (var i = 0; i < 10; ++i) {
1015
- if (reader.pos >= reader.len)
1016
- throw Error("invalid varint encoding");
1017
- b = reader.buf[reader.pos++];
1018
- value += BigInt(b & 127) << shift;
1019
- if (b < 128)
1020
- return value.toString();
1021
- shift += BigInt(7);
1022
- }
1023
- throw Error("invalid varint encoding");
1024
- }
1025
-
1026
- function hexPad(value, length) {
1027
- var str = value.toString(16);
1028
- while (str.length < length)
1029
- str = "0" + str;
1030
- return str;
1031
- }
1032
-
1033
- function formatFieldName(field) {
1034
- if (field.declaringField || field.name.charAt(0) === ".")
1035
- return "[" + formatExtensionName(field) + "]";
1036
- if (field.delimited && field.resolvedType instanceof Type && compact(field.name) === compact(field.resolvedType.name))
1037
- return field.resolvedType.name;
1038
- return underScore(field.name);
1039
- }
1040
-
1041
- function formatExtensionName(field) {
1042
- var name = field.name.replace(/^\./, ""),
1043
- dot = name.lastIndexOf("."),
1044
- path = name.substring(0, dot + 1),
1045
- last = name.substring(dot + 1);
1046
- if (field.delimited && field.resolvedType instanceof Type && field.resolvedType.group)
1047
- last = last.toLowerCase();
1048
- else
1049
- last = underScore(last);
1050
- return path + last;
1051
- }
1052
-
1053
- function formatScalar(field, value) {
1054
- if (field.resolvedType instanceof Enum) {
1055
- var name = field.resolvedType.valuesById[value];
1056
- return name === undefined ? String(value) : name;
1057
- }
1058
- switch (field.type) {
1059
- case "string":
1060
- return quoteBytes(utf8Bytes(String(value)));
1061
- case "bytes":
1062
- return quoteBytes(bytesValue(value));
1063
- case "bool":
1064
- return value ? "true" : "false";
1065
- case "double":
1066
- case "float":
1067
- if (isNaN(value))
1068
- return "nan";
1069
- if (value === 0 && 1 / value === -Infinity)
1070
- return "-0";
1071
- if (value === Infinity)
1072
- return "inf";
1073
- if (value === -Infinity)
1074
- return "-inf";
1075
- return String(value);
1076
- default:
1077
- return String(value);
1078
- }
1079
- }
1080
-
1081
- function bytesValue(value) {
1082
- if (typeof value === "string") {
1083
- var length = util.base64.length(value),
1084
- buffer = util.newBuffer(length);
1085
- util.base64.decode(value, buffer, 0);
1086
- return buffer;
1087
- }
1088
- return value;
1089
- }
1090
-
1091
- function quoteBytes(bytes) {
1092
- var out = "\"",
1093
- oct;
1094
- for (var i = 0; i < bytes.length; ++i) {
1095
- var b = bytes[i];
1096
- switch (b) {
1097
- case 9: out += "\\t"; break;
1098
- case 10: out += "\\n"; break;
1099
- case 13: out += "\\r"; break;
1100
- case 34: out += "\\\""; break;
1101
- case 92: out += "\\\\"; break;
1102
- default:
1103
- if (b >= 32 && b <= 126)
1104
- out += String.fromCharCode(b);
1105
- else {
1106
- oct = b.toString(8);
1107
- out += "\\" + (oct.length < 2 ? "00" : oct.length < 3 ? "0" : "") + oct;
1108
- }
1109
- break;
1110
- }
1111
- }
1112
- return out + "\"";
1113
- }
1114
-
1115
- function spaces(indent) {
1116
- var str = "";
1117
- while (str.length < indent)
1118
- str += " ";
1119
- return str;
1120
- }
1121
-
1122
- function utf8Read(bytes, strict) {
1123
- if (strict && !validUtf8(bytes))
1124
- throw Error("invalid UTF-8 string");
1125
- var buffer = util.newBuffer(bytes);
1126
- return util.utf8.read(buffer, 0, buffer.length);
1127
- }
1128
-
1129
- function validUtf8(bytes) {
1130
- for (var i = 0, b; i < bytes.length;) {
1131
- b = bytes[i++];
1132
- if (b <= 0x7F)
1133
- continue;
1134
- if (b >= 0xC2 && b <= 0xDF) {
1135
- if ((b = bytes[i++]) < 0x80 || b > 0xBF)
1136
- return false;
1137
- } else if (b === 0xE0) {
1138
- if ((b = bytes[i++]) < 0xA0 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1139
- return false;
1140
- } else if (b >= 0xE1 && b <= 0xEC || b >= 0xEE && b <= 0xEF) {
1141
- if ((b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1142
- return false;
1143
- } else if (b === 0xED) {
1144
- if ((b = bytes[i++]) < 0x80 || b > 0x9F || (b = bytes[i++]) < 0x80 || b > 0xBF)
1145
- return false;
1146
- } else if (b === 0xF0) {
1147
- if ((b = bytes[i++]) < 0x90 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1148
- return false;
1149
- } else if (b >= 0xF1 && b <= 0xF3) {
1150
- if ((b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1151
- return false;
1152
- } else if (b === 0xF4) {
1153
- if ((b = bytes[i++]) < 0x80 || b > 0x8F || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1154
- return false;
1155
- } else
1156
- return false;
1157
- }
1158
- return true;
1159
- }
1160
-
1161
- function utf8Bytes(str) {
1162
- var buffer = util.newBuffer(util.utf8.length(str));
1163
- util.utf8.write(str, buffer, 0);
1164
- return buffer;
1165
- }
1166
-
1167
- function pushUtf8(bytes, code) {
1168
- if (code < 0x80) {
1169
- bytes.push(code);
1170
- } else if (code < 0x800) {
1171
- bytes.push(code >> 6 | 192, code & 63 | 128);
1172
- } else if (code < 0x10000) {
1173
- bytes.push(code >> 12 | 224, code >> 6 & 63 | 128, code & 63 | 128);
1174
- } else {
1175
- bytes.push(code >> 18 | 240, code >> 12 & 63 | 128, code >> 6 & 63 | 128, code & 63 | 128);
1176
- }
1177
- }
1178
-
1179
- function verifyTextMessage(type, message) {
1180
- var fields = type.fieldsArray;
1181
- for (var i = 0; i < fields.length; ++i) {
1182
- var field = fields[i].resolve(),
1183
- value = message[field.name];
1184
- if (value == null || !Object.prototype.hasOwnProperty.call(message, field.name)) {
1185
- if (field.required)
1186
- return field.fullName + ": missing required field";
1187
- continue;
1188
- }
1189
- if (field.map) {
1190
- if (field.resolvedType instanceof Type)
1191
- for (var key in value)
1192
- if (Object.prototype.hasOwnProperty.call(value, key)) {
1193
- var mapErr = verifyTextMessage(field.resolvedType, value[key]);
1194
- if (mapErr)
1195
- return mapErr;
1196
- }
1197
- } else if (field.repeated) {
1198
- if (field.resolvedType instanceof Type)
1199
- for (var j = 0; j < value.length; ++j) {
1200
- var repeatedErr = verifyTextMessage(field.resolvedType, value[j]);
1201
- if (repeatedErr)
1202
- return repeatedErr;
1203
- }
1204
- } else if (field.resolvedType instanceof Type) {
1205
- var err = verifyTextMessage(field.resolvedType, value);
1206
- if (err)
1207
- return err;
1208
- }
1209
- }
1210
- return null;
1211
- }
1212
-
1213
- function isSeparator(token) {
1214
- return token.value === "," || token.value === ";";
1215
- }
1216
-
1217
- function validateTypeUrl(typeUrl) {
1218
- for (var i = 0; i < typeUrl.length; ++i)
1219
- if (typeUrl.charAt(i) === "%") {
1220
- if (i + 2 >= typeUrl.length || !hexRe.test(typeUrl.charAt(i + 1)) || !hexRe.test(typeUrl.charAt(i + 2)))
1221
- throw Error("invalid Any type URL");
1222
- i += 2;
1223
- }
1224
- }
1225
-
1226
- function lookupExtensionField(type, fullName) {
1227
- var fields = type.fieldsArray;
1228
- for (var i = 0; i < fields.length; ++i) {
1229
- var field = fields[i].resolve();
1230
- if (field.name.charAt(0) === "." && "." + formatExtensionName(field) === fullName)
1231
- return field;
1232
- }
1233
- return null;
1234
- }
1235
-
1236
- function checkEnumValue(field, value) {
1237
- if (isClosedEnum(field) && field.resolvedType.valuesById[value] === undefined)
1238
- throw Error(field.fullName + ": enum value expected");
1239
- return value;
1240
- }
1241
-
1242
- function isClosedEnum(field) {
1243
- return field.resolvedType
1244
- && field.resolvedType._features
1245
- && field.resolvedType._features.enum_type === "CLOSED";
1246
- }
1247
-
1248
- function compact(str) {
1249
- return str.replace(/_/g, "").toLowerCase();
1250
- }
1251
-
1252
- function underScore(str) {
1253
- return str.substring(0, 1)
1254
- + str.substring(1)
1255
- .replace(/([A-Z])(?=[a-z]|$)/g, function($0, $1) { return "_" + $1.toLowerCase(); });
1256
- }
1
+ "use strict";
2
+ var protobuf = require("../light");
3
+
4
+ var Type = protobuf.Type,
5
+ Enum = protobuf.Enum,
6
+ Field = protobuf.Field,
7
+ Reader = protobuf.Reader,
8
+ types = protobuf.types,
9
+ util = protobuf.util;
10
+
11
+ var textformat = protobuf.textformat = module.exports = {};
12
+
13
+ /**
14
+ * Maximum recursion depth for formatting length-delimited unknown fields.
15
+ * @name unknownRecursionLimit
16
+ * @type {number}
17
+ */
18
+ textformat.unknownRecursionLimit = 10;
19
+
20
+ var punct = {
21
+ "{": true,
22
+ "}": true,
23
+ "<": true,
24
+ ">": true,
25
+ ":": true,
26
+ "[": true,
27
+ "]": true,
28
+ ",": true,
29
+ ";": true,
30
+ "-": true
31
+ };
32
+
33
+ var identRe = /^[A-Za-z_][A-Za-z0-9_]*$/,
34
+ numberStartRe = /[0-9]/,
35
+ wordCharRe = /[A-Za-z0-9_]/,
36
+ hexRe = /^[0-9A-Fa-f]$/,
37
+ octRe = /^[0-7]$/,
38
+ floatRe = /^(?:[0-9]+\.[0-9]*(?:[eE][+-]?[0-9]+)?[fF]?|\.[0-9]+(?:[eE][+-]?[0-9]+)?[fF]?|[0-9]+[eE][+-]?[0-9]+[fF]?|[0-9]+[fF])/,
39
+ hexIntRe = /^0[xX][0-9A-Fa-f]+/,
40
+ octIntRe = /^0[0-7]+/,
41
+ decIntRe = /^(?:0|[1-9][0-9]*)/;
42
+
43
+ /**
44
+ * Parses protobuf text format using the specified reflected message type.
45
+ * @param {Type} type Reflected message type
46
+ * @param {string} text Text format input
47
+ * @returns {Message<{}>} Message instance
48
+ * @private
49
+ */
50
+ function parseText(type, text) {
51
+ if (!(type instanceof Type))
52
+ throw TypeError("type must be a Type");
53
+ type.root.resolveAll();
54
+ var parser = new Parser(String(text));
55
+ var object = parser.parseMessage(type, null, 0);
56
+ parser.expectEnd();
57
+ var err = verifyTextMessage(type, object),
58
+ message;
59
+ if (err)
60
+ throw Error(err);
61
+ message = type.create(object);
62
+ return message;
63
+ }
64
+
65
+ /**
66
+ * Text format options.
67
+ * @interface ITextFormatOptions
68
+ * @property {boolean} [unknowns=false] Also includes and formats unknown fields.
69
+ */
70
+
71
+ /**
72
+ * Parses a message from protobuf text format using the specified reflected type.
73
+ * @function fromText
74
+ * @name fromText
75
+ * @param {$protobuf.Type} type Reflected message type
76
+ * @param {string} text Text format input
77
+ * @returns {$protobuf.Message<{}>} Message instance
78
+ */
79
+ textformat.fromText = function fromText(type, text) {
80
+ return parseText(type, text);
81
+ };
82
+
83
+ /**
84
+ * Formats a message as protobuf text format using the specified reflected type.
85
+ * @function toText
86
+ * @name toText
87
+ * @param {$protobuf.Type} type Reflected message type
88
+ * @param {$protobuf.Message<{}>|Object.<string,*>} message Message instance or plain object
89
+ * @param {ITextFormatOptions} [options] Text format options
90
+ * @returns {string} Text format output
91
+ */
92
+ textformat.toText = function toText(type, message, options) {
93
+ if (!(type instanceof Type))
94
+ throw TypeError("type must be a Type");
95
+ type.root.resolveAll();
96
+ var lines = [];
97
+ writeMessage(type, message, lines, 0, options || {}, 0);
98
+ return lines.join("\n");
99
+ };
100
+
101
+ /**
102
+ * Installs reflected {@link Type} convenience methods.
103
+ * @function install
104
+ * @name install
105
+ * @returns {undefined}
106
+ */
107
+ textformat.install = function install() {
108
+ /**
109
+ * Parses a message of this type from protobuf text format. Convenience for {@link textformat.fromText}.
110
+ * @param {string} text Text format input
111
+ * @returns {Message<{}>} Message instance
112
+ */
113
+ Type.prototype.fromText = function fromText(text) {
114
+ return textformat.fromText(this, text);
115
+ };
116
+
117
+ /**
118
+ * Formats a message of this type as protobuf text format. Convenience for {@link textformat.toText}.
119
+ * @param {Message<{}>|Object.<string,*>} message Message instance or plain object
120
+ * @param {ITextFormatOptions} [options] Text format options
121
+ * @returns {string} Text format output
122
+ */
123
+ Type.prototype.toText = function toText(message, options) {
124
+ return textformat.toText(this, message, options);
125
+ };
126
+ };
127
+
128
+ function Tokenizer(source) {
129
+ this.source = source;
130
+ this.pos = 0;
131
+ this.len = source.length;
132
+ this.line = 1;
133
+ this.stack = [];
134
+ }
135
+
136
+ Tokenizer.prototype.error = function error(message) {
137
+ return Error(message + " (line " + this.line + ")");
138
+ };
139
+
140
+ Tokenizer.prototype.peek = function peek() {
141
+ var token = this.next();
142
+ this.push(token);
143
+ return token;
144
+ };
145
+
146
+ Tokenizer.prototype.push = function push(token) {
147
+ if (token)
148
+ this.stack.unshift(token);
149
+ };
150
+
151
+ Tokenizer.prototype.next = function next() {
152
+ if (this.stack.length)
153
+ return this.stack.shift();
154
+ this.skipSpace();
155
+ if (this.pos >= this.len)
156
+ return null;
157
+
158
+ var ch = this.source.charAt(this.pos);
159
+ if (ch === "\"" || ch === "'")
160
+ return this.readString(ch);
161
+ if (ch === "." && numberStartRe.test(this.source.charAt(this.pos + 1)) || numberStartRe.test(ch))
162
+ return this.readNumber();
163
+ if (punct[ch]) {
164
+ ++this.pos;
165
+ return { type: "punct", value: ch, raw: ch, line: this.line };
166
+ }
167
+ return this.readWord();
168
+ };
169
+
170
+ Tokenizer.prototype.expect = function expect(value) {
171
+ var token = this.next();
172
+ if (!token || token.value !== value)
173
+ throw this.error("expected '" + value + "'");
174
+ return token;
175
+ };
176
+
177
+ Tokenizer.prototype.skip = function skip(value) {
178
+ var token = this.next();
179
+ if (token && token.value === value)
180
+ return true;
181
+ this.push(token);
182
+ return false;
183
+ };
184
+
185
+ Tokenizer.prototype.skipSpace = function skipSpace() {
186
+ var ch;
187
+ while (this.pos < this.len) {
188
+ ch = this.source.charAt(this.pos);
189
+ if (ch === "#") {
190
+ while (this.pos < this.len && this.source.charAt(this.pos) !== "\n")
191
+ ++this.pos;
192
+ } else if (ch === " " || ch === "\t" || ch === "\v" || ch === "\f" || ch === "\r") {
193
+ ++this.pos;
194
+ } else if (ch === "\n") {
195
+ ++this.pos;
196
+ ++this.line;
197
+ } else
198
+ break;
199
+ }
200
+ };
201
+
202
+ Tokenizer.prototype.readWord = function readWord() {
203
+ var start = this.pos,
204
+ ch;
205
+ while (this.pos < this.len) {
206
+ ch = this.source.charAt(this.pos);
207
+ if (ch === "#" || ch === "\"" || ch === "'" || punct[ch] || /\s/.test(ch))
208
+ break;
209
+ ++this.pos;
210
+ }
211
+ if (start === this.pos)
212
+ throw this.error("illegal character '" + this.source.charAt(this.pos) + "'");
213
+ var raw = this.source.substring(start, this.pos);
214
+ return { type: "word", value: raw, raw: raw, line: this.line };
215
+ };
216
+
217
+ Tokenizer.prototype.readNumber = function readNumber() {
218
+ var rest = this.source.substring(this.pos),
219
+ matches = [
220
+ floatRe.exec(rest),
221
+ hexIntRe.exec(rest),
222
+ octIntRe.exec(rest),
223
+ decIntRe.exec(rest)
224
+ ],
225
+ raw = null;
226
+ for (var i = 0; i < matches.length; ++i)
227
+ if (matches[i] && (!raw || matches[i][0].length > raw.length))
228
+ raw = matches[i][0];
229
+ if (!raw)
230
+ throw this.error("illegal number");
231
+ this.pos += raw.length;
232
+ if (this.pos < this.len && wordCharRe.test(this.source.charAt(this.pos)))
233
+ throw this.error("illegal number '" + raw + this.source.charAt(this.pos) + "'");
234
+ return { type: "number", value: raw, raw: raw, line: this.line };
235
+ };
236
+
237
+ Tokenizer.prototype.readString = function readString(quote) {
238
+ var bytes = [],
239
+ ch,
240
+ code;
241
+ ++this.pos;
242
+ while (this.pos < this.len) {
243
+ ch = this.source.charAt(this.pos++);
244
+ if (ch === quote)
245
+ return { type: "string", value: bytes, raw: quote, line: this.line };
246
+ if (ch === "\n")
247
+ throw this.error("illegal string");
248
+ if (ch !== "\\") {
249
+ code = ch.charCodeAt(0);
250
+ if ((code & 0xFC00) === 0xD800 && this.pos < this.len) {
251
+ var next = this.source.charCodeAt(this.pos);
252
+ if ((next & 0xFC00) === 0xDC00) {
253
+ ++this.pos;
254
+ code = 0x10000 + ((code & 0x03FF) << 10) + (next & 0x03FF);
255
+ }
256
+ }
257
+ pushUtf8(bytes, code);
258
+ continue;
259
+ }
260
+ if (this.pos >= this.len)
261
+ throw this.error("illegal string escape");
262
+ ch = this.source.charAt(this.pos++);
263
+ switch (ch) {
264
+ case "a": bytes.push(7); break;
265
+ case "b": bytes.push(8); break;
266
+ case "f": bytes.push(12); break;
267
+ case "n": bytes.push(10); break;
268
+ case "r": bytes.push(13); break;
269
+ case "t": bytes.push(9); break;
270
+ case "v": bytes.push(11); break;
271
+ case "?": bytes.push(63); break;
272
+ case "\\": bytes.push(92); break;
273
+ case "'": bytes.push(39); break;
274
+ case "\"": bytes.push(34); break;
275
+ case "x":
276
+ case "X":
277
+ bytes.push(this.readHexEscape());
278
+ break;
279
+ case "u":
280
+ pushUtf8(bytes, this.readCodePoint(4));
281
+ break;
282
+ case "U":
283
+ pushUtf8(bytes, this.readCodePoint(8));
284
+ break;
285
+ default:
286
+ if (octRe.test(ch)) {
287
+ bytes.push(this.readOctEscape(ch));
288
+ break;
289
+ }
290
+ throw this.error("illegal string escape '\\" + ch + "'");
291
+ }
292
+ }
293
+ throw this.error("unterminated string");
294
+ };
295
+
296
+ Tokenizer.prototype.readHexEscape = function readHexEscape() {
297
+ var value = 0,
298
+ count = 0,
299
+ ch;
300
+ while (count < 2 && this.pos < this.len && hexRe.test(ch = this.source.charAt(this.pos))) {
301
+ value = value * 16 + parseInt(ch, 16);
302
+ ++this.pos;
303
+ ++count;
304
+ }
305
+ if (!count)
306
+ throw this.error("illegal hex escape");
307
+ return value;
308
+ };
309
+
310
+ Tokenizer.prototype.readOctEscape = function readOctEscape(first) {
311
+ var value = parseInt(first, 8),
312
+ count = 1,
313
+ ch;
314
+ while (count < 3 && this.pos < this.len && octRe.test(ch = this.source.charAt(this.pos))) {
315
+ value = value * 8 + parseInt(ch, 8);
316
+ ++this.pos;
317
+ ++count;
318
+ }
319
+ return value & 255;
320
+ };
321
+
322
+ Tokenizer.prototype.readCodePoint = function readCodePoint(size) {
323
+ var raw = this.source.substring(this.pos, this.pos + size);
324
+ if (raw.length !== size || !/^[0-9A-Fa-f]+$/.test(raw))
325
+ throw this.error("illegal unicode escape");
326
+ this.pos += size;
327
+ var code = parseInt(raw, 16);
328
+ if (code > 0x10FFFF || code >= 0xD800 && code <= 0xDFFF)
329
+ throw this.error("illegal unicode escape");
330
+ return code;
331
+ };
332
+
333
+ function Parser(source) {
334
+ this.tn = new Tokenizer(source);
335
+ }
336
+
337
+ Parser.prototype.error = function error(message) {
338
+ throw this.tn.error(message);
339
+ };
340
+
341
+ Parser.prototype.expectEnd = function expectEnd() {
342
+ var token = this.tn.next();
343
+ if (token)
344
+ this.error("unexpected token '" + token.value + "'");
345
+ };
346
+
347
+ Parser.prototype.parseMessage = function parseMessage(type, end, depth) {
348
+ if (depth > util.recursionLimit)
349
+ this.error("max depth exceeded");
350
+ var object = {},
351
+ seen = {};
352
+ for (;;) {
353
+ var token = this.tn.peek();
354
+ if (!token) {
355
+ if (end)
356
+ this.error("expected '" + end + "'");
357
+ return object;
358
+ }
359
+ if (end && token.value === end) {
360
+ this.tn.next();
361
+ return object;
362
+ }
363
+ if (isSeparator(token))
364
+ this.error("unexpected separator");
365
+ this.parseField(type, object, seen, depth);
366
+ token = this.tn.peek();
367
+ if (token && isSeparator(token)) {
368
+ this.tn.next();
369
+ token = this.tn.peek();
370
+ if (token && isSeparator(token))
371
+ this.error("unexpected separator");
372
+ }
373
+ }
374
+ };
375
+
376
+ Parser.prototype.parseField = function parseField(type, object, seen, depth) {
377
+ var info = this.readFieldName(type);
378
+ if (info.any) {
379
+ this.parseAny(type, info.name, object, seen, depth);
380
+ return;
381
+ }
382
+ if (!info.field) {
383
+ this.skipReservedValue(depth);
384
+ return;
385
+ }
386
+
387
+ var field = info.field.resolve();
388
+ if (field.map) {
389
+ this.parseMessageFieldDelimiter();
390
+ this.parseMapField(field, object, depth);
391
+ } else if (field.resolvedType instanceof Type) {
392
+ this.parseMessageFieldDelimiter();
393
+ if (this.tn.skip("[")) {
394
+ if (!field.repeated)
395
+ this.error(field.fullName + ": list value specified for singular field");
396
+ if (!this.tn.skip("]")) {
397
+ do {
398
+ addField(object, seen, field, this.parseMessageValue(field.resolvedType, depth));
399
+ } while (this.tn.skip(","));
400
+ this.tn.expect("]");
401
+ }
402
+ } else
403
+ addField(object, seen, field, this.parseMessageValue(field.resolvedType, depth));
404
+ } else {
405
+ this.tn.expect(":");
406
+ if (this.tn.skip("[")) {
407
+ if (!field.repeated)
408
+ this.error(field.fullName + ": list value specified for singular field");
409
+ if (!this.tn.skip("]")) {
410
+ do {
411
+ addField(object, seen, field, this.parseScalar(field));
412
+ } while (this.tn.skip(","));
413
+ this.tn.expect("]");
414
+ }
415
+ } else
416
+ addField(object, seen, field, this.parseScalar(field));
417
+ }
418
+ };
419
+
420
+ Parser.prototype.readFieldName = function readFieldName(type) {
421
+ var token = this.tn.next();
422
+ if (!token)
423
+ this.error("expected field name");
424
+ if (token.value === "[") {
425
+ var bracketName = this.readBracketName();
426
+ if (type.fullName === ".google.protobuf.Any" && bracketName.indexOf("/") >= 0)
427
+ return { any: true, name: bracketName };
428
+ return { field: lookupExtension(type, bracketName), name: bracketName };
429
+ }
430
+ if (token.type !== "word" || !identRe.test(token.value))
431
+ this.error("illegal field name '" + token.value + "'");
432
+
433
+ var field = lookupField(type, token.value);
434
+ if (!field) {
435
+ if (type.isReservedName(token.value))
436
+ return { name: token.value };
437
+ this.error(type.fullName + ": unknown field '" + token.value + "'");
438
+ }
439
+ return { field: field, name: token.value };
440
+ };
441
+
442
+ Parser.prototype.readBracketName = function readBracketName() {
443
+ var parts = [],
444
+ token;
445
+ while (token = this.tn.next()) {
446
+ if (token.value === "]")
447
+ return parts.join("");
448
+ parts.push(token.raw || token.value);
449
+ }
450
+ this.error("unterminated bracketed field name");
451
+ return null;
452
+ };
453
+
454
+ Parser.prototype.parseAny = function parseAny(type, typeUrl, object, seen, depth) {
455
+ this.parseMessageFieldDelimiter();
456
+ validateTypeUrl(typeUrl);
457
+ var typeName = typeUrl.substring(typeUrl.lastIndexOf("/") + 1),
458
+ embeddedType = type.root.lookupType(typeName.charAt(0) === "." ? typeName : "." + typeName),
459
+ embedded = this.parseMessageValue(embeddedType, depth),
460
+ typeUrlField = lookupField(type, "type_url") || lookupField(type, "typeUrl"),
461
+ valueField = lookupField(type, "value");
462
+ addField(object, seen, typeUrlField, typeUrl);
463
+ addField(object, seen, valueField, embeddedType.encode(embedded).finish());
464
+ };
465
+
466
+ Parser.prototype.parseMapField = function parseMapField(field, object, depth) {
467
+ if (!object[field.name])
468
+ object[field.name] = {};
469
+ if (this.tn.skip("[")) {
470
+ if (!this.tn.skip("]")) {
471
+ do {
472
+ addMapEntry(field, object[field.name], this.parseMapEntry(field, depth + 1));
473
+ } while (this.tn.skip(","));
474
+ this.tn.expect("]");
475
+ }
476
+ } else
477
+ addMapEntry(field, object[field.name], this.parseMapEntry(field, depth + 1));
478
+ };
479
+
480
+ Parser.prototype.parseMessageFieldDelimiter = function parseMessageFieldDelimiter() {
481
+ this.tn.skip(":");
482
+ };
483
+
484
+ Parser.prototype.parseMapEntry = function parseMapEntry(field, depth) {
485
+ if (depth > util.recursionLimit)
486
+ this.error("max depth exceeded");
487
+ var end;
488
+ if (this.tn.skip("{"))
489
+ end = "}";
490
+ else if (this.tn.skip("<"))
491
+ end = ">";
492
+ else
493
+ this.error("expected map entry");
494
+
495
+ var entry = {},
496
+ token,
497
+ valueField = mapValueField(field),
498
+ keyField = mapKeyField(field);
499
+ for (;;) {
500
+ token = this.tn.peek();
501
+ if (!token)
502
+ this.error("expected '" + end + "'");
503
+ if (token.value === end) {
504
+ this.tn.next();
505
+ return entry;
506
+ }
507
+ if (isSeparator(token))
508
+ this.error("unexpected separator");
509
+ token = this.tn.next();
510
+ if (token.type !== "word")
511
+ this.error("expected map field name");
512
+ if (token.value === "key") {
513
+ this.tn.expect(":");
514
+ entry.key = this.parseScalar(keyField);
515
+ } else if (token.value === "value") {
516
+ if (valueField.resolvedType instanceof Type) {
517
+ this.parseMessageFieldDelimiter();
518
+ entry.value = this.parseMessageValue(valueField.resolvedType, depth);
519
+ } else {
520
+ this.tn.expect(":");
521
+ entry.value = this.parseScalar(valueField);
522
+ }
523
+ } else
524
+ this.error("unknown map field '" + token.value + "'");
525
+ token = this.tn.peek();
526
+ if (token && isSeparator(token)) {
527
+ this.tn.next();
528
+ token = this.tn.peek();
529
+ if (token && isSeparator(token))
530
+ this.error("unexpected separator");
531
+ }
532
+ }
533
+ };
534
+
535
+ Parser.prototype.parseMessageValue = function parseMessageValue(type, depth) {
536
+ var end;
537
+ if (this.tn.skip("{"))
538
+ end = "}";
539
+ else if (this.tn.skip("<"))
540
+ end = ">";
541
+ else
542
+ this.error("expected message value");
543
+ return this.parseMessage(type, end, depth + 1);
544
+ };
545
+
546
+ Parser.prototype.parseScalar = function parseScalar(field) {
547
+ if (field.type === "string" || field.type === "bytes") {
548
+ var bytes = this.readStringBytes();
549
+ return field.type === "bytes" ? util.newBuffer(bytes) : utf8Read(bytes, true);
550
+ }
551
+
552
+ var sign = 1;
553
+ if (this.tn.skip("-"))
554
+ sign = -1;
555
+
556
+ var token = this.tn.next();
557
+ if (!token)
558
+ this.error("expected value");
559
+
560
+ if (field.resolvedType instanceof Enum)
561
+ return parseEnum(field, token, sign);
562
+
563
+ switch (field.type) {
564
+ case "double":
565
+ case "float":
566
+ return parseFloatValue(token, sign);
567
+ case "bool":
568
+ return parseBool(token, sign);
569
+ case "int32":
570
+ case "sint32":
571
+ case "sfixed32":
572
+ return parseInteger(token, sign, false, 32);
573
+ case "uint32":
574
+ case "fixed32":
575
+ return parseInteger(token, sign, true, 32);
576
+ case "int64":
577
+ case "sint64":
578
+ case "sfixed64":
579
+ return parseInteger(token, sign, false, 64);
580
+ case "uint64":
581
+ case "fixed64":
582
+ return parseInteger(token, sign, true, 64);
583
+ default:
584
+ this.error(field.fullName + ": unsupported scalar type");
585
+ }
586
+ return undefined;
587
+ };
588
+
589
+ Parser.prototype.readStringBytes = function readStringBytes() {
590
+ var token = this.tn.next(),
591
+ bytes = [];
592
+ if (!token || token.type !== "string")
593
+ this.error("expected string");
594
+ Array.prototype.push.apply(bytes, token.value);
595
+ while ((token = this.tn.peek()) && token.type === "string") {
596
+ token = this.tn.next();
597
+ Array.prototype.push.apply(bytes, token.value);
598
+ }
599
+ return bytes;
600
+ };
601
+
602
+ Parser.prototype.skipReservedValue = function skipReservedValue(depth) {
603
+ this.tn.skip(":");
604
+ var token = this.tn.peek();
605
+ if (!token)
606
+ return;
607
+ if (token.value === "{") {
608
+ this.skipBalanced("{", "}", depth);
609
+ } else if (token.value === "<") {
610
+ this.skipBalanced("<", ">", depth);
611
+ } else if (token.value === "[") {
612
+ this.skipBalanced("[", "]", depth);
613
+ } else if (token.type === "string") {
614
+ this.readStringBytes();
615
+ } else {
616
+ if (token.value === "-")
617
+ this.tn.next();
618
+ this.tn.next();
619
+ }
620
+ };
621
+
622
+ Parser.prototype.skipBalanced = function skipBalanced(open, close, depth) {
623
+ var balance = 0,
624
+ token;
625
+ do {
626
+ token = this.tn.next();
627
+ if (!token)
628
+ this.error("expected '" + close + "'");
629
+ if (token.value === open) {
630
+ if (depth + ++balance > util.recursionLimit)
631
+ this.error("max depth exceeded");
632
+ }
633
+ else if (token.value === close)
634
+ --balance;
635
+ } while (balance);
636
+ };
637
+
638
+ function addField(object, seen, field, value) {
639
+ if (field.repeated) {
640
+ (object[field.name] || (object[field.name] = [])).push(value);
641
+ return;
642
+ }
643
+ if (Object.prototype.hasOwnProperty.call(seen, field.name))
644
+ throw Error(field.fullName + ": multiple values");
645
+ if (field.partOf) {
646
+ var oneofName = "$oneof:" + field.partOf.name;
647
+ if (seen[oneofName])
648
+ throw Error(field.partOf.name + ": multiple values");
649
+ seen[oneofName] = true;
650
+ }
651
+ seen[field.name] = true;
652
+ object[field.name] = value;
653
+ }
654
+
655
+ function addMapEntry(field, map, entry) {
656
+ var keyField = mapKeyField(field),
657
+ valueField = mapValueField(field),
658
+ key = Object.prototype.hasOwnProperty.call(entry, "key")
659
+ ? entry.key
660
+ : defaultScalarValue(keyField),
661
+ value = Object.prototype.hasOwnProperty.call(entry, "value")
662
+ ? entry.value
663
+ : defaultMapValue(valueField);
664
+ map[mapKey(keyField, key)] = value;
665
+ }
666
+
667
+ function defaultMapValue(field) {
668
+ if (field.resolvedType instanceof Type)
669
+ return field.resolvedType.create();
670
+ if (field.resolvedType instanceof Enum)
671
+ return field.typeDefault;
672
+ return defaultScalarValue(field);
673
+ }
674
+
675
+ function defaultScalarValue(field) {
676
+ if (field.type === "string")
677
+ return "";
678
+ if (field.type === "bytes")
679
+ return util.newBuffer([]);
680
+ if (field.type === "bool")
681
+ return false;
682
+ return field.defaultValue;
683
+ }
684
+
685
+ function mapKeyField(field) {
686
+ return {
687
+ name: "key",
688
+ fullName: field.fullName + ".key",
689
+ type: field.keyType,
690
+ resolvedType: null,
691
+ defaultValue: field.keyType === "bool" ? false : field.keyType === "string" ? "" : 0
692
+ };
693
+ }
694
+
695
+ function mapValueField(field) {
696
+ return {
697
+ name: "value",
698
+ fullName: field.fullName + ".value",
699
+ type: field.type,
700
+ resolvedType: field.resolvedType,
701
+ defaultValue: field.resolvedType instanceof Enum ? field.resolvedType.values[Object.keys(field.resolvedType.values)[0]] : field.typeDefault
702
+ };
703
+ }
704
+
705
+ function mapKey(field, value) {
706
+ if (types.long[field.type] !== undefined)
707
+ return String(value);
708
+ if (field.type === "bool")
709
+ return value ? "true" : "false";
710
+ return String(value);
711
+ }
712
+
713
+ function lookupField(type, name) {
714
+ var fields = type.fieldsArray;
715
+ for (var i = 0; i < fields.length; ++i) {
716
+ var field = fields[i].resolve();
717
+ if (field.name === name || underScore(field.name) === name)
718
+ return field;
719
+ if (field.delimited && field.resolvedType instanceof Type) {
720
+ var groupName = field.resolvedType.name,
721
+ lowerName = name.toLowerCase(),
722
+ compactName = compact(name);
723
+ if (groupName === name || underScore(groupName) === name
724
+ || field.name.toLowerCase() === lowerName
725
+ || groupName.toLowerCase() === lowerName
726
+ || compact(field.name) === compactName
727
+ || compact(groupName) === compactName)
728
+ return field;
729
+ }
730
+ }
731
+ return null;
732
+ }
733
+
734
+ function lookupExtension(type, name) {
735
+ var fullName = name.charAt(0) === "." ? name : "." + name,
736
+ camelName = camelCaseLastPath(fullName),
737
+ field = type.get(fullName) || type.root.lookup(fullName, Field)
738
+ || type.get(camelName) || type.root.lookup(camelName, Field);
739
+ if (!field)
740
+ field = lookupExtensionField(type, fullName);
741
+ if (field && field.extend !== undefined && field.extensionField)
742
+ field = field.extensionField;
743
+ if (!field || field.parent !== type)
744
+ throw Error(type.fullName + ": unknown extension '" + name + "'");
745
+ return field;
746
+ }
747
+
748
+ function camelCaseLastPath(name) {
749
+ var dot = name.lastIndexOf(".");
750
+ return name.substring(0, dot + 1) + util.camelCase(name.substring(dot + 1));
751
+ }
752
+
753
+ function parseEnum(field, token, sign) {
754
+ if (sign < 0) {
755
+ if (token.type !== "number")
756
+ throw Error(field.fullName + ": enum value expected");
757
+ return checkEnumValue(field, parseInteger(token, sign, false, 32));
758
+ }
759
+ if (token.type === "word") {
760
+ var value = field.resolvedType.values[token.value];
761
+ if (value === undefined)
762
+ throw Error(field.fullName + ": enum value expected");
763
+ return value;
764
+ }
765
+ return checkEnumValue(field, parseInteger(token, sign, false, 32));
766
+ }
767
+
768
+ function parseBool(token, sign) {
769
+ if (sign < 0)
770
+ throw Error("bool value expected");
771
+ if (token.type === "word") {
772
+ switch (token.value) {
773
+ case "true":
774
+ case "True":
775
+ case "t":
776
+ return true;
777
+ case "false":
778
+ case "False":
779
+ case "f":
780
+ return false;
781
+ }
782
+ } else if (token.type === "number") {
783
+ var value = parseInteger(token, 1, true, 32);
784
+ if (value === 0)
785
+ return false;
786
+ if (value === 1)
787
+ return true;
788
+ }
789
+ throw Error("bool value expected");
790
+ }
791
+
792
+ function parseFloatValue(token, sign) {
793
+ if (token.type === "word") {
794
+ switch (token.value.toLowerCase()) {
795
+ case "inf":
796
+ case "infinity":
797
+ return sign * Infinity;
798
+ case "nan":
799
+ return NaN;
800
+ }
801
+ throw Error("float value expected");
802
+ }
803
+ if (token.type !== "number")
804
+ throw Error("float value expected");
805
+ var raw = token.value;
806
+ if (/^0[xX]/.test(raw) || /^0[0-7]/.test(raw) && raw.length > 1)
807
+ throw Error("float value expected");
808
+ if (/[fF]$/.test(raw))
809
+ raw = raw.substring(0, raw.length - 1);
810
+ return sign * Number(raw);
811
+ }
812
+
813
+ function parseInteger(token, sign, unsigned, bits) {
814
+ if (token.type !== "number")
815
+ throw Error("integer value expected");
816
+ if (sign < 0 && unsigned)
817
+ throw Error("unsigned integer value expected");
818
+
819
+ var raw = token.value,
820
+ radix = 10,
821
+ digits = raw;
822
+ if (/^0[xX]/.test(raw)) {
823
+ radix = 16;
824
+ digits = raw.substring(2);
825
+ } else if (/^0[0-7]/.test(raw) && raw.length > 1) {
826
+ radix = 8;
827
+ digits = raw.substring(1);
828
+ } else if (!/^(?:0|[1-9][0-9]*)$/.test(raw))
829
+ throw Error("integer value expected");
830
+
831
+ if (typeof util.global.BigInt === "function")
832
+ return parseIntegerBigInt(digits, radix, sign, unsigned, bits);
833
+
834
+ var value = parseInt(digits, radix) * sign;
835
+ if (bits === 64 && util.Long)
836
+ return util.Long.fromString(String(value), unsigned);
837
+ return value;
838
+ }
839
+
840
+ function parseIntegerBigInt(digits, radix, sign, unsigned, bits) {
841
+ var value,
842
+ BigInt = util.global.BigInt;
843
+ if (radix === 16)
844
+ value = BigInt("0x" + digits);
845
+ else if (radix === 8)
846
+ value = BigInt("0o" + digits);
847
+ else
848
+ value = BigInt(digits);
849
+ if (sign < 0)
850
+ value = -value;
851
+
852
+ var min,
853
+ max;
854
+ if (bits === 32) {
855
+ min = unsigned ? BigInt(0) : -BigInt(2147483648);
856
+ max = unsigned ? BigInt(4294967295) : BigInt(2147483647);
857
+ } else {
858
+ min = unsigned ? BigInt(0) : -BigInt("9223372036854775808");
859
+ max = unsigned ? BigInt("18446744073709551615") : BigInt("9223372036854775807");
860
+ }
861
+ if (value < min || value > max)
862
+ throw Error((unsigned ? "unsigned " : "") + "integer value out of range");
863
+ if (bits === 64 && util.Long)
864
+ return util.Long.fromString(value.toString(), unsigned, 10);
865
+ return Number(value);
866
+ }
867
+
868
+ function writeMessage(type, message, lines, indent, options, depth) {
869
+ if (depth > util.recursionLimit)
870
+ throw Error("max depth exceeded");
871
+ var fields = type.fieldsArray.slice().sort(util.compareFieldsById);
872
+ for (var i = 0; i < fields.length; ++i) {
873
+ var field = fields[i].resolve(),
874
+ value = message[field.name];
875
+ if (value == null || !Object.prototype.hasOwnProperty.call(message, field.name))
876
+ continue;
877
+ if (field.map)
878
+ writeMapField(field, value, lines, indent, options, depth);
879
+ else if (field.repeated)
880
+ for (var j = 0; j < value.length; ++j)
881
+ writeField(field, value[j], lines, indent, options, depth);
882
+ else
883
+ writeField(field, value, lines, indent, options, depth);
884
+ }
885
+ if (options.unknowns && message.$unknowns != null && Object.prototype.hasOwnProperty.call(message, "$unknowns"))
886
+ writeUnknowns(message.$unknowns, lines, indent);
887
+ }
888
+
889
+ function writeMapField(field, map, lines, indent, options, depth) {
890
+ var keys = Object.keys(map).sort(),
891
+ keyField = mapKeyField(field),
892
+ valueField = mapValueField(field),
893
+ name = formatFieldName(field),
894
+ sp = spaces(indent);
895
+ for (var i = 0; i < keys.length; ++i) {
896
+ if (depth + 1 > util.recursionLimit)
897
+ throw Error("max depth exceeded");
898
+ var key = keyField.long ? util.longFromKey(keys[i], keyField.type === "uint64" || keyField.type === "fixed64") : keys[i];
899
+ if (keyField.type === "bool")
900
+ key = util.boolFromKey(keys[i]);
901
+ lines.push(sp + name + " {");
902
+ lines.push(spaces(indent + 2) + "key: " + formatScalar(keyField, key));
903
+ if (valueField.resolvedType instanceof Type) {
904
+ lines.push(spaces(indent + 2) + "value {");
905
+ writeMessage(valueField.resolvedType, map[keys[i]], lines, indent + 4, options, depth + 2);
906
+ lines.push(spaces(indent + 2) + "}");
907
+ } else
908
+ lines.push(spaces(indent + 2) + "value: " + formatScalar(valueField, map[keys[i]]));
909
+ lines.push(sp + "}");
910
+ }
911
+ }
912
+
913
+ function writeField(field, value, lines, indent, options, depth) {
914
+ var name = formatFieldName(field),
915
+ sp = spaces(indent);
916
+ if (field.resolvedType instanceof Type) {
917
+ lines.push(sp + name + " {");
918
+ writeMessage(field.resolvedType, value, lines, indent + 2, options, depth + 1);
919
+ lines.push(sp + "}");
920
+ } else
921
+ lines.push(sp + name + ": " + formatScalar(field, value));
922
+ }
923
+
924
+ function writeUnknowns(unknowns, lines, indent) {
925
+ for (var i = 0; i < unknowns.length; ++i) {
926
+ var reader = Reader.create(unknowns[i]);
927
+ writeUnknownFieldSet(reader, lines, indent, undefined, textformat.unknownRecursionLimit);
928
+ if (reader.pos !== reader.len)
929
+ throw Error("invalid unknown field data");
930
+ }
931
+ }
932
+
933
+ function writeUnknownFieldSet(reader, lines, indent, endGroup, recursionBudget) {
934
+ if (recursionBudget < 0)
935
+ throw Error("max depth exceeded");
936
+ while (reader.pos < reader.len) {
937
+ var tag = reader.tag(),
938
+ fieldNumber = tag >>> 3,
939
+ wireType = tag & 7;
940
+ if (!fieldNumber)
941
+ throw Error("illegal tag: field number 0");
942
+ if (wireType === 4) {
943
+ if (fieldNumber !== endGroup)
944
+ throw Error("invalid end group tag");
945
+ return;
946
+ }
947
+ writeUnknownField(reader, fieldNumber, wireType, lines, indent, recursionBudget);
948
+ }
949
+ if (endGroup !== undefined)
950
+ throw Error("missing end group tag");
951
+ }
952
+
953
+ function writeUnknownField(reader, fieldNumber, wireType, lines, indent, recursionBudget) {
954
+ var sp = spaces(indent),
955
+ lo;
956
+ switch (wireType) {
957
+ case 0:
958
+ lines.push(sp + fieldNumber + ": " + readUnknownVarint(reader));
959
+ break;
960
+ case 1:
961
+ lo = reader.fixed32();
962
+ lines.push(sp + fieldNumber + ": 0x" + hexPad(reader.fixed32(), 8) + hexPad(lo, 8));
963
+ break;
964
+ case 2:
965
+ writeUnknownLengthDelimited(reader, fieldNumber, lines, indent, recursionBudget);
966
+ break;
967
+ case 3:
968
+ lines.push(sp + fieldNumber + " {");
969
+ writeUnknownFieldSet(reader, lines, indent + 2, fieldNumber, recursionBudget - 1);
970
+ lines.push(sp + "}");
971
+ break;
972
+ case 5:
973
+ lines.push(sp + fieldNumber + ": 0x" + hexPad(reader.fixed32(), 8));
974
+ break;
975
+ default:
976
+ throw Error("invalid wire type " + wireType);
977
+ }
978
+ }
979
+
980
+ function writeUnknownLengthDelimited(reader, fieldNumber, lines, indent, recursionBudget) {
981
+ var value = reader.bytes(),
982
+ nested = value.length && recursionBudget > 0
983
+ ? tryFormatUnknownMessage(value, indent + 2, recursionBudget - 1)
984
+ : null,
985
+ sp = spaces(indent);
986
+ if (nested) {
987
+ lines.push(sp + fieldNumber + " {");
988
+ for (var i = 0; i < nested.length; ++i)
989
+ lines.push(nested[i]);
990
+ lines.push(sp + "}");
991
+ } else
992
+ lines.push(sp + fieldNumber + ": " + quoteBytes(value));
993
+ }
994
+
995
+ function tryFormatUnknownMessage(bytes, indent, recursionBudget) {
996
+ var reader = Reader.create(bytes),
997
+ lines = [];
998
+ try {
999
+ writeUnknownFieldSet(reader, lines, indent, undefined, recursionBudget);
1000
+ return reader.pos === reader.len ? lines : null;
1001
+ } catch (e) {
1002
+ return null;
1003
+ }
1004
+ }
1005
+
1006
+ function readUnknownVarint(reader) {
1007
+ var BigInt = util.global.BigInt;
1008
+ if (typeof BigInt !== "function")
1009
+ return String(reader.uint64());
1010
+
1011
+ var value = BigInt(0),
1012
+ shift = BigInt(0),
1013
+ b;
1014
+ for (var i = 0; i < 10; ++i) {
1015
+ if (reader.pos >= reader.len)
1016
+ throw Error("invalid varint encoding");
1017
+ b = reader.buf[reader.pos++];
1018
+ value += BigInt(b & 127) << shift;
1019
+ if (b < 128)
1020
+ return value.toString();
1021
+ shift += BigInt(7);
1022
+ }
1023
+ throw Error("invalid varint encoding");
1024
+ }
1025
+
1026
+ function hexPad(value, length) {
1027
+ var str = value.toString(16);
1028
+ while (str.length < length)
1029
+ str = "0" + str;
1030
+ return str;
1031
+ }
1032
+
1033
+ function formatFieldName(field) {
1034
+ if (field.declaringField || field.name.charAt(0) === ".")
1035
+ return "[" + formatExtensionName(field) + "]";
1036
+ if (field.delimited && field.resolvedType instanceof Type && compact(field.name) === compact(field.resolvedType.name))
1037
+ return field.resolvedType.name;
1038
+ return underScore(field.name);
1039
+ }
1040
+
1041
+ function formatExtensionName(field) {
1042
+ var name = field.name.replace(/^\./, ""),
1043
+ dot = name.lastIndexOf("."),
1044
+ path = name.substring(0, dot + 1),
1045
+ last = name.substring(dot + 1);
1046
+ if (field.delimited && field.resolvedType instanceof Type && field.resolvedType.group)
1047
+ last = last.toLowerCase();
1048
+ else
1049
+ last = underScore(last);
1050
+ return path + last;
1051
+ }
1052
+
1053
+ function formatScalar(field, value) {
1054
+ if (field.resolvedType instanceof Enum) {
1055
+ var name = field.resolvedType.valuesById[value];
1056
+ return name === undefined ? String(value) : name;
1057
+ }
1058
+ switch (field.type) {
1059
+ case "string":
1060
+ return quoteBytes(utf8Bytes(String(value)));
1061
+ case "bytes":
1062
+ return quoteBytes(bytesValue(value));
1063
+ case "bool":
1064
+ return value ? "true" : "false";
1065
+ case "double":
1066
+ case "float":
1067
+ if (isNaN(value))
1068
+ return "nan";
1069
+ if (value === 0 && 1 / value === -Infinity)
1070
+ return "-0";
1071
+ if (value === Infinity)
1072
+ return "inf";
1073
+ if (value === -Infinity)
1074
+ return "-inf";
1075
+ return String(value);
1076
+ default:
1077
+ return String(value);
1078
+ }
1079
+ }
1080
+
1081
+ function bytesValue(value) {
1082
+ if (typeof value === "string") {
1083
+ var length = util.base64.length(value),
1084
+ buffer = util.newBuffer(length);
1085
+ util.base64.decode(value, buffer, 0);
1086
+ return buffer;
1087
+ }
1088
+ return value;
1089
+ }
1090
+
1091
+ function quoteBytes(bytes) {
1092
+ var out = "\"",
1093
+ oct;
1094
+ for (var i = 0; i < bytes.length; ++i) {
1095
+ var b = bytes[i];
1096
+ switch (b) {
1097
+ case 9: out += "\\t"; break;
1098
+ case 10: out += "\\n"; break;
1099
+ case 13: out += "\\r"; break;
1100
+ case 34: out += "\\\""; break;
1101
+ case 92: out += "\\\\"; break;
1102
+ default:
1103
+ if (b >= 32 && b <= 126)
1104
+ out += String.fromCharCode(b);
1105
+ else {
1106
+ oct = b.toString(8);
1107
+ out += "\\" + (oct.length < 2 ? "00" : oct.length < 3 ? "0" : "") + oct;
1108
+ }
1109
+ break;
1110
+ }
1111
+ }
1112
+ return out + "\"";
1113
+ }
1114
+
1115
+ function spaces(indent) {
1116
+ var str = "";
1117
+ while (str.length < indent)
1118
+ str += " ";
1119
+ return str;
1120
+ }
1121
+
1122
+ function utf8Read(bytes, strict) {
1123
+ if (strict && !validUtf8(bytes))
1124
+ throw Error("invalid UTF-8 string");
1125
+ var buffer = util.newBuffer(bytes);
1126
+ return util.utf8.read(buffer, 0, buffer.length);
1127
+ }
1128
+
1129
+ function validUtf8(bytes) {
1130
+ for (var i = 0, b; i < bytes.length;) {
1131
+ b = bytes[i++];
1132
+ if (b <= 0x7F)
1133
+ continue;
1134
+ if (b >= 0xC2 && b <= 0xDF) {
1135
+ if ((b = bytes[i++]) < 0x80 || b > 0xBF)
1136
+ return false;
1137
+ } else if (b === 0xE0) {
1138
+ if ((b = bytes[i++]) < 0xA0 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1139
+ return false;
1140
+ } else if (b >= 0xE1 && b <= 0xEC || b >= 0xEE && b <= 0xEF) {
1141
+ if ((b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1142
+ return false;
1143
+ } else if (b === 0xED) {
1144
+ if ((b = bytes[i++]) < 0x80 || b > 0x9F || (b = bytes[i++]) < 0x80 || b > 0xBF)
1145
+ return false;
1146
+ } else if (b === 0xF0) {
1147
+ if ((b = bytes[i++]) < 0x90 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1148
+ return false;
1149
+ } else if (b >= 0xF1 && b <= 0xF3) {
1150
+ if ((b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1151
+ return false;
1152
+ } else if (b === 0xF4) {
1153
+ if ((b = bytes[i++]) < 0x80 || b > 0x8F || (b = bytes[i++]) < 0x80 || b > 0xBF || (b = bytes[i++]) < 0x80 || b > 0xBF)
1154
+ return false;
1155
+ } else
1156
+ return false;
1157
+ }
1158
+ return true;
1159
+ }
1160
+
1161
+ function utf8Bytes(str) {
1162
+ var buffer = util.newBuffer(util.utf8.length(str));
1163
+ util.utf8.write(str, buffer, 0);
1164
+ return buffer;
1165
+ }
1166
+
1167
+ function pushUtf8(bytes, code) {
1168
+ if (code < 0x80) {
1169
+ bytes.push(code);
1170
+ } else if (code < 0x800) {
1171
+ bytes.push(code >> 6 | 192, code & 63 | 128);
1172
+ } else if (code < 0x10000) {
1173
+ bytes.push(code >> 12 | 224, code >> 6 & 63 | 128, code & 63 | 128);
1174
+ } else {
1175
+ bytes.push(code >> 18 | 240, code >> 12 & 63 | 128, code >> 6 & 63 | 128, code & 63 | 128);
1176
+ }
1177
+ }
1178
+
1179
+ function verifyTextMessage(type, message) {
1180
+ var fields = type.fieldsArray;
1181
+ for (var i = 0; i < fields.length; ++i) {
1182
+ var field = fields[i].resolve(),
1183
+ value = message[field.name];
1184
+ if (value == null || !Object.prototype.hasOwnProperty.call(message, field.name)) {
1185
+ if (field.required)
1186
+ return field.fullName + ": missing required field";
1187
+ continue;
1188
+ }
1189
+ if (field.map) {
1190
+ if (field.resolvedType instanceof Type)
1191
+ for (var key in value)
1192
+ if (Object.prototype.hasOwnProperty.call(value, key)) {
1193
+ var mapErr = verifyTextMessage(field.resolvedType, value[key]);
1194
+ if (mapErr)
1195
+ return mapErr;
1196
+ }
1197
+ } else if (field.repeated) {
1198
+ if (field.resolvedType instanceof Type)
1199
+ for (var j = 0; j < value.length; ++j) {
1200
+ var repeatedErr = verifyTextMessage(field.resolvedType, value[j]);
1201
+ if (repeatedErr)
1202
+ return repeatedErr;
1203
+ }
1204
+ } else if (field.resolvedType instanceof Type) {
1205
+ var err = verifyTextMessage(field.resolvedType, value);
1206
+ if (err)
1207
+ return err;
1208
+ }
1209
+ }
1210
+ return null;
1211
+ }
1212
+
1213
+ function isSeparator(token) {
1214
+ return token.value === "," || token.value === ";";
1215
+ }
1216
+
1217
+ function validateTypeUrl(typeUrl) {
1218
+ for (var i = 0; i < typeUrl.length; ++i)
1219
+ if (typeUrl.charAt(i) === "%") {
1220
+ if (i + 2 >= typeUrl.length || !hexRe.test(typeUrl.charAt(i + 1)) || !hexRe.test(typeUrl.charAt(i + 2)))
1221
+ throw Error("invalid Any type URL");
1222
+ i += 2;
1223
+ }
1224
+ }
1225
+
1226
+ function lookupExtensionField(type, fullName) {
1227
+ var fields = type.fieldsArray;
1228
+ for (var i = 0; i < fields.length; ++i) {
1229
+ var field = fields[i].resolve();
1230
+ if (field.name.charAt(0) === "." && "." + formatExtensionName(field) === fullName)
1231
+ return field;
1232
+ }
1233
+ return null;
1234
+ }
1235
+
1236
+ function checkEnumValue(field, value) {
1237
+ if (isClosedEnum(field) && field.resolvedType.valuesById[value] === undefined)
1238
+ throw Error(field.fullName + ": enum value expected");
1239
+ return value;
1240
+ }
1241
+
1242
+ function isClosedEnum(field) {
1243
+ return field.resolvedType
1244
+ && field.resolvedType._features
1245
+ && field.resolvedType._features.enum_type === "CLOSED";
1246
+ }
1247
+
1248
+ function compact(str) {
1249
+ return str.replace(/_/g, "").toLowerCase();
1250
+ }
1251
+
1252
+ function underScore(str) {
1253
+ return str.substring(0, 1)
1254
+ + str.substring(1)
1255
+ .replace(/([A-Z])(?=[a-z]|$)/g, function($0, $1) { return "_" + $1.toLowerCase(); });
1256
+ }