1 2/*! js-yaml 4.1.0 https://github.com/nodeca/js-yaml @license MIT */ 3function isNothing(subject) { 4 return (typeof subject === 'undefined') || (subject === null); 5} 6 7 8function isObject(subject) { 9 return (typeof subject === 'object') && (subject !== null); 10} 11 12 13function toArray(sequence) { 14 if (Array.isArray(sequence)) return sequence; 15 else if (isNothing(sequence)) return []; 16 17 return [ sequence ]; 18} 19 20 21function extend(target, source) { 22 var index, length, key, sourceKeys; 23 24 if (source) { 25 sourceKeys = Object.keys(source); 26 27 for (index = 0, length = sourceKeys.length; index < length; index += 1) { 28 key = sourceKeys[index]; 29 target[key] = source[key]; 30 } 31 } 32 33 return target; 34} 35 36 37function repeat(string, count) { 38 var result = '', cycle; 39 40 for (cycle = 0; cycle < count; cycle += 1) { 41 result += string; 42 } 43 44 return result; 45} 46 47 48function isNegativeZero(number) { 49 return (number === 0) && (Number.NEGATIVE_INFINITY === 1 / number); 50} 51 52 53var isNothing_1 = isNothing; 54var isObject_1 = isObject; 55var toArray_1 = toArray; 56var repeat_1 = repeat; 57var isNegativeZero_1 = isNegativeZero; 58var extend_1 = extend; 59 60var common = { 61 isNothing: isNothing_1, 62 isObject: isObject_1, 63 toArray: toArray_1, 64 repeat: repeat_1, 65 isNegativeZero: isNegativeZero_1, 66 extend: extend_1 67}; 68 69// YAML error class. http://stackoverflow.com/questions/8458984 70 71 72function formatError(exception, compact) { 73 var where = '', message = exception.reason || '(unknown reason)'; 74 75 if (!exception.mark) return message; 76 77 if (exception.mark.name) { 78 where += 'in "' + exception.mark.name + '" '; 79 } 80 81 where += '(' + (exception.mark.line + 1) + ':' + (exception.mark.column + 1) + ')'; 82 83 if (!compact && exception.mark.snippet) { 84 where += '\n\n' + exception.mark.snippet; 85 } 86 87 return message + ' ' + where; 88} 89 90 91function YAMLException$1(reason, mark) { 92 // Super constructor 93 Error.call(this); 94 95 this.name = 'YAMLException'; 96 this.reason = reason; 97 this.mark = mark; 98 this.message = formatError(this, false); 99 100 // Include stack trace in error object 101 if (Error.captureStackTrace) { 102 // Chrome and NodeJS 103 Error.captureStackTrace(this, this.constructor); 104 } else { 105 // FF, IE 10+ and Safari 6+. Fallback for others 106 this.stack = (new Error()).stack || ''; 107 } 108} 109 110 111// Inherit from Error 112YAMLException$1.prototype = Object.create(Error.prototype); 113YAMLException$1.prototype.constructor = YAMLException$1; 114 115 116YAMLException$1.prototype.toString = function toString(compact) { 117 return this.name + ': ' + formatError(this, compact); 118}; 119 120 121var exception = YAMLException$1; 122 123// get snippet for a single line, respecting maxLength 124function getLine(buffer, lineStart, lineEnd, position, maxLineLength) { 125 var head = ''; 126 var tail = ''; 127 var maxHalfLength = Math.floor(maxLineLength / 2) - 1; 128 129 if (position - lineStart > maxHalfLength) { 130 head = ' ... '; 131 lineStart = position - maxHalfLength + head.length; 132 } 133 134 if (lineEnd - position > maxHalfLength) { 135 tail = ' ...'; 136 lineEnd = position + maxHalfLength - tail.length; 137 } 138 139 return { 140 str: head + buffer.slice(lineStart, lineEnd).replace(/\t/g, '→') + tail, 141 pos: position - lineStart + head.length // relative position 142 }; 143} 144 145 146function padStart(string, max) { 147 return common.repeat(' ', max - string.length) + string; 148} 149 150 151function makeSnippet(mark, options) { 152 options = Object.create(options || null); 153 154 if (!mark.buffer) return null; 155 156 if (!options.maxLength) options.maxLength = 79; 157 if (typeof options.indent !== 'number') options.indent = 1; 158 if (typeof options.linesBefore !== 'number') options.linesBefore = 3; 159 if (typeof options.linesAfter !== 'number') options.linesAfter = 2; 160 161 var re = /\r?\n|\r|\0/g; 162 var lineStarts = [ 0 ]; 163 var lineEnds = []; 164 var match; 165 var foundLineNo = -1; 166 167 while ((match = re.exec(mark.buffer))) { 168 lineEnds.push(match.index); 169 lineStarts.push(match.index + match[0].length); 170 171 if (mark.position <= match.index && foundLineNo < 0) { 172 foundLineNo = lineStarts.length - 2; 173 } 174 } 175 176 if (foundLineNo < 0) foundLineNo = lineStarts.length - 1; 177 178 var result = '', i, line; 179 var lineNoLength = Math.min(mark.line + options.linesAfter, lineEnds.length).toString().length; 180 var maxLineLength = options.maxLength - (options.indent + lineNoLength + 3); 181 182 for (i = 1; i <= options.linesBefore; i++) { 183 if (foundLineNo - i < 0) break; 184 line = getLine( 185 mark.buffer, 186 lineStarts[foundLineNo - i], 187 lineEnds[foundLineNo - i], 188 mark.position - (lineStarts[foundLineNo] - lineStarts[foundLineNo - i]), 189 maxLineLength 190 ); 191 result = common.repeat(' ', options.indent) + padStart((mark.line - i + 1).toString(), lineNoLength) + 192 ' | ' + line.str + '\n' + result; 193 } 194 195 line = getLine(mark.buffer, lineStarts[foundLineNo], lineEnds[foundLineNo], mark.position, maxLineLength); 196 result += common.repeat(' ', options.indent) + padStart((mark.line + 1).toString(), lineNoLength) + 197 ' | ' + line.str + '\n'; 198 result += common.repeat('-', options.indent + lineNoLength + 3 + line.pos) + '^' + '\n'; 199 200 for (i = 1; i <= options.linesAfter; i++) { 201 if (foundLineNo + i >= lineEnds.length) break; 202 line = getLine( 203 mark.buffer, 204 lineStarts[foundLineNo + i], 205 lineEnds[foundLineNo + i], 206 mark.position - (lineStarts[foundLineNo] - lineStarts[foundLineNo + i]), 207 maxLineLength 208 ); 209 result += common.repeat(' ', options.indent) + padStart((mark.line + i + 1).toString(), lineNoLength) + 210 ' | ' + line.str + '\n'; 211 } 212 213 return result.replace(/\n$/, ''); 214} 215 216 217var snippet = makeSnippet; 218 219var TYPE_CONSTRUCTOR_OPTIONS = [ 220 'kind', 221 'multi', 222 'resolve', 223 'construct', 224 'instanceOf', 225 'predicate', 226 'represent', 227 'representName', 228 'defaultStyle', 229 'styleAliases' 230]; 231 232var YAML_NODE_KINDS = [ 233 'scalar', 234 'sequence', 235 'mapping' 236]; 237 238function compileStyleAliases(map) { 239 var result = {}; 240 241 if (map !== null) { 242 Object.keys(map).forEach(function (style) { 243 map[style].forEach(function (alias) { 244 result[String(alias)] = style; 245 }); 246 }); 247 } 248 249 return result; 250} 251 252function Type$1(tag, options) { 253 options = options || {}; 254 255 Object.keys(options).forEach(function (name) { 256 if (TYPE_CONSTRUCTOR_OPTIONS.indexOf(name) === -1) { 257 throw new exception('Unknown option "' + name + '" is met in definition of "' + tag + '" YAML type.'); 258 } 259 }); 260 261 // TODO: Add tag format check. 262 this.options = options; // keep original options in case user wants to extend this type later 263 this.tag = tag; 264 this.kind = options['kind'] || null; 265 this.resolve = options['resolve'] || function () { return true; }; 266 this.construct = options['construct'] || function (data) { return data; }; 267 this.instanceOf = options['instanceOf'] || null; 268 this.predicate = options['predicate'] || null; 269 this.represent = options['represent'] || null; 270 this.representName = options['representName'] || null; 271 this.defaultStyle = options['defaultStyle'] || null; 272 this.multi = options['multi'] || false; 273 this.styleAliases = compileStyleAliases(options['styleAliases'] || null); 274 275 if (YAML_NODE_KINDS.indexOf(this.kind) === -1) { 276 throw new exception('Unknown kind "' + this.kind + '" is specified for "' + tag + '" YAML type.'); 277 } 278} 279 280var type = Type$1; 281 282/*eslint-disable max-len*/ 283 284 285 286 287 288function compileList(schema, name) { 289 var result = []; 290 291 schema[name].forEach(function (currentType) { 292 var newIndex = result.length; 293 294 result.forEach(function (previousType, previousIndex) { 295 if (previousType.tag === currentType.tag && 296 previousType.kind === currentType.kind && 297 previousType.multi === currentType.multi) { 298 299 newIndex = previousIndex; 300 } 301 }); 302 303 result[newIndex] = currentType; 304 }); 305 306 return result; 307} 308 309 310function compileMap(/* lists... */) { 311 var result = { 312 scalar: {}, 313 sequence: {}, 314 mapping: {}, 315 fallback: {}, 316 multi: { 317 scalar: [], 318 sequence: [], 319 mapping: [], 320 fallback: [] 321 } 322 }, index, length; 323 324 function collectType(type) { 325 if (type.multi) { 326 result.multi[type.kind].push(type); 327 result.multi['fallback'].push(type); 328 } else { 329 result[type.kind][type.tag] = result['fallback'][type.tag] = type; 330 } 331 } 332 333 for (index = 0, length = arguments.length; index < length; index += 1) { 334 arguments[index].forEach(collectType); 335 } 336 return result; 337} 338 339 340function Schema$1(definition) { 341 return this.extend(definition); 342} 343 344 345Schema$1.prototype.extend = function extend(definition) { 346 var implicit = []; 347 var explicit = []; 348 349 if (definition instanceof type) { 350 // Schema.extend(type) 351 explicit.push(definition); 352 353 } else if (Array.isArray(definition)) { 354 // Schema.extend([ type1, type2, ... ]) 355 explicit = explicit.concat(definition); 356 357 } else if (definition && (Array.isArray(definition.implicit) || Array.isArray(definition.explicit))) { 358 // Schema.extend({ explicit: [ type1, type2, ... ], implicit: [ type1, type2, ... ] }) 359 if (definition.implicit) implicit = implicit.concat(definition.implicit); 360 if (definition.explicit) explicit = explicit.concat(definition.explicit); 361 362 } else { 363 throw new exception('Schema.extend argument should be a Type, [ Type ], ' + 364 'or a schema definition ({ implicit: [...], explicit: [...] })'); 365 } 366 367 implicit.forEach(function (type$1) { 368 if (!(type$1 instanceof type)) { 369 throw new exception('Specified list of YAML types (or a single Type object) contains a non-Type object.'); 370 } 371 372 if (type$1.loadKind && type$1.loadKind !== 'scalar') { 373 throw new exception('There is a non-scalar type in the implicit list of a schema. Implicit resolving of such types is not supported.'); 374 } 375 376 if (type$1.multi) { 377 throw new exception('There is a multi type in the implicit list of a schema. Multi tags can only be listed as explicit.'); 378 } 379 }); 380 381 explicit.forEach(function (type$1) { 382 if (!(type$1 instanceof type)) { 383 throw new exception('Specified list of YAML types (or a single Type object) contains a non-Type object.'); 384 } 385 }); 386 387 var result = Object.create(Schema$1.prototype); 388 389 result.implicit = (this.implicit || []).concat(implicit); 390 result.explicit = (this.explicit || []).concat(explicit); 391 392 result.compiledImplicit = compileList(result, 'implicit'); 393 result.compiledExplicit = compileList(result, 'explicit'); 394 result.compiledTypeMap = compileMap(result.compiledImplicit, result.compiledExplicit); 395 396 return result; 397}; 398 399 400var schema = Schema$1; 401 402var str = new type('tag:yaml.org,2002:str', { 403 kind: 'scalar', 404 construct: function (data) { return data !== null ? data : ''; } 405}); 406 407var seq = new type('tag:yaml.org,2002:seq', { 408 kind: 'sequence', 409 construct: function (data) { return data !== null ? data : []; } 410}); 411 412var map = new type('tag:yaml.org,2002:map', { 413 kind: 'mapping', 414 construct: function (data) { return data !== null ? data : {}; } 415}); 416 417var failsafe = new schema({ 418 explicit: [ 419 str, 420 seq, 421 map 422 ] 423}); 424 425function resolveYamlNull(data) { 426 if (data === null) return true; 427 428 var max = data.length; 429 430 return (max === 1 && data === '~') || 431 (max === 4 && (data === 'null' || data === 'Null' || data === 'NULL')); 432} 433 434function constructYamlNull() { 435 return null; 436} 437 438function isNull(object) { 439 return object === null; 440} 441 442var _null = new type('tag:yaml.org,2002:null', { 443 kind: 'scalar', 444 resolve: resolveYamlNull, 445 construct: constructYamlNull, 446 predicate: isNull, 447 represent: { 448 canonical: function () { return '~'; }, 449 lowercase: function () { return 'null'; }, 450 uppercase: function () { return 'NULL'; }, 451 camelcase: function () { return 'Null'; }, 452 empty: function () { return ''; } 453 }, 454 defaultStyle: 'lowercase' 455}); 456 457function resolveYamlBoolean(data) { 458 if (data === null) return false; 459 460 var max = data.length; 461 462 return (max === 4 && (data === 'true' || data === 'True' || data === 'TRUE')) || 463 (max === 5 && (data === 'false' || data === 'False' || data === 'FALSE')); 464} 465 466function constructYamlBoolean(data) { 467 return data === 'true' || 468 data === 'True' || 469 data === 'TRUE'; 470} 471 472function isBoolean(object) { 473 return Object.prototype.toString.call(object) === '[object Boolean]'; 474} 475 476var bool = new type('tag:yaml.org,2002:bool', { 477 kind: 'scalar', 478 resolve: resolveYamlBoolean, 479 construct: constructYamlBoolean, 480 predicate: isBoolean, 481 represent: { 482 lowercase: function (object) { return object ? 'true' : 'false'; }, 483 uppercase: function (object) { return object ? 'TRUE' : 'FALSE'; }, 484 camelcase: function (object) { return object ? 'True' : 'False'; } 485 }, 486 defaultStyle: 'lowercase' 487}); 488 489function isHexCode(c) { 490 return ((0x30/* 0 */ <= c) && (c <= 0x39/* 9 */)) || 491 ((0x41/* A */ <= c) && (c <= 0x46/* F */)) || 492 ((0x61/* a */ <= c) && (c <= 0x66/* f */)); 493} 494 495function isOctCode(c) { 496 return ((0x30/* 0 */ <= c) && (c <= 0x37/* 7 */)); 497} 498 499function isDecCode(c) { 500 return ((0x30/* 0 */ <= c) && (c <= 0x39/* 9 */)); 501} 502 503function resolveYamlInteger(data) { 504 if (data === null) return false; 505 506 var max = data.length, 507 index = 0, 508 hasDigits = false, 509 ch; 510 511 if (!max) return false; 512 513 ch = data[index]; 514 515 // sign 516 if (ch === '-' || ch === '+') { 517 ch = data[++index]; 518 } 519 520 if (ch === '0') { 521 // 0 522 if (index + 1 === max) return true; 523 ch = data[++index]; 524 525 // base 2, base 8, base 16 526 527 if (ch === 'b') { 528 // base 2 529 index++; 530 531 for (; index < max; index++) { 532 ch = data[index]; 533 if (ch === '_') continue; 534 if (ch !== '0' && ch !== '1') return false; 535 hasDigits = true; 536 } 537 return hasDigits && ch !== '_'; 538 } 539 540 541 if (ch === 'x') { 542 // base 16 543 index++; 544 545 for (; index < max; index++) { 546 ch = data[index]; 547 if (ch === '_') continue; 548 if (!isHexCode(data.charCodeAt(index))) return false; 549 hasDigits = true; 550 } 551 return hasDigits && ch !== '_'; 552 } 553 554 555 if (ch === 'o') { 556 // base 8 557 index++; 558 559 for (; index < max; index++) { 560 ch = data[index]; 561 if (ch === '_') continue; 562 if (!isOctCode(data.charCodeAt(index))) return false; 563 hasDigits = true; 564 } 565 return hasDigits && ch !== '_'; 566 } 567 } 568 569 // base 10 (except 0) 570 571 // value should not start with `_`; 572 if (ch === '_') return false; 573 574 for (; index < max; index++) { 575 ch = data[index]; 576 if (ch === '_') continue; 577 if (!isDecCode(data.charCodeAt(index))) { 578 return false; 579 } 580 hasDigits = true; 581 } 582 583 // Should have digits and should not end with `_` 584 if (!hasDigits || ch === '_') return false; 585 586 return true; 587} 588 589function constructYamlInteger(data) { 590 var value = data, sign = 1, ch; 591 592 if (value.indexOf('_') !== -1) { 593 value = value.replace(/_/g, ''); 594 } 595 596 ch = value[0]; 597 598 if (ch === '-' || ch === '+') { 599 if (ch === '-') sign = -1; 600 value = value.slice(1); 601 ch = value[0]; 602 } 603 604 if (value === '0') return 0; 605 606 if (ch === '0') { 607 if (value[1] === 'b') return sign * parseInt(value.slice(2), 2); 608 if (value[1] === 'x') return sign * parseInt(value.slice(2), 16); 609 if (value[1] === 'o') return sign * parseInt(value.slice(2), 8); 610 } 611 612 return sign * parseInt(value, 10); 613} 614 615function isInteger(object) { 616 return (Object.prototype.toString.call(object)) === '[object Number]' && 617 (object % 1 === 0 && !common.isNegativeZero(object)); 618} 619 620var int = new type('tag:yaml.org,2002:int', { 621 kind: 'scalar', 622 resolve: resolveYamlInteger, 623 construct: constructYamlInteger, 624 predicate: isInteger, 625 represent: { 626 binary: function (obj) { return obj >= 0 ? '0b' + obj.toString(2) : '-0b' + obj.toString(2).slice(1); }, 627 octal: function (obj) { return obj >= 0 ? '0o' + obj.toString(8) : '-0o' + obj.toString(8).slice(1); }, 628 decimal: function (obj) { return obj.toString(10); }, 629 /* eslint-disable max-len */ 630 hexadecimal: function (obj) { return obj >= 0 ? '0x' + obj.toString(16).toUpperCase() : '-0x' + obj.toString(16).toUpperCase().slice(1); } 631 }, 632 defaultStyle: 'decimal', 633 styleAliases: { 634 binary: [ 2, 'bin' ], 635 octal: [ 8, 'oct' ], 636 decimal: [ 10, 'dec' ], 637 hexadecimal: [ 16, 'hex' ] 638 } 639}); 640 641var YAML_FLOAT_PATTERN = new RegExp( 642 // 2.5e4, 2.5 and integers 643 '^(?:[-+]?(?:[0-9][0-9_]*)(?:\\.[0-9_]*)?(?:[eE][-+]?[0-9]+)?' + 644 // .2e4, .2 645 // special case, seems not from spec 646 '|\\.[0-9_]+(?:[eE][-+]?[0-9]+)?' + 647 // .inf 648 '|[-+]?\\.(?:inf|Inf|INF)' + 649 // .nan 650 '|\\.(?:nan|NaN|NAN))$'); 651 652function resolveYamlFloat(data) { 653 if (data === null) return false; 654 655 if (!YAML_FLOAT_PATTERN.test(data) || 656 // Quick hack to not allow integers end with `_` 657 // Probably should update regexp & check speed 658 data[data.length - 1] === '_') { 659 return false; 660 } 661 662 return true; 663} 664 665function constructYamlFloat(data) { 666 var value, sign; 667 668 value = data.replace(/_/g, '').toLowerCase(); 669 sign = value[0] === '-' ? -1 : 1; 670 671 if ('+-'.indexOf(value[0]) >= 0) { 672 value = value.slice(1); 673 } 674 675 if (value === '.inf') { 676 return (sign === 1) ? Number.POSITIVE_INFINITY : Number.NEGATIVE_INFINITY; 677 678 } else if (value === '.nan') { 679 return NaN; 680 } 681 return sign * parseFloat(value, 10); 682} 683 684 685var SCIENTIFIC_WITHOUT_DOT = /^[-+]?[0-9]+e/; 686 687function representYamlFloat(object, style) { 688 var res; 689 690 if (isNaN(object)) { 691 switch (style) { 692 case 'lowercase': return '.nan'; 693 case 'uppercase': return '.NAN'; 694 case 'camelcase': return '.NaN'; 695 } 696 } else if (Number.POSITIVE_INFINITY === object) { 697 switch (style) { 698 case 'lowercase': return '.inf'; 699 case 'uppercase': return '.INF'; 700 case 'camelcase': return '.Inf'; 701 } 702 } else if (Number.NEGATIVE_INFINITY === object) { 703 switch (style) { 704 case 'lowercase': return '-.inf'; 705 case 'uppercase': return '-.INF'; 706 case 'camelcase': return '-.Inf'; 707 } 708 } else if (common.isNegativeZero(object)) { 709 return '-0.0'; 710 } 711 712 res = object.toString(10); 713 714 // JS stringifier can build scientific format without dots: 5e-100, 715 // while YAML requres dot: 5.e-100. Fix it with simple hack 716 717 return SCIENTIFIC_WITHOUT_DOT.test(res) ? res.replace('e', '.e') : res; 718} 719 720function isFloat(object) { 721 return (Object.prototype.toString.call(object) === '[object Number]') && 722 (object % 1 !== 0 || common.isNegativeZero(object)); 723} 724 725var float = new type('tag:yaml.org,2002:float', { 726 kind: 'scalar', 727 resolve: resolveYamlFloat, 728 construct: constructYamlFloat, 729 predicate: isFloat, 730 represent: representYamlFloat, 731 defaultStyle: 'lowercase' 732}); 733 734var json = failsafe.extend({ 735 implicit: [ 736 _null, 737 bool, 738 int, 739 float 740 ] 741}); 742 743var core = json; 744 745var YAML_DATE_REGEXP = new RegExp( 746 '^([0-9][0-9][0-9][0-9])' + // [1] year 747 '-([0-9][0-9])' + // [2] month 748 '-([0-9][0-9])$'); // [3] day 749 750var YAML_TIMESTAMP_REGEXP = new RegExp( 751 '^([0-9][0-9][0-9][0-9])' + // [1] year 752 '-([0-9][0-9]?)' + // [2] month 753 '-([0-9][0-9]?)' + // [3] day 754 '(?:[Tt]|[ \\t]+)' + // ... 755 '([0-9][0-9]?)' + // [4] hour 756 ':([0-9][0-9])' + // [5] minute 757 ':([0-9][0-9])' + // [6] second 758 '(?:\\.([0-9]*))?' + // [7] fraction 759 '(?:[ \\t]*(Z|([-+])([0-9][0-9]?)' + // [8] tz [9] tz_sign [10] tz_hour 760 '(?::([0-9][0-9]))?))?$'); // [11] tz_minute 761 762function resolveYamlTimestamp(data) { 763 if (data === null) return false; 764 if (YAML_DATE_REGEXP.exec(data) !== null) return true; 765 if (YAML_TIMESTAMP_REGEXP.exec(data) !== null) return true; 766 return false; 767} 768 769function constructYamlTimestamp(data) { 770 var match, year, month, day, hour, minute, second, fraction = 0, 771 delta = null, tz_hour, tz_minute, date; 772 773 match = YAML_DATE_REGEXP.exec(data); 774 if (match === null) match = YAML_TIMESTAMP_REGEXP.exec(data); 775 776 if (match === null) throw new Error('Date resolve error'); 777 778 // match: [1] year [2] month [3] day 779 780 year = +(match[1]); 781 month = +(match[2]) - 1; // JS month starts with 0 782 day = +(match[3]); 783 784 if (!match[4]) { // no hour 785 return new Date(Date.UTC(year, month, day)); 786 } 787 788 // match: [4] hour [5] minute [6] second [7] fraction 789 790 hour = +(match[4]); 791 minute = +(match[5]); 792 second = +(match[6]); 793 794 if (match[7]) { 795 fraction = match[7].slice(0, 3); 796 while (fraction.length < 3) { // milli-seconds 797 fraction += '0'; 798 } 799 fraction = +fraction; 800 } 801 802 // match: [8] tz [9] tz_sign [10] tz_hour [11] tz_minute 803 804 if (match[9]) { 805 tz_hour = +(match[10]); 806 tz_minute = +(match[11] || 0); 807 delta = (tz_hour * 60 + tz_minute) * 60000; // delta in mili-seconds 808 if (match[9] === '-') delta = -delta; 809 } 810 811 date = new Date(Date.UTC(year, month, day, hour, minute, second, fraction)); 812 813 if (delta) date.setTime(date.getTime() - delta); 814 815 return date; 816} 817 818function representYamlTimestamp(object /*, style*/) { 819 return object.toISOString(); 820} 821 822var timestamp = new type('tag:yaml.org,2002:timestamp', { 823 kind: 'scalar', 824 resolve: resolveYamlTimestamp, 825 construct: constructYamlTimestamp, 826 instanceOf: Date, 827 represent: representYamlTimestamp 828}); 829 830function resolveYamlMerge(data) { 831 return data === '<<' || data === null; 832} 833 834var merge = new type('tag:yaml.org,2002:merge', { 835 kind: 'scalar', 836 resolve: resolveYamlMerge 837}); 838 839/*eslint-disable no-bitwise*/ 840 841 842 843 844 845// [ 64, 65, 66 ] -> [ padding, CR, LF ] 846var BASE64_MAP = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=\n\r'; 847 848 849function resolveYamlBinary(data) { 850 if (data === null) return false; 851 852 var code, idx, bitlen = 0, max = data.length, map = BASE64_MAP; 853 854 // Convert one by one. 855 for (idx = 0; idx < max; idx++) { 856 code = map.indexOf(data.charAt(idx)); 857 858 // Skip CR/LF 859 if (code > 64) continue; 860 861 // Fail on illegal characters 862 if (code < 0) return false; 863 864 bitlen += 6; 865 } 866 867 // If there are any bits left, source was corrupted 868 return (bitlen % 8) === 0; 869} 870 871function constructYamlBinary(data) { 872 var idx, tailbits, 873 input = data.replace(/[\r\n=]/g, ''), // remove CR/LF & padding to simplify scan 874 max = input.length, 875 map = BASE64_MAP, 876 bits = 0, 877 result = []; 878 879 // Collect by 6*4 bits (3 bytes) 880 881 for (idx = 0; idx < max; idx++) { 882 if ((idx % 4 === 0) && idx) { 883 result.push((bits >> 16) & 0xFF); 884 result.push((bits >> 8) & 0xFF); 885 result.push(bits & 0xFF); 886 } 887 888 bits = (bits << 6) | map.indexOf(input.charAt(idx)); 889 } 890 891 // Dump tail 892 893 tailbits = (max % 4) * 6; 894 895 if (tailbits === 0) { 896 result.push((bits >> 16) & 0xFF); 897 result.push((bits >> 8) & 0xFF); 898 result.push(bits & 0xFF); 899 } else if (tailbits === 18) { 900 result.push((bits >> 10) & 0xFF); 901 result.push((bits >> 2) & 0xFF); 902 } else if (tailbits === 12) { 903 result.push((bits >> 4) & 0xFF); 904 } 905 906 return new Uint8Array(result); 907} 908 909function representYamlBinary(object /*, style*/) { 910 var result = '', bits = 0, idx, tail, 911 max = object.length, 912 map = BASE64_MAP; 913 914 // Convert every three bytes to 4 ASCII characters. 915 916 for (idx = 0; idx < max; idx++) { 917 if ((idx % 3 === 0) && idx) { 918 result += map[(bits >> 18) & 0x3F]; 919 result += map[(bits >> 12) & 0x3F]; 920 result += map[(bits >> 6) & 0x3F]; 921 result += map[bits & 0x3F]; 922 } 923 924 bits = (bits << 8) + object[idx]; 925 } 926 927 // Dump tail 928 929 tail = max % 3; 930 931 if (tail === 0) { 932 result += map[(bits >> 18) & 0x3F]; 933 result += map[(bits >> 12) & 0x3F]; 934 result += map[(bits >> 6) & 0x3F]; 935 result += map[bits & 0x3F]; 936 } else if (tail === 2) { 937 result += map[(bits >> 10) & 0x3F]; 938 result += map[(bits >> 4) & 0x3F]; 939 result += map[(bits << 2) & 0x3F]; 940 result += map[64]; 941 } else if (tail === 1) { 942 result += map[(bits >> 2) & 0x3F]; 943 result += map[(bits << 4) & 0x3F]; 944 result += map[64]; 945 result += map[64]; 946 } 947 948 return result; 949} 950 951function isBinary(obj) { 952 return Object.prototype.toString.call(obj) === '[object Uint8Array]'; 953} 954 955var binary = new type('tag:yaml.org,2002:binary', { 956 kind: 'scalar', 957 resolve: resolveYamlBinary, 958 construct: constructYamlBinary, 959 predicate: isBinary, 960 represent: representYamlBinary 961}); 962 963var _hasOwnProperty$3 = Object.prototype.hasOwnProperty; 964var _toString$2 = Object.prototype.toString; 965 966function resolveYamlOmap(data) { 967 if (data === null) return true; 968 969 var objectKeys = [], index, length, pair, pairKey, pairHasKey, 970 object = data; 971 972 for (index = 0, length = object.length; index < length; index += 1) { 973 pair = object[index]; 974 pairHasKey = false; 975 976 if (_toString$2.call(pair) !== '[object Object]') return false; 977 978 for (pairKey in pair) { 979 if (_hasOwnProperty$3.call(pair, pairKey)) { 980 if (!pairHasKey) pairHasKey = true; 981 else return false; 982 } 983 } 984 985 if (!pairHasKey) return false; 986 987 if (objectKeys.indexOf(pairKey) === -1) objectKeys.push(pairKey); 988 else return false; 989 } 990 991 return true; 992} 993 994function constructYamlOmap(data) { 995 return data !== null ? data : []; 996} 997 998var omap = new type('tag:yaml.org,2002:omap', { 999 kind: 'sequence', 1000 resolve: resolveYamlOmap, 1001 construct: constructYamlOmap 1002}); 1003 1004var _toString$1 = Object.prototype.toString; 1005 1006function resolveYamlPairs(data) { 1007 if (data === null) return true; 1008 1009 var index, length, pair, keys, result, 1010 object = data; 1011 1012 result = new Array(object.length); 1013 1014 for (index = 0, length = object.length; index < length; index += 1) { 1015 pair = object[index]; 1016 1017 if (_toString$1.call(pair) !== '[object Object]') return false; 1018 1019 keys = Object.keys(pair); 1020 1021 if (keys.length !== 1) return false; 1022 1023 result[index] = [ keys[0], pair[keys[0]] ]; 1024 } 1025 1026 return true; 1027} 1028 1029function constructYamlPairs(data) { 1030 if (data === null) return []; 1031 1032 var index, length, pair, keys, result, 1033 object = data; 1034 1035 result = new Array(object.length); 1036 1037 for (index = 0, length = object.length; index < length; index += 1) { 1038 pair = object[index]; 1039 1040 keys = Object.keys(pair); 1041 1042 result[index] = [ keys[0], pair[keys[0]] ]; 1043 } 1044 1045 return result; 1046} 1047 1048var pairs = new type('tag:yaml.org,2002:pairs', { 1049 kind: 'sequence', 1050 resolve: resolveYamlPairs, 1051 construct: constructYamlPairs 1052}); 1053 1054var _hasOwnProperty$2 = Object.prototype.hasOwnProperty; 1055 1056function resolveYamlSet(data) { 1057 if (data === null) return true; 1058 1059 var key, object = data; 1060 1061 for (key in object) { 1062 if (_hasOwnProperty$2.call(object, key)) { 1063 if (object[key] !== null) return false; 1064 } 1065 } 1066 1067 return true; 1068} 1069 1070function constructYamlSet(data) { 1071 return data !== null ? data : {}; 1072} 1073 1074var set = new type('tag:yaml.org,2002:set', { 1075 kind: 'mapping', 1076 resolve: resolveYamlSet, 1077 construct: constructYamlSet 1078}); 1079 1080var _default = core.extend({ 1081 implicit: [ 1082 timestamp, 1083 merge 1084 ], 1085 explicit: [ 1086 binary, 1087 omap, 1088 pairs, 1089 set 1090 ] 1091}); 1092 1093/*eslint-disable max-len,no-use-before-define*/ 1094 1095 1096 1097 1098 1099 1100 1101var _hasOwnProperty$1 = Object.prototype.hasOwnProperty; 1102 1103 1104var CONTEXT_FLOW_IN = 1; 1105var CONTEXT_FLOW_OUT = 2; 1106var CONTEXT_BLOCK_IN = 3; 1107var CONTEXT_BLOCK_OUT = 4; 1108 1109 1110var CHOMPING_CLIP = 1; 1111var CHOMPING_STRIP = 2; 1112var CHOMPING_KEEP = 3; 1113 1114 1115var PATTERN_NON_PRINTABLE = /[\x00-\x08\x0B\x0C\x0E-\x1F\x7F-\x84\x86-\x9F\uFFFE\uFFFF]|[\uD800-\uDBFF](?![\uDC00-\uDFFF])|(?:[^\uD800-\uDBFF]|^)[\uDC00-\uDFFF]/; 1116var PATTERN_NON_ASCII_LINE_BREAKS = /[\x85\u2028\u2029]/; 1117var PATTERN_FLOW_INDICATORS = /[,\[\]\{\}]/; 1118var PATTERN_TAG_HANDLE = /^(?:!|!!|![a-z\-]+!)$/i; 1119var PATTERN_TAG_URI = /^(?:!|[^,\[\]\{\}])(?:%[0-9a-f]{2}|[0-9a-z\-#;\/\?:@&=\+\$,_\.!~\*'\(\)\[\]])*$/i; 1120 1121 1122function _class(obj) { return Object.prototype.toString.call(obj); } 1123 1124function is_EOL(c) { 1125 return (c === 0x0A/* LF */) || (c === 0x0D/* CR */); 1126} 1127 1128function is_WHITE_SPACE(c) { 1129 return (c === 0x09/* Tab */) || (c === 0x20/* Space */); 1130} 1131 1132function is_WS_OR_EOL(c) { 1133 return (c === 0x09/* Tab */) || 1134 (c === 0x20/* Space */) || 1135 (c === 0x0A/* LF */) || 1136 (c === 0x0D/* CR */); 1137} 1138 1139function is_FLOW_INDICATOR(c) { 1140 return c === 0x2C/* , */ || 1141 c === 0x5B/* [ */ || 1142 c === 0x5D/* ] */ || 1143 c === 0x7B/* { */ || 1144 c === 0x7D/* } */; 1145} 1146 1147function fromHexCode(c) { 1148 var lc; 1149 1150 if ((0x30/* 0 */ <= c) && (c <= 0x39/* 9 */)) { 1151 return c - 0x30; 1152 } 1153 1154 /*eslint-disable no-bitwise*/ 1155 lc = c | 0x20; 1156 1157 if ((0x61/* a */ <= lc) && (lc <= 0x66/* f */)) { 1158 return lc - 0x61 + 10; 1159 } 1160 1161 return -1; 1162} 1163 1164function escapedHexLen(c) { 1165 if (c === 0x78/* x */) { return 2; } 1166 if (c === 0x75/* u */) { return 4; } 1167 if (c === 0x55/* U */) { return 8; } 1168 return 0; 1169} 1170 1171function fromDecimalCode(c) { 1172 if ((0x30/* 0 */ <= c) && (c <= 0x39/* 9 */)) { 1173 return c - 0x30; 1174 } 1175 1176 return -1; 1177} 1178 1179function simpleEscapeSequence(c) { 1180 /* eslint-disable indent */ 1181 return (c === 0x30/* 0 */) ? '\x00' : 1182 (c === 0x61/* a */) ? '\x07' : 1183 (c === 0x62/* b */) ? '\x08' : 1184 (c === 0x74/* t */) ? '\x09' : 1185 (c === 0x09/* Tab */) ? '\x09' : 1186 (c === 0x6E/* n */) ? '\x0A' : 1187 (c === 0x76/* v */) ? '\x0B' : 1188 (c === 0x66/* f */) ? '\x0C' : 1189 (c === 0x72/* r */) ? '\x0D' : 1190 (c === 0x65/* e */) ? '\x1B' : 1191 (c === 0x20/* Space */) ? ' ' : 1192 (c === 0x22/* " */) ? '\x22' : 1193 (c === 0x2F/* / */) ? '/' : 1194 (c === 0x5C/* \ */) ? '\x5C' : 1195 (c === 0x4E/* N */) ? '\x85' : 1196 (c === 0x5F/* _ */) ? '\xA0' : 1197 (c === 0x4C/* L */) ? '\u2028' : 1198 (c === 0x50/* P */) ? '\u2029' : ''; 1199} 1200 1201function charFromCodepoint(c) { 1202 if (c <= 0xFFFF) { 1203 return String.fromCharCode(c); 1204 } 1205 // Encode UTF-16 surrogate pair 1206 // https://en.wikipedia.org/wiki/UTF-16#Code_points_U.2B010000_to_U.2B10FFFF 1207 return String.fromCharCode( 1208 ((c - 0x010000) >> 10) + 0xD800, 1209 ((c - 0x010000) & 0x03FF) + 0xDC00 1210 ); 1211} 1212 1213var simpleEscapeCheck = new Array(256); // integer, for fast access 1214var simpleEscapeMap = new Array(256); 1215for (var i = 0; i < 256; i++) { 1216 simpleEscapeCheck[i] = simpleEscapeSequence(i) ? 1 : 0; 1217 simpleEscapeMap[i] = simpleEscapeSequence(i); 1218} 1219 1220 1221function State$1(input, options) { 1222 this.input = input; 1223 1224 this.filename = options['filename'] || null; 1225 this.schema = options['schema'] || _default; 1226 this.onWarning = options['onWarning'] || null; 1227 // (Hidden) Remove? makes the loader to expect YAML 1.1 documents 1228 // if such documents have no explicit %YAML directive 1229 this.legacy = options['legacy'] || false; 1230 1231 this.json = options['json'] || false; 1232 this.listener = options['listener'] || null; 1233 1234 this.implicitTypes = this.schema.compiledImplicit; 1235 this.typeMap = this.schema.compiledTypeMap; 1236 1237 this.length = input.length; 1238 this.position = 0; 1239 this.line = 0; 1240 this.lineStart = 0; 1241 this.lineIndent = 0; 1242 1243 // position of first leading tab in the current line, 1244 // used to make sure there are no tabs in the indentation 1245 this.firstTabInLine = -1; 1246 1247 this.documents = []; 1248 1249 /* 1250 this.version; 1251 this.checkLineBreaks; 1252 this.tagMap; 1253 this.anchorMap; 1254 this.tag; 1255 this.anchor; 1256 this.kind; 1257 this.result;*/ 1258 1259} 1260 1261 1262function generateError(state, message) { 1263 var mark = { 1264 name: state.filename, 1265 buffer: state.input.slice(0, -1), // omit trailing \0 1266 position: state.position, 1267 line: state.line, 1268 column: state.position - state.lineStart 1269 }; 1270 1271 mark.snippet = snippet(mark); 1272 1273 return new exception(message, mark); 1274} 1275 1276function throwError(state, message) { 1277 throw generateError(state, message); 1278} 1279 1280function throwWarning(state, message) { 1281 if (state.onWarning) { 1282 state.onWarning.call(null, generateError(state, message)); 1283 } 1284} 1285 1286 1287var directiveHandlers = { 1288 1289 YAML: function handleYamlDirective(state, name, args) { 1290 1291 var match, major, minor; 1292 1293 if (state.version !== null) { 1294 throwError(state, 'duplication of %YAML directive'); 1295 } 1296 1297 if (args.length !== 1) { 1298 throwError(state, 'YAML directive accepts exactly one argument'); 1299 } 1300 1301 match = /^([0-9]+)\.([0-9]+)$/.exec(args[0]); 1302 1303 if (match === null) { 1304 throwError(state, 'ill-formed argument of the YAML directive'); 1305 } 1306 1307 major = parseInt(match[1], 10); 1308 minor = parseInt(match[2], 10); 1309 1310 if (major !== 1) { 1311 throwError(state, 'unacceptable YAML version of the document'); 1312 } 1313 1314 state.version = args[0]; 1315 state.checkLineBreaks = (minor < 2); 1316 1317 if (minor !== 1 && minor !== 2) { 1318 throwWarning(state, 'unsupported YAML version of the document'); 1319 } 1320 }, 1321 1322 TAG: function handleTagDirective(state, name, args) { 1323 1324 var handle, prefix; 1325 1326 if (args.length !== 2) { 1327 throwError(state, 'TAG directive accepts exactly two arguments'); 1328 } 1329 1330 handle = args[0]; 1331 prefix = args[1]; 1332 1333 if (!PATTERN_TAG_HANDLE.test(handle)) { 1334 throwError(state, 'ill-formed tag handle (first argument) of the TAG directive'); 1335 } 1336 1337 if (_hasOwnProperty$1.call(state.tagMap, handle)) { 1338 throwError(state, 'there is a previously declared suffix for "' + handle + '" tag handle'); 1339 } 1340 1341 if (!PATTERN_TAG_URI.test(prefix)) { 1342 throwError(state, 'ill-formed tag prefix (second argument) of the TAG directive'); 1343 } 1344 1345 try { 1346 prefix = decodeURIComponent(prefix); 1347 } catch (err) { 1348 throwError(state, 'tag prefix is malformed: ' + prefix); 1349 } 1350 1351 state.tagMap[handle] = prefix; 1352 } 1353}; 1354 1355 1356function captureSegment(state, start, end, checkJson) { 1357 var _position, _length, _character, _result; 1358 1359 if (start < end) { 1360 _result = state.input.slice(start, end); 1361 1362 if (checkJson) { 1363 for (_position = 0, _length = _result.length; _position < _length; _position += 1) { 1364 _character = _result.charCodeAt(_position); 1365 if (!(_character === 0x09 || 1366 (0x20 <= _character && _character <= 0x10FFFF))) { 1367 throwError(state, 'expected valid JSON character'); 1368 } 1369 } 1370 } else if (PATTERN_NON_PRINTABLE.test(_result)) { 1371 throwError(state, 'the stream contains non-printable characters'); 1372 } 1373 1374 state.result += _result; 1375 } 1376} 1377 1378function mergeMappings(state, destination, source, overridableKeys) { 1379 var sourceKeys, key, index, quantity; 1380 1381 if (!common.isObject(source)) { 1382 throwError(state, 'cannot merge mappings; the provided source object is unacceptable'); 1383 } 1384 1385 sourceKeys = Object.keys(source); 1386 1387 for (index = 0, quantity = sourceKeys.length; index < quantity; index += 1) { 1388 key = sourceKeys[index]; 1389 1390 if (!_hasOwnProperty$1.call(destination, key)) { 1391 destination[key] = source[key]; 1392 overridableKeys[key] = true; 1393 } 1394 } 1395} 1396 1397function storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, valueNode, 1398 startLine, startLineStart, startPos) { 1399 1400 var index, quantity; 1401 1402 // The output is a plain object here, so keys can only be strings. 1403 // We need to convert keyNode to a string, but doing so can hang the process 1404 // (deeply nested arrays that explode exponentially using aliases). 1405 if (Array.isArray(keyNode)) { 1406 keyNode = Array.prototype.slice.call(keyNode); 1407 1408 for (index = 0, quantity = keyNode.length; index < quantity; index += 1) { 1409 if (Array.isArray(keyNode[index])) { 1410 throwError(state, 'nested arrays are not supported inside keys'); 1411 } 1412 1413 if (typeof keyNode === 'object' && _class(keyNode[index]) === '[object Object]') { 1414 keyNode[index] = '[object Object]'; 1415 } 1416 } 1417 } 1418 1419 // Avoid code execution in load() via toString property 1420 // (still use its own toString for arrays, timestamps, 1421 // and whatever user schema extensions happen to have @@toStringTag) 1422 if (typeof keyNode === 'object' && _class(keyNode) === '[object Object]') { 1423 keyNode = '[object Object]'; 1424 } 1425 1426 1427 keyNode = String(keyNode); 1428 1429 if (_result === null) { 1430 _result = {}; 1431 } 1432 1433 if (keyTag === 'tag:yaml.org,2002:merge') { 1434 if (Array.isArray(valueNode)) { 1435 for (index = 0, quantity = valueNode.length; index < quantity; index += 1) { 1436 mergeMappings(state, _result, valueNode[index], overridableKeys); 1437 } 1438 } else { 1439 mergeMappings(state, _result, valueNode, overridableKeys); 1440 } 1441 } else { 1442 if (!state.json && 1443 !_hasOwnProperty$1.call(overridableKeys, keyNode) && 1444 _hasOwnProperty$1.call(_result, keyNode)) { 1445 state.line = startLine || state.line; 1446 state.lineStart = startLineStart || state.lineStart; 1447 state.position = startPos || state.position; 1448 throwError(state, 'duplicated mapping key'); 1449 } 1450 1451 // used for this specific key only because Object.defineProperty is slow 1452 if (keyNode === '__proto__') { 1453 Object.defineProperty(_result, keyNode, { 1454 configurable: true, 1455 enumerable: true, 1456 writable: true, 1457 value: valueNode 1458 }); 1459 } else { 1460 _result[keyNode] = valueNode; 1461 } 1462 delete overridableKeys[keyNode]; 1463 } 1464 1465 return _result; 1466} 1467 1468function readLineBreak(state) { 1469 var ch; 1470 1471 ch = state.input.charCodeAt(state.position); 1472 1473 if (ch === 0x0A/* LF */) { 1474 state.position++; 1475 } else if (ch === 0x0D/* CR */) { 1476 state.position++; 1477 if (state.input.charCodeAt(state.position) === 0x0A/* LF */) { 1478 state.position++; 1479 } 1480 } else { 1481 throwError(state, 'a line break is expected'); 1482 } 1483 1484 state.line += 1; 1485 state.lineStart = state.position; 1486 state.firstTabInLine = -1; 1487} 1488 1489function skipSeparationSpace(state, allowComments, checkIndent) { 1490 var lineBreaks = 0, 1491 ch = state.input.charCodeAt(state.position); 1492 1493 while (ch !== 0) { 1494 while (is_WHITE_SPACE(ch)) { 1495 if (ch === 0x09/* Tab */ && state.firstTabInLine === -1) { 1496 state.firstTabInLine = state.position; 1497 } 1498 ch = state.input.charCodeAt(++state.position); 1499 } 1500 1501 if (allowComments && ch === 0x23/* # */) { 1502 do { 1503 ch = state.input.charCodeAt(++state.position); 1504 } while (ch !== 0x0A/* LF */ && ch !== 0x0D/* CR */ && ch !== 0); 1505 } 1506 1507 if (is_EOL(ch)) { 1508 readLineBreak(state); 1509 1510 ch = state.input.charCodeAt(state.position); 1511 lineBreaks++; 1512 state.lineIndent = 0; 1513 1514 while (ch === 0x20/* Space */) { 1515 state.lineIndent++; 1516 ch = state.input.charCodeAt(++state.position); 1517 } 1518 } else { 1519 break; 1520 } 1521 } 1522 1523 if (checkIndent !== -1 && lineBreaks !== 0 && state.lineIndent < checkIndent) { 1524 throwWarning(state, 'deficient indentation'); 1525 } 1526 1527 return lineBreaks; 1528} 1529 1530function testDocumentSeparator(state) { 1531 var _position = state.position, 1532 ch; 1533 1534 ch = state.input.charCodeAt(_position); 1535 1536 // Condition state.position === state.lineStart is tested 1537 // in parent on each call, for efficiency. No needs to test here again. 1538 if ((ch === 0x2D/* - */ || ch === 0x2E/* . */) && 1539 ch === state.input.charCodeAt(_position + 1) && 1540 ch === state.input.charCodeAt(_position + 2)) { 1541 1542 _position += 3; 1543 1544 ch = state.input.charCodeAt(_position); 1545 1546 if (ch === 0 || is_WS_OR_EOL(ch)) { 1547 return true; 1548 } 1549 } 1550 1551 return false; 1552} 1553 1554function writeFoldedLines(state, count) { 1555 if (count === 1) { 1556 state.result += ' '; 1557 } else if (count > 1) { 1558 state.result += common.repeat('\n', count - 1); 1559 } 1560} 1561 1562 1563function readPlainScalar(state, nodeIndent, withinFlowCollection) { 1564 var preceding, 1565 following, 1566 captureStart, 1567 captureEnd, 1568 hasPendingContent, 1569 _line, 1570 _lineStart, 1571 _lineIndent, 1572 _kind = state.kind, 1573 _result = state.result, 1574 ch; 1575 1576 ch = state.input.charCodeAt(state.position); 1577 1578 if (is_WS_OR_EOL(ch) || 1579 is_FLOW_INDICATOR(ch) || 1580 ch === 0x23/* # */ || 1581 ch === 0x26/* & */ || 1582 ch === 0x2A/* * */ || 1583 ch === 0x21/* ! */ || 1584 ch === 0x7C/* | */ || 1585 ch === 0x3E/* > */ || 1586 ch === 0x27/* ' */ || 1587 ch === 0x22/* " */ || 1588 ch === 0x25/* % */ || 1589 ch === 0x40/* @ */ || 1590 ch === 0x60/* ` */) { 1591 return false; 1592 } 1593 1594 if (ch === 0x3F/* ? */ || ch === 0x2D/* - */) { 1595 following = state.input.charCodeAt(state.position + 1); 1596 1597 if (is_WS_OR_EOL(following) || 1598 withinFlowCollection && is_FLOW_INDICATOR(following)) { 1599 return false; 1600 } 1601 } 1602 1603 state.kind = 'scalar'; 1604 state.result = ''; 1605 captureStart = captureEnd = state.position; 1606 hasPendingContent = false; 1607 1608 while (ch !== 0) { 1609 if (ch === 0x3A/* : */) { 1610 following = state.input.charCodeAt(state.position + 1); 1611 1612 if (is_WS_OR_EOL(following) || 1613 withinFlowCollection && is_FLOW_INDICATOR(following)) { 1614 break; 1615 } 1616 1617 } else if (ch === 0x23/* # */) { 1618 preceding = state.input.charCodeAt(state.position - 1); 1619 1620 if (is_WS_OR_EOL(preceding)) { 1621 break; 1622 } 1623 1624 } else if ((state.position === state.lineStart && testDocumentSeparator(state)) || 1625 withinFlowCollection && is_FLOW_INDICATOR(ch)) { 1626 break; 1627 1628 } else if (is_EOL(ch)) { 1629 _line = state.line; 1630 _lineStart = state.lineStart; 1631 _lineIndent = state.lineIndent; 1632 skipSeparationSpace(state, false, -1); 1633 1634 if (state.lineIndent >= nodeIndent) { 1635 hasPendingContent = true; 1636 ch = state.input.charCodeAt(state.position); 1637 continue; 1638 } else { 1639 state.position = captureEnd; 1640 state.line = _line; 1641 state.lineStart = _lineStart; 1642 state.lineIndent = _lineIndent; 1643 break; 1644 } 1645 } 1646 1647 if (hasPendingContent) { 1648 captureSegment(state, captureStart, captureEnd, false); 1649 writeFoldedLines(state, state.line - _line); 1650 captureStart = captureEnd = state.position; 1651 hasPendingContent = false; 1652 } 1653 1654 if (!is_WHITE_SPACE(ch)) { 1655 captureEnd = state.position + 1; 1656 } 1657 1658 ch = state.input.charCodeAt(++state.position); 1659 } 1660 1661 captureSegment(state, captureStart, captureEnd, false); 1662 1663 if (state.result) { 1664 return true; 1665 } 1666 1667 state.kind = _kind; 1668 state.result = _result; 1669 return false; 1670} 1671 1672function readSingleQuotedScalar(state, nodeIndent) { 1673 var ch, 1674 captureStart, captureEnd; 1675 1676 ch = state.input.charCodeAt(state.position); 1677 1678 if (ch !== 0x27/* ' */) { 1679 return false; 1680 } 1681 1682 state.kind = 'scalar'; 1683 state.result = ''; 1684 state.position++; 1685 captureStart = captureEnd = state.position; 1686 1687 while ((ch = state.input.charCodeAt(state.position)) !== 0) { 1688 if (ch === 0x27/* ' */) { 1689 captureSegment(state, captureStart, state.position, true); 1690 ch = state.input.charCodeAt(++state.position); 1691 1692 if (ch === 0x27/* ' */) { 1693 captureStart = state.position; 1694 state.position++; 1695 captureEnd = state.position; 1696 } else { 1697 return true; 1698 } 1699 1700 } else if (is_EOL(ch)) { 1701 captureSegment(state, captureStart, captureEnd, true); 1702 writeFoldedLines(state, skipSeparationSpace(state, false, nodeIndent)); 1703 captureStart = captureEnd = state.position; 1704 1705 } else if (state.position === state.lineStart && testDocumentSeparator(state)) { 1706 throwError(state, 'unexpected end of the document within a single quoted scalar'); 1707 1708 } else { 1709 state.position++; 1710 captureEnd = state.position; 1711 } 1712 } 1713 1714 throwError(state, 'unexpected end of the stream within a single quoted scalar'); 1715} 1716 1717function readDoubleQuotedScalar(state, nodeIndent) { 1718 var captureStart, 1719 captureEnd, 1720 hexLength, 1721 hexResult, 1722 tmp, 1723 ch; 1724 1725 ch = state.input.charCodeAt(state.position); 1726 1727 if (ch !== 0x22/* " */) { 1728 return false; 1729 } 1730 1731 state.kind = 'scalar'; 1732 state.result = ''; 1733 state.position++; 1734 captureStart = captureEnd = state.position; 1735 1736 while ((ch = state.input.charCodeAt(state.position)) !== 0) { 1737 if (ch === 0x22/* " */) { 1738 captureSegment(state, captureStart, state.position, true); 1739 state.position++; 1740 return true; 1741 1742 } else if (ch === 0x5C/* \ */) { 1743 captureSegment(state, captureStart, state.position, true); 1744 ch = state.input.charCodeAt(++state.position); 1745 1746 if (is_EOL(ch)) { 1747 skipSeparationSpace(state, false, nodeIndent); 1748 1749 // TODO: rework to inline fn with no type cast? 1750 } else if (ch < 256 && simpleEscapeCheck[ch]) { 1751 state.result += simpleEscapeMap[ch]; 1752 state.position++; 1753 1754 } else if ((tmp = escapedHexLen(ch)) > 0) { 1755 hexLength = tmp; 1756 hexResult = 0; 1757 1758 for (; hexLength > 0; hexLength--) { 1759 ch = state.input.charCodeAt(++state.position); 1760 1761 if ((tmp = fromHexCode(ch)) >= 0) { 1762 hexResult = (hexResult << 4) + tmp; 1763 1764 } else { 1765 throwError(state, 'expected hexadecimal character'); 1766 } 1767 } 1768 1769 state.result += charFromCodepoint(hexResult); 1770 1771 state.position++; 1772 1773 } else { 1774 throwError(state, 'unknown escape sequence'); 1775 } 1776 1777 captureStart = captureEnd = state.position; 1778 1779 } else if (is_EOL(ch)) { 1780 captureSegment(state, captureStart, captureEnd, true); 1781 writeFoldedLines(state, skipSeparationSpace(state, false, nodeIndent)); 1782 captureStart = captureEnd = state.position; 1783 1784 } else if (state.position === state.lineStart && testDocumentSeparator(state)) { 1785 throwError(state, 'unexpected end of the document within a double quoted scalar'); 1786 1787 } else { 1788 state.position++; 1789 captureEnd = state.position; 1790 } 1791 } 1792 1793 throwError(state, 'unexpected end of the stream within a double quoted scalar'); 1794} 1795 1796function readFlowCollection(state, nodeIndent) { 1797 var readNext = true, 1798 _line, 1799 _lineStart, 1800 _pos, 1801 _tag = state.tag, 1802 _result, 1803 _anchor = state.anchor, 1804 following, 1805 terminator, 1806 isPair, 1807 isExplicitPair, 1808 isMapping, 1809 overridableKeys = Object.create(null), 1810 keyNode, 1811 keyTag, 1812 valueNode, 1813 ch; 1814 1815 ch = state.input.charCodeAt(state.position); 1816 1817 if (ch === 0x5B/* [ */) { 1818 terminator = 0x5D;/* ] */ 1819 isMapping = false; 1820 _result = []; 1821 } else if (ch === 0x7B/* { */) { 1822 terminator = 0x7D;/* } */ 1823 isMapping = true; 1824 _result = {}; 1825 } else { 1826 return false; 1827 } 1828 1829 if (state.anchor !== null) { 1830 state.anchorMap[state.anchor] = _result; 1831 } 1832 1833 ch = state.input.charCodeAt(++state.position); 1834 1835 while (ch !== 0) { 1836 skipSeparationSpace(state, true, nodeIndent); 1837 1838 ch = state.input.charCodeAt(state.position); 1839 1840 if (ch === terminator) { 1841 state.position++; 1842 state.tag = _tag; 1843 state.anchor = _anchor; 1844 state.kind = isMapping ? 'mapping' : 'sequence'; 1845 state.result = _result; 1846 return true; 1847 } else if (!readNext) { 1848 throwError(state, 'missed comma between flow collection entries'); 1849 } else if (ch === 0x2C/* , */) { 1850 // "flow collection entries can never be completely empty", as per YAML 1.2, section 7.4 1851 throwError(state, "expected the node content, but found ','"); 1852 } 1853 1854 keyTag = keyNode = valueNode = null; 1855 isPair = isExplicitPair = false; 1856 1857 if (ch === 0x3F/* ? */) { 1858 following = state.input.charCodeAt(state.position + 1); 1859 1860 if (is_WS_OR_EOL(following)) { 1861 isPair = isExplicitPair = true; 1862 state.position++; 1863 skipSeparationSpace(state, true, nodeIndent); 1864 } 1865 } 1866 1867 _line = state.line; // Save the current line. 1868 _lineStart = state.lineStart; 1869 _pos = state.position; 1870 composeNode(state, nodeIndent, CONTEXT_FLOW_IN, false, true); 1871 keyTag = state.tag; 1872 keyNode = state.result; 1873 skipSeparationSpace(state, true, nodeIndent); 1874 1875 ch = state.input.charCodeAt(state.position); 1876 1877 if ((isExplicitPair || state.line === _line) && ch === 0x3A/* : */) { 1878 isPair = true; 1879 ch = state.input.charCodeAt(++state.position); 1880 skipSeparationSpace(state, true, nodeIndent); 1881 composeNode(state, nodeIndent, CONTEXT_FLOW_IN, false, true); 1882 valueNode = state.result; 1883 } 1884 1885 if (isMapping) { 1886 storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, valueNode, _line, _lineStart, _pos); 1887 } else if (isPair) { 1888 _result.push(storeMappingPair(state, null, overridableKeys, keyTag, keyNode, valueNode, _line, _lineStart, _pos)); 1889 } else { 1890 _result.push(keyNode); 1891 } 1892 1893 skipSeparationSpace(state, true, nodeIndent); 1894 1895 ch = state.input.charCodeAt(state.position); 1896 1897 if (ch === 0x2C/* , */) { 1898 readNext = true; 1899 ch = state.input.charCodeAt(++state.position); 1900 } else { 1901 readNext = false; 1902 } 1903 } 1904 1905 throwError(state, 'unexpected end of the stream within a flow collection'); 1906} 1907 1908function readBlockScalar(state, nodeIndent) { 1909 var captureStart, 1910 folding, 1911 chomping = CHOMPING_CLIP, 1912 didReadContent = false, 1913 detectedIndent = false, 1914 textIndent = nodeIndent, 1915 emptyLines = 0, 1916 atMoreIndented = false, 1917 tmp, 1918 ch; 1919 1920 ch = state.input.charCodeAt(state.position); 1921 1922 if (ch === 0x7C/* | */) { 1923 folding = false; 1924 } else if (ch === 0x3E/* > */) { 1925 folding = true; 1926 } else { 1927 return false; 1928 } 1929 1930 state.kind = 'scalar'; 1931 state.result = ''; 1932 1933 while (ch !== 0) { 1934 ch = state.input.charCodeAt(++state.position); 1935 1936 if (ch === 0x2B/* + */ || ch === 0x2D/* - */) { 1937 if (CHOMPING_CLIP === chomping) { 1938 chomping = (ch === 0x2B/* + */) ? CHOMPING_KEEP : CHOMPING_STRIP; 1939 } else { 1940 throwError(state, 'repeat of a chomping mode identifier'); 1941 } 1942 1943 } else if ((tmp = fromDecimalCode(ch)) >= 0) { 1944 if (tmp === 0) { 1945 throwError(state, 'bad explicit indentation width of a block scalar; it cannot be less than one'); 1946 } else if (!detectedIndent) { 1947 textIndent = nodeIndent + tmp - 1; 1948 detectedIndent = true; 1949 } else { 1950 throwError(state, 'repeat of an indentation width identifier'); 1951 } 1952 1953 } else { 1954 break; 1955 } 1956 } 1957 1958 if (is_WHITE_SPACE(ch)) { 1959 do { ch = state.input.charCodeAt(++state.position); } 1960 while (is_WHITE_SPACE(ch)); 1961 1962 if (ch === 0x23/* # */) { 1963 do { ch = state.input.charCodeAt(++state.position); } 1964 while (!is_EOL(ch) && (ch !== 0)); 1965 } 1966 } 1967 1968 while (ch !== 0) { 1969 readLineBreak(state); 1970 state.lineIndent = 0; 1971 1972 ch = state.input.charCodeAt(state.position); 1973 1974 while ((!detectedIndent || state.lineIndent < textIndent) && 1975 (ch === 0x20/* Space */)) { 1976 state.lineIndent++; 1977 ch = state.input.charCodeAt(++state.position); 1978 } 1979 1980 if (!detectedIndent && state.lineIndent > textIndent) { 1981 textIndent = state.lineIndent; 1982 } 1983 1984 if (is_EOL(ch)) { 1985 emptyLines++; 1986 continue; 1987 } 1988 1989 // End of the scalar. 1990 if (state.lineIndent < textIndent) { 1991 1992 // Perform the chomping. 1993 if (chomping === CHOMPING_KEEP) { 1994 state.result += common.repeat('\n', didReadContent ? 1 + emptyLines : emptyLines); 1995 } else if (chomping === CHOMPING_CLIP) { 1996 if (didReadContent) { // i.e. only if the scalar is not empty. 1997 state.result += '\n'; 1998 } 1999 } 2000 2001 // Break this `while` cycle and go to the funciton's epilogue. 2002 break; 2003 } 2004 2005 // Folded style: use fancy rules to handle line breaks. 2006 if (folding) { 2007 2008 // Lines starting with white space characters (more-indented lines) are not folded. 2009 if (is_WHITE_SPACE(ch)) { 2010 atMoreIndented = true; 2011 // except for the first content line (cf. Example 8.1) 2012 state.result += common.repeat('\n', didReadContent ? 1 + emptyLines : emptyLines); 2013 2014 // End of more-indented block. 2015 } else if (atMoreIndented) { 2016 atMoreIndented = false; 2017 state.result += common.repeat('\n', emptyLines + 1); 2018 2019 // Just one line break - perceive as the same line. 2020 } else if (emptyLines === 0) { 2021 if (didReadContent) { // i.e. only if we have already read some scalar content. 2022 state.result += ' '; 2023 } 2024 2025 // Several line breaks - perceive as different lines. 2026 } else { 2027 state.result += common.repeat('\n', emptyLines); 2028 } 2029 2030 // Literal style: just add exact number of line breaks between content lines. 2031 } else { 2032 // Keep all line breaks except the header line break. 2033 state.result += common.repeat('\n', didReadContent ? 1 + emptyLines : emptyLines); 2034 } 2035 2036 didReadContent = true; 2037 detectedIndent = true; 2038 emptyLines = 0; 2039 captureStart = state.position; 2040 2041 while (!is_EOL(ch) && (ch !== 0)) { 2042 ch = state.input.charCodeAt(++state.position); 2043 } 2044 2045 captureSegment(state, captureStart, state.position, false); 2046 } 2047 2048 return true; 2049} 2050 2051function readBlockSequence(state, nodeIndent) { 2052 var _line, 2053 _tag = state.tag, 2054 _anchor = state.anchor, 2055 _result = [], 2056 following, 2057 detected = false, 2058 ch; 2059 2060 // there is a leading tab before this token, so it can't be a block sequence/mapping; 2061 // it can still be flow sequence/mapping or a scalar 2062 if (state.firstTabInLine !== -1) return false; 2063 2064 if (state.anchor !== null) { 2065 state.anchorMap[state.anchor] = _result; 2066 } 2067 2068 ch = state.input.charCodeAt(state.position); 2069 2070 while (ch !== 0) { 2071 if (state.firstTabInLine !== -1) { 2072 state.position = state.firstTabInLine; 2073 throwError(state, 'tab characters must not be used in indentation'); 2074 } 2075 2076 if (ch !== 0x2D/* - */) { 2077 break; 2078 } 2079 2080 following = state.input.charCodeAt(state.position + 1); 2081 2082 if (!is_WS_OR_EOL(following)) { 2083 break; 2084 } 2085 2086 detected = true; 2087 state.position++; 2088 2089 if (skipSeparationSpace(state, true, -1)) { 2090 if (state.lineIndent <= nodeIndent) { 2091 _result.push(null); 2092 ch = state.input.charCodeAt(state.position); 2093 continue; 2094 } 2095 } 2096 2097 _line = state.line; 2098 composeNode(state, nodeIndent, CONTEXT_BLOCK_IN, false, true); 2099 _result.push(state.result); 2100 skipSeparationSpace(state, true, -1); 2101 2102 ch = state.input.charCodeAt(state.position); 2103 2104 if ((state.line === _line || state.lineIndent > nodeIndent) && (ch !== 0)) { 2105 throwError(state, 'bad indentation of a sequence entry'); 2106 } else if (state.lineIndent < nodeIndent) { 2107 break; 2108 } 2109 } 2110 2111 if (detected) { 2112 state.tag = _tag; 2113 state.anchor = _anchor; 2114 state.kind = 'sequence'; 2115 state.result = _result; 2116 return true; 2117 } 2118 return false; 2119} 2120 2121function readBlockMapping(state, nodeIndent, flowIndent) { 2122 var following, 2123 allowCompact, 2124 _line, 2125 _keyLine, 2126 _keyLineStart, 2127 _keyPos, 2128 _tag = state.tag, 2129 _anchor = state.anchor, 2130 _result = {}, 2131 overridableKeys = Object.create(null), 2132 keyTag = null, 2133 keyNode = null, 2134 valueNode = null, 2135 atExplicitKey = false, 2136 detected = false, 2137 ch; 2138 2139 // there is a leading tab before this token, so it can't be a block sequence/mapping; 2140 // it can still be flow sequence/mapping or a scalar 2141 if (state.firstTabInLine !== -1) return false; 2142 2143 if (state.anchor !== null) { 2144 state.anchorMap[state.anchor] = _result; 2145 } 2146 2147 ch = state.input.charCodeAt(state.position); 2148 2149 while (ch !== 0) { 2150 if (!atExplicitKey && state.firstTabInLine !== -1) { 2151 state.position = state.firstTabInLine; 2152 throwError(state, 'tab characters must not be used in indentation'); 2153 } 2154 2155 following = state.input.charCodeAt(state.position + 1); 2156 _line = state.line; // Save the current line. 2157 2158 // 2159 // Explicit notation case. There are two separate blocks: 2160 // first for the key (denoted by "?") and second for the value (denoted by ":") 2161 // 2162 if ((ch === 0x3F/* ? */ || ch === 0x3A/* : */) && is_WS_OR_EOL(following)) { 2163 2164 if (ch === 0x3F/* ? */) { 2165 if (atExplicitKey) { 2166 storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, null, _keyLine, _keyLineStart, _keyPos); 2167 keyTag = keyNode = valueNode = null; 2168 } 2169 2170 detected = true; 2171 atExplicitKey = true; 2172 allowCompact = true; 2173 2174 } else if (atExplicitKey) { 2175 // i.e. 0x3A/* : */ === character after the explicit key. 2176 atExplicitKey = false; 2177 allowCompact = true; 2178 2179 } else { 2180 throwError(state, 'incomplete explicit mapping pair; a key node is missed; or followed by a non-tabulated empty line'); 2181 } 2182 2183 state.position += 1; 2184 ch = following; 2185 2186 // 2187 // Implicit notation case. Flow-style node as the key first, then ":", and the value. 2188 // 2189 } else { 2190 _keyLine = state.line; 2191 _keyLineStart = state.lineStart; 2192 _keyPos = state.position; 2193 2194 if (!composeNode(state, flowIndent, CONTEXT_FLOW_OUT, false, true)) { 2195 // Neither implicit nor explicit notation. 2196 // Reading is done. Go to the epilogue. 2197 break; 2198 } 2199 2200 if (state.line === _line) { 2201 ch = state.input.charCodeAt(state.position); 2202 2203 while (is_WHITE_SPACE(ch)) { 2204 ch = state.input.charCodeAt(++state.position); 2205 } 2206 2207 if (ch === 0x3A/* : */) { 2208 ch = state.input.charCodeAt(++state.position); 2209 2210 if (!is_WS_OR_EOL(ch)) { 2211 throwError(state, 'a whitespace character is expected after the key-value separator within a block mapping'); 2212 } 2213 2214 if (atExplicitKey) { 2215 storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, null, _keyLine, _keyLineStart, _keyPos); 2216 keyTag = keyNode = valueNode = null; 2217 } 2218 2219 detected = true; 2220 atExplicitKey = false; 2221 allowCompact = false; 2222 keyTag = state.tag; 2223 keyNode = state.result; 2224 2225 } else if (detected) { 2226 throwError(state, 'can not read an implicit mapping pair; a colon is missed'); 2227 2228 } else { 2229 state.tag = _tag; 2230 state.anchor = _anchor; 2231 return true; // Keep the result of `composeNode`. 2232 } 2233 2234 } else if (detected) { 2235 throwError(state, 'can not read a block mapping entry; a multiline key may not be an implicit key'); 2236 2237 } else { 2238 state.tag = _tag; 2239 state.anchor = _anchor; 2240 return true; // Keep the result of `composeNode`. 2241 } 2242 } 2243 2244 // 2245 // Common reading code for both explicit and implicit notations. 2246 // 2247 if (state.line === _line || state.lineIndent > nodeIndent) { 2248 if (atExplicitKey) { 2249 _keyLine = state.line; 2250 _keyLineStart = state.lineStart; 2251 _keyPos = state.position; 2252 } 2253 2254 if (composeNode(state, nodeIndent, CONTEXT_BLOCK_OUT, true, allowCompact)) { 2255 if (atExplicitKey) { 2256 keyNode = state.result; 2257 } else { 2258 valueNode = state.result; 2259 } 2260 } 2261 2262 if (!atExplicitKey) { 2263 storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, valueNode, _keyLine, _keyLineStart, _keyPos); 2264 keyTag = keyNode = valueNode = null; 2265 } 2266 2267 skipSeparationSpace(state, true, -1); 2268 ch = state.input.charCodeAt(state.position); 2269 } 2270 2271 if ((state.line === _line || state.lineIndent > nodeIndent) && (ch !== 0)) { 2272 throwError(state, 'bad indentation of a mapping entry'); 2273 } else if (state.lineIndent < nodeIndent) { 2274 break; 2275 } 2276 } 2277 2278 // 2279 // Epilogue. 2280 // 2281 2282 // Special case: last mapping's node contains only the key in explicit notation. 2283 if (atExplicitKey) { 2284 storeMappingPair(state, _result, overridableKeys, keyTag, keyNode, null, _keyLine, _keyLineStart, _keyPos); 2285 } 2286 2287 // Expose the resulting mapping. 2288 if (detected) { 2289 state.tag = _tag; 2290 state.anchor = _anchor; 2291 state.kind = 'mapping'; 2292 state.result = _result; 2293 } 2294 2295 return detected; 2296} 2297 2298function readTagProperty(state) { 2299 var _position, 2300 isVerbatim = false, 2301 isNamed = false, 2302 tagHandle, 2303 tagName, 2304 ch; 2305 2306 ch = state.input.charCodeAt(state.position); 2307 2308 if (ch !== 0x21/* ! */) return false; 2309 2310 if (state.tag !== null) { 2311 throwError(state, 'duplication of a tag property'); 2312 } 2313 2314 ch = state.input.charCodeAt(++state.position); 2315 2316 if (ch === 0x3C/* < */) { 2317 isVerbatim = true; 2318 ch = state.input.charCodeAt(++state.position); 2319 2320 } else if (ch === 0x21/* ! */) { 2321 isNamed = true; 2322 tagHandle = '!!'; 2323 ch = state.input.charCodeAt(++state.position); 2324 2325 } else { 2326 tagHandle = '!'; 2327 } 2328 2329 _position = state.position; 2330 2331 if (isVerbatim) { 2332 do { ch = state.input.charCodeAt(++state.position); } 2333 while (ch !== 0 && ch !== 0x3E/* > */); 2334 2335 if (state.position < state.length) { 2336 tagName = state.input.slice(_position, state.position); 2337 ch = state.input.charCodeAt(++state.position); 2338 } else { 2339 throwError(state, 'unexpected end of the stream within a verbatim tag'); 2340 } 2341 } else { 2342 while (ch !== 0 && !is_WS_OR_EOL(ch)) { 2343 2344 if (ch === 0x21/* ! */) { 2345 if (!isNamed) { 2346 tagHandle = state.input.slice(_position - 1, state.position + 1); 2347 2348 if (!PATTERN_TAG_HANDLE.test(tagHandle)) { 2349 throwError(state, 'named tag handle cannot contain such characters'); 2350 } 2351 2352 isNamed = true; 2353 _position = state.position + 1; 2354 } else { 2355 throwError(state, 'tag suffix cannot contain exclamation marks'); 2356 } 2357 } 2358 2359 ch = state.input.charCodeAt(++state.position); 2360 } 2361 2362 tagName = state.input.slice(_position, state.position); 2363 2364 if (PATTERN_FLOW_INDICATORS.test(tagName)) { 2365 throwError(state, 'tag suffix cannot contain flow indicator characters'); 2366 } 2367 } 2368 2369 if (tagName && !PATTERN_TAG_URI.test(tagName)) { 2370 throwError(state, 'tag name cannot contain such characters: ' + tagName); 2371 } 2372 2373 try { 2374 tagName = decodeURIComponent(tagName); 2375 } catch (err) { 2376 throwError(state, 'tag name is malformed: ' + tagName); 2377 } 2378 2379 if (isVerbatim) { 2380 state.tag = tagName; 2381 2382 } else if (_hasOwnProperty$1.call(state.tagMap, tagHandle)) { 2383 state.tag = state.tagMap[tagHandle] + tagName; 2384 2385 } else if (tagHandle === '!') { 2386 state.tag = '!' + tagName; 2387 2388 } else if (tagHandle === '!!') { 2389 state.tag = 'tag:yaml.org,2002:' + tagName; 2390 2391 } else { 2392 throwError(state, 'undeclared tag handle "' + tagHandle + '"'); 2393 } 2394 2395 return true; 2396} 2397 2398function readAnchorProperty(state) { 2399 var _position, 2400 ch; 2401 2402 ch = state.input.charCodeAt(state.position); 2403 2404 if (ch !== 0x26/* & */) return false; 2405 2406 if (state.anchor !== null) { 2407 throwError(state, 'duplication of an anchor property'); 2408 } 2409 2410 ch = state.input.charCodeAt(++state.position); 2411 _position = state.position; 2412 2413 while (ch !== 0 && !is_WS_OR_EOL(ch) && !is_FLOW_INDICATOR(ch)) { 2414 ch = state.input.charCodeAt(++state.position); 2415 } 2416 2417 if (state.position === _position) { 2418 throwError(state, 'name of an anchor node must contain at least one character'); 2419 } 2420 2421 state.anchor = state.input.slice(_position, state.position); 2422 return true; 2423} 2424 2425function readAlias(state) { 2426 var _position, alias, 2427 ch; 2428 2429 ch = state.input.charCodeAt(state.position); 2430 2431 if (ch !== 0x2A/* * */) return false; 2432 2433 ch = state.input.charCodeAt(++state.position); 2434 _position = state.position; 2435 2436 while (ch !== 0 && !is_WS_OR_EOL(ch) && !is_FLOW_INDICATOR(ch)) { 2437 ch = state.input.charCodeAt(++state.position); 2438 } 2439 2440 if (state.position === _position) { 2441 throwError(state, 'name of an alias node must contain at least one character'); 2442 } 2443 2444 alias = state.input.slice(_position, state.position); 2445 2446 if (!_hasOwnProperty$1.call(state.anchorMap, alias)) { 2447 throwError(state, 'unidentified alias "' + alias + '"'); 2448 } 2449 2450 state.result = state.anchorMap[alias]; 2451 skipSeparationSpace(state, true, -1); 2452 return true; 2453} 2454 2455function composeNode(state, parentIndent, nodeContext, allowToSeek, allowCompact) { 2456 var allowBlockStyles, 2457 allowBlockScalars, 2458 allowBlockCollections, 2459 indentStatus = 1, // 1: this>parent, 0: this=parent, -1: this<parent 2460 atNewLine = false, 2461 hasContent = false, 2462 typeIndex, 2463 typeQuantity, 2464 typeList, 2465 type, 2466 flowIndent, 2467 blockIndent; 2468 2469 if (state.listener !== null) { 2470 state.listener('open', state); 2471 } 2472 2473 state.tag = null; 2474 state.anchor = null; 2475 state.kind = null; 2476 state.result = null; 2477 2478 allowBlockStyles = allowBlockScalars = allowBlockCollections = 2479 CONTEXT_BLOCK_OUT === nodeContext || 2480 CONTEXT_BLOCK_IN === nodeContext; 2481 2482 if (allowToSeek) { 2483 if (skipSeparationSpace(state, true, -1)) { 2484 atNewLine = true; 2485 2486 if (state.lineIndent > parentIndent) { 2487 indentStatus = 1; 2488 } else if (state.lineIndent === parentIndent) { 2489 indentStatus = 0; 2490 } else if (state.lineIndent < parentIndent) { 2491 indentStatus = -1; 2492 } 2493 } 2494 } 2495 2496 if (indentStatus === 1) { 2497 while (readTagProperty(state) || readAnchorProperty(state)) { 2498 if (skipSeparationSpace(state, true, -1)) { 2499 atNewLine = true; 2500 allowBlockCollections = allowBlockStyles; 2501 2502 if (state.lineIndent > parentIndent) { 2503 indentStatus = 1; 2504 } else if (state.lineIndent === parentIndent) { 2505 indentStatus = 0; 2506 } else if (state.lineIndent < parentIndent) { 2507 indentStatus = -1; 2508 } 2509 } else { 2510 allowBlockCollections = false; 2511 } 2512 } 2513 } 2514 2515 if (allowBlockCollections) { 2516 allowBlockCollections = atNewLine || allowCompact; 2517 } 2518 2519 if (indentStatus === 1 || CONTEXT_BLOCK_OUT === nodeContext) { 2520 if (CONTEXT_FLOW_IN === nodeContext || CONTEXT_FLOW_OUT === nodeContext) { 2521 flowIndent = parentIndent; 2522 } else { 2523 flowIndent = parentIndent + 1; 2524 } 2525 2526 blockIndent = state.position - state.lineStart; 2527 2528 if (indentStatus === 1) { 2529 if (allowBlockCollections && 2530 (readBlockSequence(state, blockIndent) || 2531 readBlockMapping(state, blockIndent, flowIndent)) || 2532 readFlowCollection(state, flowIndent)) { 2533 hasContent = true; 2534 } else { 2535 if ((allowBlockScalars && readBlockScalar(state, flowIndent)) || 2536 readSingleQuotedScalar(state, flowIndent) || 2537 readDoubleQuotedScalar(state, flowIndent)) { 2538 hasContent = true; 2539 2540 } else if (readAlias(state)) { 2541 hasContent = true; 2542 2543 if (state.tag !== null || state.anchor !== null) { 2544 throwError(state, 'alias node should not have any properties'); 2545 } 2546 2547 } else if (readPlainScalar(state, flowIndent, CONTEXT_FLOW_IN === nodeContext)) { 2548 hasContent = true; 2549 2550 if (state.tag === null) { 2551 state.tag = '?'; 2552 } 2553 } 2554 2555 if (state.anchor !== null) { 2556 state.anchorMap[state.anchor] = state.result; 2557 } 2558 } 2559 } else if (indentStatus === 0) { 2560 // Special case: block sequences are allowed to have same indentation level as the parent. 2561 // http://www.yaml.org/spec/1.2/spec.html#id2799784 2562 hasContent = allowBlockCollections && readBlockSequence(state, blockIndent); 2563 } 2564 } 2565 2566 if (state.tag === null) { 2567 if (state.anchor !== null) { 2568 state.anchorMap[state.anchor] = state.result; 2569 } 2570 2571 } else if (state.tag === '?') { 2572 // Implicit resolving is not allowed for non-scalar types, and '?' 2573 // non-specific tag is only automatically assigned to plain scalars. 2574 // 2575 // We only need to check kind conformity in case user explicitly assigns '?' 2576 // tag, for example like this: "!<?> [0]" 2577 // 2578 if (state.result !== null && state.kind !== 'scalar') { 2579 throwError(state, 'unacceptable node kind for !<?> tag; it should be "scalar", not "' + state.kind + '"'); 2580 } 2581 2582 for (typeIndex = 0, typeQuantity = state.implicitTypes.length; typeIndex < typeQuantity; typeIndex += 1) { 2583 type = state.implicitTypes[typeIndex]; 2584 2585 if (type.resolve(state.result)) { // `state.result` updated in resolver if matched 2586 state.result = type.construct(state.result); 2587 state.tag = type.tag; 2588 if (state.anchor !== null) { 2589 state.anchorMap[state.anchor] = state.result; 2590 } 2591 break; 2592 } 2593 } 2594 } else if (state.tag !== '!') { 2595 if (_hasOwnProperty$1.call(state.typeMap[state.kind || 'fallback'], state.tag)) { 2596 type = state.typeMap[state.kind || 'fallback'][state.tag]; 2597 } else { 2598 // looking for multi type 2599 type = null; 2600 typeList = state.typeMap.multi[state.kind || 'fallback']; 2601 2602 for (typeIndex = 0, typeQuantity = typeList.length; typeIndex < typeQuantity; typeIndex += 1) { 2603 if (state.tag.slice(0, typeList[typeIndex].tag.length) === typeList[typeIndex].tag) { 2604 type = typeList[typeIndex]; 2605 break; 2606 } 2607 } 2608 } 2609 2610 if (!type) { 2611 throwError(state, 'unknown tag !<' + state.tag + '>'); 2612 } 2613 2614 if (state.result !== null && type.kind !== state.kind) { 2615 throwError(state, 'unacceptable node kind for !<' + state.tag + '> tag; it should be "' + type.kind + '", not "' + state.kind + '"'); 2616 } 2617 2618 if (!type.resolve(state.result, state.tag)) { // `state.result` updated in resolver if matched 2619 throwError(state, 'cannot resolve a node with !<' + state.tag + '> explicit tag'); 2620 } else { 2621 state.result = type.construct(state.result, state.tag); 2622 if (state.anchor !== null) { 2623 state.anchorMap[state.anchor] = state.result; 2624 } 2625 } 2626 } 2627 2628 if (state.listener !== null) { 2629 state.listener('close', state); 2630 } 2631 return state.tag !== null || state.anchor !== null || hasContent; 2632} 2633 2634function readDocument(state) { 2635 var documentStart = state.position, 2636 _position, 2637 directiveName, 2638 directiveArgs, 2639 hasDirectives = false, 2640 ch; 2641 2642 state.version = null; 2643 state.checkLineBreaks = state.legacy; 2644 state.tagMap = Object.create(null); 2645 state.anchorMap = Object.create(null); 2646 2647 while ((ch = state.input.charCodeAt(state.position)) !== 0) { 2648 skipSeparationSpace(state, true, -1); 2649 2650 ch = state.input.charCodeAt(state.position); 2651 2652 if (state.lineIndent > 0 || ch !== 0x25/* % */) { 2653 break; 2654 } 2655 2656 hasDirectives = true; 2657 ch = state.input.charCodeAt(++state.position); 2658 _position = state.position; 2659 2660 while (ch !== 0 && !is_WS_OR_EOL(ch)) { 2661 ch = state.input.charCodeAt(++state.position); 2662 } 2663 2664 directiveName = state.input.slice(_position, state.position); 2665 directiveArgs = []; 2666 2667 if (directiveName.length < 1) { 2668 throwError(state, 'directive name must not be less than one character in length'); 2669 } 2670 2671 while (ch !== 0) { 2672 while (is_WHITE_SPACE(ch)) { 2673 ch = state.input.charCodeAt(++state.position); 2674 } 2675 2676 if (ch === 0x23/* # */) { 2677 do { ch = state.input.charCodeAt(++state.position); } 2678 while (ch !== 0 && !is_EOL(ch)); 2679 break; 2680 } 2681 2682 if (is_EOL(ch)) break; 2683 2684 _position = state.position; 2685 2686 while (ch !== 0 && !is_WS_OR_EOL(ch)) { 2687 ch = state.input.charCodeAt(++state.position); 2688 } 2689 2690 directiveArgs.push(state.input.slice(_position, state.position)); 2691 } 2692 2693 if (ch !== 0) readLineBreak(state); 2694 2695 if (_hasOwnProperty$1.call(directiveHandlers, directiveName)) { 2696 directiveHandlers[directiveName](state, directiveName, directiveArgs); 2697 } else { 2698 throwWarning(state, 'unknown document directive "' + directiveName + '"'); 2699 } 2700 } 2701 2702 skipSeparationSpace(state, true, -1); 2703 2704 if (state.lineIndent === 0 && 2705 state.input.charCodeAt(state.position) === 0x2D/* - */ && 2706 state.input.charCodeAt(state.position + 1) === 0x2D/* - */ && 2707 state.input.charCodeAt(state.position + 2) === 0x2D/* - */) { 2708 state.position += 3; 2709 skipSeparationSpace(state, true, -1); 2710 2711 } else if (hasDirectives) { 2712 throwError(state, 'directives end mark is expected'); 2713 } 2714 2715 composeNode(state, state.lineIndent - 1, CONTEXT_BLOCK_OUT, false, true); 2716 skipSeparationSpace(state, true, -1); 2717 2718 if (state.checkLineBreaks && 2719 PATTERN_NON_ASCII_LINE_BREAKS.test(state.input.slice(documentStart, state.position))) { 2720 throwWarning(state, 'non-ASCII line breaks are interpreted as content'); 2721 } 2722 2723 state.documents.push(state.result); 2724 2725 if (state.position === state.lineStart && testDocumentSeparator(state)) { 2726 2727 if (state.input.charCodeAt(state.position) === 0x2E/* . */) { 2728 state.position += 3; 2729 skipSeparationSpace(state, true, -1); 2730 } 2731 return; 2732 } 2733 2734 if (state.position < (state.length - 1)) { 2735 throwError(state, 'end of the stream or a document separator is expected'); 2736 } else { 2737 return; 2738 } 2739} 2740 2741 2742function loadDocuments(input, options) { 2743 input = String(input); 2744 options = options || {}; 2745 2746 if (input.length !== 0) { 2747 2748 // Add tailing `\n` if not exists 2749 if (input.charCodeAt(input.length - 1) !== 0x0A/* LF */ && 2750 input.charCodeAt(input.length - 1) !== 0x0D/* CR */) { 2751 input += '\n'; 2752 } 2753 2754 // Strip BOM 2755 if (input.charCodeAt(0) === 0xFEFF) { 2756 input = input.slice(1); 2757 } 2758 } 2759 2760 var state = new State$1(input, options); 2761 2762 var nullpos = input.indexOf('\0'); 2763 2764 if (nullpos !== -1) { 2765 state.position = nullpos; 2766 throwError(state, 'null byte is not allowed in input'); 2767 } 2768 2769 // Use 0 as string terminator. That significantly simplifies bounds check. 2770 state.input += '\0'; 2771 2772 while (state.input.charCodeAt(state.position) === 0x20/* Space */) { 2773 state.lineIndent += 1; 2774 state.position += 1; 2775 } 2776 2777 while (state.position < (state.length - 1)) { 2778 readDocument(state); 2779 } 2780 2781 return state.documents; 2782} 2783 2784 2785function loadAll$1(input, iterator, options) { 2786 if (iterator !== null && typeof iterator === 'object' && typeof options === 'undefined') { 2787 options = iterator; 2788 iterator = null; 2789 } 2790 2791 var documents = loadDocuments(input, options); 2792 2793 if (typeof iterator !== 'function') { 2794 return documents; 2795 } 2796 2797 for (var index = 0, length = documents.length; index < length; index += 1) { 2798 iterator(documents[index]); 2799 } 2800} 2801 2802 2803function load$1(input, options) { 2804 var documents = loadDocuments(input, options); 2805 2806 if (documents.length === 0) { 2807 /*eslint-disable no-undefined*/ 2808 return undefined; 2809 } else if (documents.length === 1) { 2810 return documents[0]; 2811 } 2812 throw new exception('expected a single document in the stream, but found more'); 2813} 2814 2815 2816var loadAll_1 = loadAll$1; 2817var load_1 = load$1; 2818 2819var loader = { 2820 loadAll: loadAll_1, 2821 load: load_1 2822}; 2823 2824/*eslint-disable no-use-before-define*/ 2825 2826 2827 2828 2829 2830var _toString = Object.prototype.toString; 2831var _hasOwnProperty = Object.prototype.hasOwnProperty; 2832 2833var CHAR_BOM = 0xFEFF; 2834var CHAR_TAB = 0x09; /* Tab */ 2835var CHAR_LINE_FEED = 0x0A; /* LF */ 2836var CHAR_CARRIAGE_RETURN = 0x0D; /* CR */ 2837var CHAR_SPACE = 0x20; /* Space */ 2838var CHAR_EXCLAMATION = 0x21; /* ! */ 2839var CHAR_DOUBLE_QUOTE = 0x22; /* " */ 2840var CHAR_SHARP = 0x23; /* # */ 2841var CHAR_PERCENT = 0x25; /* % */ 2842var CHAR_AMPERSAND = 0x26; /* & */ 2843var CHAR_SINGLE_QUOTE = 0x27; /* ' */ 2844var CHAR_ASTERISK = 0x2A; /* * */ 2845var CHAR_COMMA = 0x2C; /* , */ 2846var CHAR_MINUS = 0x2D; /* - */ 2847var CHAR_COLON = 0x3A; /* : */ 2848var CHAR_EQUALS = 0x3D; /* = */ 2849var CHAR_GREATER_THAN = 0x3E; /* > */ 2850var CHAR_QUESTION = 0x3F; /* ? */ 2851var CHAR_COMMERCIAL_AT = 0x40; /* @ */ 2852var CHAR_LEFT_SQUARE_BRACKET = 0x5B; /* [ */ 2853var CHAR_RIGHT_SQUARE_BRACKET = 0x5D; /* ] */ 2854var CHAR_GRAVE_ACCENT = 0x60; /* ` */ 2855var CHAR_LEFT_CURLY_BRACKET = 0x7B; /* { */ 2856var CHAR_VERTICAL_LINE = 0x7C; /* | */ 2857var CHAR_RIGHT_CURLY_BRACKET = 0x7D; /* } */ 2858 2859var ESCAPE_SEQUENCES = {}; 2860 2861ESCAPE_SEQUENCES[0x00] = '\\0'; 2862ESCAPE_SEQUENCES[0x07] = '\\a'; 2863ESCAPE_SEQUENCES[0x08] = '\\b'; 2864ESCAPE_SEQUENCES[0x09] = '\\t'; 2865ESCAPE_SEQUENCES[0x0A] = '\\n'; 2866ESCAPE_SEQUENCES[0x0B] = '\\v'; 2867ESCAPE_SEQUENCES[0x0C] = '\\f'; 2868ESCAPE_SEQUENCES[0x0D] = '\\r'; 2869ESCAPE_SEQUENCES[0x1B] = '\\e'; 2870ESCAPE_SEQUENCES[0x22] = '\\"'; 2871ESCAPE_SEQUENCES[0x5C] = '\\\\'; 2872ESCAPE_SEQUENCES[0x85] = '\\N'; 2873ESCAPE_SEQUENCES[0xA0] = '\\_'; 2874ESCAPE_SEQUENCES[0x2028] = '\\L'; 2875ESCAPE_SEQUENCES[0x2029] = '\\P'; 2876 2877var DEPRECATED_BOOLEANS_SYNTAX = [ 2878 'y', 'Y', 'yes', 'Yes', 'YES', 'on', 'On', 'ON', 2879 'n', 'N', 'no', 'No', 'NO', 'off', 'Off', 'OFF' 2880]; 2881 2882var DEPRECATED_BASE60_SYNTAX = /^[-+]?[0-9_]+(?::[0-9_]+)+(?:\.[0-9_]*)?$/; 2883 2884function compileStyleMap(schema, map) { 2885 var result, keys, index, length, tag, style, type; 2886 2887 if (map === null) return {}; 2888 2889 result = {}; 2890 keys = Object.keys(map); 2891 2892 for (index = 0, length = keys.length; index < length; index += 1) { 2893 tag = keys[index]; 2894 style = String(map[tag]); 2895 2896 if (tag.slice(0, 2) === '!!') { 2897 tag = 'tag:yaml.org,2002:' + tag.slice(2); 2898 } 2899 type = schema.compiledTypeMap['fallback'][tag]; 2900 2901 if (type && _hasOwnProperty.call(type.styleAliases, style)) { 2902 style = type.styleAliases[style]; 2903 } 2904 2905 result[tag] = style; 2906 } 2907 2908 return result; 2909} 2910 2911function encodeHex(character) { 2912 var string, handle, length; 2913 2914 string = character.toString(16).toUpperCase(); 2915 2916 if (character <= 0xFF) { 2917 handle = 'x'; 2918 length = 2; 2919 } else if (character <= 0xFFFF) { 2920 handle = 'u'; 2921 length = 4; 2922 } else if (character <= 0xFFFFFFFF) { 2923 handle = 'U'; 2924 length = 8; 2925 } else { 2926 throw new exception('code point within a string may not be greater than 0xFFFFFFFF'); 2927 } 2928 2929 return '\\' + handle + common.repeat('0', length - string.length) + string; 2930} 2931 2932 2933var QUOTING_TYPE_SINGLE = 1, 2934 QUOTING_TYPE_DOUBLE = 2; 2935 2936function State(options) { 2937 this.schema = options['schema'] || _default; 2938 this.indent = Math.max(1, (options['indent'] || 2)); 2939 this.noArrayIndent = options['noArrayIndent'] || false; 2940 this.skipInvalid = options['skipInvalid'] || false; 2941 this.flowLevel = (common.isNothing(options['flowLevel']) ? -1 : options['flowLevel']); 2942 this.styleMap = compileStyleMap(this.schema, options['styles'] || null); 2943 this.sortKeys = options['sortKeys'] || false; 2944 this.lineWidth = options['lineWidth'] || 80; 2945 this.noRefs = options['noRefs'] || false; 2946 this.noCompatMode = options['noCompatMode'] || false; 2947 this.condenseFlow = options['condenseFlow'] || false; 2948 this.quotingType = options['quotingType'] === '"' ? QUOTING_TYPE_DOUBLE : QUOTING_TYPE_SINGLE; 2949 this.forceQuotes = options['forceQuotes'] || false; 2950 this.replacer = typeof options['replacer'] === 'function' ? options['replacer'] : null; 2951 2952 this.implicitTypes = this.schema.compiledImplicit; 2953 this.explicitTypes = this.schema.compiledExplicit; 2954 2955 this.tag = null; 2956 this.result = ''; 2957 2958 this.duplicates = []; 2959 this.usedDuplicates = null; 2960} 2961 2962// Indents every line in a string. Empty lines (\n only) are not indented. 2963function indentString(string, spaces) { 2964 var ind = common.repeat(' ', spaces), 2965 position = 0, 2966 next = -1, 2967 result = '', 2968 line, 2969 length = string.length; 2970 2971 while (position < length) { 2972 next = string.indexOf('\n', position); 2973 if (next === -1) { 2974 line = string.slice(position); 2975 position = length; 2976 } else { 2977 line = string.slice(position, next + 1); 2978 position = next + 1; 2979 } 2980 2981 if (line.length && line !== '\n') result += ind; 2982 2983 result += line; 2984 } 2985 2986 return result; 2987} 2988 2989function generateNextLine(state, level) { 2990 return '\n' + common.repeat(' ', state.indent * level); 2991} 2992 2993function testImplicitResolving(state, str) { 2994 var index, length, type; 2995 2996 for (index = 0, length = state.implicitTypes.length; index < length; index += 1) { 2997 type = state.implicitTypes[index]; 2998 2999 if (type.resolve(str)) { 3000 return true; 3001 } 3002 } 3003 3004 return false; 3005} 3006 3007// [33] s-white ::= s-space | s-tab 3008function isWhitespace(c) { 3009 return c === CHAR_SPACE || c === CHAR_TAB; 3010} 3011 3012// Returns true if the character can be printed without escaping. 3013// From YAML 1.2: "any allowed characters known to be non-printable 3014// should also be escaped. [However,] This isn’t mandatory" 3015// Derived from nb-char - \t - #x85 - #xA0 - #x2028 - #x2029. 3016function isPrintable(c) { 3017 return (0x00020 <= c && c <= 0x00007E) 3018 || ((0x000A1 <= c && c <= 0x00D7FF) && c !== 0x2028 && c !== 0x2029) 3019 || ((0x0E000 <= c && c <= 0x00FFFD) && c !== CHAR_BOM) 3020 || (0x10000 <= c && c <= 0x10FFFF); 3021} 3022 3023// [34] ns-char ::= nb-char - s-white 3024// [27] nb-char ::= c-printable - b-char - c-byte-order-mark 3025// [26] b-char ::= b-line-feed | b-carriage-return 3026// Including s-white (for some reason, examples doesn't match specs in this aspect) 3027// ns-char ::= c-printable - b-line-feed - b-carriage-return - c-byte-order-mark 3028function isNsCharOrWhitespace(c) { 3029 return isPrintable(c) 3030 && c !== CHAR_BOM 3031 // - b-char 3032 && c !== CHAR_CARRIAGE_RETURN 3033 && c !== CHAR_LINE_FEED; 3034} 3035 3036// [127] ns-plain-safe(c) ::= c = flow-out ⇒ ns-plain-safe-out 3037// c = flow-in ⇒ ns-plain-safe-in 3038// c = block-key ⇒ ns-plain-safe-out 3039// c = flow-key ⇒ ns-plain-safe-in 3040// [128] ns-plain-safe-out ::= ns-char 3041// [129] ns-plain-safe-in ::= ns-char - c-flow-indicator 3042// [130] ns-plain-char(c) ::= ( ns-plain-safe(c) - “:” - “#” ) 3043// | ( /* An ns-char preceding */ “#” ) 3044// | ( “:” /* Followed by an ns-plain-safe(c) */ ) 3045function isPlainSafe(c, prev, inblock) { 3046 var cIsNsCharOrWhitespace = isNsCharOrWhitespace(c); 3047 var cIsNsChar = cIsNsCharOrWhitespace && !isWhitespace(c); 3048 return ( 3049 // ns-plain-safe 3050 inblock ? // c = flow-in 3051 cIsNsCharOrWhitespace 3052 : cIsNsCharOrWhitespace 3053 // - c-flow-indicator 3054 && c !== CHAR_COMMA 3055 && c !== CHAR_LEFT_SQUARE_BRACKET 3056 && c !== CHAR_RIGHT_SQUARE_BRACKET 3057 && c !== CHAR_LEFT_CURLY_BRACKET 3058 && c !== CHAR_RIGHT_CURLY_BRACKET 3059 ) 3060 // ns-plain-char 3061 && c !== CHAR_SHARP // false on '#' 3062 && !(prev === CHAR_COLON && !cIsNsChar) // false on ': ' 3063 || (isNsCharOrWhitespace(prev) && !isWhitespace(prev) && c === CHAR_SHARP) // change to true on '[^ ]#' 3064 || (prev === CHAR_COLON && cIsNsChar); // change to true on ':[^ ]' 3065} 3066 3067// Simplified test for values allowed as the first character in plain style. 3068function isPlainSafeFirst(c) { 3069 // Uses a subset of ns-char - c-indicator 3070 // where ns-char = nb-char - s-white. 3071 // No support of ( ( “?” | “:” | “-” ) /* Followed by an ns-plain-safe(c)) */ ) part 3072 return isPrintable(c) && c !== CHAR_BOM 3073 && !isWhitespace(c) // - s-white 3074 // - (c-indicator ::= 3075 // “-” | “?” | “:” | “,” | “[” | “]” | “{” | “}” 3076 && c !== CHAR_MINUS 3077 && c !== CHAR_QUESTION 3078 && c !== CHAR_COLON 3079 && c !== CHAR_COMMA 3080 && c !== CHAR_LEFT_SQUARE_BRACKET 3081 && c !== CHAR_RIGHT_SQUARE_BRACKET 3082 && c !== CHAR_LEFT_CURLY_BRACKET 3083 && c !== CHAR_RIGHT_CURLY_BRACKET 3084 // | “#” | “&” | “*” | “!” | “|” | “=” | “>” | “'” | “"” 3085 && c !== CHAR_SHARP 3086 && c !== CHAR_AMPERSAND 3087 && c !== CHAR_ASTERISK 3088 && c !== CHAR_EXCLAMATION 3089 && c !== CHAR_VERTICAL_LINE 3090 && c !== CHAR_EQUALS 3091 && c !== CHAR_GREATER_THAN 3092 && c !== CHAR_SINGLE_QUOTE 3093 && c !== CHAR_DOUBLE_QUOTE 3094 // | “%” | “@” | “`”) 3095 && c !== CHAR_PERCENT 3096 && c !== CHAR_COMMERCIAL_AT 3097 && c !== CHAR_GRAVE_ACCENT; 3098} 3099 3100// Simplified test for values allowed as the last character in plain style. 3101function isPlainSafeLast(c) { 3102 // just not whitespace or colon, it will be checked to be plain character later 3103 return !isWhitespace(c) && c !== CHAR_COLON; 3104} 3105 3106// Same as 'string'.codePointAt(pos), but works in older browsers. 3107function codePointAt(string, pos) { 3108 var first = string.charCodeAt(pos), second; 3109 if (first >= 0xD800 && first <= 0xDBFF && pos + 1 < string.length) { 3110 second = string.charCodeAt(pos + 1); 3111 if (second >= 0xDC00 && second <= 0xDFFF) { 3112 // https://mathiasbynens.be/notes/javascript-encoding#surrogate-formulae 3113 return (first - 0xD800) * 0x400 + second - 0xDC00 + 0x10000; 3114 } 3115 } 3116 return first; 3117} 3118 3119// Determines whether block indentation indicator is required. 3120function needIndentIndicator(string) { 3121 var leadingSpaceRe = /^\n* /; 3122 return leadingSpaceRe.test(string); 3123} 3124 3125var STYLE_PLAIN = 1, 3126 STYLE_SINGLE = 2, 3127 STYLE_LITERAL = 3, 3128 STYLE_FOLDED = 4, 3129 STYLE_DOUBLE = 5; 3130 3131// Determines which scalar styles are possible and returns the preferred style. 3132// lineWidth = -1 => no limit. 3133// Pre-conditions: str.length > 0. 3134// Post-conditions: 3135// STYLE_PLAIN or STYLE_SINGLE => no \n are in the string. 3136// STYLE_LITERAL => no lines are suitable for folding (or lineWidth is -1). 3137// STYLE_FOLDED => a line > lineWidth and can be folded (and lineWidth != -1). 3138function chooseScalarStyle(string, singleLineOnly, indentPerLevel, lineWidth, 3139 testAmbiguousType, quotingType, forceQuotes, inblock) { 3140 3141 var i; 3142 var char = 0; 3143 var prevChar = null; 3144 var hasLineBreak = false; 3145 var hasFoldableLine = false; // only checked if shouldTrackWidth 3146 var shouldTrackWidth = lineWidth !== -1; 3147 var previousLineBreak = -1; // count the first line correctly 3148 var plain = isPlainSafeFirst(codePointAt(string, 0)) 3149 && isPlainSafeLast(codePointAt(string, string.length - 1)); 3150 3151 if (singleLineOnly || forceQuotes) { 3152 // Case: no block styles. 3153 // Check for disallowed characters to rule out plain and single. 3154 for (i = 0; i < string.length; char >= 0x10000 ? i += 2 : i++) { 3155 char = codePointAt(string, i); 3156 if (!isPrintable(char)) { 3157 return STYLE_DOUBLE; 3158 } 3159 plain = plain && isPlainSafe(char, prevChar, inblock); 3160 prevChar = char; 3161 } 3162 } else { 3163 // Case: block styles permitted. 3164 for (i = 0; i < string.length; char >= 0x10000 ? i += 2 : i++) { 3165 char = codePointAt(string, i); 3166 if (char === CHAR_LINE_FEED) { 3167 hasLineBreak = true; 3168 // Check if any line can be folded. 3169 if (shouldTrackWidth) { 3170 hasFoldableLine = hasFoldableLine || 3171 // Foldable line = too long, and not more-indented. 3172 (i - previousLineBreak - 1 > lineWidth && 3173 string[previousLineBreak + 1] !== ' '); 3174 previousLineBreak = i; 3175 } 3176 } else if (!isPrintable(char)) { 3177 return STYLE_DOUBLE; 3178 } 3179 plain = plain && isPlainSafe(char, prevChar, inblock); 3180 prevChar = char; 3181 } 3182 // in case the end is missing a \n 3183 hasFoldableLine = hasFoldableLine || (shouldTrackWidth && 3184 (i - previousLineBreak - 1 > lineWidth && 3185 string[previousLineBreak + 1] !== ' ')); 3186 } 3187 // Although every style can represent \n without escaping, prefer block styles 3188 // for multiline, since they're more readable and they don't add empty lines. 3189 // Also prefer folding a super-long line. 3190 if (!hasLineBreak && !hasFoldableLine) { 3191 // Strings interpretable as another type have to be quoted; 3192 // e.g. the string 'true' vs. the boolean true. 3193 if (plain && !forceQuotes && !testAmbiguousType(string)) { 3194 return STYLE_PLAIN; 3195 } 3196 return quotingType === QUOTING_TYPE_DOUBLE ? STYLE_DOUBLE : STYLE_SINGLE; 3197 } 3198 // Edge case: block indentation indicator can only have one digit. 3199 if (indentPerLevel > 9 && needIndentIndicator(string)) { 3200 return STYLE_DOUBLE; 3201 } 3202 // At this point we know block styles are valid. 3203 // Prefer literal style unless we want to fold. 3204 if (!forceQuotes) { 3205 return hasFoldableLine ? STYLE_FOLDED : STYLE_LITERAL; 3206 } 3207 return quotingType === QUOTING_TYPE_DOUBLE ? STYLE_DOUBLE : STYLE_SINGLE; 3208} 3209 3210// Note: line breaking/folding is implemented for only the folded style. 3211// NB. We drop the last trailing newline (if any) of a returned block scalar 3212// since the dumper adds its own newline. This always works: 3213// • No ending newline => unaffected; already using strip "-" chomping. 3214// • Ending newline => removed then restored. 3215// Importantly, this keeps the "+" chomp indicator from gaining an extra line. 3216function writeScalar(state, string, level, iskey, inblock) { 3217 state.dump = (function () { 3218 if (string.length === 0) { 3219 return state.quotingType === QUOTING_TYPE_DOUBLE ? '""' : "''"; 3220 } 3221 if (!state.noCompatMode) { 3222 if (DEPRECATED_BOOLEANS_SYNTAX.indexOf(string) !== -1 || DEPRECATED_BASE60_SYNTAX.test(string)) { 3223 return state.quotingType === QUOTING_TYPE_DOUBLE ? ('"' + string + '"') : ("'" + string + "'"); 3224 } 3225 } 3226 3227 var indent = state.indent * Math.max(1, level); // no 0-indent scalars 3228 // As indentation gets deeper, let the width decrease monotonically 3229 // to the lower bound min(state.lineWidth, 40). 3230 // Note that this implies 3231 // state.lineWidth ≤ 40 + state.indent: width is fixed at the lower bound. 3232 // state.lineWidth > 40 + state.indent: width decreases until the lower bound. 3233 // This behaves better than a constant minimum width which disallows narrower options, 3234 // or an indent threshold which causes the width to suddenly increase. 3235 var lineWidth = state.lineWidth === -1 3236 ? -1 : Math.max(Math.min(state.lineWidth, 40), state.lineWidth - indent); 3237 3238 // Without knowing if keys are implicit/explicit, assume implicit for safety. 3239 var singleLineOnly = iskey 3240 // No block styles in flow mode. 3241 || (state.flowLevel > -1 && level >= state.flowLevel); 3242 function testAmbiguity(string) { 3243 return testImplicitResolving(state, string); 3244 } 3245 3246 switch (chooseScalarStyle(string, singleLineOnly, state.indent, lineWidth, 3247 testAmbiguity, state.quotingType, state.forceQuotes && !iskey, inblock)) { 3248 3249 case STYLE_PLAIN: 3250 return string; 3251 case STYLE_SINGLE: 3252 return "'" + string.replace(/'/g, "''") + "'"; 3253 case STYLE_LITERAL: 3254 return '|' + blockHeader(string, state.indent) 3255 + dropEndingNewline(indentString(string, indent)); 3256 case STYLE_FOLDED: 3257 return '>' + blockHeader(string, state.indent) 3258 + dropEndingNewline(indentString(foldString(string, lineWidth), indent)); 3259 case STYLE_DOUBLE: 3260 return '"' + escapeString(string) + '"'; 3261 default: 3262 throw new exception('impossible error: invalid scalar style'); 3263 } 3264 }()); 3265} 3266 3267// Pre-conditions: string is valid for a block scalar, 1 <= indentPerLevel <= 9. 3268function blockHeader(string, indentPerLevel) { 3269 var indentIndicator = needIndentIndicator(string) ? String(indentPerLevel) : ''; 3270 3271 // note the special case: the string '\n' counts as a "trailing" empty line. 3272 var clip = string[string.length - 1] === '\n'; 3273 var keep = clip && (string[string.length - 2] === '\n' || string === '\n'); 3274 var chomp = keep ? '+' : (clip ? '' : '-'); 3275 3276 return indentIndicator + chomp + '\n'; 3277} 3278 3279// (See the note for writeScalar.) 3280function dropEndingNewline(string) { 3281 return string[string.length - 1] === '\n' ? string.slice(0, -1) : string; 3282} 3283 3284// Note: a long line without a suitable break point will exceed the width limit. 3285// Pre-conditions: every char in str isPrintable, str.length > 0, width > 0. 3286function foldString(string, width) { 3287 // In folded style, $k$ consecutive newlines output as $k+1$ newlines— 3288 // unless they're before or after a more-indented line, or at the very 3289 // beginning or end, in which case $k$ maps to $k$. 3290 // Therefore, parse each chunk as newline(s) followed by a content line. 3291 var lineRe = /(\n+)([^\n]*)/g; 3292 3293 // first line (possibly an empty line) 3294 var result = (function () { 3295 var nextLF = string.indexOf('\n'); 3296 nextLF = nextLF !== -1 ? nextLF : string.length; 3297 lineRe.lastIndex = nextLF; 3298 return foldLine(string.slice(0, nextLF), width); 3299 }()); 3300 // If we haven't reached the first content line yet, don't add an extra \n. 3301 var prevMoreIndented = string[0] === '\n' || string[0] === ' '; 3302 var moreIndented; 3303 3304 // rest of the lines 3305 var match; 3306 while ((match = lineRe.exec(string))) { 3307 var prefix = match[1], line = match[2]; 3308 moreIndented = (line[0] === ' '); 3309 result += prefix 3310 + (!prevMoreIndented && !moreIndented && line !== '' 3311 ? '\n' : '') 3312 + foldLine(line, width); 3313 prevMoreIndented = moreIndented; 3314 } 3315 3316 return result; 3317} 3318 3319// Greedy line breaking. 3320// Picks the longest line under the limit each time, 3321// otherwise settles for the shortest line over the limit. 3322// NB. More-indented lines *cannot* be folded, as that would add an extra \n. 3323function foldLine(line, width) { 3324 if (line === '' || line[0] === ' ') return line; 3325 3326 // Since a more-indented line adds a \n, breaks can't be followed by a space. 3327 var breakRe = / [^ ]/g; // note: the match index will always be <= length-2. 3328 var match; 3329 // start is an inclusive index. end, curr, and next are exclusive. 3330 var start = 0, end, curr = 0, next = 0; 3331 var result = ''; 3332 3333 // Invariants: 0 <= start <= length-1. 3334 // 0 <= curr <= next <= max(0, length-2). curr - start <= width. 3335 // Inside the loop: 3336 // A match implies length >= 2, so curr and next are <= length-2. 3337 while ((match = breakRe.exec(line))) { 3338 next = match.index; 3339 // maintain invariant: curr - start <= width 3340 if (next - start > width) { 3341 end = (curr > start) ? curr : next; // derive end <= length-2 3342 result += '\n' + line.slice(start, end); 3343 // skip the space that was output as \n 3344 start = end + 1; // derive start <= length-1 3345 } 3346 curr = next; 3347 } 3348 3349 // By the invariants, start <= length-1, so there is something left over. 3350 // It is either the whole string or a part starting from non-whitespace. 3351 result += '\n'; 3352 // Insert a break if the remainder is too long and there is a break available. 3353 if (line.length - start > width && curr > start) { 3354 result += line.slice(start, curr) + '\n' + line.slice(curr + 1); 3355 } else { 3356 result += line.slice(start); 3357 } 3358 3359 return result.slice(1); // drop extra \n joiner 3360} 3361 3362// Escapes a double-quoted string. 3363function escapeString(string) { 3364 var result = ''; 3365 var char = 0; 3366 var escapeSeq; 3367 3368 for (var i = 0; i < string.length; char >= 0x10000 ? i += 2 : i++) { 3369 char = codePointAt(string, i); 3370 escapeSeq = ESCAPE_SEQUENCES[char]; 3371 3372 if (!escapeSeq && isPrintable(char)) { 3373 result += string[i]; 3374 if (char >= 0x10000) result += string[i + 1]; 3375 } else { 3376 result += escapeSeq || encodeHex(char); 3377 } 3378 } 3379 3380 return result; 3381} 3382 3383function writeFlowSequence(state, level, object) { 3384 var _result = '', 3385 _tag = state.tag, 3386 index, 3387 length, 3388 value; 3389 3390 for (index = 0, length = object.length; index < length; index += 1) { 3391 value = object[index]; 3392 3393 if (state.replacer) { 3394 value = state.replacer.call(object, String(index), value); 3395 } 3396 3397 // Write only valid elements, put null instead of invalid elements. 3398 if (writeNode(state, level, value, false, false) || 3399 (typeof value === 'undefined' && 3400 writeNode(state, level, null, false, false))) { 3401 3402 if (_result !== '') _result += ',' + (!state.condenseFlow ? ' ' : ''); 3403 _result += state.dump; 3404 } 3405 } 3406 3407 state.tag = _tag; 3408 state.dump = '[' + _result + ']'; 3409} 3410 3411function writeBlockSequence(state, level, object, compact) { 3412 var _result = '', 3413 _tag = state.tag, 3414 index, 3415 length, 3416 value; 3417 3418 for (index = 0, length = object.length; index < length; index += 1) { 3419 value = object[index]; 3420 3421 if (state.replacer) { 3422 value = state.replacer.call(object, String(index), value); 3423 } 3424 3425 // Write only valid elements, put null instead of invalid elements. 3426 if (writeNode(state, level + 1, value, true, true, false, true) || 3427 (typeof value === 'undefined' && 3428 writeNode(state, level + 1, null, true, true, false, true))) { 3429 3430 if (!compact || _result !== '') { 3431 _result += generateNextLine(state, level); 3432 } 3433 3434 if (state.dump && CHAR_LINE_FEED === state.dump.charCodeAt(0)) { 3435 _result += '-'; 3436 } else { 3437 _result += '- '; 3438 } 3439 3440 _result += state.dump; 3441 } 3442 } 3443 3444 state.tag = _tag; 3445 state.dump = _result || '[]'; // Empty sequence if no valid values. 3446} 3447 3448function writeFlowMapping(state, level, object) { 3449 var _result = '', 3450 _tag = state.tag, 3451 objectKeyList = Object.keys(object), 3452 index, 3453 length, 3454 objectKey, 3455 objectValue, 3456 pairBuffer; 3457 3458 for (index = 0, length = objectKeyList.length; index < length; index += 1) { 3459 3460 pairBuffer = ''; 3461 if (_result !== '') pairBuffer += ', '; 3462 3463 if (state.condenseFlow) pairBuffer += '"'; 3464 3465 objectKey = objectKeyList[index]; 3466 objectValue = object[objectKey]; 3467 3468 if (state.replacer) { 3469 objectValue = state.replacer.call(object, objectKey, objectValue); 3470 } 3471 3472 if (!writeNode(state, level, objectKey, false, false)) { 3473 continue; // Skip this pair because of invalid key; 3474 } 3475 3476 if (state.dump.length > 1024) pairBuffer += '? '; 3477 3478 pairBuffer += state.dump + (state.condenseFlow ? '"' : '') + ':' + (state.condenseFlow ? '' : ' '); 3479 3480 if (!writeNode(state, level, objectValue, false, false)) { 3481 continue; // Skip this pair because of invalid value. 3482 } 3483 3484 pairBuffer += state.dump; 3485 3486 // Both key and value are valid. 3487 _result += pairBuffer; 3488 } 3489 3490 state.tag = _tag; 3491 state.dump = '{' + _result + '}'; 3492} 3493 3494function writeBlockMapping(state, level, object, compact) { 3495 var _result = '', 3496 _tag = state.tag, 3497 objectKeyList = Object.keys(object), 3498 index, 3499 length, 3500 objectKey, 3501 objectValue, 3502 explicitPair, 3503 pairBuffer; 3504 3505 // Allow sorting keys so that the output file is deterministic 3506 if (state.sortKeys === true) { 3507 // Default sorting 3508 objectKeyList.sort(); 3509 } else if (typeof state.sortKeys === 'function') { 3510 // Custom sort function 3511 objectKeyList.sort(state.sortKeys); 3512 } else if (state.sortKeys) { 3513 // Something is wrong 3514 throw new exception('sortKeys must be a boolean or a function'); 3515 } 3516 3517 for (index = 0, length = objectKeyList.length; index < length; index += 1) { 3518 pairBuffer = ''; 3519 3520 if (!compact || _result !== '') { 3521 pairBuffer += generateNextLine(state, level); 3522 } 3523 3524 objectKey = objectKeyList[index]; 3525 objectValue = object[objectKey]; 3526 3527 if (state.replacer) { 3528 objectValue = state.replacer.call(object, objectKey, objectValue); 3529 } 3530 3531 if (!writeNode(state, level + 1, objectKey, true, true, true)) { 3532 continue; // Skip this pair because of invalid key. 3533 } 3534 3535 explicitPair = (state.tag !== null && state.tag !== '?') || 3536 (state.dump && state.dump.length > 1024); 3537 3538 if (explicitPair) { 3539 if (state.dump && CHAR_LINE_FEED === state.dump.charCodeAt(0)) { 3540 pairBuffer += '?'; 3541 } else { 3542 pairBuffer += '? '; 3543 } 3544 } 3545 3546 pairBuffer += state.dump; 3547 3548 if (explicitPair) { 3549 pairBuffer += generateNextLine(state, level); 3550 } 3551 3552 if (!writeNode(state, level + 1, objectValue, true, explicitPair)) { 3553 continue; // Skip this pair because of invalid value. 3554 } 3555 3556 if (state.dump && CHAR_LINE_FEED === state.dump.charCodeAt(0)) { 3557 pairBuffer += ':'; 3558 } else { 3559 pairBuffer += ': '; 3560 } 3561 3562 pairBuffer += state.dump; 3563 3564 // Both key and value are valid. 3565 _result += pairBuffer; 3566 } 3567 3568 state.tag = _tag; 3569 state.dump = _result || '{}'; // Empty mapping if no valid pairs. 3570} 3571 3572function detectType(state, object, explicit) { 3573 var _result, typeList, index, length, type, style; 3574 3575 typeList = explicit ? state.explicitTypes : state.implicitTypes; 3576 3577 for (index = 0, length = typeList.length; index < length; index += 1) { 3578 type = typeList[index]; 3579 3580 if ((type.instanceOf || type.predicate) && 3581 (!type.instanceOf || ((typeof object === 'object') && (object instanceof type.instanceOf))) && 3582 (!type.predicate || type.predicate(object))) { 3583 3584 if (explicit) { 3585 if (type.multi && type.representName) { 3586 state.tag = type.representName(object); 3587 } else { 3588 state.tag = type.tag; 3589 } 3590 } else { 3591 state.tag = '?'; 3592 } 3593 3594 if (type.represent) { 3595 style = state.styleMap[type.tag] || type.defaultStyle; 3596 3597 if (_toString.call(type.represent) === '[object Function]') { 3598 _result = type.represent(object, style); 3599 } else if (_hasOwnProperty.call(type.represent, style)) { 3600 _result = type.represent[style](object, style); 3601 } else { 3602 throw new exception('!<' + type.tag + '> tag resolver accepts not "' + style + '" style'); 3603 } 3604 3605 state.dump = _result; 3606 } 3607 3608 return true; 3609 } 3610 } 3611 3612 return false; 3613} 3614 3615// Serializes `object` and writes it to global `result`. 3616// Returns true on success, or false on invalid object. 3617// 3618function writeNode(state, level, object, block, compact, iskey, isblockseq) { 3619 state.tag = null; 3620 state.dump = object; 3621 3622 if (!detectType(state, object, false)) { 3623 detectType(state, object, true); 3624 } 3625 3626 var type = _toString.call(state.dump); 3627 var inblock = block; 3628 var tagStr; 3629 3630 if (block) { 3631 block = (state.flowLevel < 0 || state.flowLevel > level); 3632 } 3633 3634 var objectOrArray = type === '[object Object]' || type === '[object Array]', 3635 duplicateIndex, 3636 duplicate; 3637 3638 if (objectOrArray) { 3639 duplicateIndex = state.duplicates.indexOf(object); 3640 duplicate = duplicateIndex !== -1; 3641 } 3642 3643 if ((state.tag !== null && state.tag !== '?') || duplicate || (state.indent !== 2 && level > 0)) { 3644 compact = false; 3645 } 3646 3647 if (duplicate && state.usedDuplicates[duplicateIndex]) { 3648 state.dump = '*ref_' + duplicateIndex; 3649 } else { 3650 if (objectOrArray && duplicate && !state.usedDuplicates[duplicateIndex]) { 3651 state.usedDuplicates[duplicateIndex] = true; 3652 } 3653 if (type === '[object Object]') { 3654 if (block && (Object.keys(state.dump).length !== 0)) { 3655 writeBlockMapping(state, level, state.dump, compact); 3656 if (duplicate) { 3657 state.dump = '&ref_' + duplicateIndex + state.dump; 3658 } 3659 } else { 3660 writeFlowMapping(state, level, state.dump); 3661 if (duplicate) { 3662 state.dump = '&ref_' + duplicateIndex + ' ' + state.dump; 3663 } 3664 } 3665 } else if (type === '[object Array]') { 3666 if (block && (state.dump.length !== 0)) { 3667 if (state.noArrayIndent && !isblockseq && level > 0) { 3668 writeBlockSequence(state, level - 1, state.dump, compact); 3669 } else { 3670 writeBlockSequence(state, level, state.dump, compact); 3671 } 3672 if (duplicate) { 3673 state.dump = '&ref_' + duplicateIndex + state.dump; 3674 } 3675 } else { 3676 writeFlowSequence(state, level, state.dump); 3677 if (duplicate) { 3678 state.dump = '&ref_' + duplicateIndex + ' ' + state.dump; 3679 } 3680 } 3681 } else if (type === '[object String]') { 3682 if (state.tag !== '?') { 3683 writeScalar(state, state.dump, level, iskey, inblock); 3684 } 3685 } else if (type === '[object Undefined]') { 3686 return false; 3687 } else { 3688 if (state.skipInvalid) return false; 3689 throw new exception('unacceptable kind of an object to dump ' + type); 3690 } 3691 3692 if (state.tag !== null && state.tag !== '?') { 3693 // Need to encode all characters except those allowed by the spec: 3694 // 3695 // [35] ns-dec-digit ::= [#x30-#x39] /* 0-9 */ 3696 // [36] ns-hex-digit ::= ns-dec-digit 3697 // | [#x41-#x46] /* A-F */ | [#x61-#x66] /* a-f */ 3698 // [37] ns-ascii-letter ::= [#x41-#x5A] /* A-Z */ | [#x61-#x7A] /* a-z */ 3699 // [38] ns-word-char ::= ns-dec-digit | ns-ascii-letter | “-” 3700 // [39] ns-uri-char ::= “%” ns-hex-digit ns-hex-digit | ns-word-char | “#” 3701 // | “;” | “/” | “?” | “:” | “@” | “&” | “=” | “+” | “$” | “,” 3702 // | “_” | “.” | “!” | “~” | “*” | “'” | “(” | “)” | “[” | “]” 3703 // 3704 // Also need to encode '!' because it has special meaning (end of tag prefix). 3705 // 3706 tagStr = encodeURI( 3707 state.tag[0] === '!' ? state.tag.slice(1) : state.tag 3708 ).replace(/!/g, '%21'); 3709 3710 if (state.tag[0] === '!') { 3711 tagStr = '!' + tagStr; 3712 } else if (tagStr.slice(0, 18) === 'tag:yaml.org,2002:') { 3713 tagStr = '!!' + tagStr.slice(18); 3714 } else { 3715 tagStr = '!<' + tagStr + '>'; 3716 } 3717 3718 state.dump = tagStr + ' ' + state.dump; 3719 } 3720 } 3721 3722 return true; 3723} 3724 3725function getDuplicateReferences(object, state) { 3726 var objects = [], 3727 duplicatesIndexes = [], 3728 index, 3729 length; 3730 3731 inspectNode(object, objects, duplicatesIndexes); 3732 3733 for (index = 0, length = duplicatesIndexes.length; index < length; index += 1) { 3734 state.duplicates.push(objects[duplicatesIndexes[index]]); 3735 } 3736 state.usedDuplicates = new Array(length); 3737} 3738 3739function inspectNode(object, objects, duplicatesIndexes) { 3740 var objectKeyList, 3741 index, 3742 length; 3743 3744 if (object !== null && typeof object === 'object') { 3745 index = objects.indexOf(object); 3746 if (index !== -1) { 3747 if (duplicatesIndexes.indexOf(index) === -1) { 3748 duplicatesIndexes.push(index); 3749 } 3750 } else { 3751 objects.push(object); 3752 3753 if (Array.isArray(object)) { 3754 for (index = 0, length = object.length; index < length; index += 1) { 3755 inspectNode(object[index], objects, duplicatesIndexes); 3756 } 3757 } else { 3758 objectKeyList = Object.keys(object); 3759 3760 for (index = 0, length = objectKeyList.length; index < length; index += 1) { 3761 inspectNode(object[objectKeyList[index]], objects, duplicatesIndexes); 3762 } 3763 } 3764 } 3765 } 3766} 3767 3768function dump$1(input, options) { 3769 options = options || {}; 3770 3771 var state = new State(options); 3772 3773 if (!state.noRefs) getDuplicateReferences(input, state); 3774 3775 var value = input; 3776 3777 if (state.replacer) { 3778 value = state.replacer.call({ '': value }, '', value); 3779 } 3780 3781 if (writeNode(state, 0, value, true, true)) return state.dump + '\n'; 3782 3783 return ''; 3784} 3785 3786var dump_1 = dump$1; 3787 3788var dumper = { 3789 dump: dump_1 3790}; 3791 3792function renamed(from, to) { 3793 return function () { 3794 throw new Error('Function yaml.' + from + ' is removed in js-yaml 4. ' + 3795 'Use yaml.' + to + ' instead, which is now safe by default.'); 3796 }; 3797} 3798 3799 3800var Type = type; 3801var Schema = schema; 3802var FAILSAFE_SCHEMA = failsafe; 3803var JSON_SCHEMA = json; 3804var CORE_SCHEMA = core; 3805var DEFAULT_SCHEMA = _default; 3806var load = loader.load; 3807var loadAll = loader.loadAll; 3808var dump = dumper.dump; 3809var YAMLException = exception; 3810 3811// Re-export all types in case user wants to create custom schema 3812var types = { 3813 binary: binary, 3814 float: float, 3815 map: map, 3816 null: _null, 3817 pairs: pairs, 3818 set: set, 3819 timestamp: timestamp, 3820 bool: bool, 3821 int: int, 3822 merge: merge, 3823 omap: omap, 3824 seq: seq, 3825 str: str 3826}; 3827 3828// Removed functions from JS-YAML 3.0.x 3829var safeLoad = renamed('safeLoad', 'load'); 3830var safeLoadAll = renamed('safeLoadAll', 'loadAll'); 3831var safeDump = renamed('safeDump', 'dump'); 3832 3833var jsYaml = { 3834 Type: Type, 3835 Schema: Schema, 3836 FAILSAFE_SCHEMA: FAILSAFE_SCHEMA, 3837 JSON_SCHEMA: JSON_SCHEMA, 3838 CORE_SCHEMA: CORE_SCHEMA, 3839 DEFAULT_SCHEMA: DEFAULT_SCHEMA, 3840 load: load, 3841 loadAll: loadAll, 3842 dump: dump, 3843 YAMLException: YAMLException, 3844 types: types, 3845 safeLoad: safeLoad, 3846 safeLoadAll: safeLoadAll, 3847 safeDump: safeDump 3848}; 3849 3850export default jsYaml; 3851export { CORE_SCHEMA, DEFAULT_SCHEMA, FAILSAFE_SCHEMA, JSON_SCHEMA, Schema, Type, YAMLException, dump, load, loadAll, safeDump, safeLoad, safeLoadAll, types }; 3852