1var Vue = (function (exports) { 2 'use strict'; 3 4 /** 5 * Make a map and return a function for checking if a key 6 * is in that map. 7 * IMPORTANT: all calls of this function must be prefixed with 8 * \/\*#\_\_PURE\_\_\*\/ 9 * So that rollup can tree-shake them if necessary. 10 */ 11 function makeMap(str, expectsLowerCase) { 12 const map = Object.create(null); 13 const list = str.split(','); 14 for (let i = 0; i < list.length; i++) { 15 map[list[i]] = true; 16 } 17 return expectsLowerCase ? val => !!map[val.toLowerCase()] : val => !!map[val]; 18 } 19 20 /** 21 * dev only flag -> name mapping 22 */ 23 const PatchFlagNames = { 24 [1 /* PatchFlags.TEXT */]: `TEXT`, 25 [2 /* PatchFlags.CLASS */]: `CLASS`, 26 [4 /* PatchFlags.STYLE */]: `STYLE`, 27 [8 /* PatchFlags.PROPS */]: `PROPS`, 28 [16 /* PatchFlags.FULL_PROPS */]: `FULL_PROPS`, 29 [32 /* PatchFlags.HYDRATE_EVENTS */]: `HYDRATE_EVENTS`, 30 [64 /* PatchFlags.STABLE_FRAGMENT */]: `STABLE_FRAGMENT`, 31 [128 /* PatchFlags.KEYED_FRAGMENT */]: `KEYED_FRAGMENT`, 32 [256 /* PatchFlags.UNKEYED_FRAGMENT */]: `UNKEYED_FRAGMENT`, 33 [512 /* PatchFlags.NEED_PATCH */]: `NEED_PATCH`, 34 [1024 /* PatchFlags.DYNAMIC_SLOTS */]: `DYNAMIC_SLOTS`, 35 [2048 /* PatchFlags.DEV_ROOT_FRAGMENT */]: `DEV_ROOT_FRAGMENT`, 36 [-1 /* PatchFlags.HOISTED */]: `HOISTED`, 37 [-2 /* PatchFlags.BAIL */]: `BAIL` 38 }; 39 40 /** 41 * Dev only 42 */ 43 const slotFlagsText = { 44 [1 /* SlotFlags.STABLE */]: 'STABLE', 45 [2 /* SlotFlags.DYNAMIC */]: 'DYNAMIC', 46 [3 /* SlotFlags.FORWARDED */]: 'FORWARDED' 47 }; 48 49 const GLOBALS_WHITE_LISTED = 'Infinity,undefined,NaN,isFinite,isNaN,parseFloat,parseInt,decodeURI,' + 50 'decodeURIComponent,encodeURI,encodeURIComponent,Math,Number,Date,Array,' + 51 'Object,Boolean,String,RegExp,Map,Set,JSON,Intl,BigInt'; 52 const isGloballyWhitelisted = /*#__PURE__*/ makeMap(GLOBALS_WHITE_LISTED); 53 54 const range = 2; 55 function generateCodeFrame(source, start = 0, end = source.length) {
vendor: 4,204 bytes, lines 56-173
56 // Split the content into individual lines but capture the newline sequence 57 // that separated each line. This is important because the actual sequence is 58 // needed to properly take into account the full line length for offset 59 // comparison 60 let lines = source.split(/(\r?\n)/); 61 // Separate the lines and newline sequences into separate arrays for easier referencing 62 const newlineSequences = lines.filter((_, idx) => idx % 2 === 1); 63 lines = lines.filter((_, idx) => idx % 2 === 0); 64 let count = 0; 65 const res = []; 66 for (let i = 0; i < lines.length; i++) { 67 count += 68 lines[i].length + 69 ((newlineSequences[i] && newlineSequences[i].length) || 0); 70 if (count >= start) { 71 for (let j = i - range; j <= i + range || end > count; j++) { 72 if (j < 0 || j >= lines.length) 73 continue; 74 const line = j + 1; 75 res.push(`${line}${' '.repeat(Math.max(3 - String(line).length, 0))}| ${lines[j]}`); 76 const lineLength = lines[j].length; 77 const newLineSeqLength = (newlineSequences[j] && newlineSequences[j].length) || 0; 78 if (j === i) { 79 // push underline 80 const pad = start - (count - (lineLength + newLineSeqLength)); 81 const length = Math.max(1, end > count ? lineLength - pad : end - start); 82 res.push(` | ` + ' '.repeat(pad) + '^'.repeat(length)); 83 } 84 else if (j > i) { 85 if (end > count) { 86 const length = Math.max(Math.min(end - count, lineLength), 1); 87 res.push(` | ` + '^'.repeat(length)); 88 } 89 count += lineLength + newLineSeqLength; 90 } 91 } 92 break; 93 } 94 } 95 return res.join('\n'); 96 } 97 98 function normalizeStyle(value) { 99 if (isArray(value)) { 100 const res = {}; 101 for (let i = 0; i < value.length; i++) { 102 const item = value[i]; 103 const normalized = isString(item) 104 ? parseStringStyle(item) 105 : normalizeStyle(item); 106 if (normalized) { 107 for (const key in normalized) { 108 res[key] = normalized[key]; 109 } 110 } 111 } 112 return res; 113 } 114 else if (isString(value)) { 115 return value; 116 } 117 else if (isObject(value)) { 118 return value; 119 } 120 } 121 const listDelimiterRE = /;(?![^(]*\))/g; 122 const propertyDelimiterRE = /:([^]+)/; 123 const styleCommentRE = /\/\*.*?\*\//gs; 124 function parseStringStyle(cssText) { 125 const ret = {}; 126 cssText 127 .replace(styleCommentRE, '') 128 .split(listDelimiterRE) 129 .forEach(item => { 130 if (item) { 131 const tmp = item.split(propertyDelimiterRE); 132 tmp.length > 1 && (ret[tmp[0].trim()] = tmp[1].trim()); 133 } 134 }); 135 return ret; 136 } 137 function normalizeClass(value) { 138 let res = ''; 139 if (isString(value)) { 140 res = value; 141 } 142 else if (isArray(value)) { 143 for (let i = 0; i < value.length; i++) { 144 const normalized = normalizeClass(value[i]); 145 if (normalized) { 146 res += normalized + ' '; 147 } 148 } 149 } 150 else if (isObject(value)) { 151 for (const name in value) { 152 if (value[name]) { 153 res += name + ' '; 154 } 155 } 156 } 157 return res.trim(); 158 } 159 function normalizeProps(props) { 160 if (!props) 161 return null; 162 let { class: klass, style } = props; 163 if (klass && !isString(klass)) { 164 props.class = normalizeClass(klass); 165 } 166 if (style) { 167 props.style = normalizeStyle(style); 168 } 169 return props; 170 } 171 172 // These tag configs are shared between compiler-dom and runtime-dom, so they 173 // https://developer.mozilla.org/en-US/docs/Web/HTML/Element
174 const HTML_TAGS = 'html,body,base,head,link,meta,style,title,address,article,aside,footer,' + 175 'header,h1,h2,h3,h4,h5,h6,nav,section,div,dd,dl,dt,figcaption,' + 176 'figure,picture,hr,img,li,main,ol,p,pre,ul,a,b,abbr,bdi,bdo,br,cite,code,' + 177 'data,dfn,em,i,kbd,mark,q,rp,rt,ruby,s,samp,small,span,strong,sub,sup,' + 178 'time,u,var,wbr,area,audio,map,track,video,embed,object,param,source,' + 179 'canvas,script,noscript,del,ins,caption,col,colgroup,table,thead,tbody,td,' + 180 'th,tr,button,datalist,fieldset,form,input,label,legend,meter,optgroup,' + 181 'option,output,progress,select,textarea,details,dialog,menu,' + 182 'summary,template,blockquote,iframe,tfoot'; 183 // https://developer.mozilla.org/en-US/docs/Web/SVG/Element 184 const SVG_TAGS = 'svg,animate,animateMotion,animateTransform,circle,clipPath,color-profile,' + 185 'defs,desc,discard,ellipse,feBlend,feColorMatrix,feComponentTransfer,' + 186 'feComposite,feConvolveMatrix,feDiffuseLighting,feDisplacementMap,' + 187 'feDistanceLight,feDropShadow,feFlood,feFuncA,feFuncB,feFuncG,feFuncR,' + 188 'feGaussianBlur,feImage,feMerge,feMergeNode,feMorphology,feOffset,' + 189 'fePointLight,feSpecularLighting,feSpotLight,feTile,feTurbulence,filter,' + 190 'foreignObject,g,hatch,hatchpath,image,line,linearGradient,marker,mask,' + 191 'mesh,meshgradient,meshpatch,meshrow,metadata,mpath,path,pattern,' + 192 'polygon,polyline,radialGradient,rect,set,solidcolor,stop,switch,symbol,' + 193 'text,textPath,title,tspan,unknown,use,view'; 194 const VOID_TAGS = 'area,base,br,col,embed,hr,img,input,link,meta,param,source,track,wbr'; 195 /** 196 * Compiler only. 197 * Do NOT use in runtime code paths unless behind `true` flag. 198 */ 199 const isHTMLTag = /*#__PURE__*/ makeMap(HTML_TAGS); 200 /** 201 * Compiler only. 202 * Do NOT use in runtime code paths unless behind `true` flag. 203 */ 204 const isSVGTag = /*#__PURE__*/ makeMap(SVG_TAGS); 205 /** 206 * Compiler only. 207 * Do NOT use in runtime code paths unless behind `true` flag. 208 */ 209 const isVoidTag = /*#__PURE__*/ makeMap(VOID_TAGS); 210 211 /** 212 * On the client we only need to offer special cases for boolean attributes that 213 * have different names from their corresponding dom properties: 214 * - itemscope -> N/A 215 * - allowfullscreen -> allowFullscreen 216 * - formnovalidate -> formNoValidate 217 * - ismap -> isMap 218 * - nomodule -> noModule 219 * - novalidate -> noValidate 220 * - readonly -> readOnly 221 */ 222 const specialBooleanAttrs = `itemscope,allowfullscreen,formnovalidate,ismap,nomodule,novalidate,readonly`; 223 const isSpecialBooleanAttr = /*#__PURE__*/ makeMap(specialBooleanAttrs); 224 /** 225 * Boolean attributes should be included if the value is truthy or ''. 226 * e.g. `<select multiple>` compiles to `{ multiple: '' }` 227 */ 228 function includeBooleanAttr(value) { 229 return !!value || value === ''; 230 } 231 232 function looseCompareArrays(a, b) { 233 if (a.length !== b.length) 234 return false; 235 let equal = true; 236 for (let i = 0; equal && i < a.length; i++) { 237 equal = looseEqual(a[i], b[i]); 238 } 239 return equal; 240 } 241 function looseEqual(a, b) { 242 if (a === b) 243 return true; 244 let aValidType = isDate(a); 245 let bValidType = isDate(b); 246 if (aValidType || bValidType) { 247 return aValidType && bValidType ? a.getTime() === b.getTime() : false; 248 } 249 aValidType = isSymbol(a); 250 bValidType = isSymbol(b); 251 if (aValidType || bValidType) { 252 return a === b; 253 } 254 aValidType = isArray(a); 255 bValidType = isArray(b); 256 if (aValidType || bValidType) { 257 return aValidType && bValidType ? looseCompareArrays(a, b) : false; 258 } 259 aValidType = isObject(a); 260 bValidType = isObject(b); 261 if (aValidType || bValidType) { 262 /* istanbul ignore if: this if will probably never be called */ 263 if (!aValidType || !bValidType) { 264 return false; 265 } 266 const aKeysCount = Object.keys(a).length; 267 const bKeysCount = Object.keys(b).length; 268 if (aKeysCount !== bKeysCount) { 269 return false;
270 } 271 for (const key in a) { 272 const aHasKey = a.hasOwnProperty(key); 273 const bHasKey = b.hasOwnProperty(key); 274 if ((aHasKey && !bHasKey) || 275 (!aHasKey && bHasKey) || 276 !looseEqual(a[key], b[key])) { 277 return false; 278 } 279 } 280 } 281 return String(a) === String(b); 282 } 283 function looseIndexOf(arr, val) { 284 return arr.findIndex(item => looseEqual(item, val)); 285 } 286 287 /** 288 * For converting {{ interpolation }} values to displayed strings. 289 * @private 290 */ 291 const toDisplayString = (val) => { 292 return isString(val) 293 ? val 294 : val == null 295 ? '' 296 : isArray(val) || 297 (isObject(val) && 298 (val.toString === objectToString || !isFunction(val.toString))) 299 ? JSON.stringify(val, replacer, 2) 300 : String(val); 301 }; 302 const replacer = (_key, val) => { 303 // can't use isRef here since @vue/shared has no deps 304 if (val && val.__v_isRef) { 305 return replacer(_key, val.value); 306 } 307 else if (isMap(val)) { 308 return { 309 [`Map(${val.size})`]: [...val.entries()].reduce((entries, [key, val]) => { 310 entries[`${key} =>`] = val; 311 return entries; 312 }, {}) 313 }; 314 } 315 else if (isSet(val)) { 316 return { 317 [`Set(${val.size})`]: [...val.values()] 318 }; 319 } 320 else if (isObject(val) && !isArray(val) && !isPlainObject(val)) { 321 return String(val); 322 } 323 return val; 324 }; 325 326 const EMPTY_OBJ = Object.freeze({}) 327 ; 328 const EMPTY_ARR = Object.freeze([]) ; 329 const NOOP = () => { }; 330 /** 331 * Always return false. 332 */ 333 const NO = () => false; 334 const onRE = /^on[^a-z]/; 335 const isOn = (key) => onRE.test(key); 336 const isModelListener = (key) => key.startsWith('onUpdate:'); 337 const extend = Object.assign; 338 const remove = (arr, el) => { 339 const i = arr.indexOf(el); 340 if (i > -1) { 341 arr.splice(i, 1); 342 } 343 }; 344 const hasOwnProperty = Object.prototype.hasOwnProperty; 345 const hasOwn = (val, key) => hasOwnProperty.call(val, key); 346 const isArray = Array.isArray; 347 const isMap = (val) => toTypeString(val) === '[object Map]'; 348 const isSet = (val) => toTypeString(val) === '[object Set]'; 349 const isDate = (val) => toTypeString(val) === '[object Date]'; 350 const isFunction = (val) => typeof val === 'function'; 351 const isString = (val) => typeof val === 'string'; 352 const isSymbol = (val) => typeof val === 'symbol'; 353 const isObject = (val) => val !== null && typeof val === 'object'; 354 const isPromise = (val) => { 355 return isObject(val) && isFunction(val.then) && isFunction(val.catch); 356 }; 357 const objectToString = Object.prototype.toString; 358 const toTypeString = (value) => objectToString.call(value); 359 const toRawType = (value) => { 360 // extract "RawType" from strings like "[object RawType]" 361 return toTypeString(value).slice(8, -1); 362 }; 363 const isPlainObject = (val) => toTypeString(val) === '[object Object]'; 364 const isIntegerKey = (key) => isString(key) && 365 key !== 'NaN' && 366 key[0] !== '-' && 367 '' + parseInt(key, 10) === key; 368 const isReservedProp = /*#__PURE__*/ makeMap( 369 // the leading comma is intentional so empty string "" is also included 370 ',key,ref,ref_for,ref_key,' + 371 'onVnodeBeforeMount,onVnodeMounted,' + 372 'onVnodeBeforeUpdate,onVnodeUpdated,' + 373 'onVnodeBeforeUnmount,onVnodeUnmounted'); 374 const isBuiltInDirective = /*#__PURE__*/ makeMap('bind,cloak,else-if,else,for,html,if,model,on,once,pre,show,slot,text,memo'); 375 const cacheStringFunction = (fn) => { 376 const cache = Object.create(null); 377 return ((str) => { 378 const hit = cache[str]; 379 return hit || (cache[str] = fn(str)); 380 }); 381 }; 382 const camelizeRE = /-(\w)/g; 383 /** 384 * @private 385 */ 386 const camelize = cacheStringFunction((str) => { 387 return str.replace(camelizeRE, (_, c) => (c ? c.toUpperCase() : '')); 388 }); 389 const hyphenateRE = /\B([A-Z])/g; 390 /** 391 * @private 392 */ 393 const hyphenate = cacheStringFunction((str) => str.replace(hyphenateRE, '-$1').toLowerCase()); 394 /** 395 * @private 396 */ 397 const capitalize = cacheStringFunction((str) => str.charAt(0).toUpperCase() + str.slice(1)); 398 /** 399 * @private 400 */ 401 const toHandlerKey = cacheStringFunction((str) => str ? `on${capitalize(str)}` : ``); 402 // compare whether a value has changed, accounting for NaN. 403 const hasChanged = (value, oldValue) => !Object.is(value, oldValue); 404 const invokeArrayFns = (fns, arg) => { 405 for (let i = 0; i < fns.length; i++) { 406 fns[i](arg); 407 } 408 }; 409 const def = (obj, key, value) => { 410 Object.defineProperty(obj, key, { 411 configurable: true, 412 enumerable: false, 413 value 414 }); 415 }; 416 const toNumber = (val) => { 417 const n = parseFloat(val); 418 return isNaN(n) ? val : n; 419 }; 420 let _globalThis; 421 const getGlobalThis = () => { 422 return (_globalThis || 423 (_globalThis = 424 typeof globalThis !== 'undefined' 425 ? globalThis 426 : typeof self !== 'undefined' 427 ? self 428 : typeof window !== 'undefined' 429 ? window 430 : typeof global !== 'undefined' 431 ? global 432 : {})); 433 }; 434 435 function warn(msg, ...args) { 436 console.warn(`[Vue warn] ${msg}`, ...args); 437 } 438 439 let activeEffectScope; 440 class EffectScope { 441 constructor(detached = false) { 442 this.detached = detached; 443 /** 444 * @internal 445 */ 446 this.active = true; 447 /** 448 * @internal 449 */ 450 this.effects = []; 451 /** 452 * @internal 453 */ 454 this.cleanups = []; 455 this.parent = activeEffectScope; 456 if (!detached && activeEffectScope) { 457 this.index = 458 (activeEffectScope.scopes || (activeEffectScope.scopes = [])).push(this) - 1; 459 } 460 } 461 run(fn) { 462 if (this.active) { 463 const currentEffectScope = activeEffectScope; 464 try { 465 activeEffectScope = this; 466 return fn(); 467 } 468 finally { 469 activeEffectScope = currentEffectScope; 470 } 471 } 472 else { 473 warn(`cannot run an inactive effect scope.`); 474 } 475 } 476 /** 477 * This should only be called on non-detached scopes 478 * @internal 479 */ 480 on() { 481 activeEffectScope = this; 482 } 483 /** 484 * This should only be called on non-detached scopes 485 * @internal 486 */ 487 off() { 488 activeEffectScope = this.parent; 489 } 490 stop(fromParent) { 491 if (this.active) { 492 let i, l; 493 for (i = 0, l = this.effects.length; i < l; i++) { 494 this.effects[i].stop(); 495 } 496 for (i = 0, l = this.cleanups.length; i < l; i++) { 497 this.cleanups[i](); 498 } 499 if (this.scopes) { 500 for (i = 0, l = this.scopes.length; i < l; i++) { 501 this.scopes[i].stop(true); 502 } 503 } 504 // nested scope, dereference from parent to avoid memory leaks 505 if (!this.detached && this.parent && !fromParent) { 506 // optimized O(1) removal 507 const last = this.parent.scopes.pop(); 508 if (last && last !== this) { 509 this.parent.scopes[this.index] = last; 510 last.index = this.index; 511 } 512 } 513 this.parent = undefined; 514 this.active = false;
515 } 516 } 517 } 518 function effectScope(detached) { 519 return new EffectScope(detached); 520 } 521 function recordEffectScope(effect, scope = activeEffectScope) { 522 if (scope && scope.active) { 523 scope.effects.push(effect); 524 } 525 } 526 function getCurrentScope() { 527 return activeEffectScope; 528 } 529 function onScopeDispose(fn) { 530 if (activeEffectScope) { 531 activeEffectScope.cleanups.push(fn); 532 } 533 else { 534 warn(`onScopeDispose() is called when there is no active effect scope` + 535 ` to be associated with.`); 536 } 537 } 538 539 const createDep = (effects) => { 540 const dep = new Set(effects); 541 dep.w = 0; 542 dep.n = 0; 543 return dep; 544 }; 545 const wasTracked = (dep) => (dep.w & trackOpBit) > 0; 546 const newTracked = (dep) => (dep.n & trackOpBit) > 0; 547 const initDepMarkers = ({ deps }) => { 548 if (deps.length) { 549 for (let i = 0; i < deps.length; i++) { 550 deps[i].w |= trackOpBit; // set was tracked 551 } 552 } 553 }; 554 const finalizeDepMarkers = (effect) => { 555 const { deps } = effect; 556 if (deps.length) { 557 let ptr = 0; 558 for (let i = 0; i < deps.length; i++) { 559 const dep = deps[i]; 560 if (wasTracked(dep) && !newTracked(dep)) { 561 dep.delete(effect); 562 } 563 else { 564 deps[ptr++] = dep; 565 } 566 // clear bits 567 dep.w &= ~trackOpBit; 568 dep.n &= ~trackOpBit; 569 } 570 deps.length = ptr; 571 } 572 }; 573 574 const targetMap = new WeakMap(); 575 // The number of effects currently being tracked recursively. 576 let effectTrackDepth = 0; 577 let trackOpBit = 1; 578 /** 579 * The bitwise track markers support at most 30 levels of recursion. 580 * This value is chosen to enable modern JS engines to use a SMI on all platforms. 581 * When recursion depth is greater, fall back to using a full cleanup. 582 */ 583 const maxMarkerBits = 30; 584 let activeEffect; 585 const ITERATE_KEY = Symbol('iterate' ); 586 const MAP_KEY_ITERATE_KEY = Symbol('Map key iterate' ); 587 class ReactiveEffect { 588 constructor(fn, scheduler = null, scope) { 589 this.fn = fn; 590 this.scheduler = scheduler; 591 this.active = true; 592 this.deps = []; 593 this.parent = undefined; 594 recordEffectScope(this, scope); 595 } 596 run() { 597 if (!this.active) { 598 return this.fn(); 599 } 600 let parent = activeEffect; 601 let lastShouldTrack = shouldTrack; 602 while (parent) { 603 if (parent === this) { 604 return; 605 } 606 parent = parent.parent; 607 } 608 try { 609 this.parent = activeEffect; 610 activeEffect = this; 611 shouldTrack = true; 612 trackOpBit = 1 << ++effectTrackDepth; 613 if (effectTrackDepth <= maxMarkerBits) { 614 initDepMarkers(this); 615 } 616 else { 617 cleanupEffect(this); 618 } 619 return this.fn(); 620 } 621 finally { 622 if (effectTrackDepth <= maxMarkerBits) { 623 finalizeDepMarkers(this); 624 } 625 trackOpBit = 1 << --effectTrackDepth; 626 activeEffect = this.parent; 627 shouldTrack = lastShouldTrack; 628 this.parent = undefined; 629 if (this.deferStop) { 630 this.stop(); 631 } 632 } 633 } 634 stop() { 635 // stopped while running itself - defer the cleanup 636 if (activeEffect === this) { 637 this.deferStop = true; 638 } 639 else if (this.active) { 640 cleanupEffect(this); 641 if (this.onStop) { 642 this.onStop(); 643 } 644 this.active = false; 645 } 646 } 647 } 648 function cleanupEffect(effect) { 649 const { deps } = effect; 650 if (deps.length) { 651 for (let i = 0; i < deps.length; i++) { 652 deps[i].delete(effect); 653 } 654 deps.length = 0; 655 } 656 } 657 function effect(fn, options) { 658 if (fn.effect) { 659 fn = fn.effect.fn; 660 } 661 const _effect = new ReactiveEffect(fn); 662 if (options) { 663 extend(_effect, options); 664 if (options.scope) 665 recordEffectScope(_effect, options.scope); 666 } 667 if (!options || !options.lazy) { 668 _effect.run(); 669 } 670 const runner = _effect.run.bind(_effect); 671 runner.effect = _effect; 672 return runner; 673 } 674 function stop(runner) { 675 runner.effect.stop(); 676 } 677 let shouldTrack = true; 678 const trackStack = []; 679 function pauseTracking() { 680 trackStack.push(shouldTrack); 681 shouldTrack = false;
682 } 683 function resetTracking() { 684 const last = trackStack.pop(); 685 shouldTrack = last === undefined ? true : last; 686 } 687 function track(target, type, key) { 688 if (shouldTrack && activeEffect) { 689 let depsMap = targetMap.get(target); 690 if (!depsMap) { 691 targetMap.set(target, (depsMap = new Map())); 692 } 693 let dep = depsMap.get(key); 694 if (!dep) { 695 depsMap.set(key, (dep = createDep())); 696 } 697 const eventInfo = { effect: activeEffect, target, type, key } 698 ; 699 trackEffects(dep, eventInfo); 700 } 701 } 702 function trackEffects(dep, debuggerEventExtraInfo) { 703 let shouldTrack = false; 704 if (effectTrackDepth <= maxMarkerBits) { 705 if (!newTracked(dep)) { 706 dep.n |= trackOpBit; // set newly tracked 707 shouldTrack = !wasTracked(dep); 708 } 709 } 710 else { 711 // Full cleanup mode. 712 shouldTrack = !dep.has(activeEffect); 713 } 714 if (shouldTrack) { 715 dep.add(activeEffect); 716 activeEffect.deps.push(dep); 717 if (activeEffect.onTrack) { 718 activeEffect.onTrack(Object.assign({ effect: activeEffect }, debuggerEventExtraInfo)); 719 } 720 } 721 } 722 function trigger(target, type, key, newValue, oldValue, oldTarget) { 723 const depsMap = targetMap.get(target); 724 if (!depsMap) { 725 // never been tracked 726 return; 727 } 728 let deps = []; 729 if (type === "clear" /* TriggerOpTypes.CLEAR */) { 730 // collection being cleared 731 // trigger all effects for target 732 deps = [...depsMap.values()]; 733 } 734 else if (key === 'length' && isArray(target)) { 735 const newLength = toNumber(newValue); 736 depsMap.forEach((dep, key) => { 737 if (key === 'length' || key >= newLength) { 738 deps.push(dep); 739 } 740 }); 741 } 742 else { 743 // schedule runs for SET | ADD | DELETE 744 if (key !== void 0) { 745 deps.push(depsMap.get(key)); 746 } 747 // also run for iteration key on ADD | DELETE | Map.SET 748 switch (type) { 749 case "add" /* TriggerOpTypes.ADD */: 750 if (!isArray(target)) { 751 deps.push(depsMap.get(ITERATE_KEY)); 752 if (isMap(target)) { 753 deps.push(depsMap.get(MAP_KEY_ITERATE_KEY)); 754 } 755 } 756 else if (isIntegerKey(key)) { 757 // new index added to array -> length changes 758 deps.push(depsMap.get('length')); 759 } 760 break; 761 case "delete" /* TriggerOpTypes.DELETE */: 762 if (!isArray(target)) { 763 deps.push(depsMap.get(ITERATE_KEY)); 764 if (isMap(target)) { 765 deps.push(depsMap.get(MAP_KEY_ITERATE_KEY)); 766 } 767 } 768 break; 769 case "set" /* TriggerOpTypes.SET */: 770 if (isMap(target)) { 771 deps.push(depsMap.get(ITERATE_KEY)); 772 } 773 break; 774 } 775 } 776 const eventInfo = { target, type, key, newValue, oldValue, oldTarget } 777 ; 778 if (deps.length === 1) { 779 if (deps[0]) { 780 { 781 triggerEffects(deps[0], eventInfo); 782 } 783 } 784 } 785 else { 786 const effects = []; 787 for (const dep of deps) { 788 if (dep) { 789 effects.push(...dep); 790 } 791 } 792 { 793 triggerEffects(createDep(effects), eventInfo); 794 } 795 } 796 } 797 function triggerEffects(dep, debuggerEventExtraInfo) { 798 // spread into array for stabilization 799 const effects = isArray(dep) ? dep : [...dep]; 800 for (const effect of effects) { 801 if (effect.computed) { 802 triggerEffect(effect, debuggerEventExtraInfo); 803 } 804 } 805 for (const effect of effects) { 806 if (!effect.computed) { 807 triggerEffect(effect, debuggerEventExtraInfo); 808 } 809 } 810 } 811 function triggerEffect(effect, debuggerEventExtraInfo) { 812 if (effect !== activeEffect || effect.allowRecurse) { 813 if (effect.onTrigger) { 814 effect.onTrigger(extend({ effect }, debuggerEventExtraInfo)); 815 } 816 if (effect.scheduler) { 817 effect.scheduler(); 818 } 819 else { 820 effect.run(); 821 } 822 } 823 } 824 825 const isNonTrackableKeys = /*#__PURE__*/ makeMap(`__proto__,__v_isRef,__isVue`);
826 const builtInSymbols = new Set( 827 /*#__PURE__*/ 828 Object.getOwnPropertyNames(Symbol) 829 // ios10.x Object.getOwnPropertyNames(Symbol) can enumerate 'arguments' and 'caller' 830 // but accessing them on Symbol leads to TypeError because Symbol is a strict mode 831 // function 832 .filter(key => key !== 'arguments' && key !== 'caller') 833 .map(key => Symbol[key]) 834 .filter(isSymbol)); 835 const get = /*#__PURE__*/ createGetter(); 836 const shallowGet = /*#__PURE__*/ createGetter(false, true); 837 const readonlyGet = /*#__PURE__*/ createGetter(true); 838 const shallowReadonlyGet = /*#__PURE__*/ createGetter(true, true); 839 const arrayInstrumentations = /*#__PURE__*/ createArrayInstrumentations(); 840 function createArrayInstrumentations() { 841 const instrumentations = {}; 842 ['includes', 'indexOf', 'lastIndexOf'].forEach(key => { 843 instrumentations[key] = function (...args) { 844 const arr = toRaw(this); 845 for (let i = 0, l = this.length; i < l; i++) { 846 track(arr, "get" /* TrackOpTypes.GET */, i + ''); 847 } 848 // we run the method using the original args first (which may be reactive) 849 const res = arr[key](...args); 850 if (res === -1 || res === false) { 851 // if that didn't work, run it again using raw values. 852 return arr[key](...args.map(toRaw)); 853 } 854 else { 855 return res; 856 } 857 }; 858 }); 859 ['push', 'pop', 'shift', 'unshift', 'splice'].forEach(key => { 860 instrumentations[key] = function (...args) { 861 pauseTracking(); 862 const res = toRaw(this)[key].apply(this, args); 863 resetTracking(); 864 return res; 865 }; 866 }); 867 return instrumentations; 868 } 869 function createGetter(isReadonly = false, shallow = false) { 870 return function get(target, key, receiver) { 871 if (key === "__v_isReactive" /* ReactiveFlags.IS_REACTIVE */) { 872 return !isReadonly; 873 } 874 else if (key === "__v_isReadonly" /* ReactiveFlags.IS_READONLY */) { 875 return isReadonly; 876 } 877 else if (key === "__v_isShallow" /* ReactiveFlags.IS_SHALLOW */) { 878 return shallow; 879 } 880 else if (key === "__v_raw" /* ReactiveFlags.RAW */ && 881 receiver === 882 (isReadonly 883 ? shallow 884 ? shallowReadonlyMap 885 : readonlyMap 886 : shallow 887 ? shallowReactiveMap 888 : reactiveMap).get(target)) { 889 return target; 890 } 891 const targetIsArray = isArray(target); 892 if (!isReadonly && targetIsArray && hasOwn(arrayInstrumentations, key)) { 893 return Reflect.get(arrayInstrumentations, key, receiver); 894 } 895 const res = Reflect.get(target, key, receiver); 896 if (isSymbol(key) ? builtInSymbols.has(key) : isNonTrackableKeys(key)) { 897 return res; 898 } 899 if (!isReadonly) { 900 track(target, "get" /* TrackOpTypes.GET */, key); 901 } 902 if (shallow) { 903 return res; 904 } 905 if (isRef(res)) { 906 // ref unwrapping - skip unwrap for Array + integer key. 907 return targetIsArray && isIntegerKey(key) ? res : res.value; 908 } 909 if (isObject(res)) { 910 // Convert returned value into a proxy as well. we do the isObject check 911 // here to avoid invalid value warning. Also need to lazy access readonly 912 // and reactive here to avoid circular dependency. 913 return isReadonly ? readonly(res) : reactive(res); 914 } 915 return res; 916 }; 917 } 918 const set = /*#__PURE__*/ createSetter(); 919 const shallowSet = /*#__PURE__*/ createSetter(true); 920 function createSetter(shallow = false) { 921 return function set(target, key, value, receiver) { 922 let oldValue = target[key]; 923 if (isReadonly(oldValue) && isRef(oldValue) && !isRef(value)) { 924 return false;
925 } 926 if (!shallow) { 927 if (!isShallow(value) && !isReadonly(value)) { 928 oldValue = toRaw(oldValue); 929 value = toRaw(value); 930 } 931 if (!isArray(target) && isRef(oldValue) && !isRef(value)) { 932 oldValue.value = value; 933 return true; 934 } 935 } 936 const hadKey = isArray(target) && isIntegerKey(key) 937 ? Number(key) < target.length 938 : hasOwn(target, key); 939 const result = Reflect.set(target, key, value, receiver); 940 // don't trigger if target is something up in the prototype chain of original 941 if (target === toRaw(receiver)) { 942 if (!hadKey) { 943 trigger(target, "add" /* TriggerOpTypes.ADD */, key, value); 944 } 945 else if (hasChanged(value, oldValue)) { 946 trigger(target, "set" /* TriggerOpTypes.SET */, key, value, oldValue); 947 } 948 } 949 return result; 950 }; 951 } 952 function deleteProperty(target, key) { 953 const hadKey = hasOwn(target, key); 954 const oldValue = target[key]; 955 const result = Reflect.deleteProperty(target, key); 956 if (result && hadKey) { 957 trigger(target, "delete" /* TriggerOpTypes.DELETE */, key, undefined, oldValue); 958 } 959 return result; 960 } 961 function has(target, key) { 962 const result = Reflect.has(target, key); 963 if (!isSymbol(key) || !builtInSymbols.has(key)) { 964 track(target, "has" /* TrackOpTypes.HAS */, key); 965 } 966 return result; 967 } 968 function ownKeys(target) { 969 track(target, "iterate" /* TrackOpTypes.ITERATE */, isArray(target) ? 'length' : ITERATE_KEY); 970 return Reflect.ownKeys(target); 971 } 972 const mutableHandlers = { 973 get, 974 set, 975 deleteProperty, 976 has, 977 ownKeys 978 }; 979 const readonlyHandlers = { 980 get: readonlyGet, 981 set(target, key) { 982 { 983 warn(`Set operation on key "${String(key)}" failed: target is readonly.`, target); 984 } 985 return true; 986 }, 987 deleteProperty(target, key) { 988 { 989 warn(`Delete operation on key "${String(key)}" failed: target is readonly.`, target); 990 } 991 return true; 992 } 993 }; 994 const shallowReactiveHandlers = /*#__PURE__*/ extend({}, mutableHandlers, { 995 get: shallowGet, 996 set: shallowSet 997 }); 998 // Props handlers are special in the sense that it should not unwrap top-level 999 // refs (in order to allow refs to be explicitly passed down), but should 1000 // retain the reactivity of the normal readonly object. 1001 const shallowReadonlyHandlers = /*#__PURE__*/ extend({}, readonlyHandlers, { 1002 get: shallowReadonlyGet 1003 }); 1004 1005 const toShallow = (value) => value; 1006 const getProto = (v) => Reflect.getPrototypeOf(v); 1007 function get$1(target, key, isReadonly = false, isShallow = false) { 1008 // #1772: readonly(reactive(Map)) should return readonly + reactive version 1009 // of the value 1010 target = target["__v_raw" /* ReactiveFlags.RAW */]; 1011 const rawTarget = toRaw(target); 1012 const rawKey = toRaw(key); 1013 if (!isReadonly) { 1014 if (key !== rawKey) { 1015 track(rawTarget, "get" /* TrackOpTypes.GET */, key); 1016 } 1017 track(rawTarget, "get" /* TrackOpTypes.GET */, rawKey); 1018 } 1019 const { has } = getProto(rawTarget); 1020 const wrap = isShallow ? toShallow : isReadonly ? toReadonly : toReactive; 1021 if (has.call(rawTarget, key)) { 1022 return wrap(target.get(key)); 1023 } 1024 else if (has.call(rawTarget, rawKey)) { 1025 return wrap(target.get(rawKey)); 1026 } 1027 else if (target !== rawTarget) { 1028 // #3602 readonly(reactive(Map)) 1029 // ensure that the nested reactive `Map` can do tracking for itself 1030 target.get(key); 1031 } 1032 } 1033 function has$1(key, isReadonly = false) { 1034 const target = this["__v_raw" /* ReactiveFlags.RAW */]; 1035 const rawTarget = toRaw(target); 1036 const rawKey = toRaw(key); 1037 if (!isReadonly) {
1038 if (key !== rawKey) { 1039 track(rawTarget, "has" /* TrackOpTypes.HAS */, key); 1040 } 1041 track(rawTarget, "has" /* TrackOpTypes.HAS */, rawKey); 1042 } 1043 return key === rawKey 1044 ? target.has(key) 1045 : target.has(key) || target.has(rawKey); 1046 } 1047 function size(target, isReadonly = false) { 1048 target = target["__v_raw" /* ReactiveFlags.RAW */]; 1049 !isReadonly && track(toRaw(target), "iterate" /* TrackOpTypes.ITERATE */, ITERATE_KEY); 1050 return Reflect.get(target, 'size', target); 1051 } 1052 function add(value) { 1053 value = toRaw(value); 1054 const target = toRaw(this); 1055 const proto = getProto(target); 1056 const hadKey = proto.has.call(target, value); 1057 if (!hadKey) { 1058 target.add(value); 1059 trigger(target, "add" /* TriggerOpTypes.ADD */, value, value); 1060 } 1061 return this; 1062 } 1063 function set$1(key, value) { 1064 value = toRaw(value); 1065 const target = toRaw(this); 1066 const { has, get } = getProto(target); 1067 let hadKey = has.call(target, key); 1068 if (!hadKey) { 1069 key = toRaw(key); 1070 hadKey = has.call(target, key); 1071 } 1072 else { 1073 checkIdentityKeys(target, has, key); 1074 } 1075 const oldValue = get.call(target, key); 1076 target.set(key, value); 1077 if (!hadKey) { 1078 trigger(target, "add" /* TriggerOpTypes.ADD */, key, value); 1079 } 1080 else if (hasChanged(value, oldValue)) { 1081 trigger(target, "set" /* TriggerOpTypes.SET */, key, value, oldValue); 1082 } 1083 return this; 1084 } 1085 function deleteEntry(key) { 1086 const target = toRaw(this); 1087 const { has, get } = getProto(target); 1088 let hadKey = has.call(target, key); 1089 if (!hadKey) { 1090 key = toRaw(key); 1091 hadKey = has.call(target, key); 1092 } 1093 else { 1094 checkIdentityKeys(target, has, key); 1095 } 1096 const oldValue = get ? get.call(target, key) : undefined; 1097 // forward the operation before queueing reactions 1098 const result = target.delete(key); 1099 if (hadKey) { 1100 trigger(target, "delete" /* TriggerOpTypes.DELETE */, key, undefined, oldValue); 1101 } 1102 return result; 1103 } 1104 function clear() { 1105 const target = toRaw(this); 1106 const hadItems = target.size !== 0; 1107 const oldTarget = isMap(target) 1108 ? new Map(target) 1109 : new Set(target) 1110 ; 1111 // forward the operation before queueing reactions 1112 const result = target.clear(); 1113 if (hadItems) { 1114 trigger(target, "clear" /* TriggerOpTypes.CLEAR */, undefined, undefined, oldTarget); 1115 } 1116 return result; 1117 } 1118 function createForEach(isReadonly, isShallow) { 1119 return function forEach(callback, thisArg) { 1120 const observed = this; 1121 const target = observed["__v_raw" /* ReactiveFlags.RAW */]; 1122 const rawTarget = toRaw(target); 1123 const wrap = isShallow ? toShallow : isReadonly ? toReadonly : toReactive; 1124 !isReadonly && track(rawTarget, "iterate" /* TrackOpTypes.ITERATE */, ITERATE_KEY); 1125 return target.forEach((value, key) => { 1126 // important: make sure the callback is 1127 // 1. invoked with the reactive map as `this` and 3rd arg 1128 // 2. the value received should be a corresponding reactive/readonly. 1129 return callback.call(thisArg, wrap(value), wrap(key), observed); 1130 }); 1131 }; 1132 } 1133 function createIterableMethod(method, isReadonly, isShallow) { 1134 return function (...args) { 1135 const target = this["__v_raw" /* ReactiveFlags.RAW */]; 1136 const rawTarget = toRaw(target); 1137 const targetIsMap = isMap(rawTarget); 1138 const isPair = method === 'entries' || (method === Symbol.iterator && targetIsMap); 1139 const isKeyOnly = method === 'keys' && targetIsMap; 1140 const innerIterator = target[method](...args); 1141 const wrap = isShallow ? toShallow : isReadonly ? toReadonly : toReactive; 1142 !isReadonly && 1143 track(rawTarget, "iterate" /* TrackOpTypes.ITERATE */, isKeyOnly ? MAP_KEY_ITERATE_KEY : ITERATE_KEY); 1144 // return a wrapped iterator which returns observed versions of the 1145 // values emitted from the real iterator 1146 return { 1147 // iterator protocol 1148 next() { 1149 const { value, done } = innerIterator.next(); 1150 return done 1151 ? { value, done } 1152 : { 1153 value: isPair ? [wrap(value[0]), wrap(value[1])] : wrap(value),
1154 done 1155 }; 1156 }, 1157 // iterable protocol 1158 [Symbol.iterator]() { 1159 return this; 1160 } 1161 }; 1162 }; 1163 } 1164 function createReadonlyMethod(type) { 1165 return function (...args) { 1166 { 1167 const key = args[0] ? `on key "${args[0]}" ` : ``; 1168 console.warn(`${capitalize(type)} operation ${key}failed: target is readonly.`, toRaw(this)); 1169 } 1170 return type === "delete" /* TriggerOpTypes.DELETE */ ? false : this; 1171 }; 1172 } 1173 function createInstrumentations() { 1174 const mutableInstrumentations = { 1175 get(key) { 1176 return get$1(this, key); 1177 }, 1178 get size() { 1179 return size(this); 1180 }, 1181 has: has$1, 1182 add, 1183 set: set$1, 1184 delete: deleteEntry, 1185 clear, 1186 forEach: createForEach(false, false) 1187 }; 1188 const shallowInstrumentations = { 1189 get(key) { 1190 return get$1(this, key, false, true); 1191 }, 1192 get size() { 1193 return size(this); 1194 }, 1195 has: has$1, 1196 add, 1197 set: set$1, 1198 delete: deleteEntry, 1199 clear, 1200 forEach: createForEach(false, true) 1201 }; 1202 const readonlyInstrumentations = { 1203 get(key) { 1204 return get$1(this, key, true); 1205 }, 1206 get size() { 1207 return size(this, true); 1208 }, 1209 has(key) { 1210 return has$1.call(this, key, true); 1211 }, 1212 add: createReadonlyMethod("add" /* TriggerOpTypes.ADD */), 1213 set: createReadonlyMethod("set" /* TriggerOpTypes.SET */), 1214 delete: createReadonlyMethod("delete" /* TriggerOpTypes.DELETE */), 1215 clear: createReadonlyMethod("clear" /* TriggerOpTypes.CLEAR */), 1216 forEach: createForEach(true, false) 1217 }; 1218 const shallowReadonlyInstrumentations = { 1219 get(key) { 1220 return get$1(this, key, true, true); 1221 }, 1222 get size() { 1223 return size(this, true); 1224 }, 1225 has(key) { 1226 return has$1.call(this, key, true); 1227 }, 1228 add: createReadonlyMethod("add" /* TriggerOpTypes.ADD */), 1229 set: createReadonlyMethod("set" /* TriggerOpTypes.SET */), 1230 delete: createReadonlyMethod("delete" /* TriggerOpTypes.DELETE */), 1231 clear: createReadonlyMethod("clear" /* TriggerOpTypes.CLEAR */), 1232 forEach: createForEach(true, true) 1233 }; 1234 const iteratorMethods = ['keys', 'values', 'entries', Symbol.iterator]; 1235 iteratorMethods.forEach(method => { 1236 mutableInstrumentations[method] = createIterableMethod(method, false, false); 1237 readonlyInstrumentations[method] = createIterableMethod(method, true, false); 1238 shallowInstrumentations[method] = createIterableMethod(method, false, true); 1239 shallowReadonlyInstrumentations[method] = createIterableMethod(method, true, true); 1240 }); 1241 return [ 1242 mutableInstrumentations, 1243 readonlyInstrumentations, 1244 shallowInstrumentations, 1245 shallowReadonlyInstrumentations 1246 ]; 1247 } 1248 const [mutableInstrumentations, readonlyInstrumentations, shallowInstrumentations, shallowReadonlyInstrumentations] = /* #__PURE__*/ createInstrumentations(); 1249 function createInstrumentationGetter(isReadonly, shallow) { 1250 const instrumentations = shallow 1251 ? isReadonly 1252 ? shallowReadonlyInstrumentations 1253 : shallowInstrumentations 1254 : isReadonly 1255 ? readonlyInstrumentations 1256 : mutableInstrumentations; 1257 return (target, key, receiver) => { 1258 if (key === "__v_isReactive" /* ReactiveFlags.IS_REACTIVE */) { 1259 return !isReadonly; 1260 } 1261 else if (key === "__v_isReadonly" /* ReactiveFlags.IS_READONLY */) { 1262 return isReadonly; 1263 } 1264 else if (key === "__v_raw" /* ReactiveFlags.RAW */) { 1265 return target; 1266 } 1267 return Reflect.get(hasOwn(instrumentations, key) && key in target 1268 ? instrumentations 1269 : target, key, receiver); 1270 }; 1271 } 1272 const mutableCollectionHandlers = { 1273 get: /*#__PURE__*/ createInstrumentationGetter(false, false) 1274 }; 1275 const shallowCollectionHandlers = { 1276 get: /*#__PURE__*/ createInstrumentationGetter(false, true) 1277 }; 1278 const readonlyCollectionHandlers = { 1279 get: /*#__PURE__*/ createInstrumentationGetter(true, false) 1280 }; 1281 const shallowReadonlyCollectionHandlers = { 1282 get: /*#__PURE__*/ createInstrumentationGetter(true, true) 1283 }; 1284 function checkIdentityKeys(target, has, key) { 1285 const rawKey = toRaw(key); 1286 if (rawKey !== key && has.call(target, rawKey)) { 1287 const type = toRawType(target); 1288 console.warn(`Reactive ${type} contains both the raw and reactive ` + 1289 `versions of the same object${type === `Map` ? ` as keys` : ``}, ` + 1290 `which can lead to inconsistencies. ` + 1291 `Avoid differentiating between the raw and reactive versions ` + 1292 `of an object and only use the reactive version if possible.`); 1293 } 1294 } 1295 1296 const reactiveMap = new WeakMap(); 1297 const shallowReactiveMap = new WeakMap(); 1298 const readonlyMap = new WeakMap(); 1299 const shallowReadonlyMap = new WeakMap(); 1300 function targetTypeMap(rawType) { 1301 switch (rawType) { 1302 case 'Object': 1303 case 'Array': 1304 return 1 /* TargetType.COMMON */; 1305 case 'Map': 1306 case 'Set': 1307 case 'WeakMap': 1308 case 'WeakSet': 1309 return 2 /* TargetType.COLLECTION */; 1310 default: 1311 return 0 /* TargetType.INVALID */; 1312 } 1313 } 1314 function getTargetType(value) { 1315 return value["__v_skip" /* ReactiveFlags.SKIP */] || !Object.isExtensible(value) 1316 ? 0 /* TargetType.INVALID */ 1317 : targetTypeMap(toRawType(value)); 1318 } 1319 function reactive(target) { 1320 // if trying to observe a readonly proxy, return the readonly version. 1321 if (isReadonly(target)) { 1322 return target; 1323 } 1324 return createReactiveObject(target, false, mutableHandlers, mutableCollectionHandlers, reactiveMap); 1325 } 1326 /** 1327 * Return a shallowly-reactive copy of the original object, where only the root 1328 * level properties are reactive. It also does not auto-unwrap refs (even at the 1329 * root level). 1330 */ 1331 function shallowReactive(target) { 1332 return createReactiveObject(target, false, shallowReactiveHandlers, shallowCollectionHandlers, shallowReactiveMap); 1333 } 1334 /** 1335 * Creates a readonly copy of the original object. Note the returned copy is not 1336 * made reactive, but `readonly` can be called on an already reactive object. 1337 */ 1338 function readonly(target) { 1339 return createReactiveObject(target, true, readonlyHandlers, readonlyCollectionHandlers, readonlyMap); 1340 } 1341 /** 1342 * Returns a reactive-copy of the original object, where only the root level 1343 * properties are readonly, and does NOT unwrap refs nor recursively convert 1344 * returned properties. 1345 * This is used for creating the props proxy object for stateful components. 1346 */ 1347 function shallowReadonly(target) { 1348 return createReactiveObject(target, true, shallowReadonlyHandlers, shallowReadonlyCollectionHandlers, shallowReadonlyMap); 1349 } 1350 function createReactiveObject(target, isReadonly, baseHandlers, collectionHandlers, proxyMap) { 1351 if (!isObject(target)) { 1352 { 1353 console.warn(`value cannot be made reactive: ${String(target)}`); 1354 } 1355 return target; 1356 } 1357 // target is already a Proxy, return it. 1358 // exception: calling readonly() on a reactive object 1359 if (target["__v_raw" /* ReactiveFlags.RAW */] && 1360 !(isReadonly && target["__v_isReactive" /* ReactiveFlags.IS_REACTIVE */])) { 1361 return target; 1362 } 1363 // target already has corresponding Proxy 1364 const existingProxy = proxyMap.get(target); 1365 if (existingProxy) { 1366 return existingProxy; 1367 } 1368 // only specific value types can be observed. 1369 const targetType = getTargetType(target); 1370 if (targetType === 0 /* TargetType.INVALID */) { 1371 return target; 1372 } 1373 const proxy = new Proxy(target, targetType === 2 /* TargetType.COLLECTION */ ? collectionHandlers : baseHandlers); 1374 proxyMap.set(target, proxy); 1375 return proxy; 1376 } 1377 function isReactive(value) { 1378 if (isReadonly(value)) { 1379 return isReactive(value["__v_raw" /* ReactiveFlags.RAW */]); 1380 } 1381 return !!(value && value["__v_isReactive" /* ReactiveFlags.IS_REACTIVE */]); 1382 } 1383 function isReadonly(value) { 1384 return !!(value && value["__v_isReadonly" /* ReactiveFlags.IS_READONLY */]); 1385 } 1386 function isShallow(value) { 1387 return !!(value && value["__v_isShallow" /* ReactiveFlags.IS_SHALLOW */]); 1388 } 1389 function isProxy(value) { 1390 return isReactive(value) || isReadonly(value); 1391 } 1392 function toRaw(observed) { 1393 const raw = observed && observed["__v_raw" /* ReactiveFlags.RAW */]; 1394 return raw ? toRaw(raw) : observed; 1395 } 1396 function markRaw(value) { 1397 def(value, "__v_skip" /* ReactiveFlags.SKIP */, true); 1398 return value; 1399 } 1400 const toReactive = (value) => isObject(value) ? reactive(value) : value; 1401 const toReadonly = (value) => isObject(value) ? readonly(value) : value; 1402 1403 function trackRefValue(ref) { 1404 if (shouldTrack && activeEffect) { 1405 ref = toRaw(ref); 1406 { 1407 trackEffects(ref.dep || (ref.dep = createDep()), { 1408 target: ref, 1409 type: "get" /* TrackOpTypes.GET */, 1410 key: 'value' 1411 }); 1412 } 1413 } 1414 } 1415 function triggerRefValue(ref, newVal) { 1416 ref = toRaw(ref); 1417 if (ref.dep) { 1418 { 1419 triggerEffects(ref.dep, { 1420 target: ref, 1421 type: "set" /* TriggerOpTypes.SET */, 1422 key: 'value', 1423 newValue: newVal 1424 }); 1425 } 1426 } 1427 } 1428 function isRef(r) { 1429 return !!(r && r.__v_isRef === true); 1430 } 1431 function ref(value) { 1432 return createRef(value, false); 1433 } 1434 function shallowRef(value) { 1435 return createRef(value, true); 1436 } 1437 function createRef(rawValue, shallow) { 1438 if (isRef(rawValue)) { 1439 return rawValue; 1440 } 1441 return new RefImpl(rawValue, shallow); 1442 } 1443 class RefImpl { 1444 constructor(value, __v_isShallow) { 1445 this.__v_isShallow = __v_isShallow; 1446 this.dep = undefined; 1447 this.__v_isRef = true; 1448 this._rawValue = __v_isShallow ? value : toRaw(value); 1449 this._value = __v_isShallow ? value : toReactive(value); 1450 } 1451 get value() { 1452 trackRefValue(this); 1453 return this._value; 1454 } 1455 set value(newVal) { 1456 const useDirectValue = this.__v_isShallow || isShallow(newVal) || isReadonly(newVal); 1457 newVal = useDirectValue ? newVal : toRaw(newVal); 1458 if (hasChanged(newVal, this._rawValue)) { 1459 this._rawValue = newVal; 1460 this._value = useDirectValue ? newVal : toReactive(newVal); 1461 triggerRefValue(this, newVal); 1462 } 1463 } 1464 } 1465 function triggerRef(ref) { 1466 triggerRefValue(ref, ref.value ); 1467 } 1468 function unref(ref) { 1469 return isRef(ref) ? ref.value : ref; 1470 } 1471 const shallowUnwrapHandlers = { 1472 get: (target, key, receiver) => unref(Reflect.get(target, key, receiver)), 1473 set: (target, key, value, receiver) => { 1474 const oldValue = target[key]; 1475 if (isRef(oldValue) && !isRef(value)) { 1476 oldValue.value = value; 1477 return true; 1478 } 1479 else { 1480 return Reflect.set(target, key, value, receiver); 1481 } 1482 } 1483 }; 1484 function proxyRefs(objectWithRefs) { 1485 return isReactive(objectWithRefs) 1486 ? objectWithRefs 1487 : new Proxy(objectWithRefs, shallowUnwrapHandlers); 1488 } 1489 class CustomRefImpl { 1490 constructor(factory) { 1491 this.dep = undefined; 1492 this.__v_isRef = true; 1493 const { get, set } = factory(() => trackRefValue(this), () => triggerRefValue(this)); 1494 this._get = get; 1495 this._set = set; 1496 } 1497 get value() { 1498 return this._get(); 1499 } 1500 set value(newVal) { 1501 this._set(newVal); 1502 } 1503 } 1504 function customRef(factory) { 1505 return new CustomRefImpl(factory); 1506 } 1507 function toRefs(object) { 1508 if (!isProxy(object)) { 1509 console.warn(`toRefs() expects a reactive object but received a plain one.`); 1510 } 1511 const ret = isArray(object) ? new Array(object.length) : {}; 1512 for (const key in object) { 1513 ret[key] = toRef(object, key); 1514 } 1515 return ret; 1516 } 1517 class ObjectRefImpl { 1518 constructor(_object, _key, _defaultValue) { 1519 this._object = _object; 1520 this._key = _key; 1521 this._defaultValue = _defaultValue; 1522 this.__v_isRef = true; 1523 } 1524 get value() { 1525 const val = this._object[this._key]; 1526 return val === undefined ? this._defaultValue : val; 1527 } 1528 set value(newVal) { 1529 this._object[this._key] = newVal; 1530 } 1531 } 1532 function toRef(object, key, defaultValue) { 1533 const val = object[key]; 1534 return isRef(val) 1535 ? val 1536 : new ObjectRefImpl(object, key, defaultValue); 1537 } 1538 1539 var _a; 1540 class ComputedRefImpl { 1541 constructor(getter, _setter, isReadonly, isSSR) { 1542 this._setter = _setter; 1543 this.dep = undefined; 1544 this.__v_isRef = true; 1545 this[_a] = false;
1546 this._dirty = true; 1547 this.effect = new ReactiveEffect(getter, () => { 1548 if (!this._dirty) { 1549 this._dirty = true; 1550 triggerRefValue(this); 1551 } 1552 }); 1553 this.effect.computed = this; 1554 this.effect.active = this._cacheable = !isSSR; 1555 this["__v_isReadonly" /* ReactiveFlags.IS_READONLY */] = isReadonly; 1556 } 1557 get value() { 1558 // the computed ref may get wrapped by other proxies e.g. readonly() #3376 1559 const self = toRaw(this); 1560 trackRefValue(self); 1561 if (self._dirty || !self._cacheable) { 1562 self._dirty = false; 1563 self._value = self.effect.run(); 1564 } 1565 return self._value; 1566 } 1567 set value(newValue) { 1568 this._setter(newValue); 1569 } 1570 } 1571 _a = "__v_isReadonly" /* ReactiveFlags.IS_READONLY */; 1572 function computed(getterOrOptions, debugOptions, isSSR = false) { 1573 let getter; 1574 let setter; 1575 const onlyGetter = isFunction(getterOrOptions); 1576 if (onlyGetter) { 1577 getter = getterOrOptions; 1578 setter = () => { 1579 console.warn('Write operation failed: computed value is readonly'); 1580 } 1581 ; 1582 } 1583 else { 1584 getter = getterOrOptions.get; 1585 setter = getterOrOptions.set; 1586 } 1587 const cRef = new ComputedRefImpl(getter, setter, onlyGetter || !setter, isSSR); 1588 if (debugOptions && !isSSR) { 1589 cRef.effect.onTrack = debugOptions.onTrack; 1590 cRef.effect.onTrigger = debugOptions.onTrigger; 1591 } 1592 return cRef; 1593 } 1594 1595 const stack = []; 1596 function pushWarningContext(vnode) { 1597 stack.push(vnode); 1598 } 1599 function popWarningContext() { 1600 stack.pop(); 1601 } 1602 function warn$1(msg, ...args) { 1603 // avoid props formatting or warn handler tracking deps that might be mutated 1604 // during patch, leading to infinite recursion. 1605 pauseTracking(); 1606 const instance = stack.length ? stack[stack.length - 1].component : null; 1607 const appWarnHandler = instance && instance.appContext.config.warnHandler; 1608 const trace = getComponentTrace(); 1609 if (appWarnHandler) { 1610 callWithErrorHandling(appWarnHandler, instance, 11 /* ErrorCodes.APP_WARN_HANDLER */, [ 1611 msg + args.join(''), 1612 instance && instance.proxy, 1613 trace 1614 .map(({ vnode }) => `at <${formatComponentName(instance, vnode.type)}>`) 1615 .join('\n'), 1616 trace 1617 ]); 1618 } 1619 else { 1620 const warnArgs = [`[Vue warn]: ${msg}`, ...args]; 1621 /* istanbul ignore if */ 1622 if (trace.length && 1623 // avoid spamming console during tests 1624 !false) { 1625 warnArgs.push(`\n`, ...formatTrace(trace)); 1626 } 1627 console.warn(...warnArgs); 1628 } 1629 resetTracking(); 1630 } 1631 function getComponentTrace() { 1632 let currentVNode = stack[stack.length - 1]; 1633 if (!currentVNode) { 1634 return []; 1635 } 1636 // we can't just use the stack because it will be incomplete during updates 1637 // that did not start from the root. Re-construct the parent chain using 1638 // instance parent pointers. 1639 const normalizedStack = []; 1640 while (currentVNode) { 1641 const last = normalizedStack[0]; 1642 if (last && last.vnode === currentVNode) { 1643 last.recurseCount++; 1644 } 1645 else { 1646 normalizedStack.push({ 1647 vnode: currentVNode, 1648 recurseCount: 0 1649 }); 1650 } 1651 const parentInstance = currentVNode.component && currentVNode.component.parent; 1652 currentVNode = parentInstance && parentInstance.vnode; 1653 } 1654 return normalizedStack; 1655 } 1656 /* istanbul ignore next */ 1657 function formatTrace(trace) { 1658 const logs = []; 1659 trace.forEach((entry, i) => { 1660 logs.push(...(i === 0 ? [] : [`\n`]), ...formatTraceEntry(entry)); 1661 }); 1662 return logs; 1663 } 1664 function formatTraceEntry({ vnode, recurseCount }) { 1665 const postfix = recurseCount > 0 ? `... (${recurseCount} recursive calls)` : ``; 1666 const isRoot = vnode.component ? vnode.component.parent == null : false;
1667 const open = ` at <${formatComponentName(vnode.component, vnode.type, isRoot)}`; 1668 const close = `>` + postfix; 1669 return vnode.props 1670 ? [open, ...formatProps(vnode.props), close] 1671 : [open + close]; 1672 } 1673 /* istanbul ignore next */ 1674 function formatProps(props) { 1675 const res = []; 1676 const keys = Object.keys(props); 1677 keys.slice(0, 3).forEach(key => { 1678 res.push(...formatProp(key, props[key])); 1679 }); 1680 if (keys.length > 3) { 1681 res.push(` ...`); 1682 } 1683 return res; 1684 } 1685 /* istanbul ignore next */ 1686 function formatProp(key, value, raw) { 1687 if (isString(value)) { 1688 value = JSON.stringify(value); 1689 return raw ? value : [`${key}=${value}`]; 1690 } 1691 else if (typeof value === 'number' || 1692 typeof value === 'boolean' || 1693 value == null) { 1694 return raw ? value : [`${key}=${value}`]; 1695 } 1696 else if (isRef(value)) { 1697 value = formatProp(key, toRaw(value.value), true); 1698 return raw ? value : [`${key}=Ref<`, value, `>`]; 1699 } 1700 else if (isFunction(value)) { 1701 return [`${key}=fn${value.name ? `<${value.name}>` : ``}`]; 1702 } 1703 else { 1704 value = toRaw(value); 1705 return raw ? value : [`${key}=`, value]; 1706 } 1707 } 1708 1709 const ErrorTypeStrings = { 1710 ["sp" /* LifecycleHooks.SERVER_PREFETCH */]: 'serverPrefetch hook', 1711 ["bc" /* LifecycleHooks.BEFORE_CREATE */]: 'beforeCreate hook', 1712 ["c" /* LifecycleHooks.CREATED */]: 'created hook', 1713 ["bm" /* LifecycleHooks.BEFORE_MOUNT */]: 'beforeMount hook', 1714 ["m" /* LifecycleHooks.MOUNTED */]: 'mounted hook', 1715 ["bu" /* LifecycleHooks.BEFORE_UPDATE */]: 'beforeUpdate hook', 1716 ["u" /* LifecycleHooks.UPDATED */]: 'updated', 1717 ["bum" /* LifecycleHooks.BEFORE_UNMOUNT */]: 'beforeUnmount hook', 1718 ["um" /* LifecycleHooks.UNMOUNTED */]: 'unmounted hook', 1719 ["a" /* LifecycleHooks.ACTIVATED */]: 'activated hook', 1720 ["da" /* LifecycleHooks.DEACTIVATED */]: 'deactivated hook', 1721 ["ec" /* LifecycleHooks.ERROR_CAPTURED */]: 'errorCaptured hook', 1722 ["rtc" /* LifecycleHooks.RENDER_TRACKED */]: 'renderTracked hook', 1723 ["rtg" /* LifecycleHooks.RENDER_TRIGGERED */]: 'renderTriggered hook', 1724 [0 /* ErrorCodes.SETUP_FUNCTION */]: 'setup function', 1725 [1 /* ErrorCodes.RENDER_FUNCTION */]: 'render function', 1726 [2 /* ErrorCodes.WATCH_GETTER */]: 'watcher getter', 1727 [3 /* ErrorCodes.WATCH_CALLBACK */]: 'watcher callback', 1728 [4 /* ErrorCodes.WATCH_CLEANUP */]: 'watcher cleanup function', 1729 [5 /* ErrorCodes.NATIVE_EVENT_HANDLER */]: 'native event handler', 1730 [6 /* ErrorCodes.COMPONENT_EVENT_HANDLER */]: 'component event handler', 1731 [7 /* ErrorCodes.VNODE_HOOK */]: 'vnode hook', 1732 [8 /* ErrorCodes.DIRECTIVE_HOOK */]: 'directive hook', 1733 [9 /* ErrorCodes.TRANSITION_HOOK */]: 'transition hook', 1734 [10 /* ErrorCodes.APP_ERROR_HANDLER */]: 'app errorHandler', 1735 [11 /* ErrorCodes.APP_WARN_HANDLER */]: 'app warnHandler', 1736 [12 /* ErrorCodes.FUNCTION_REF */]: 'ref function', 1737 [13 /* ErrorCodes.ASYNC_COMPONENT_LOADER */]: 'async component loader', 1738 [14 /* ErrorCodes.SCHEDULER */]: 'scheduler flush. This is likely a Vue internals bug. ' + 1739 'Please open an issue at https://new-issue.vuejs.org/?repo=vuejs/core' 1740 }; 1741 function callWithErrorHandling(fn, instance, type, args) { 1742 let res; 1743 try { 1744 res = args ? fn(...args) : fn(); 1745 } 1746 catch (err) { 1747 handleError(err, instance, type); 1748 } 1749 return res; 1750 } 1751 function callWithAsyncErrorHandling(fn, instance, type, args) { 1752 if (isFunction(fn)) { 1753 const res = callWithErrorHandling(fn, instance, type, args); 1754 if (res && isPromise(res)) { 1755 res.catch(err => { 1756 handleError(err, instance, type); 1757 }); 1758 } 1759 return res; 1760 } 1761 const values = []; 1762 for (let i = 0; i < fn.length; i++) { 1763 values.push(callWithAsyncErrorHandling(fn[i], instance, type, args)); 1764 } 1765 return values; 1766 } 1767 function handleError(err, instance, type, throwInDev = true) { 1768 const contextVNode = instance ? instance.vnode : null; 1769 if (instance) { 1770 let cur = instance.parent; 1771 // the exposed instance is the render proxy to keep it consistent with 2.x 1772 const exposedInstance = instance.proxy; 1773 // in production the hook receives only the error code 1774 const errorInfo = ErrorTypeStrings[type] ; 1775 while (cur) {
1776 const errorCapturedHooks = cur.ec; 1777 if (errorCapturedHooks) { 1778 for (let i = 0; i < errorCapturedHooks.length; i++) { 1779 if (errorCapturedHooks[i](err, exposedInstance, errorInfo) === false) { 1780 return; 1781 } 1782 } 1783 } 1784 cur = cur.parent; 1785 } 1786 // app-level handling 1787 const appErrorHandler = instance.appContext.config.errorHandler; 1788 if (appErrorHandler) { 1789 callWithErrorHandling(appErrorHandler, null, 10 /* ErrorCodes.APP_ERROR_HANDLER */, [err, exposedInstance, errorInfo]); 1790 return; 1791 } 1792 } 1793 logError(err, type, contextVNode, throwInDev); 1794 } 1795 function logError(err, type, contextVNode, throwInDev = true) { 1796 { 1797 const info = ErrorTypeStrings[type]; 1798 if (contextVNode) { 1799 pushWarningContext(contextVNode); 1800 } 1801 warn$1(`Unhandled error${info ? ` during execution of ${info}` : ``}`); 1802 if (contextVNode) { 1803 popWarningContext(); 1804 } 1805 // crash in dev by default so it's more noticeable 1806 if (throwInDev) { 1807 throw err; 1808 } 1809 else { 1810 console.error(err); 1811 } 1812 } 1813 } 1814 1815 let isFlushing = false; 1816 let isFlushPending = false; 1817 const queue = []; 1818 let flushIndex = 0; 1819 const pendingPostFlushCbs = []; 1820 let activePostFlushCbs = null; 1821 let postFlushIndex = 0; 1822 const resolvedPromise = /*#__PURE__*/ Promise.resolve(); 1823 let currentFlushPromise = null; 1824 const RECURSION_LIMIT = 100; 1825 function nextTick(fn) { 1826 const p = currentFlushPromise || resolvedPromise; 1827 return fn ? p.then(this ? fn.bind(this) : fn) : p; 1828 } 1829 // #2768 1830 // Use binary-search to find a suitable position in the queue, 1831 // so that the queue maintains the increasing order of job's id, 1832 // which can prevent the job from being skipped and also can avoid repeated patching. 1833 function findInsertionIndex(id) { 1834 // the start index should be `flushIndex + 1` 1835 let start = flushIndex + 1; 1836 let end = queue.length; 1837 while (start < end) { 1838 const middle = (start + end) >>> 1; 1839 const middleJobId = getId(queue[middle]); 1840 middleJobId < id ? (start = middle + 1) : (end = middle); 1841 } 1842 return start; 1843 } 1844 function queueJob(job) { 1845 // the dedupe search uses the startIndex argument of Array.includes() 1846 // by default the search index includes the current job that is being run 1847 // so it cannot recursively trigger itself again. 1848 // if the job is a watch() callback, the search will start with a +1 index to 1849 // allow it recursively trigger itself - it is the user's responsibility to 1850 // ensure it doesn't end up in an infinite loop. 1851 if (!queue.length || 1852 !queue.includes(job, isFlushing && job.allowRecurse ? flushIndex + 1 : flushIndex)) { 1853 if (job.id == null) { 1854 queue.push(job); 1855 } 1856 else { 1857 queue.splice(findInsertionIndex(job.id), 0, job); 1858 } 1859 queueFlush(); 1860 } 1861 } 1862 function queueFlush() { 1863 if (!isFlushing && !isFlushPending) { 1864 isFlushPending = true; 1865 currentFlushPromise = resolvedPromise.then(flushJobs); 1866 } 1867 }
1868 function invalidateJob(job) { 1869 const i = queue.indexOf(job); 1870 if (i > flushIndex) { 1871 queue.splice(i, 1); 1872 } 1873 } 1874 function queuePostFlushCb(cb) { 1875 if (!isArray(cb)) { 1876 if (!activePostFlushCbs || 1877 !activePostFlushCbs.includes(cb, cb.allowRecurse ? postFlushIndex + 1 : postFlushIndex)) { 1878 pendingPostFlushCbs.push(cb); 1879 } 1880 } 1881 else { 1882 // if cb is an array, it is a component lifecycle hook which can only be 1883 // triggered by a job, which is already deduped in the main queue, so 1884 // we can skip duplicate check here to improve perf 1885 pendingPostFlushCbs.push(...cb); 1886 } 1887 queueFlush(); 1888 } 1889 function flushPreFlushCbs(seen, 1890 // if currently flushing, skip the current job itself 1891 i = isFlushing ? flushIndex + 1 : 0) { 1892 { 1893 seen = seen || new Map(); 1894 } 1895 for (; i < queue.length; i++) { 1896 const cb = queue[i]; 1897 if (cb && cb.pre) { 1898 if (checkRecursiveUpdates(seen, cb)) { 1899 continue; 1900 } 1901 queue.splice(i, 1); 1902 i--; 1903 cb(); 1904 } 1905 } 1906 } 1907 function flushPostFlushCbs(seen) { 1908 if (pendingPostFlushCbs.length) { 1909 const deduped = [...new Set(pendingPostFlushCbs)]; 1910 pendingPostFlushCbs.length = 0; 1911 // #1947 already has active queue, nested flushPostFlushCbs call 1912 if (activePostFlushCbs) { 1913 activePostFlushCbs.push(...deduped); 1914 return; 1915 } 1916 activePostFlushCbs = deduped; 1917 { 1918 seen = seen || new Map(); 1919 } 1920 activePostFlushCbs.sort((a, b) => getId(a) - getId(b)); 1921 for (postFlushIndex = 0; postFlushIndex < activePostFlushCbs.length; postFlushIndex++) { 1922 if (checkRecursiveUpdates(seen, activePostFlushCbs[postFlushIndex])) { 1923 continue; 1924 } 1925 activePostFlushCbs[postFlushIndex](); 1926 } 1927 activePostFlushCbs = null; 1928 postFlushIndex = 0; 1929 } 1930 } 1931 const getId = (job) => job.id == null ? Infinity : job.id; 1932 const comparator = (a, b) => { 1933 const diff = getId(a) - getId(b); 1934 if (diff === 0) { 1935 if (a.pre && !b.pre) 1936 return -1; 1937 if (b.pre && !a.pre) 1938 return 1; 1939 } 1940 return diff; 1941 }; 1942 function flushJobs(seen) { 1943 isFlushPending = false; 1944 isFlushing = true; 1945 { 1946 seen = seen || new Map(); 1947 } 1948 // Sort queue before flush. 1949 // This ensures that: 1950 // 1. Components are updated from parent to child. (because parent is always 1951 // created before the child so its render effect will have smaller 1952 // priority number) 1953 // 2. If a component is unmounted during a parent component's update, 1954 // its update can be skipped. 1955 queue.sort(comparator); 1956 // conditional usage of checkRecursiveUpdate must be determined out of 1957 // try ... catch block since Rollup by default de-optimizes treeshaking 1958 // inside try-catch. This can leave all warning code unshaked. Although 1959 // they would get eventually shaken by a minifier like terser, some minifiers 1960 // would fail to do that (e.g. https://github.com/evanw/esbuild/issues/1610) 1961 const check = (job) => checkRecursiveUpdates(seen, job) 1962 ; 1963 try { 1964 for (flushIndex = 0; flushIndex < queue.length; flushIndex++) { 1965 const job = queue[flushIndex]; 1966 if (job && job.active !== false) { 1967 if (true && check(job)) { 1968 continue; 1969 } 1970 // console.log(`running:`, job.id) 1971 callWithErrorHandling(job, null, 14 /* ErrorCodes.SCHEDULER */); 1972 } 1973 } 1974 } 1975 finally { 1976 flushIndex = 0; 1977 queue.length = 0; 1978 flushPostFlushCbs(seen); 1979 isFlushing = false; 1980 currentFlushPromise = null; 1981 // some postFlushCb queued jobs! 1982 // keep flushing until it drains. 1983 if (queue.length || pendingPostFlushCbs.length) { 1984 flushJobs(seen); 1985 } 1986 } 1987 } 1988 function checkRecursiveUpdates(seen, fn) { 1989 if (!seen.has(fn)) { 1990 seen.set(fn, 1); 1991 } 1992 else { 1993 const count = seen.get(fn); 1994 if (count > RECURSION_LIMIT) { 1995 const instance = fn.ownerInstance; 1996 const componentName = instance && getComponentName(instance.type); 1997 warn$1(`Maximum recursive updates exceeded${componentName ? ` in component <${componentName}>` : ``}. ` + 1998 `This means you have a reactive effect that is mutating its own ` + 1999 `dependencies and thus recursively triggering itself. Possible sources ` + 2000 `include component template, render function, updated hook or ` + 2001 `watcher source function.`); 2002 return true; 2003 } 2004 else { 2005 seen.set(fn, count + 1); 2006 } 2007 } 2008 } 2009 2010 /* eslint-disable no-restricted-globals */ 2011 let isHmrUpdating = false;
2012 const hmrDirtyComponents = new Set(); 2013 // Expose the HMR runtime on the global object 2014 // This makes it entirely tree-shakable without polluting the exports and makes 2015 // it easier to be used in toolings like vue-loader 2016 // Note: for a component to be eligible for HMR it also needs the __hmrId option 2017 // to be set so that its instances can be registered / removed. 2018 { 2019 getGlobalThis().__VUE_HMR_RUNTIME__ = { 2020 createRecord: tryWrap(createRecord), 2021 rerender: tryWrap(rerender), 2022 reload: tryWrap(reload) 2023 }; 2024 } 2025 const map = new Map(); 2026 function registerHMR(instance) { 2027 const id = instance.type.__hmrId; 2028 let record = map.get(id); 2029 if (!record) { 2030 createRecord(id, instance.type); 2031 record = map.get(id); 2032 } 2033 record.instances.add(instance); 2034 } 2035 function unregisterHMR(instance) { 2036 map.get(instance.type.__hmrId).instances.delete(instance); 2037 } 2038 function createRecord(id, initialDef) { 2039 if (map.has(id)) { 2040 return false; 2041 } 2042 map.set(id, { 2043 initialDef: normalizeClassComponent(initialDef), 2044 instances: new Set() 2045 }); 2046 return true; 2047 } 2048 function normalizeClassComponent(component) { 2049 return isClassComponent(component) ? component.__vccOpts : component; 2050 } 2051 function rerender(id, newRender) { 2052 const record = map.get(id); 2053 if (!record) { 2054 return; 2055 } 2056 // update initial record (for not-yet-rendered component) 2057 record.initialDef.render = newRender; 2058 [...record.instances].forEach(instance => { 2059 if (newRender) { 2060 instance.render = newRender; 2061 normalizeClassComponent(instance.type).render = newRender; 2062 } 2063 instance.renderCache = []; 2064 // this flag forces child components with slot content to update 2065 isHmrUpdating = true; 2066 instance.update(); 2067 isHmrUpdating = false; 2068 }); 2069 } 2070 function reload(id, newComp) { 2071 const record = map.get(id); 2072 if (!record) 2073 return; 2074 newComp = normalizeClassComponent(newComp); 2075 // update initial def (for not-yet-rendered components) 2076 updateComponentDef(record.initialDef, newComp); 2077 // create a snapshot which avoids the set being mutated during updates 2078 const instances = [...record.instances]; 2079 for (const instance of instances) { 2080 const oldComp = normalizeClassComponent(instance.type); 2081 if (!hmrDirtyComponents.has(oldComp)) { 2082 // 1. Update existing comp definition to match new one 2083 if (oldComp !== record.initialDef) { 2084 updateComponentDef(oldComp, newComp); 2085 } 2086 // 2. mark definition dirty. This forces the renderer to replace the 2087 // component on patch. 2088 hmrDirtyComponents.add(oldComp); 2089 } 2090 // 3. invalidate options resolution cache 2091 instance.appContext.optionsCache.delete(instance.type); 2092 // 4. actually update 2093 if (instance.ceReload) { 2094 // custom element 2095 hmrDirtyComponents.add(oldComp); 2096 instance.ceReload(newComp.styles); 2097 hmrDirtyComponents.delete(oldComp); 2098 } 2099 else if (instance.parent) { 2100 // 4. Force the parent instance to re-render. This will cause all updated 2101 // components to be unmounted and re-mounted. Queue the update so that we 2102 // don't end up forcing the same parent to re-render multiple times. 2103 queueJob(instance.parent.update); 2104 } 2105 else if (instance.appContext.reload) { 2106 // root instance mounted via createApp() has a reload method 2107 instance.appContext.reload(); 2108 } 2109 else if (typeof window !== 'undefined') { 2110 // root instance inside tree created via raw render(). Force reload. 2111 window.location.reload(); 2112 } 2113 else { 2114 console.warn('[HMR] Root or manually mounted instance modified. Full reload required.'); 2115 } 2116 } 2117 // 5. make sure to cleanup dirty hmr components after update 2118 queuePostFlushCb(() => { 2119 for (const instance of instances) { 2120 hmrDirtyComponents.delete(normalizeClassComponent(instance.type)); 2121 } 2122 }); 2123 } 2124 function updateComponentDef(oldComp, newComp) { 2125 extend(oldComp, newComp); 2126 for (const key in oldComp) { 2127 if (key !== '__file' && !(key in newComp)) {
2128 delete oldComp[key]; 2129 } 2130 } 2131 } 2132 function tryWrap(fn) { 2133 return (id, arg) => { 2134 try { 2135 return fn(id, arg); 2136 } 2137 catch (e) { 2138 console.error(e); 2139 console.warn(`[HMR] Something went wrong during Vue component hot-reload. ` + 2140 `Full reload required.`); 2141 } 2142 }; 2143 } 2144 2145 let buffer = []; 2146 let devtoolsNotInstalled = false; 2147 function emit(event, ...args) { 2148 if (exports.devtools) { 2149 exports.devtools.emit(event, ...args); 2150 } 2151 else if (!devtoolsNotInstalled) { 2152 buffer.push({ event, args }); 2153 } 2154 } 2155 function setDevtoolsHook(hook, target) { 2156 var _a, _b; 2157 exports.devtools = hook; 2158 if (exports.devtools) { 2159 exports.devtools.enabled = true; 2160 buffer.forEach(({ event, args }) => exports.devtools.emit(event, ...args)); 2161 buffer = []; 2162 } 2163 else if ( 2164 // handle late devtools injection - only do this if we are in an actual 2165 // browser environment to avoid the timer handle stalling test runner exit 2166 // (#4815) 2167 typeof window !== 'undefined' && 2168 // some envs mock window but not fully 2169 window.HTMLElement && 2170 // also exclude jsdom 2171 !((_b = (_a = window.navigator) === null || _a === void 0 ? void 0 : _a.userAgent) === null || _b === void 0 ? void 0 : _b.includes('jsdom'))) { 2172 const replay = (target.__VUE_DEVTOOLS_HOOK_REPLAY__ = 2173 target.__VUE_DEVTOOLS_HOOK_REPLAY__ || []); 2174 replay.push((newHook) => { 2175 setDevtoolsHook(newHook, target); 2176 }); 2177 // clear buffer after 3s - the user probably doesn't have devtools installed 2178 // at all, and keeping the buffer will cause memory leaks (#4738) 2179 setTimeout(() => { 2180 if (!exports.devtools) { 2181 target.__VUE_DEVTOOLS_HOOK_REPLAY__ = null; 2182 devtoolsNotInstalled = true; 2183 buffer = []; 2184 } 2185 }, 3000); 2186 } 2187 else { 2188 // non-browser env, assume not installed 2189 devtoolsNotInstalled = true; 2190 buffer = []; 2191 } 2192 } 2193 function devtoolsInitApp(app, version) { 2194 emit("app:init" /* DevtoolsHooks.APP_INIT */, app, version, { 2195 Fragment, 2196 Text, 2197 Comment, 2198 Static 2199 }); 2200 } 2201 function devtoolsUnmountApp(app) { 2202 emit("app:unmount" /* DevtoolsHooks.APP_UNMOUNT */, app); 2203 } 2204 const devtoolsComponentAdded = /*#__PURE__*/ createDevtoolsComponentHook("component:added" /* DevtoolsHooks.COMPONENT_ADDED */); 2205 const devtoolsComponentUpdated = 2206 /*#__PURE__*/ createDevtoolsComponentHook("component:updated" /* DevtoolsHooks.COMPONENT_UPDATED */); 2207 const _devtoolsComponentRemoved = /*#__PURE__*/ createDevtoolsComponentHook("component:removed" /* DevtoolsHooks.COMPONENT_REMOVED */); 2208 const devtoolsComponentRemoved = (component) => { 2209 if (exports.devtools && 2210 typeof exports.devtools.cleanupBuffer === 'function' && 2211 // remove the component if it wasn't buffered 2212 !exports.devtools.cleanupBuffer(component)) { 2213 _devtoolsComponentRemoved(component); 2214 } 2215 }; 2216 function createDevtoolsComponentHook(hook) { 2217 return (component) => { 2218 emit(hook, component.appContext.app, component.uid, component.parent ? component.parent.uid : undefined, component); 2219 }; 2220 } 2221 const devtoolsPerfStart = /*#__PURE__*/ createDevtoolsPerformanceHook("perf:start" /* DevtoolsHooks.PERFORMANCE_START */); 2222 const devtoolsPerfEnd = /*#__PURE__*/ createDevtoolsPerformanceHook("perf:end" /* DevtoolsHooks.PERFORMANCE_END */); 2223 function createDevtoolsPerformanceHook(hook) { 2224 return (component, type, time) => { 2225 emit(hook, component.appContext.app, component.uid, component, type, time); 2226 }; 2227 } 2228 function devtoolsComponentEmit(component, event, params) { 2229 emit("component:emit" /* DevtoolsHooks.COMPONENT_EMIT */, component.appContext.app, component, event, params); 2230 } 2231 2232 function emit$1(instance, event, ...rawArgs) { 2233 if (instance.isUnmounted) 2234 return; 2235 const props = instance.vnode.props || EMPTY_OBJ; 2236 { 2237 const { emitsOptions, propsOptions: [propsOptions] } = instance; 2238 if (emitsOptions) { 2239 if (!(event in emitsOptions) && 2240 !(false )) { 2241 if (!propsOptions || !(toHandlerKey(event) in propsOptions)) { 2242 warn$1(`Component emitted event "${event}" but it is neither declared in ` + 2243 `the emits option nor as an "${toHandlerKey(event)}" prop.`); 2244 } 2245 } 2246 else { 2247 const validator = emitsOptions[event];
2248 if (isFunction(validator)) { 2249 const isValid = validator(...rawArgs); 2250 if (!isValid) { 2251 warn$1(`Invalid event arguments: event validation failed for event "${event}".`); 2252 } 2253 } 2254 } 2255 } 2256 } 2257 let args = rawArgs; 2258 const isModelListener = event.startsWith('update:'); 2259 // for v-model update:xxx events, apply modifiers on args 2260 const modelArg = isModelListener && event.slice(7); 2261 if (modelArg && modelArg in props) { 2262 const modifiersKey = `${modelArg === 'modelValue' ? 'model' : modelArg}Modifiers`; 2263 const { number, trim } = props[modifiersKey] || EMPTY_OBJ; 2264 if (trim) { 2265 args = rawArgs.map(a => (isString(a) ? a.trim() : a)); 2266 } 2267 if (number) { 2268 args = rawArgs.map(toNumber); 2269 } 2270 } 2271 { 2272 devtoolsComponentEmit(instance, event, args); 2273 } 2274 { 2275 const lowerCaseEvent = event.toLowerCase(); 2276 if (lowerCaseEvent !== event && props[toHandlerKey(lowerCaseEvent)]) { 2277 warn$1(`Event "${lowerCaseEvent}" is emitted in component ` + 2278 `${formatComponentName(instance, instance.type)} but the handler is registered for "${event}". ` + 2279 `Note that HTML attributes are case-insensitive and you cannot use ` + 2280 `v-on to listen to camelCase events when using in-DOM templates. ` + 2281 `You should probably use "${hyphenate(event)}" instead of "${event}".`); 2282 } 2283 } 2284 let handlerName; 2285 let handler = props[(handlerName = toHandlerKey(event))] || 2286 // also try camelCase event handler (#2249) 2287 props[(handlerName = toHandlerKey(camelize(event)))]; 2288 // for v-model update:xxx events, also trigger kebab-case equivalent 2289 // for props passed via kebab-case 2290 if (!handler && isModelListener) { 2291 handler = props[(handlerName = toHandlerKey(hyphenate(event)))]; 2292 } 2293 if (handler) { 2294 callWithAsyncErrorHandling(handler, instance, 6 /* ErrorCodes.COMPONENT_EVENT_HANDLER */, args); 2295 } 2296 const onceHandler = props[handlerName + `Once`]; 2297 if (onceHandler) { 2298 if (!instance.emitted) { 2299 instance.emitted = {}; 2300 } 2301 else if (instance.emitted[handlerName]) { 2302 return; 2303 } 2304 instance.emitted[handlerName] = true; 2305 callWithAsyncErrorHandling(onceHandler, instance, 6 /* ErrorCodes.COMPONENT_EVENT_HANDLER */, args); 2306 } 2307 } 2308 function normalizeEmitsOptions(comp, appContext, asMixin = false) { 2309 const cache = appContext.emitsCache; 2310 const cached = cache.get(comp); 2311 if (cached !== undefined) { 2312 return cached; 2313 } 2314 const raw = comp.emits; 2315 let normalized = {}; 2316 // apply mixin/extends props 2317 let hasExtends = false; 2318 if (!isFunction(comp)) { 2319 const extendEmits = (raw) => { 2320 const normalizedFromExtend = normalizeEmitsOptions(raw, appContext, true); 2321 if (normalizedFromExtend) { 2322 hasExtends = true; 2323 extend(normalized, normalizedFromExtend); 2324 } 2325 }; 2326 if (!asMixin && appContext.mixins.length) { 2327 appContext.mixins.forEach(extendEmits); 2328 } 2329 if (comp.extends) { 2330 extendEmits(comp.extends); 2331 } 2332 if (comp.mixins) { 2333 comp.mixins.forEach(extendEmits); 2334 } 2335 } 2336 if (!raw && !hasExtends) { 2337 if (isObject(comp)) { 2338 cache.set(comp, null); 2339 } 2340 return null; 2341 } 2342 if (isArray(raw)) { 2343 raw.forEach(key => (normalized[key] = null)); 2344 } 2345 else { 2346 extend(normalized, raw); 2347 } 2348 if (isObject(comp)) { 2349 cache.set(comp, normalized); 2350 } 2351 return normalized; 2352 } 2353 // Check if an incoming prop key is a declared emit event listener. 2354 // e.g. With `emits: { click: null }`, props named `onClick` and `onclick` are 2355 // both considered matched listeners. 2356 function isEmitListener(options, key) { 2357 if (!options || !isOn(key)) { 2358 return false;
2359 } 2360 key = key.slice(2).replace(/Once$/, ''); 2361 return (hasOwn(options, key[0].toLowerCase() + key.slice(1)) || 2362 hasOwn(options, hyphenate(key)) || 2363 hasOwn(options, key)); 2364 } 2365 2366 /** 2367 * mark the current rendering instance for asset resolution (e.g. 2368 * resolveComponent, resolveDirective) during render 2369 */ 2370 let currentRenderingInstance = null; 2371 let currentScopeId = null; 2372 /** 2373 * Note: rendering calls maybe nested. The function returns the parent rendering 2374 * instance if present, which should be restored after the render is done: 2375 * 2376 * ```js 2377 * const prev = setCurrentRenderingInstance(i) 2378 * // ...render 2379 * setCurrentRenderingInstance(prev) 2380 * ``` 2381 */ 2382 function setCurrentRenderingInstance(instance) { 2383 const prev = currentRenderingInstance; 2384 currentRenderingInstance = instance; 2385 currentScopeId = (instance && instance.type.__scopeId) || null; 2386 return prev; 2387 } 2388 /** 2389 * Set scope id when creating hoisted vnodes. 2390 * @private compiler helper 2391 */ 2392 function pushScopeId(id) { 2393 currentScopeId = id; 2394 } 2395 /** 2396 * Technically we no longer need this after 3.0.8 but we need to keep the same 2397 * API for backwards compat w/ code generated by compilers. 2398 * @private 2399 */ 2400 function popScopeId() { 2401 currentScopeId = null; 2402 } 2403 /** 2404 * Only for backwards compat 2405 * @private 2406 */ 2407 const withScopeId = (_id) => withCtx; 2408 /** 2409 * Wrap a slot function to memoize current rendering instance 2410 * @private compiler helper 2411 */ 2412 function withCtx(fn, ctx = currentRenderingInstance, isNonScopedSlot // false only 2413 ) { 2414 if (!ctx) 2415 return fn; 2416 // already normalized 2417 if (fn._n) { 2418 return fn; 2419 } 2420 const renderFnWithContext = (...args) => { 2421 // If a user calls a compiled slot inside a template expression (#1745), it 2422 // can mess up block tracking, so by default we disable block tracking and 2423 // force bail out when invoking a compiled slot (indicated by the ._d flag). 2424 // This isn't necessary if rendering a compiled `<slot>`, so we flip the 2425 // ._d flag off when invoking the wrapped fn inside `renderSlot`. 2426 if (renderFnWithContext._d) { 2427 setBlockTracking(-1); 2428 } 2429 const prevInstance = setCurrentRenderingInstance(ctx); 2430 let res; 2431 try { 2432 res = fn(...args); 2433 } 2434 finally { 2435 setCurrentRenderingInstance(prevInstance); 2436 if (renderFnWithContext._d) { 2437 setBlockTracking(1); 2438 } 2439 } 2440 { 2441 devtoolsComponentUpdated(ctx); 2442 } 2443 return res; 2444 }; 2445 // mark normalized to avoid duplicated wrapping 2446 renderFnWithContext._n = true; 2447 // mark this as compiled by default 2448 // this is used in vnode.ts -> normalizeChildren() to set the slot 2449 // rendering flag. 2450 renderFnWithContext._c = true; 2451 // disable block tracking by default 2452 renderFnWithContext._d = true; 2453 return renderFnWithContext; 2454 } 2455 2456 /** 2457 * dev only flag to track whether $attrs was used during render. 2458 * If $attrs was used during render then the warning for failed attrs 2459 * fallthrough can be suppressed. 2460 */ 2461 let accessedAttrs = false; 2462 function markAttrsAccessed() { 2463 accessedAttrs = true; 2464 } 2465 function renderComponentRoot(instance) { 2466 const { type: Component, vnode, proxy, withProxy, props, propsOptions: [propsOptions], slots, attrs, emit, render, renderCache, data, setupState, ctx, inheritAttrs } = instance; 2467 let result; 2468 let fallthroughAttrs; 2469 const prev = setCurrentRenderingInstance(instance); 2470 { 2471 accessedAttrs = false; 2472 } 2473 try { 2474 if (vnode.shapeFlag & 4 /* ShapeFlags.STATEFUL_COMPONENT */) { 2475 // withProxy is a proxy with a different `has` trap only for 2476 // runtime-compiled render functions using `with` block. 2477 const proxyToUse = withProxy || proxy; 2478 result = normalizeVNode(render.call(proxyToUse, proxyToUse, renderCache, props, setupState, data, ctx)); 2479 fallthroughAttrs = attrs; 2480 } 2481 else { 2482 // functional 2483 const render = Component; 2484 // in dev, mark attrs accessed if optional props (attrs === props) 2485 if (true && attrs === props) { 2486 markAttrsAccessed(); 2487 } 2488 result = normalizeVNode(render.length > 1 2489 ? render(props, true 2490 ? { 2491 get attrs() { 2492 markAttrsAccessed(); 2493 return attrs; 2494 }, 2495 slots, 2496 emit 2497 } 2498 : { attrs, slots, emit }) 2499 : render(props, null /* we know it doesn't need it */)); 2500 fallthroughAttrs = Component.props 2501 ? attrs 2502 : getFunctionalFallthrough(attrs); 2503 } 2504 } 2505 catch (err) { 2506 blockStack.length = 0; 2507 handleError(err, instance, 1 /* ErrorCodes.RENDER_FUNCTION */); 2508 result = createVNode(Comment); 2509 } 2510 // attr merging 2511 // in dev mode, comments are preserved, and it's possible for a template 2512 // to have comments along side the root element which makes it a fragment 2513 let root = result; 2514 let setRoot = undefined; 2515 if (result.patchFlag > 0 && 2516 result.patchFlag & 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */) { 2517 [root, setRoot] = getChildRoot(result); 2518 } 2519 if (fallthroughAttrs && inheritAttrs !== false) {
2520 const keys = Object.keys(fallthroughAttrs); 2521 const { shapeFlag } = root; 2522 if (keys.length) { 2523 if (shapeFlag & (1 /* ShapeFlags.ELEMENT */ | 6 /* ShapeFlags.COMPONENT */)) { 2524 if (propsOptions && keys.some(isModelListener)) { 2525 // If a v-model listener (onUpdate:xxx) has a corresponding declared 2526 // prop, it indicates this component expects to handle v-model and 2527 // it should not fallthrough. 2528 // related: #1543, #1643, #1989 2529 fallthroughAttrs = filterModelListeners(fallthroughAttrs, propsOptions); 2530 } 2531 root = cloneVNode(root, fallthroughAttrs); 2532 } 2533 else if (!accessedAttrs && root.type !== Comment) { 2534 const allAttrs = Object.keys(attrs); 2535 const eventAttrs = []; 2536 const extraAttrs = []; 2537 for (let i = 0, l = allAttrs.length; i < l; i++) { 2538 const key = allAttrs[i]; 2539 if (isOn(key)) { 2540 // ignore v-model handlers when they fail to fallthrough 2541 if (!isModelListener(key)) { 2542 // remove `on`, lowercase first letter to reflect event casing 2543 // accurately 2544 eventAttrs.push(key[2].toLowerCase() + key.slice(3)); 2545 } 2546 } 2547 else { 2548 extraAttrs.push(key); 2549 } 2550 } 2551 if (extraAttrs.length) { 2552 warn$1(`Extraneous non-props attributes (` + 2553 `${extraAttrs.join(', ')}) ` + 2554 `were passed to component but could not be automatically inherited ` + 2555 `because component renders fragment or text root nodes.`); 2556 } 2557 if (eventAttrs.length) { 2558 warn$1(`Extraneous non-emits event listeners (` + 2559 `${eventAttrs.join(', ')}) ` + 2560 `were passed to component but could not be automatically inherited ` + 2561 `because component renders fragment or text root nodes. ` + 2562 `If the listener is intended to be a component custom event listener only, ` + 2563 `declare it using the "emits" option.`); 2564 } 2565 } 2566 } 2567 } 2568 // inherit directives 2569 if (vnode.dirs) { 2570 if (!isElementRoot(root)) { 2571 warn$1(`Runtime directive used on component with non-element root node. ` + 2572 `The directives will not function as intended.`); 2573 } 2574 // clone before mutating since the root may be a hoisted vnode 2575 root = cloneVNode(root); 2576 root.dirs = root.dirs ? root.dirs.concat(vnode.dirs) : vnode.dirs; 2577 } 2578 // inherit transition data 2579 if (vnode.transition) { 2580 if (!isElementRoot(root)) { 2581 warn$1(`Component inside <Transition> renders non-element root node ` + 2582 `that cannot be animated.`); 2583 } 2584 root.transition = vnode.transition; 2585 } 2586 if (setRoot) { 2587 setRoot(root); 2588 } 2589 else { 2590 result = root; 2591 } 2592 setCurrentRenderingInstance(prev); 2593 return result; 2594 } 2595 /** 2596 * dev only 2597 * In dev mode, template root level comments are rendered, which turns the 2598 * template into a fragment root, but we need to locate the single element 2599 * root for attrs and scope id processing. 2600 */ 2601 const getChildRoot = (vnode) => { 2602 const rawChildren = vnode.children; 2603 const dynamicChildren = vnode.dynamicChildren; 2604 const childRoot = filterSingleRoot(rawChildren); 2605 if (!childRoot) { 2606 return [vnode, undefined]; 2607 } 2608 const index = rawChildren.indexOf(childRoot); 2609 const dynamicIndex = dynamicChildren ? dynamicChildren.indexOf(childRoot) : -1; 2610 const setRoot = (updatedRoot) => { 2611 rawChildren[index] = updatedRoot; 2612 if (dynamicChildren) { 2613 if (dynamicIndex > -1) { 2614 dynamicChildren[dynamicIndex] = updatedRoot; 2615 } 2616 else if (updatedRoot.patchFlag > 0) { 2617 vnode.dynamicChildren = [...dynamicChildren, updatedRoot]; 2618 } 2619 } 2620 }; 2621 return [normalizeVNode(childRoot), setRoot]; 2622 }; 2623 function filterSingleRoot(children) { 2624 let singleRoot; 2625 for (let i = 0; i < children.length; i++) { 2626 const child = children[i]; 2627 if (isVNode(child)) { 2628 // ignore user comment 2629 if (child.type !== Comment || child.children === 'v-if') { 2630 if (singleRoot) { 2631 // has more than 1 non-comment child, return now 2632 return; 2633 } 2634 else { 2635 singleRoot = child; 2636 } 2637 } 2638 } 2639 else { 2640 return; 2641 } 2642 } 2643 return singleRoot; 2644 } 2645 const getFunctionalFallthrough = (attrs) => { 2646 let res; 2647 for (const key in attrs) {
2648 if (key === 'class' || key === 'style' || isOn(key)) { 2649 (res || (res = {}))[key] = attrs[key]; 2650 } 2651 } 2652 return res; 2653 }; 2654 const filterModelListeners = (attrs, props) => { 2655 const res = {}; 2656 for (const key in attrs) { 2657 if (!isModelListener(key) || !(key.slice(9) in props)) { 2658 res[key] = attrs[key]; 2659 } 2660 } 2661 return res; 2662 }; 2663 const isElementRoot = (vnode) => { 2664 return (vnode.shapeFlag & (6 /* ShapeFlags.COMPONENT */ | 1 /* ShapeFlags.ELEMENT */) || 2665 vnode.type === Comment // potential v-if branch switch 2666 ); 2667 }; 2668 function shouldUpdateComponent(prevVNode, nextVNode, optimized) { 2669 const { props: prevProps, children: prevChildren, component } = prevVNode; 2670 const { props: nextProps, children: nextChildren, patchFlag } = nextVNode; 2671 const emits = component.emitsOptions; 2672 // Parent component's render function was hot-updated. Since this may have 2673 // caused the child component's slots content to have changed, we need to 2674 // force the child to update as well. 2675 if ((prevChildren || nextChildren) && isHmrUpdating) { 2676 return true; 2677 } 2678 // force child update for runtime directive or transition on component vnode. 2679 if (nextVNode.dirs || nextVNode.transition) { 2680 return true; 2681 } 2682 if (optimized && patchFlag >= 0) { 2683 if (patchFlag & 1024 /* PatchFlags.DYNAMIC_SLOTS */) { 2684 // slot content that references values that might have changed, 2685 // e.g. in a v-for 2686 return true; 2687 } 2688 if (patchFlag & 16 /* PatchFlags.FULL_PROPS */) { 2689 if (!prevProps) { 2690 return !!nextProps; 2691 } 2692 // presence of this flag indicates props are always non-null 2693 return hasPropsChanged(prevProps, nextProps, emits); 2694 } 2695 else if (patchFlag & 8 /* PatchFlags.PROPS */) { 2696 const dynamicProps = nextVNode.dynamicProps; 2697 for (let i = 0; i < dynamicProps.length; i++) { 2698 const key = dynamicProps[i]; 2699 if (nextProps[key] !== prevProps[key] && 2700 !isEmitListener(emits, key)) { 2701 return true; 2702 } 2703 } 2704 } 2705 } 2706 else { 2707 // this path is only taken by manually written render functions 2708 // so presence of any children leads to a forced update 2709 if (prevChildren || nextChildren) { 2710 if (!nextChildren || !nextChildren.$stable) { 2711 return true; 2712 } 2713 } 2714 if (prevProps === nextProps) { 2715 return false; 2716 } 2717 if (!prevProps) { 2718 return !!nextProps; 2719 } 2720 if (!nextProps) { 2721 return true; 2722 } 2723 return hasPropsChanged(prevProps, nextProps, emits); 2724 } 2725 return false; 2726 } 2727 function hasPropsChanged(prevProps, nextProps, emitsOptions) { 2728 const nextKeys = Object.keys(nextProps); 2729 if (nextKeys.length !== Object.keys(prevProps).length) { 2730 return true; 2731 } 2732 for (let i = 0; i < nextKeys.length; i++) { 2733 const key = nextKeys[i]; 2734 if (nextProps[key] !== prevProps[key] && 2735 !isEmitListener(emitsOptions, key)) { 2736 return true; 2737 } 2738 } 2739 return false; 2740 } 2741 function updateHOCHostEl({ vnode, parent }, el // HostNode 2742 ) { 2743 while (parent && parent.subTree === vnode) { 2744 (vnode = parent.vnode).el = el; 2745 parent = parent.parent; 2746 } 2747 } 2748 2749 const isSuspense = (type) => type.__isSuspense; 2750 // Suspense exposes a component-like API, and is treated like a component 2751 // in the compiler, but internally it's a special built-in type that hooks 2752 // directly into the renderer. 2753 const SuspenseImpl = { 2754 name: 'Suspense', 2755 // In order to make Suspense tree-shakable, we need to avoid importing it 2756 // directly in the renderer. The renderer checks for the __isSuspense flag 2757 // on a vnode's type and calls the `process` method, passing in renderer 2758 // internals. 2759 __isSuspense: true, 2760 process(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, 2761 // platform-specific impl passed from renderer 2762 rendererInternals) { 2763 if (n1 == null) { 2764 mountSuspense(n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, rendererInternals); 2765 } 2766 else { 2767 patchSuspense(n1, n2, container, anchor, parentComponent, isSVG, slotScopeIds, optimized, rendererInternals); 2768 } 2769 }, 2770 hydrate: hydrateSuspense, 2771 create: createSuspenseBoundary, 2772 normalize: normalizeSuspenseChildren 2773 }; 2774 // Force-casted public typing for h and TSX props inference 2775 const Suspense = (SuspenseImpl 2776 ); 2777 function triggerEvent(vnode, name) { 2778 const eventListener = vnode.props && vnode.props[name]; 2779 if (isFunction(eventListener)) { 2780 eventListener(); 2781 } 2782 } 2783 function mountSuspense(vnode, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, rendererInternals) { 2784 const { p: patch, o: { createElement } } = rendererInternals; 2785 const hiddenContainer = createElement('div'); 2786 const suspense = (vnode.suspense = createSuspenseBoundary(vnode, parentSuspense, parentComponent, container, hiddenContainer, anchor, isSVG, slotScopeIds, optimized, rendererInternals)); 2787 // start mounting the content subtree in an off-dom container 2788 patch(null, (suspense.pendingBranch = vnode.ssContent), hiddenContainer, null, parentComponent, suspense, isSVG, slotScopeIds); 2789 // now check if we have encountered any async deps 2790 if (suspense.deps > 0) { 2791 // has async 2792 // invoke @fallback event 2793 triggerEvent(vnode, 'onPending'); 2794 triggerEvent(vnode, 'onFallback'); 2795 // mount the fallback tree 2796 patch(null, vnode.ssFallback, container, anchor, parentComponent, null, // fallback tree will not have suspense context 2797 isSVG, slotScopeIds);
2798 setActiveBranch(suspense, vnode.ssFallback); 2799 } 2800 else { 2801 // Suspense has no async deps. Just resolve. 2802 suspense.resolve(); 2803 } 2804 } 2805 function patchSuspense(n1, n2, container, anchor, parentComponent, isSVG, slotScopeIds, optimized, { p: patch, um: unmount, o: { createElement } }) { 2806 const suspense = (n2.suspense = n1.suspense); 2807 suspense.vnode = n2; 2808 n2.el = n1.el; 2809 const newBranch = n2.ssContent; 2810 const newFallback = n2.ssFallback; 2811 const { activeBranch, pendingBranch, isInFallback, isHydrating } = suspense; 2812 if (pendingBranch) { 2813 suspense.pendingBranch = newBranch; 2814 if (isSameVNodeType(newBranch, pendingBranch)) { 2815 // same root type but content may have changed. 2816 patch(pendingBranch, newBranch, suspense.hiddenContainer, null, parentComponent, suspense, isSVG, slotScopeIds, optimized); 2817 if (suspense.deps <= 0) { 2818 suspense.resolve(); 2819 } 2820 else if (isInFallback) { 2821 patch(activeBranch, newFallback, container, anchor, parentComponent, null, // fallback tree will not have suspense context 2822 isSVG, slotScopeIds, optimized);
2823 setActiveBranch(suspense, newFallback); 2824 } 2825 } 2826 else { 2827 // toggled before pending tree is resolved 2828 suspense.pendingId++; 2829 if (isHydrating) { 2830 // if toggled before hydration is finished, the current DOM tree is 2831 // no longer valid. set it as the active branch so it will be unmounted 2832 // when resolved 2833 suspense.isHydrating = false; 2834 suspense.activeBranch = pendingBranch; 2835 } 2836 else { 2837 unmount(pendingBranch, parentComponent, suspense); 2838 } 2839 // increment pending ID. this is used to invalidate async callbacks 2840 // reset suspense state 2841 suspense.deps = 0; 2842 // discard effects from pending branch 2843 suspense.effects.length = 0; 2844 // discard previous container 2845 suspense.hiddenContainer = createElement('div'); 2846 if (isInFallback) { 2847 // already in fallback state 2848 patch(null, newBranch, suspense.hiddenContainer, null, parentComponent, suspense, isSVG, slotScopeIds, optimized); 2849 if (suspense.deps <= 0) { 2850 suspense.resolve(); 2851 } 2852 else { 2853 patch(activeBranch, newFallback, container, anchor, parentComponent, null, // fallback tree will not have suspense context 2854 isSVG, slotScopeIds, optimized);
2855 setActiveBranch(suspense, newFallback); 2856 } 2857 } 2858 else if (activeBranch && isSameVNodeType(newBranch, activeBranch)) { 2859 // toggled "back" to current active branch 2860 patch(activeBranch, newBranch, container, anchor, parentComponent, suspense, isSVG, slotScopeIds, optimized); 2861 // force resolve 2862 suspense.resolve(true); 2863 } 2864 else { 2865 // switched to a 3rd branch 2866 patch(null, newBranch, suspense.hiddenContainer, null, parentComponent, suspense, isSVG, slotScopeIds, optimized); 2867 if (suspense.deps <= 0) { 2868 suspense.resolve(); 2869 } 2870 } 2871 } 2872 } 2873 else { 2874 if (activeBranch && isSameVNodeType(newBranch, activeBranch)) { 2875 // root did not change, just normal patch 2876 patch(activeBranch, newBranch, container, anchor, parentComponent, suspense, isSVG, slotScopeIds, optimized);
2877 setActiveBranch(suspense, newBranch); 2878 } 2879 else { 2880 // root node toggled 2881 // invoke @pending event 2882 triggerEvent(n2, 'onPending'); 2883 // mount pending branch in off-dom container 2884 suspense.pendingBranch = newBranch; 2885 suspense.pendingId++; 2886 patch(null, newBranch, suspense.hiddenContainer, null, parentComponent, suspense, isSVG, slotScopeIds, optimized); 2887 if (suspense.deps <= 0) { 2888 // incoming branch has no async deps, resolve now. 2889 suspense.resolve(); 2890 } 2891 else { 2892 const { timeout, pendingId } = suspense; 2893 if (timeout > 0) { 2894 setTimeout(() => { 2895 if (suspense.pendingId === pendingId) { 2896 suspense.fallback(newFallback); 2897 } 2898 }, timeout); 2899 } 2900 else if (timeout === 0) { 2901 suspense.fallback(newFallback); 2902 } 2903 } 2904 } 2905 } 2906 } 2907 let hasWarned = false; 2908 function createSuspenseBoundary(vnode, parent, parentComponent, container, hiddenContainer, anchor, isSVG, slotScopeIds, optimized, rendererInternals, isHydrating = false) { 2909 /* istanbul ignore if */ 2910 if (!hasWarned) { 2911 hasWarned = true; 2912 // @ts-ignore `console.info` cannot be null error 2913 console[console.info ? 'info' : 'log'](`<Suspense> is an experimental feature and its API will likely change.`); 2914 } 2915 const { p: patch, m: move, um: unmount, n: next, o: { parentNode, remove } } = rendererInternals; 2916 const timeout = toNumber(vnode.props && vnode.props.timeout); 2917 const suspense = { 2918 vnode, 2919 parent, 2920 parentComponent, 2921 isSVG, 2922 container, 2923 hiddenContainer, 2924 anchor, 2925 deps: 0, 2926 pendingId: 0, 2927 timeout: typeof timeout === 'number' ? timeout : -1, 2928 activeBranch: null, 2929 pendingBranch: null, 2930 isInFallback: true, 2931 isHydrating, 2932 isUnmounted: false, 2933 effects: [], 2934 resolve(resume = false) { 2935 { 2936 if (!resume && !suspense.pendingBranch) { 2937 throw new Error(`suspense.resolve() is called without a pending branch.`); 2938 } 2939 if (suspense.isUnmounted) { 2940 throw new Error(`suspense.resolve() is called on an already unmounted suspense boundary.`); 2941 } 2942 } 2943 const { vnode, activeBranch, pendingBranch, pendingId, effects, parentComponent, container } = suspense; 2944 if (suspense.isHydrating) { 2945 suspense.isHydrating = false; 2946 } 2947 else if (!resume) { 2948 const delayEnter = activeBranch && 2949 pendingBranch.transition && 2950 pendingBranch.transition.mode === 'out-in'; 2951 if (delayEnter) { 2952 activeBranch.transition.afterLeave = () => { 2953 if (pendingId === suspense.pendingId) { 2954 move(pendingBranch, container, anchor, 0 /* MoveType.ENTER */); 2955 } 2956 }; 2957 } 2958 // this is initial anchor on mount 2959 let { anchor } = suspense; 2960 // unmount current active tree 2961 if (activeBranch) { 2962 // if the fallback tree was mounted, it may have been moved 2963 // as part of a parent suspense. get the latest anchor for insertion 2964 anchor = next(activeBranch); 2965 unmount(activeBranch, parentComponent, suspense, true); 2966 } 2967 if (!delayEnter) { 2968 // move content from off-dom container to actual container 2969 move(pendingBranch, container, anchor, 0 /* MoveType.ENTER */); 2970 } 2971 }
2972 setActiveBranch(suspense, pendingBranch); 2973 suspense.pendingBranch = null; 2974 suspense.isInFallback = false; 2975 // flush buffered effects 2976 // check if there is a pending parent suspense 2977 let parent = suspense.parent; 2978 let hasUnresolvedAncestor = false; 2979 while (parent) { 2980 if (parent.pendingBranch) { 2981 // found a pending parent suspense, merge buffered post jobs 2982 // into that parent 2983 parent.effects.push(...effects); 2984 hasUnresolvedAncestor = true; 2985 break; 2986 } 2987 parent = parent.parent; 2988 } 2989 // no pending parent suspense, flush all jobs 2990 if (!hasUnresolvedAncestor) { 2991 queuePostFlushCb(effects); 2992 } 2993 suspense.effects = []; 2994 // invoke @resolve event 2995 triggerEvent(vnode, 'onResolve'); 2996 }, 2997 fallback(fallbackVNode) { 2998 if (!suspense.pendingBranch) { 2999 return; 3000 } 3001 const { vnode, activeBranch, parentComponent, container, isSVG } = suspense; 3002 // invoke @fallback event 3003 triggerEvent(vnode, 'onFallback'); 3004 const anchor = next(activeBranch); 3005 const mountFallback = () => { 3006 if (!suspense.isInFallback) { 3007 return; 3008 } 3009 // mount the fallback tree 3010 patch(null, fallbackVNode, container, anchor, parentComponent, null, // fallback tree will not have suspense context 3011 isSVG, slotScopeIds, optimized);
3012 setActiveBranch(suspense, fallbackVNode); 3013 }; 3014 const delayEnter = fallbackVNode.transition && fallbackVNode.transition.mode === 'out-in'; 3015 if (delayEnter) { 3016 activeBranch.transition.afterLeave = mountFallback; 3017 } 3018 suspense.isInFallback = true; 3019 // unmount current active branch 3020 unmount(activeBranch, parentComponent, null, // no suspense so unmount hooks fire now 3021 true // shouldRemove 3022 ); 3023 if (!delayEnter) { 3024 mountFallback(); 3025 } 3026 }, 3027 move(container, anchor, type) { 3028 suspense.activeBranch && 3029 move(suspense.activeBranch, container, anchor, type); 3030 suspense.container = container; 3031 }, 3032 next() { 3033 return suspense.activeBranch && next(suspense.activeBranch); 3034 }, 3035 registerDep(instance, setupRenderEffect) { 3036 const isInPendingSuspense = !!suspense.pendingBranch; 3037 if (isInPendingSuspense) { 3038 suspense.deps++; 3039 } 3040 const hydratedEl = instance.vnode.el; 3041 instance 3042 .asyncDep.catch(err => { 3043 handleError(err, instance, 0 /* ErrorCodes.SETUP_FUNCTION */); 3044 }) 3045 .then(asyncSetupResult => { 3046 // retry when the setup() promise resolves. 3047 // component may have been unmounted before resolve. 3048 if (instance.isUnmounted || 3049 suspense.isUnmounted || 3050 suspense.pendingId !== instance.suspenseId) { 3051 return; 3052 } 3053 // retry from this component 3054 instance.asyncResolved = true; 3055 const { vnode } = instance; 3056 { 3057 pushWarningContext(vnode); 3058 } 3059 handleSetupResult(instance, asyncSetupResult, false); 3060 if (hydratedEl) { 3061 // vnode may have been replaced if an update happened before the 3062 // async dep is resolved. 3063 vnode.el = hydratedEl; 3064 } 3065 const placeholder = !hydratedEl && instance.subTree.el; 3066 setupRenderEffect(instance, vnode, 3067 // component may have been moved before resolve. 3068 // if this is not a hydration, instance.subTree will be the comment 3069 // placeholder. 3070 parentNode(hydratedEl || instance.subTree.el), 3071 // anchor will not be used if this is hydration, so only need to 3072 // consider the comment placeholder case. 3073 hydratedEl ? null : next(instance.subTree), suspense, isSVG, optimized); 3074 if (placeholder) { 3075 remove(placeholder); 3076 } 3077 updateHOCHostEl(instance, vnode.el); 3078 { 3079 popWarningContext(); 3080 } 3081 // only decrease deps count if suspense is not already resolved 3082 if (isInPendingSuspense && --suspense.deps === 0) { 3083 suspense.resolve(); 3084 } 3085 }); 3086 }, 3087 unmount(parentSuspense, doRemove) { 3088 suspense.isUnmounted = true; 3089 if (suspense.activeBranch) { 3090 unmount(suspense.activeBranch, parentComponent, parentSuspense, doRemove); 3091 } 3092 if (suspense.pendingBranch) { 3093 unmount(suspense.pendingBranch, parentComponent, parentSuspense, doRemove); 3094 } 3095 } 3096 }; 3097 return suspense; 3098 } 3099 function hydrateSuspense(node, vnode, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, rendererInternals, hydrateNode) { 3100 /* eslint-disable no-restricted-globals */ 3101 const suspense = (vnode.suspense = createSuspenseBoundary(vnode, parentSuspense, parentComponent, node.parentNode, document.createElement('div'), null, isSVG, slotScopeIds, optimized, rendererInternals, true /* hydrating */)); 3102 // there are two possible scenarios for server-rendered suspense: 3103 // - success: ssr content should be fully resolved 3104 // - failure: ssr content should be the fallback branch. 3105 // however, on the client we don't really know if it has failed or not 3106 // attempt to hydrate the DOM assuming it has succeeded, but we still 3107 // need to construct a suspense boundary first 3108 const result = hydrateNode(node, (suspense.pendingBranch = vnode.ssContent), parentComponent, suspense, slotScopeIds, optimized); 3109 if (suspense.deps === 0) { 3110 suspense.resolve(); 3111 } 3112 return result; 3113 /* eslint-enable no-restricted-globals */ 3114 } 3115 function normalizeSuspenseChildren(vnode) { 3116 const { shapeFlag, children } = vnode; 3117 const isSlotChildren = shapeFlag & 32 /* ShapeFlags.SLOTS_CHILDREN */; 3118 vnode.ssContent = normalizeSuspenseSlot(isSlotChildren ? children.default : children); 3119 vnode.ssFallback = isSlotChildren 3120 ? normalizeSuspenseSlot(children.fallback) 3121 : createVNode(Comment); 3122 } 3123 function normalizeSuspenseSlot(s) { 3124 let block; 3125 if (isFunction(s)) { 3126 const trackBlock = isBlockTreeEnabled && s._c; 3127 if (trackBlock) { 3128 // disableTracking: false 3129 // allow block tracking for compiled slots 3130 // (see ./componentRenderContext.ts) 3131 s._d = false;
3132 openBlock(); 3133 } 3134 s = s(); 3135 if (trackBlock) { 3136 s._d = true; 3137 block = currentBlock; 3138 closeBlock(); 3139 } 3140 } 3141 if (isArray(s)) { 3142 const singleChild = filterSingleRoot(s); 3143 if (!singleChild) { 3144 warn$1(`<Suspense> slots expect a single root node.`); 3145 } 3146 s = singleChild; 3147 } 3148 s = normalizeVNode(s); 3149 if (block && !s.dynamicChildren) { 3150 s.dynamicChildren = block.filter(c => c !== s); 3151 } 3152 return s; 3153 } 3154 function queueEffectWithSuspense(fn, suspense) { 3155 if (suspense && suspense.pendingBranch) { 3156 if (isArray(fn)) { 3157 suspense.effects.push(...fn); 3158 } 3159 else { 3160 suspense.effects.push(fn); 3161 } 3162 } 3163 else { 3164 queuePostFlushCb(fn); 3165 } 3166 } 3167 function setActiveBranch(suspense, branch) { 3168 suspense.activeBranch = branch; 3169 const { vnode, parentComponent } = suspense; 3170 const el = (vnode.el = branch.el); 3171 // in case suspense is the root node of a component, 3172 // recursively update the HOC el 3173 if (parentComponent && parentComponent.subTree === vnode) { 3174 parentComponent.vnode.el = el; 3175 updateHOCHostEl(parentComponent, el); 3176 } 3177 } 3178 3179 function provide(key, value) { 3180 if (!currentInstance) { 3181 { 3182 warn$1(`provide() can only be used inside setup().`); 3183 } 3184 } 3185 else { 3186 let provides = currentInstance.provides; 3187 // by default an instance inherits its parent's provides object 3188 // but when it needs to provide values of its own, it creates its 3189 // own provides object using parent provides object as prototype. 3190 // this way in `inject` we can simply look up injections from direct 3191 // parent and let the prototype chain do the work. 3192 const parentProvides = currentInstance.parent && currentInstance.parent.provides; 3193 if (parentProvides === provides) { 3194 provides = currentInstance.provides = Object.create(parentProvides); 3195 } 3196 // TS doesn't allow symbol as index type 3197 provides[key] = value; 3198 } 3199 } 3200 function inject(key, defaultValue, treatDefaultAsFactory = false) { 3201 // fallback to `currentRenderingInstance` so that this can be called in 3202 // a functional component 3203 const instance = currentInstance || currentRenderingInstance; 3204 if (instance) { 3205 // #2400 3206 // to support `app.use` plugins, 3207 // fallback to appContext's `provides` if the instance is at root 3208 const provides = instance.parent == null 3209 ? instance.vnode.appContext && instance.vnode.appContext.provides 3210 : instance.parent.provides; 3211 if (provides && key in provides) { 3212 // TS doesn't allow symbol as index type 3213 return provides[key]; 3214 } 3215 else if (arguments.length > 1) { 3216 return treatDefaultAsFactory && isFunction(defaultValue) 3217 ? defaultValue.call(instance.proxy) 3218 : defaultValue; 3219 } 3220 else { 3221 warn$1(`injection "${String(key)}" not found.`); 3222 } 3223 } 3224 else { 3225 warn$1(`inject() can only be used inside setup() or functional components.`); 3226 } 3227 } 3228 3229 // Simple effect. 3230 function watchEffect(effect, options) { 3231 return doWatch(effect, null, options); 3232 } 3233 function watchPostEffect(effect, options) { 3234 return doWatch(effect, null, (Object.assign(Object.assign({}, options), { flush: 'post' }) )); 3235 } 3236 function watchSyncEffect(effect, options) { 3237 return doWatch(effect, null, (Object.assign(Object.assign({}, options), { flush: 'sync' }) )); 3238 } 3239 // initial value for watchers to trigger on undefined initial values 3240 const INITIAL_WATCHER_VALUE = {}; 3241 // implementation 3242 function watch(source, cb, options) { 3243 if (!isFunction(cb)) { 3244 warn$1(`\`watch(fn, options?)\` signature has been moved to a separate API. ` + 3245 `Use \`watchEffect(fn, options?)\` instead. \`watch\` now only ` + 3246 `supports \`watch(source, cb, options?) signature.`); 3247 } 3248 return doWatch(source, cb, options); 3249 } 3250 function doWatch(source, cb, { immediate, deep, flush, onTrack, onTrigger } = EMPTY_OBJ) { 3251 if (!cb) { 3252 if (immediate !== undefined) { 3253 warn$1(`watch() "immediate" option is only respected when using the ` + 3254 `watch(source, callback, options?) signature.`); 3255 } 3256 if (deep !== undefined) { 3257 warn$1(`watch() "deep" option is only respected when using the ` + 3258 `watch(source, callback, options?) signature.`); 3259 } 3260 }
3261 const warnInvalidSource = (s) => { 3262 warn$1(`Invalid watch source: `, s, `A watch source can only be a getter/effect function, a ref, ` + 3263 `a reactive object, or an array of these types.`); 3264 }; 3265 const instance = currentInstance; 3266 let getter; 3267 let forceTrigger = false; 3268 let isMultiSource = false; 3269 if (isRef(source)) { 3270 getter = () => source.value; 3271 forceTrigger = isShallow(source); 3272 } 3273 else if (isReactive(source)) { 3274 getter = () => source; 3275 deep = true; 3276 } 3277 else if (isArray(source)) { 3278 isMultiSource = true; 3279 forceTrigger = source.some(s => isReactive(s) || isShallow(s)); 3280 getter = () => source.map(s => { 3281 if (isRef(s)) { 3282 return s.value; 3283 } 3284 else if (isReactive(s)) { 3285 return traverse(s); 3286 } 3287 else if (isFunction(s)) { 3288 return callWithErrorHandling(s, instance, 2 /* ErrorCodes.WATCH_GETTER */); 3289 } 3290 else { 3291 warnInvalidSource(s); 3292 } 3293 }); 3294 } 3295 else if (isFunction(source)) { 3296 if (cb) { 3297 // getter with cb 3298 getter = () => callWithErrorHandling(source, instance, 2 /* ErrorCodes.WATCH_GETTER */); 3299 } 3300 else { 3301 // no cb -> simple effect 3302 getter = () => { 3303 if (instance && instance.isUnmounted) { 3304 return; 3305 } 3306 if (cleanup) { 3307 cleanup(); 3308 } 3309 return callWithAsyncErrorHandling(source, instance, 3 /* ErrorCodes.WATCH_CALLBACK */, [onCleanup]); 3310 }; 3311 } 3312 } 3313 else { 3314 getter = NOOP; 3315 warnInvalidSource(source); 3316 } 3317 if (cb && deep) { 3318 const baseGetter = getter; 3319 getter = () => traverse(baseGetter()); 3320 } 3321 let cleanup; 3322 let onCleanup = (fn) => { 3323 cleanup = effect.onStop = () => { 3324 callWithErrorHandling(fn, instance, 4 /* ErrorCodes.WATCH_CLEANUP */); 3325 }; 3326 }; 3327 let oldValue = isMultiSource 3328 ? new Array(source.length).fill(INITIAL_WATCHER_VALUE) 3329 : INITIAL_WATCHER_VALUE; 3330 const job = () => { 3331 if (!effect.active) { 3332 return; 3333 } 3334 if (cb) { 3335 // watch(source, cb) 3336 const newValue = effect.run(); 3337 if (deep || 3338 forceTrigger || 3339 (isMultiSource 3340 ? newValue.some((v, i) => hasChanged(v, oldValue[i])) 3341 : hasChanged(newValue, oldValue)) || 3342 (false )) { 3343 // cleanup before running cb again 3344 if (cleanup) { 3345 cleanup(); 3346 } 3347 callWithAsyncErrorHandling(cb, instance, 3 /* ErrorCodes.WATCH_CALLBACK */, [ 3348 newValue, 3349 // pass undefined as the old value when it's changed for the first time 3350 oldValue === INITIAL_WATCHER_VALUE 3351 ? undefined 3352 : (isMultiSource && oldValue[0] === INITIAL_WATCHER_VALUE) 3353 ? [] 3354 : oldValue, 3355 onCleanup 3356 ]); 3357 oldValue = newValue; 3358 } 3359 } 3360 else { 3361 // watchEffect 3362 effect.run(); 3363 } 3364 }; 3365 // important: mark the job as a watcher callback so that scheduler knows 3366 // it is allowed to self-trigger (#1727) 3367 job.allowRecurse = !!cb; 3368 let scheduler; 3369 if (flush === 'sync') { 3370 scheduler = job; // the scheduler function gets called directly 3371 } 3372 else if (flush === 'post') { 3373 scheduler = () => queuePostRenderEffect(job, instance && instance.suspense); 3374 } 3375 else { 3376 // default: 'pre' 3377 job.pre = true; 3378 if (instance) 3379 job.id = instance.uid; 3380 scheduler = () => queueJob(job); 3381 } 3382 const effect = new ReactiveEffect(getter, scheduler); 3383 { 3384 effect.onTrack = onTrack; 3385 effect.onTrigger = onTrigger; 3386 } 3387 // initial run 3388 if (cb) { 3389 if (immediate) { 3390 job(); 3391 } 3392 else { 3393 oldValue = effect.run(); 3394 } 3395 } 3396 else if (flush === 'post') { 3397 queuePostRenderEffect(effect.run.bind(effect), instance && instance.suspense); 3398 } 3399 else { 3400 effect.run(); 3401 } 3402 const unwatch = () => { 3403 effect.stop(); 3404 if (instance && instance.scope) { 3405 remove(instance.scope.effects, effect); 3406 } 3407 }; 3408 return unwatch; 3409 } 3410 // this.$watch 3411 function instanceWatch(source, value, options) { 3412 const publicThis = this.proxy; 3413 const getter = isString(source) 3414 ? source.includes('.') 3415 ? createPathGetter(publicThis, source) 3416 : () => publicThis[source] 3417 : source.bind(publicThis, publicThis); 3418 let cb; 3419 if (isFunction(value)) { 3420 cb = value; 3421 } 3422 else { 3423 cb = value.handler; 3424 options = value; 3425 } 3426 const cur = currentInstance; 3427 setCurrentInstance(this); 3428 const res = doWatch(getter, cb.bind(publicThis), options); 3429 if (cur) { 3430 setCurrentInstance(cur); 3431 } 3432 else { 3433 unsetCurrentInstance(); 3434 } 3435 return res; 3436 } 3437 function createPathGetter(ctx, path) { 3438 const segments = path.split('.'); 3439 return () => { 3440 let cur = ctx; 3441 for (let i = 0; i < segments.length && cur; i++) { 3442 cur = cur[segments[i]]; 3443 } 3444 return cur; 3445 }; 3446 } 3447 function traverse(value, seen) { 3448 if (!isObject(value) || value["__v_skip" /* ReactiveFlags.SKIP */]) { 3449 return value; 3450 } 3451 seen = seen || new Set(); 3452 if (seen.has(value)) { 3453 return value; 3454 } 3455 seen.add(value); 3456 if (isRef(value)) { 3457 traverse(value.value, seen); 3458 } 3459 else if (isArray(value)) { 3460 for (let i = 0; i < value.length; i++) { 3461 traverse(value[i], seen); 3462 } 3463 } 3464 else if (isSet(value) || isMap(value)) { 3465 value.forEach((v) => { 3466 traverse(v, seen); 3467 }); 3468 } 3469 else if (isPlainObject(value)) { 3470 for (const key in value) { 3471 traverse(value[key], seen); 3472 } 3473 } 3474 return value; 3475 } 3476 3477 function useTransitionState() { 3478 const state = { 3479 isMounted: false, 3480 isLeaving: false, 3481 isUnmounting: false, 3482 leavingVNodes: new Map() 3483 }; 3484 onMounted(() => { 3485 state.isMounted = true; 3486 }); 3487 onBeforeUnmount(() => { 3488 state.isUnmounting = true; 3489 }); 3490 return state; 3491 } 3492 const TransitionHookValidator = [Function, Array]; 3493 const BaseTransitionImpl = { 3494 name: `BaseTransition`, 3495 props: { 3496 mode: String, 3497 appear: Boolean, 3498 persisted: Boolean, 3499 // enter 3500 onBeforeEnter: TransitionHookValidator, 3501 onEnter: TransitionHookValidator, 3502 onAfterEnter: TransitionHookValidator, 3503 onEnterCancelled: TransitionHookValidator, 3504 // leave 3505 onBeforeLeave: TransitionHookValidator, 3506 onLeave: TransitionHookValidator, 3507 onAfterLeave: TransitionHookValidator, 3508 onLeaveCancelled: TransitionHookValidator, 3509 // appear 3510 onBeforeAppear: TransitionHookValidator, 3511 onAppear: TransitionHookValidator, 3512 onAfterAppear: TransitionHookValidator, 3513 onAppearCancelled: TransitionHookValidator 3514 }, 3515 setup(props, { slots }) { 3516 const instance = getCurrentInstance(); 3517 const state = useTransitionState(); 3518 let prevTransitionKey; 3519 return () => { 3520 const children = slots.default && getTransitionRawChildren(slots.default(), true); 3521 if (!children || !children.length) { 3522 return; 3523 } 3524 let child = children[0]; 3525 if (children.length > 1) { 3526 let hasFound = false;
3527 // locate first non-comment child 3528 for (const c of children) { 3529 if (c.type !== Comment) { 3530 if (hasFound) { 3531 // warn more than one non-comment child 3532 warn$1('<transition> can only be used on a single element or component. ' + 3533 'Use <transition-group> for lists.'); 3534 break; 3535 } 3536 child = c; 3537 hasFound = true; 3538 } 3539 } 3540 } 3541 // there's no need to track reactivity for these props so use the raw 3542 // props for a bit better perf 3543 const rawProps = toRaw(props); 3544 const { mode } = rawProps; 3545 // check mode 3546 if (mode && 3547 mode !== 'in-out' && 3548 mode !== 'out-in' && 3549 mode !== 'default') { 3550 warn$1(`invalid <transition> mode: ${mode}`); 3551 } 3552 if (state.isLeaving) { 3553 return emptyPlaceholder(child); 3554 } 3555 // in the case of <transition><keep-alive/></transition>, we need to 3556 // compare the type of the kept-alive children. 3557 const innerChild = getKeepAliveChild(child); 3558 if (!innerChild) { 3559 return emptyPlaceholder(child); 3560 } 3561 const enterHooks = resolveTransitionHooks(innerChild, rawProps, state, instance); 3562 setTransitionHooks(innerChild, enterHooks); 3563 const oldChild = instance.subTree; 3564 const oldInnerChild = oldChild && getKeepAliveChild(oldChild); 3565 let transitionKeyChanged = false; 3566 const { getTransitionKey } = innerChild.type; 3567 if (getTransitionKey) { 3568 const key = getTransitionKey(); 3569 if (prevTransitionKey === undefined) { 3570 prevTransitionKey = key; 3571 } 3572 else if (key !== prevTransitionKey) { 3573 prevTransitionKey = key; 3574 transitionKeyChanged = true; 3575 } 3576 } 3577 // handle mode 3578 if (oldInnerChild && 3579 oldInnerChild.type !== Comment && 3580 (!isSameVNodeType(innerChild, oldInnerChild) || transitionKeyChanged)) { 3581 const leavingHooks = resolveTransitionHooks(oldInnerChild, rawProps, state, instance); 3582 // update old tree's hooks in case of dynamic transition 3583 setTransitionHooks(oldInnerChild, leavingHooks); 3584 // switching between different views 3585 if (mode === 'out-in') { 3586 state.isLeaving = true; 3587 // return placeholder node and queue update when leave finishes 3588 leavingHooks.afterLeave = () => { 3589 state.isLeaving = false; 3590 // #6835 3591 // it also needs to be updated when active is undefined 3592 if (instance.update.active !== false) { 3593 instance.update(); 3594 } 3595 }; 3596 return emptyPlaceholder(child); 3597 } 3598 else if (mode === 'in-out' && innerChild.type !== Comment) { 3599 leavingHooks.delayLeave = (el, earlyRemove, delayedLeave) => { 3600 const leavingVNodesCache = getLeavingNodesForType(state, oldInnerChild); 3601 leavingVNodesCache[String(oldInnerChild.key)] = oldInnerChild; 3602 // early removal callback 3603 el._leaveCb = () => { 3604 earlyRemove(); 3605 el._leaveCb = undefined; 3606 delete enterHooks.delayedLeave; 3607 }; 3608 enterHooks.delayedLeave = delayedLeave; 3609 }; 3610 } 3611 } 3612 return child; 3613 }; 3614 } 3615 }; 3616 // export the public type for h/tsx inference 3617 // also to avoid inline import() in generated d.ts files 3618 const BaseTransition = BaseTransitionImpl; 3619 function getLeavingNodesForType(state, vnode) { 3620 const { leavingVNodes } = state;
3621 let leavingVNodesCache = leavingVNodes.get(vnode.type); 3622 if (!leavingVNodesCache) { 3623 leavingVNodesCache = Object.create(null); 3624 leavingVNodes.set(vnode.type, leavingVNodesCache); 3625 } 3626 return leavingVNodesCache; 3627 } 3628 // The transition hooks are attached to the vnode as vnode.transition 3629 // and will be called at appropriate timing in the renderer. 3630 function resolveTransitionHooks(vnode, props, state, instance) { 3631 const { appear, mode, persisted = false, onBeforeEnter, onEnter, onAfterEnter, onEnterCancelled, onBeforeLeave, onLeave, onAfterLeave, onLeaveCancelled, onBeforeAppear, onAppear, onAfterAppear, onAppearCancelled } = props; 3632 const key = String(vnode.key); 3633 const leavingVNodesCache = getLeavingNodesForType(state, vnode); 3634 const callHook = (hook, args) => { 3635 hook && 3636 callWithAsyncErrorHandling(hook, instance, 9 /* ErrorCodes.TRANSITION_HOOK */, args); 3637 }; 3638 const callAsyncHook = (hook, args) => { 3639 const done = args[1]; 3640 callHook(hook, args); 3641 if (isArray(hook)) { 3642 if (hook.every(hook => hook.length <= 1)) 3643 done(); 3644 } 3645 else if (hook.length <= 1) { 3646 done(); 3647 } 3648 }; 3649 const hooks = { 3650 mode, 3651 persisted, 3652 beforeEnter(el) { 3653 let hook = onBeforeEnter; 3654 if (!state.isMounted) { 3655 if (appear) { 3656 hook = onBeforeAppear || onBeforeEnter; 3657 } 3658 else { 3659 return; 3660 } 3661 } 3662 // for same element (v-show) 3663 if (el._leaveCb) { 3664 el._leaveCb(true /* cancelled */); 3665 } 3666 // for toggled element with same key (v-if) 3667 const leavingVNode = leavingVNodesCache[key]; 3668 if (leavingVNode && 3669 isSameVNodeType(vnode, leavingVNode) && 3670 leavingVNode.el._leaveCb) { 3671 // force early removal (not cancelled) 3672 leavingVNode.el._leaveCb(); 3673 } 3674 callHook(hook, [el]); 3675 }, 3676 enter(el) { 3677 let hook = onEnter; 3678 let afterHook = onAfterEnter; 3679 let cancelHook = onEnterCancelled; 3680 if (!state.isMounted) { 3681 if (appear) { 3682 hook = onAppear || onEnter; 3683 afterHook = onAfterAppear || onAfterEnter; 3684 cancelHook = onAppearCancelled || onEnterCancelled; 3685 } 3686 else { 3687 return; 3688 } 3689 } 3690 let called = false; 3691 const done = (el._enterCb = (cancelled) => { 3692 if (called) 3693 return; 3694 called = true; 3695 if (cancelled) { 3696 callHook(cancelHook, [el]); 3697 } 3698 else { 3699 callHook(afterHook, [el]); 3700 } 3701 if (hooks.delayedLeave) { 3702 hooks.delayedLeave(); 3703 } 3704 el._enterCb = undefined; 3705 }); 3706 if (hook) { 3707 callAsyncHook(hook, [el, done]); 3708 } 3709 else { 3710 done(); 3711 } 3712 }, 3713 leave(el, remove) { 3714 const key = String(vnode.key); 3715 if (el._enterCb) { 3716 el._enterCb(true /* cancelled */); 3717 } 3718 if (state.isUnmounting) { 3719 return remove(); 3720 } 3721 callHook(onBeforeLeave, [el]); 3722 let called = false; 3723 const done = (el._leaveCb = (cancelled) => { 3724 if (called) 3725 return; 3726 called = true; 3727 remove(); 3728 if (cancelled) { 3729 callHook(onLeaveCancelled, [el]); 3730 } 3731 else { 3732 callHook(onAfterLeave, [el]); 3733 } 3734 el._leaveCb = undefined; 3735 if (leavingVNodesCache[key] === vnode) { 3736 delete leavingVNodesCache[key]; 3737 } 3738 }); 3739 leavingVNodesCache[key] = vnode; 3740 if (onLeave) { 3741 callAsyncHook(onLeave, [el, done]); 3742 } 3743 else { 3744 done(); 3745 } 3746 }, 3747 clone(vnode) { 3748 return resolveTransitionHooks(vnode, props, state, instance); 3749 } 3750 }; 3751 return hooks; 3752 } 3753 // the placeholder really only handles one special case: KeepAlive 3754 // in the case of a KeepAlive in a leave phase we need to return a KeepAlive 3755 // placeholder with empty content to avoid the KeepAlive instance from being 3756 // unmounted. 3757 function emptyPlaceholder(vnode) { 3758 if (isKeepAlive(vnode)) { 3759 vnode = cloneVNode(vnode); 3760 vnode.children = null; 3761 return vnode; 3762 } 3763 } 3764 function getKeepAliveChild(vnode) { 3765 return isKeepAlive(vnode) 3766 ? vnode.children 3767 ? vnode.children[0] 3768 : undefined 3769 : vnode; 3770 } 3771 function setTransitionHooks(vnode, hooks) {
3772 if (vnode.shapeFlag & 6 /* ShapeFlags.COMPONENT */ && vnode.component) { 3773 setTransitionHooks(vnode.component.subTree, hooks); 3774 } 3775 else if (vnode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 3776 vnode.ssContent.transition = hooks.clone(vnode.ssContent); 3777 vnode.ssFallback.transition = hooks.clone(vnode.ssFallback); 3778 } 3779 else { 3780 vnode.transition = hooks; 3781 } 3782 } 3783 function getTransitionRawChildren(children, keepComment = false, parentKey) { 3784 let ret = []; 3785 let keyedFragmentCount = 0; 3786 for (let i = 0; i < children.length; i++) { 3787 let child = children[i]; 3788 // #5360 inherit parent key in case of <template v-for> 3789 const key = parentKey == null 3790 ? child.key 3791 : String(parentKey) + String(child.key != null ? child.key : i); 3792 // handle fragment children case, e.g. v-for 3793 if (child.type === Fragment) { 3794 if (child.patchFlag & 128 /* PatchFlags.KEYED_FRAGMENT */) 3795 keyedFragmentCount++; 3796 ret = ret.concat(getTransitionRawChildren(child.children, keepComment, key)); 3797 } 3798 // comment placeholders should be skipped, e.g. v-if 3799 else if (keepComment || child.type !== Comment) { 3800 ret.push(key != null ? cloneVNode(child, { key }) : child); 3801 } 3802 } 3803 // #1126 if a transition children list contains multiple sub fragments, these 3804 // fragments will be merged into a flat children array. Since each v-for 3805 // fragment may contain different static bindings inside, we need to de-op 3806 // these children to force full diffs to ensure correct behavior. 3807 if (keyedFragmentCount > 1) { 3808 for (let i = 0; i < ret.length; i++) { 3809 ret[i].patchFlag = -2 /* PatchFlags.BAIL */; 3810 } 3811 } 3812 return ret; 3813 } 3814 3815 // implementation, close to no-op 3816 function defineComponent(options) { 3817 return isFunction(options) ? { setup: options, name: options.name } : options; 3818 } 3819 3820 const isAsyncWrapper = (i) => !!i.type.__asyncLoader; 3821 function defineAsyncComponent(source) { 3822 if (isFunction(source)) { 3823 source = { loader: source }; 3824 } 3825 const { loader, loadingComponent, errorComponent, delay = 200, timeout, // undefined = never times out 3826 suspensible = true, onError: userOnError } = source; 3827 let pendingRequest = null; 3828 let resolvedComp; 3829 let retries = 0; 3830 const retry = () => { 3831 retries++; 3832 pendingRequest = null; 3833 return load(); 3834 }; 3835 const load = () => { 3836 let thisRequest; 3837 return (pendingRequest || 3838 (thisRequest = pendingRequest = 3839 loader() 3840 .catch(err => { 3841 err = err instanceof Error ? err : new Error(String(err)); 3842 if (userOnError) { 3843 return new Promise((resolve, reject) => { 3844 const userRetry = () => resolve(retry()); 3845 const userFail = () => reject(err); 3846 userOnError(err, userRetry, userFail, retries + 1); 3847 }); 3848 } 3849 else { 3850 throw err; 3851 } 3852 }) 3853 .then((comp) => { 3854 if (thisRequest !== pendingRequest && pendingRequest) { 3855 return pendingRequest; 3856 } 3857 if (!comp) { 3858 warn$1(`Async component loader resolved to undefined. ` + 3859 `If you are using retry(), make sure to return its return value.`); 3860 } 3861 // interop module default 3862 if (comp && 3863 (comp.__esModule || comp[Symbol.toStringTag] === 'Module')) { 3864 comp = comp.default; 3865 } 3866 if (comp && !isObject(comp) && !isFunction(comp)) { 3867 throw new Error(`Invalid async component load result: ${comp}`); 3868 } 3869 resolvedComp = comp; 3870 return comp; 3871 }))); 3872 }; 3873 return defineComponent({ 3874 name: 'AsyncComponentWrapper', 3875 __asyncLoader: load, 3876 get __asyncResolved() { 3877 return resolvedComp; 3878 }, 3879 setup() { 3880 const instance = currentInstance; 3881 // already resolved 3882 if (resolvedComp) { 3883 return () => createInnerComp(resolvedComp, instance); 3884 } 3885 const onError = (err) => { 3886 pendingRequest = null; 3887 handleError(err, instance, 13 /* ErrorCodes.ASYNC_COMPONENT_LOADER */, !errorComponent /* do not throw in dev if user provided error component */); 3888 }; 3889 // suspense-controlled or SSR. 3890 if ((suspensible && instance.suspense) || 3891 (false )) { 3892 return load() 3893 .then(comp => { 3894 return () => createInnerComp(comp, instance); 3895 }) 3896 .catch(err => { 3897 onError(err); 3898 return () => errorComponent 3899 ? createVNode(errorComponent, { 3900 error: err 3901 }) 3902 : null; 3903 }); 3904 } 3905 const loaded = ref(false); 3906 const error = ref(); 3907 const delayed = ref(!!delay); 3908 if (delay) { 3909 setTimeout(() => { 3910 delayed.value = false;
vendor: 5,627 bytes, lines 3911-4043
3911 }, delay); 3912 } 3913 if (timeout != null) { 3914 setTimeout(() => { 3915 if (!loaded.value && !error.value) { 3916 const err = new Error(`Async component timed out after ${timeout}ms.`); 3917 onError(err); 3918 error.value = err; 3919 } 3920 }, timeout); 3921 } 3922 load() 3923 .then(() => { 3924 loaded.value = true; 3925 if (instance.parent && isKeepAlive(instance.parent.vnode)) { 3926 // parent is keep-alive, force update so the loaded component's 3927 // name is taken into account 3928 queueJob(instance.parent.update); 3929 } 3930 }) 3931 .catch(err => { 3932 onError(err); 3933 error.value = err; 3934 }); 3935 return () => { 3936 if (loaded.value && resolvedComp) { 3937 return createInnerComp(resolvedComp, instance); 3938 } 3939 else if (error.value && errorComponent) { 3940 return createVNode(errorComponent, { 3941 error: error.value 3942 }); 3943 } 3944 else if (loadingComponent && !delayed.value) { 3945 return createVNode(loadingComponent); 3946 } 3947 }; 3948 } 3949 }); 3950 } 3951 function createInnerComp(comp, parent) { 3952 const { ref, props, children, ce } = parent.vnode; 3953 const vnode = createVNode(comp, props, children); 3954 // ensure inner component inherits the async wrapper's ref owner 3955 vnode.ref = ref; 3956 // pass the custom element callback on to the inner comp 3957 // and remove it from the async wrapper 3958 vnode.ce = ce; 3959 delete parent.vnode.ce; 3960 return vnode; 3961 } 3962 3963 const isKeepAlive = (vnode) => vnode.type.__isKeepAlive; 3964 const KeepAliveImpl = { 3965 name: `KeepAlive`, 3966 // Marker for special handling inside the renderer. We are not using a === 3967 // check directly on KeepAlive in the renderer, because importing it directly 3968 // would prevent it from being tree-shaken. 3969 __isKeepAlive: true, 3970 props: { 3971 include: [String, RegExp, Array], 3972 exclude: [String, RegExp, Array], 3973 max: [String, Number] 3974 }, 3975 setup(props, { slots }) { 3976 const instance = getCurrentInstance(); 3977 // KeepAlive communicates with the instantiated renderer via the 3978 // ctx where the renderer passes in its internals, 3979 // and the KeepAlive instance exposes activate/deactivate implementations. 3980 // The whole point of this is to avoid importing KeepAlive directly in the 3981 // renderer to facilitate tree-shaking. 3982 const sharedContext = instance.ctx; 3983 const cache = new Map(); 3984 const keys = new Set(); 3985 let current = null; 3986 { 3987 instance.__v_cache = cache; 3988 } 3989 const parentSuspense = instance.suspense; 3990 const { renderer: { p: patch, m: move, um: _unmount, o: { createElement } } } = sharedContext; 3991 const storageContainer = createElement('div'); 3992 sharedContext.activate = (vnode, container, anchor, isSVG, optimized) => { 3993 const instance = vnode.component; 3994 move(vnode, container, anchor, 0 /* MoveType.ENTER */, parentSuspense); 3995 // in case props have changed 3996 patch(instance.vnode, vnode, container, anchor, instance, parentSuspense, isSVG, vnode.slotScopeIds, optimized); 3997 queuePostRenderEffect(() => { 3998 instance.isDeactivated = false; 3999 if (instance.a) { 4000 invokeArrayFns(instance.a); 4001 } 4002 const vnodeHook = vnode.props && vnode.props.onVnodeMounted; 4003 if (vnodeHook) { 4004 invokeVNodeHook(vnodeHook, instance.parent, vnode); 4005 } 4006 }, parentSuspense); 4007 { 4008 // Update components tree 4009 devtoolsComponentAdded(instance); 4010 } 4011 }; 4012 sharedContext.deactivate = (vnode) => { 4013 const instance = vnode.component; 4014 move(vnode, storageContainer, null, 1 /* MoveType.LEAVE */, parentSuspense); 4015 queuePostRenderEffect(() => { 4016 if (instance.da) { 4017 invokeArrayFns(instance.da); 4018 } 4019 const vnodeHook = vnode.props && vnode.props.onVnodeUnmounted; 4020 if (vnodeHook) { 4021 invokeVNodeHook(vnodeHook, instance.parent, vnode); 4022 } 4023 instance.isDeactivated = true; 4024 }, parentSuspense); 4025 { 4026 // Update components tree 4027 devtoolsComponentAdded(instance); 4028 } 4029 }; 4030 function unmount(vnode) { 4031 // reset the shapeFlag so it can be properly unmounted 4032 resetShapeFlag(vnode); 4033 _unmount(vnode, instance, parentSuspense, true); 4034 } 4035 function pruneCache(filter) { 4036 cache.forEach((vnode, key) => { 4037 const name = getComponentName(vnode.type); 4038 if (name && (!filter || !filter(name))) { 4039 pruneCacheEntry(key); 4040 } 4041 }); 4042 } 4043 function pruneCacheEntry(key) {
4044 const cached = cache.get(key); 4045 if (!current || cached.type !== current.type) { 4046 unmount(cached); 4047 } 4048 else if (current) { 4049 // current active instance should no longer be kept-alive. 4050 // we can't unmount it now but it might be later, so reset its flag now. 4051 resetShapeFlag(current); 4052 } 4053 cache.delete(key); 4054 keys.delete(key); 4055 } 4056 // prune cache on include/exclude prop change 4057 watch(() => [props.include, props.exclude], ([include, exclude]) => { 4058 include && pruneCache(name => matches(include, name)); 4059 exclude && pruneCache(name => !matches(exclude, name)); 4060 }, 4061 // prune post-render after `current` has been updated 4062 { flush: 'post', deep: true }); 4063 // cache sub tree after render 4064 let pendingCacheKey = null; 4065 const cacheSubtree = () => { 4066 // fix #1621, the pendingCacheKey could be 0 4067 if (pendingCacheKey != null) { 4068 cache.set(pendingCacheKey, getInnerChild(instance.subTree)); 4069 } 4070 }; 4071 onMounted(cacheSubtree); 4072 onUpdated(cacheSubtree); 4073 onBeforeUnmount(() => { 4074 cache.forEach(cached => { 4075 const { subTree, suspense } = instance; 4076 const vnode = getInnerChild(subTree); 4077 if (cached.type === vnode.type) { 4078 // current instance will be unmounted as part of keep-alive's unmount 4079 resetShapeFlag(vnode); 4080 // but invoke its deactivated hook here 4081 const da = vnode.component.da; 4082 da && queuePostRenderEffect(da, suspense); 4083 return; 4084 } 4085 unmount(cached); 4086 }); 4087 }); 4088 return () => { 4089 pendingCacheKey = null; 4090 if (!slots.default) { 4091 return null; 4092 } 4093 const children = slots.default(); 4094 const rawVNode = children[0]; 4095 if (children.length > 1) { 4096 { 4097 warn$1(`KeepAlive should contain exactly one component child.`); 4098 } 4099 current = null; 4100 return children; 4101 } 4102 else if (!isVNode(rawVNode) || 4103 (!(rawVNode.shapeFlag & 4 /* ShapeFlags.STATEFUL_COMPONENT */) && 4104 !(rawVNode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */))) { 4105 current = null; 4106 return rawVNode; 4107 } 4108 let vnode = getInnerChild(rawVNode); 4109 const comp = vnode.type; 4110 // for async components, name check should be based in its loaded 4111 // inner component if available 4112 const name = getComponentName(isAsyncWrapper(vnode) 4113 ? vnode.type.__asyncResolved || {} 4114 : comp); 4115 const { include, exclude, max } = props; 4116 if ((include && (!name || !matches(include, name))) || 4117 (exclude && name && matches(exclude, name))) { 4118 current = vnode; 4119 return rawVNode; 4120 } 4121 const key = vnode.key == null ? comp : vnode.key; 4122 const cachedVNode = cache.get(key); 4123 // clone vnode if it's reused because we are going to mutate it 4124 if (vnode.el) { 4125 vnode = cloneVNode(vnode); 4126 if (rawVNode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 4127 rawVNode.ssContent = vnode; 4128 } 4129 } 4130 // #1513 it's possible for the returned vnode to be cloned due to attr 4131 // fallthrough or scopeId, so the vnode here may not be the final vnode 4132 // that is mounted. Instead of caching it directly, we store the pending 4133 // key and cache `instance.subTree` (the normalized vnode) in 4134 // beforeMount/beforeUpdate hooks. 4135 pendingCacheKey = key; 4136 if (cachedVNode) { 4137 // copy over mounted state 4138 vnode.el = cachedVNode.el; 4139 vnode.component = cachedVNode.component; 4140 if (vnode.transition) { 4141 // recursively update transition hooks on subTree 4142 setTransitionHooks(vnode, vnode.transition); 4143 } 4144 // avoid vnode being mounted as fresh
vendor: 4,606 bytes, lines 4145-4252
4145 vnode.shapeFlag |= 512 /* ShapeFlags.COMPONENT_KEPT_ALIVE */; 4146 // make this key the freshest 4147 keys.delete(key); 4148 keys.add(key); 4149 } 4150 else { 4151 keys.add(key); 4152 // prune oldest entry 4153 if (max && keys.size > parseInt(max, 10)) { 4154 pruneCacheEntry(keys.values().next().value); 4155 } 4156 } 4157 // avoid vnode being unmounted 4158 vnode.shapeFlag |= 256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */; 4159 current = vnode; 4160 return isSuspense(rawVNode.type) ? rawVNode : vnode; 4161 }; 4162 } 4163 }; 4164 // export the public type for h/tsx inference 4165 // also to avoid inline import() in generated d.ts files 4166 const KeepAlive = KeepAliveImpl; 4167 function matches(pattern, name) { 4168 if (isArray(pattern)) { 4169 return pattern.some((p) => matches(p, name)); 4170 } 4171 else if (isString(pattern)) { 4172 return pattern.split(',').includes(name); 4173 } 4174 else if (pattern.test) { 4175 return pattern.test(name); 4176 } 4177 /* istanbul ignore next */ 4178 return false; 4179 } 4180 function onActivated(hook, target) { 4181 registerKeepAliveHook(hook, "a" /* LifecycleHooks.ACTIVATED */, target); 4182 } 4183 function onDeactivated(hook, target) { 4184 registerKeepAliveHook(hook, "da" /* LifecycleHooks.DEACTIVATED */, target); 4185 } 4186 function registerKeepAliveHook(hook, type, target = currentInstance) { 4187 // cache the deactivate branch check wrapper for injected hooks so the same 4188 // hook can be properly deduped by the scheduler. "__wdc" stands for "with 4189 // deactivation check". 4190 const wrappedHook = hook.__wdc || 4191 (hook.__wdc = () => { 4192 // only fire the hook if the target instance is NOT in a deactivated branch. 4193 let current = target; 4194 while (current) { 4195 if (current.isDeactivated) { 4196 return; 4197 } 4198 current = current.parent; 4199 } 4200 return hook(); 4201 }); 4202 injectHook(type, wrappedHook, target); 4203 // In addition to registering it on the target instance, we walk up the parent 4204 // chain and register it on all ancestor instances that are keep-alive roots. 4205 // This avoids the need to walk the entire component tree when invoking these 4206 // hooks, and more importantly, avoids the need to track child components in 4207 // arrays. 4208 if (target) { 4209 let current = target.parent; 4210 while (current && current.parent) { 4211 if (isKeepAlive(current.parent.vnode)) { 4212 injectToKeepAliveRoot(wrappedHook, type, target, current); 4213 } 4214 current = current.parent; 4215 } 4216 } 4217 } 4218 function injectToKeepAliveRoot(hook, type, target, keepAliveRoot) { 4219 // injectHook wraps the original for error handling, so make sure to remove 4220 // the wrapped version. 4221 const injected = injectHook(type, hook, keepAliveRoot, true /* prepend */); 4222 onUnmounted(() => { 4223 remove(keepAliveRoot[type], injected); 4224 }, target); 4225 } 4226 function resetShapeFlag(vnode) { 4227 // bitwise operations to remove keep alive flags 4228 vnode.shapeFlag &= ~256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */; 4229 vnode.shapeFlag &= ~512 /* ShapeFlags.COMPONENT_KEPT_ALIVE */; 4230 } 4231 function getInnerChild(vnode) { 4232 return vnode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */ ? vnode.ssContent : vnode; 4233 } 4234 4235 function injectHook(type, hook, target = currentInstance, prepend = false) { 4236 if (target) { 4237 const hooks = target[type] || (target[type] = []); 4238 // cache the error handling wrapper for injected hooks so the same hook 4239 // can be properly deduped by the scheduler. "__weh" stands for "with error 4240 // handling". 4241 const wrappedHook = hook.__weh || 4242 (hook.__weh = (...args) => { 4243 if (target.isUnmounted) { 4244 return; 4245 } 4246 // disable tracking inside all lifecycle hooks 4247 // since they can potentially be called inside effects. 4248 pauseTracking(); 4249 // Set currentInstance during hook invocation. 4250 // This assumes the hook does not synchronously trigger other hooks, which 4251 // can only be false when the user does something really funky. 4252 setCurrentInstance(target);
4253 const res = callWithAsyncErrorHandling(hook, target, type, args); 4254 unsetCurrentInstance(); 4255 resetTracking(); 4256 return res; 4257 }); 4258 if (prepend) { 4259 hooks.unshift(wrappedHook); 4260 } 4261 else { 4262 hooks.push(wrappedHook); 4263 } 4264 return wrappedHook; 4265 } 4266 else { 4267 const apiName = toHandlerKey(ErrorTypeStrings[type].replace(/ hook$/, '')); 4268 warn$1(`${apiName} is called when there is no active component instance to be ` + 4269 `associated with. ` + 4270 `Lifecycle injection APIs can only be used during execution of setup().` + 4271 (` If you are using async setup(), make sure to register lifecycle ` + 4272 `hooks before the first await statement.` 4273 )); 4274 } 4275 } 4276 const createHook = (lifecycle) => (hook, target = currentInstance) => 4277 // post-create lifecycle registrations are noops during SSR (except for serverPrefetch) 4278 (!isInSSRComponentSetup || lifecycle === "sp" /* LifecycleHooks.SERVER_PREFETCH */) && 4279 injectHook(lifecycle, (...args) => hook(...args), target); 4280 const onBeforeMount = createHook("bm" /* LifecycleHooks.BEFORE_MOUNT */); 4281 const onMounted = createHook("m" /* LifecycleHooks.MOUNTED */); 4282 const onBeforeUpdate = createHook("bu" /* LifecycleHooks.BEFORE_UPDATE */); 4283 const onUpdated = createHook("u" /* LifecycleHooks.UPDATED */); 4284 const onBeforeUnmount = createHook("bum" /* LifecycleHooks.BEFORE_UNMOUNT */); 4285 const onUnmounted = createHook("um" /* LifecycleHooks.UNMOUNTED */); 4286 const onServerPrefetch = createHook("sp" /* LifecycleHooks.SERVER_PREFETCH */); 4287 const onRenderTriggered = createHook("rtg" /* LifecycleHooks.RENDER_TRIGGERED */); 4288 const onRenderTracked = createHook("rtc" /* LifecycleHooks.RENDER_TRACKED */); 4289 function onErrorCaptured(hook, target = currentInstance) { 4290 injectHook("ec" /* LifecycleHooks.ERROR_CAPTURED */, hook, target); 4291 } 4292 4293 /** 4294 Runtime helper for applying directives to a vnode. Example usage: 4295 4296 const comp = resolveComponent('comp') 4297 const foo = resolveDirective('foo') 4298 const bar = resolveDirective('bar') 4299 4300 return withDirectives(h(comp), [ 4301 [foo, this.x], 4302 [bar, this.y] 4303 ]) 4304 */ 4305 function validateDirectiveName(name) { 4306 if (isBuiltInDirective(name)) { 4307 warn$1('Do not use built-in directive ids as custom directive id: ' + name); 4308 } 4309 } 4310 /** 4311 * Adds directives to a VNode. 4312 */ 4313 function withDirectives(vnode, directives) { 4314 const internalInstance = currentRenderingInstance; 4315 if (internalInstance === null) { 4316 warn$1(`withDirectives can only be used inside render functions.`); 4317 return vnode; 4318 } 4319 const instance = getExposeProxy(internalInstance) || 4320 internalInstance.proxy; 4321 const bindings = vnode.dirs || (vnode.dirs = []); 4322 for (let i = 0; i < directives.length; i++) { 4323 let [dir, value, arg, modifiers = EMPTY_OBJ] = directives[i]; 4324 if (dir) { 4325 if (isFunction(dir)) { 4326 dir = { 4327 mounted: dir, 4328 updated: dir 4329 }; 4330 } 4331 if (dir.deep) { 4332 traverse(value); 4333 } 4334 bindings.push({ 4335 dir, 4336 instance, 4337 value, 4338 oldValue: void 0, 4339 arg, 4340 modifiers 4341 }); 4342 } 4343 } 4344 return vnode; 4345 } 4346 function invokeDirectiveHook(vnode, prevVNode, instance, name) { 4347 const bindings = vnode.dirs; 4348 const oldBindings = prevVNode && prevVNode.dirs; 4349 for (let i = 0; i < bindings.length; i++) { 4350 const binding = bindings[i]; 4351 if (oldBindings) { 4352 binding.oldValue = oldBindings[i].value; 4353 } 4354 let hook = binding.dir[name]; 4355 if (hook) { 4356 // disable tracking inside all lifecycle hooks 4357 // since they can potentially be called inside effects. 4358 pauseTracking();
4359 callWithAsyncErrorHandling(hook, instance, 8 /* ErrorCodes.DIRECTIVE_HOOK */, [ 4360 vnode.el, 4361 binding, 4362 vnode, 4363 prevVNode 4364 ]); 4365 resetTracking(); 4366 } 4367 } 4368 } 4369 4370 const COMPONENTS = 'components'; 4371 const DIRECTIVES = 'directives'; 4372 /** 4373 * @private 4374 */ 4375 function resolveComponent(name, maybeSelfReference) { 4376 return resolveAsset(COMPONENTS, name, true, maybeSelfReference) || name; 4377 } 4378 const NULL_DYNAMIC_COMPONENT = Symbol(); 4379 /** 4380 * @private 4381 */ 4382 function resolveDynamicComponent(component) { 4383 if (isString(component)) { 4384 return resolveAsset(COMPONENTS, component, false) || component; 4385 } 4386 else { 4387 // invalid types will fallthrough to createVNode and raise warning 4388 return (component || NULL_DYNAMIC_COMPONENT); 4389 } 4390 } 4391 /** 4392 * @private 4393 */ 4394 function resolveDirective(name) { 4395 return resolveAsset(DIRECTIVES, name); 4396 } 4397 // implementation 4398 function resolveAsset(type, name, warnMissing = true, maybeSelfReference = false) { 4399 const instance = currentRenderingInstance || currentInstance; 4400 if (instance) { 4401 const Component = instance.type; 4402 // explicit self name has highest priority 4403 if (type === COMPONENTS) { 4404 const selfName = getComponentName(Component, false /* do not include inferred name to avoid breaking existing code */); 4405 if (selfName && 4406 (selfName === name || 4407 selfName === camelize(name) || 4408 selfName === capitalize(camelize(name)))) { 4409 return Component; 4410 } 4411 } 4412 const res = 4413 // local registration 4414 // check instance[type] first which is resolved for options API 4415 resolve(instance[type] || Component[type], name) || 4416 // global registration 4417 resolve(instance.appContext[type], name); 4418 if (!res && maybeSelfReference) { 4419 // fallback to implicit self-reference 4420 return Component; 4421 } 4422 if (warnMissing && !res) { 4423 const extra = type === COMPONENTS 4424 ? `\nIf this is a native custom element, make sure to exclude it from ` + 4425 `component resolution via compilerOptions.isCustomElement.` 4426 : ``; 4427 warn$1(`Failed to resolve ${type.slice(0, -1)}: ${name}${extra}`); 4428 } 4429 return res; 4430 } 4431 else { 4432 warn$1(`resolve${capitalize(type.slice(0, -1))} ` + 4433 `can only be used in render() or setup().`); 4434 } 4435 } 4436 function resolve(registry, name) { 4437 return (registry && 4438 (registry[name] || 4439 registry[camelize(name)] || 4440 registry[capitalize(camelize(name))])); 4441 } 4442 4443 /** 4444 * Actual implementation 4445 */ 4446 function renderList(source, renderItem, cache, index) { 4447 let ret; 4448 const cached = (cache && cache[index]); 4449 if (isArray(source) || isString(source)) { 4450 ret = new Array(source.length); 4451 for (let i = 0, l = source.length; i < l; i++) { 4452 ret[i] = renderItem(source[i], i, undefined, cached && cached[i]); 4453 } 4454 } 4455 else if (typeof source === 'number') { 4456 if (!Number.isInteger(source)) { 4457 warn$1(`The v-for range expect an integer value but got ${source}.`); 4458 } 4459 ret = new Array(source); 4460 for (let i = 0; i < source; i++) { 4461 ret[i] = renderItem(i + 1, i, undefined, cached && cached[i]); 4462 } 4463 } 4464 else if (isObject(source)) { 4465 if (source[Symbol.iterator]) { 4466 ret = Array.from(source, (item, i) => renderItem(item, i, undefined, cached && cached[i])); 4467 } 4468 else { 4469 const keys = Object.keys(source); 4470 ret = new Array(keys.length); 4471 for (let i = 0, l = keys.length; i < l; i++) { 4472 const key = keys[i]; 4473 ret[i] = renderItem(source[key], key, i, cached && cached[i]); 4474 } 4475 } 4476 } 4477 else { 4478 ret = []; 4479 } 4480 if (cache) { 4481 cache[index] = ret; 4482 } 4483 return ret; 4484 } 4485 4486 /** 4487 * Compiler runtime helper for creating dynamic slots object 4488 * @private 4489 */ 4490 function createSlots(slots, dynamicSlots) { 4491 for (let i = 0; i < dynamicSlots.length; i++) { 4492 const slot = dynamicSlots[i]; 4493 // array of dynamic slot generated by <template v-for="..." #[...]> 4494 if (isArray(slot)) { 4495 for (let j = 0; j < slot.length; j++) { 4496 slots[slot[j].name] = slot[j].fn; 4497 } 4498 } 4499 else if (slot) { 4500 // conditional single slot generated by <template v-if="..." #foo> 4501 slots[slot.name] = slot.key 4502 ? (...args) => { 4503 const res = slot.fn(...args); 4504 // attach branch key so each conditional branch is considered a 4505 // different fragment 4506 if (res) 4507 res.key = slot.key; 4508 return res; 4509 } 4510 : slot.fn; 4511 } 4512 } 4513 return slots; 4514 } 4515 4516 /** 4517 * Compiler runtime helper for rendering `<slot/>` 4518 * @private 4519 */
4520 function renderSlot(slots, name, props = {}, 4521 // this is not a user-facing function, so the fallback is always generated by 4522 // the compiler and guaranteed to be a function returning an array 4523 fallback, noSlotted) { 4524 if (currentRenderingInstance.isCE || 4525 (currentRenderingInstance.parent && 4526 isAsyncWrapper(currentRenderingInstance.parent) && 4527 currentRenderingInstance.parent.isCE)) { 4528 if (name !== 'default') 4529 props.name = name; 4530 return createVNode('slot', props, fallback && fallback()); 4531 } 4532 let slot = slots[name]; 4533 if (slot && slot.length > 1) { 4534 warn$1(`SSR-optimized slot function detected in a non-SSR-optimized render ` + 4535 `function. You need to mark this component with $dynamic-slots in the ` + 4536 `parent template.`); 4537 slot = () => []; 4538 } 4539 // a compiled slot disables block tracking by default to avoid manual 4540 // invocation interfering with template-based block tracking, but in 4541 // `renderSlot` we can be sure that it's template-based so we can force 4542 // enable it. 4543 if (slot && slot._c) { 4544 slot._d = false; 4545 } 4546 openBlock(); 4547 const validSlotContent = slot && ensureValidVNode(slot(props)); 4548 const rendered = createBlock(Fragment, { 4549 key: props.key || 4550 // slot content array of a dynamic conditional slot may have a branch 4551 // key attached in the `createSlots` helper, respect that 4552 (validSlotContent && validSlotContent.key) || 4553 `_${name}` 4554 }, validSlotContent || (fallback ? fallback() : []), validSlotContent && slots._ === 1 /* SlotFlags.STABLE */ 4555 ? 64 /* PatchFlags.STABLE_FRAGMENT */ 4556 : -2 /* PatchFlags.BAIL */); 4557 if (!noSlotted && rendered.scopeId) { 4558 rendered.slotScopeIds = [rendered.scopeId + '-s']; 4559 } 4560 if (slot && slot._c) { 4561 slot._d = true; 4562 } 4563 return rendered; 4564 } 4565 function ensureValidVNode(vnodes) { 4566 return vnodes.some(child => { 4567 if (!isVNode(child)) 4568 return true; 4569 if (child.type === Comment) 4570 return false; 4571 if (child.type === Fragment && 4572 !ensureValidVNode(child.children)) 4573 return false; 4574 return true; 4575 }) 4576 ? vnodes 4577 : null; 4578 } 4579 4580 /** 4581 * For prefixing keys in v-on="obj" with "on" 4582 * @private 4583 */ 4584 function toHandlers(obj, preserveCaseIfNecessary) { 4585 const ret = {}; 4586 if (!isObject(obj)) { 4587 warn$1(`v-on with no argument expects an object value.`); 4588 return ret; 4589 } 4590 for (const key in obj) { 4591 ret[preserveCaseIfNecessary && /[A-Z]/.test(key) 4592 ? `on:${key}` 4593 : toHandlerKey(key)] = obj[key]; 4594 } 4595 return ret; 4596 } 4597 4598 /** 4599 * #2437 In Vue 3, functional components do not have a public instance proxy but 4600 * they exist in the internal parent chain. For code that relies on traversing 4601 * public $parent chains, skip functional ones and go to the parent instead. 4602 */ 4603 const getPublicInstance = (i) => { 4604 if (!i) 4605 return null; 4606 if (isStatefulComponent(i)) 4607 return getExposeProxy(i) || i.proxy; 4608 return getPublicInstance(i.parent); 4609 }; 4610 const publicPropertiesMap = 4611 // Move PURE marker to new line to workaround compiler discarding it 4612 // due to type annotation 4613 /*#__PURE__*/ extend(Object.create(null), { 4614 $: i => i, 4615 $el: i => i.vnode.el, 4616 $data: i => i.data, 4617 $props: i => (shallowReadonly(i.props) ), 4618 $attrs: i => (shallowReadonly(i.attrs) ), 4619 $slots: i => (shallowReadonly(i.slots) ), 4620 $refs: i => (shallowReadonly(i.refs) ), 4621 $parent: i => getPublicInstance(i.parent), 4622 $root: i => getPublicInstance(i.root), 4623 $emit: i => i.emit, 4624 $options: i => (resolveMergedOptions(i) ), 4625 $forceUpdate: i => i.f || (i.f = () => queueJob(i.update)), 4626 $nextTick: i => i.n || (i.n = nextTick.bind(i.proxy)), 4627 $watch: i => (instanceWatch.bind(i) ) 4628 }); 4629 const isReservedPrefix = (key) => key === '_' || key === '$'; 4630 const hasSetupBinding = (state, key) => state !== EMPTY_OBJ && !state.__isScriptSetup && hasOwn(state, key); 4631 const PublicInstanceProxyHandlers = { 4632 get({ _: instance }, key) { 4633 const { ctx, setupState, data, props, accessCache, type, appContext } = instance; 4634 // for internal formatters to know that this is a Vue instance 4635 if (key === '__isVue') { 4636 return true; 4637 } 4638 // data / props / ctx 4639 // This getter gets called for every property access on the render context 4640 // during render and is a major hotspot. The most expensive part of this 4641 // is the multiple hasOwn() calls. It's much faster to do a simple property 4642 // access on a plain object, so we use an accessCache object (with null 4643 // prototype) to memoize what access type a key corresponds to. 4644 let normalizedProps; 4645 if (key[0] !== '$') { 4646 const n = accessCache[key]; 4647 if (n !== undefined) { 4648 switch (n) { 4649 case 1 /* AccessTypes.SETUP */: 4650 return setupState[key]; 4651 case 2 /* AccessTypes.DATA */: 4652 return data[key]; 4653 case 4 /* AccessTypes.CONTEXT */: 4654 return ctx[key]; 4655 case 3 /* AccessTypes.PROPS */: 4656 return props[key]; 4657 // default: just fallthrough 4658 } 4659 } 4660 else if (hasSetupBinding(setupState, key)) { 4661 accessCache[key] = 1 /* AccessTypes.SETUP */; 4662 return setupState[key]; 4663 } 4664 else if (data !== EMPTY_OBJ && hasOwn(data, key)) { 4665 accessCache[key] = 2 /* AccessTypes.DATA */; 4666 return data[key]; 4667 } 4668 else if ( 4669 // only cache other properties when instance has declared (thus stable) 4670 // props 4671 (normalizedProps = instance.propsOptions[0]) && 4672 hasOwn(normalizedProps, key)) { 4673 accessCache[key] = 3 /* AccessTypes.PROPS */; 4674 return props[key]; 4675 } 4676 else if (ctx !== EMPTY_OBJ && hasOwn(ctx, key)) { 4677 accessCache[key] = 4 /* AccessTypes.CONTEXT */; 4678 return ctx[key]; 4679 } 4680 else if (shouldCacheAccess) { 4681 accessCache[key] = 0 /* AccessTypes.OTHER */; 4682 } 4683 } 4684 const publicGetter = publicPropertiesMap[key]; 4685 let cssModule, globalProperties; 4686 // public $xxx properties 4687 if (publicGetter) { 4688 if (key === '$attrs') { 4689 track(instance, "get" /* TrackOpTypes.GET */, key); 4690 markAttrsAccessed(); 4691 } 4692 return publicGetter(instance); 4693 } 4694 else if ( 4695 // css module (injected by vue-loader) 4696 (cssModule = type.__cssModules) && 4697 (cssModule = cssModule[key])) { 4698 return cssModule; 4699 } 4700 else if (ctx !== EMPTY_OBJ && hasOwn(ctx, key)) { 4701 // user may set custom properties to `this` that start with `$` 4702 accessCache[key] = 4 /* AccessTypes.CONTEXT */; 4703 return ctx[key]; 4704 } 4705 else if ( 4706 // global properties 4707 ((globalProperties = appContext.config.globalProperties), 4708 hasOwn(globalProperties, key))) { 4709 { 4710 return globalProperties[key]; 4711 } 4712 } 4713 else if (currentRenderingInstance && 4714 (!isString(key) || 4715 // #1091 avoid internal isRef/isVNode checks on component instance leading 4716 // to infinite warning loop 4717 key.indexOf('__v') !== 0)) { 4718 if (data !== EMPTY_OBJ && isReservedPrefix(key[0]) && hasOwn(data, key)) { 4719 warn$1(`Property ${JSON.stringify(key)} must be accessed via $data because it starts with a reserved ` + 4720 `character ("$" or "_") and is not proxied on the render context.`); 4721 } 4722 else if (instance === currentRenderingInstance) { 4723 warn$1(`Property ${JSON.stringify(key)} was accessed during render ` + 4724 `but is not defined on instance.`); 4725 } 4726 } 4727 }, 4728 set({ _: instance }, key, value) { 4729 const { data, setupState, ctx } = instance; 4730 if (hasSetupBinding(setupState, key)) { 4731 setupState[key] = value; 4732 return true; 4733 } 4734 else if (setupState.__isScriptSetup && 4735 hasOwn(setupState, key)) { 4736 warn$1(`Cannot mutate <script setup> binding "${key}" from Options API.`); 4737 return false;
vendor: 4,408 bytes, lines 4738-4851
4738 } 4739 else if (data !== EMPTY_OBJ && hasOwn(data, key)) { 4740 data[key] = value; 4741 return true; 4742 } 4743 else if (hasOwn(instance.props, key)) { 4744 warn$1(`Attempting to mutate prop "${key}". Props are readonly.`); 4745 return false; 4746 } 4747 if (key[0] === '$' && key.slice(1) in instance) { 4748 warn$1(`Attempting to mutate public property "${key}". ` + 4749 `Properties starting with $ are reserved and readonly.`); 4750 return false; 4751 } 4752 else { 4753 if (key in instance.appContext.config.globalProperties) { 4754 Object.defineProperty(ctx, key, { 4755 enumerable: true, 4756 configurable: true, 4757 value 4758 }); 4759 } 4760 else { 4761 ctx[key] = value; 4762 } 4763 } 4764 return true; 4765 }, 4766 has({ _: { data, setupState, accessCache, ctx, appContext, propsOptions } }, key) { 4767 let normalizedProps; 4768 return (!!accessCache[key] || 4769 (data !== EMPTY_OBJ && hasOwn(data, key)) || 4770 hasSetupBinding(setupState, key) || 4771 ((normalizedProps = propsOptions[0]) && hasOwn(normalizedProps, key)) || 4772 hasOwn(ctx, key) || 4773 hasOwn(publicPropertiesMap, key) || 4774 hasOwn(appContext.config.globalProperties, key)); 4775 }, 4776 defineProperty(target, key, descriptor) { 4777 if (descriptor.get != null) { 4778 // invalidate key cache of a getter based property #5417 4779 target._.accessCache[key] = 0; 4780 } 4781 else if (hasOwn(descriptor, 'value')) { 4782 this.set(target, key, descriptor.value, null); 4783 } 4784 return Reflect.defineProperty(target, key, descriptor); 4785 } 4786 }; 4787 { 4788 PublicInstanceProxyHandlers.ownKeys = (target) => { 4789 warn$1(`Avoid app logic that relies on enumerating keys on a component instance. ` + 4790 `The keys will be empty in production mode to avoid performance overhead.`); 4791 return Reflect.ownKeys(target); 4792 }; 4793 } 4794 const RuntimeCompiledPublicInstanceProxyHandlers = /*#__PURE__*/ extend({}, PublicInstanceProxyHandlers, { 4795 get(target, key) { 4796 // fast path for unscopables when using `with` block 4797 if (key === Symbol.unscopables) { 4798 return; 4799 } 4800 return PublicInstanceProxyHandlers.get(target, key, target); 4801 }, 4802 has(_, key) { 4803 const has = key[0] !== '_' && !isGloballyWhitelisted(key); 4804 if (!has && PublicInstanceProxyHandlers.has(_, key)) { 4805 warn$1(`Property ${JSON.stringify(key)} should not start with _ which is a reserved prefix for Vue internals.`); 4806 } 4807 return has; 4808 } 4809 }); 4810 // dev only 4811 // In dev mode, the proxy target exposes the same properties as seen on `this` 4812 // for easier console inspection. In prod mode it will be an empty object so 4813 // these properties definitions can be skipped. 4814 function createDevRenderContext(instance) { 4815 const target = {}; 4816 // expose internal instance for proxy handlers 4817 Object.defineProperty(target, `_`, { 4818 configurable: true, 4819 enumerable: false, 4820 get: () => instance 4821 }); 4822 // expose public properties 4823 Object.keys(publicPropertiesMap).forEach(key => { 4824 Object.defineProperty(target, key, { 4825 configurable: true, 4826 enumerable: false, 4827 get: () => publicPropertiesMap[key](instance), 4828 // intercepted by the proxy so no need for implementation, 4829 // but needed to prevent set errors 4830 set: NOOP 4831 }); 4832 }); 4833 return target; 4834 } 4835 // dev only 4836 function exposePropsOnRenderContext(instance) { 4837 const { ctx, propsOptions: [propsOptions] } = instance; 4838 if (propsOptions) { 4839 Object.keys(propsOptions).forEach(key => { 4840 Object.defineProperty(ctx, key, { 4841 enumerable: true, 4842 configurable: true, 4843 get: () => instance.props[key], 4844 set: NOOP 4845 }); 4846 }); 4847 } 4848 } 4849 // dev only 4850 function exposeSetupStateOnRenderContext(instance) { 4851 const { ctx, setupState } = instance;
4852 Object.keys(toRaw(setupState)).forEach(key => { 4853 if (!setupState.__isScriptSetup) { 4854 if (isReservedPrefix(key[0])) { 4855 warn$1(`setup() return property ${JSON.stringify(key)} should not start with "$" or "_" ` + 4856 `which are reserved prefixes for Vue internals.`); 4857 return; 4858 } 4859 Object.defineProperty(ctx, key, { 4860 enumerable: true, 4861 configurable: true, 4862 get: () => setupState[key], 4863 set: NOOP 4864 }); 4865 } 4866 }); 4867 } 4868 4869 function createDuplicateChecker() { 4870 const cache = Object.create(null); 4871 return (type, key) => { 4872 if (cache[key]) { 4873 warn$1(`${type} property "${key}" is already defined in ${cache[key]}.`); 4874 } 4875 else { 4876 cache[key] = type; 4877 } 4878 }; 4879 } 4880 let shouldCacheAccess = true; 4881 function applyOptions(instance) { 4882 const options = resolveMergedOptions(instance); 4883 const publicThis = instance.proxy; 4884 const ctx = instance.ctx; 4885 // do not cache property access on public proxy during state initialization 4886 shouldCacheAccess = false; 4887 // call beforeCreate first before accessing other options since 4888 // the hook may mutate resolved options (#2791) 4889 if (options.beforeCreate) { 4890 callHook(options.beforeCreate, instance, "bc" /* LifecycleHooks.BEFORE_CREATE */); 4891 } 4892 const { 4893 // state 4894 data: dataOptions, computed: computedOptions, methods, watch: watchOptions, provide: provideOptions, inject: injectOptions, 4895 // lifecycle 4896 created, beforeMount, mounted, beforeUpdate, updated, activated, deactivated, beforeDestroy, beforeUnmount, destroyed, unmounted, render, renderTracked, renderTriggered, errorCaptured, serverPrefetch, 4897 // public API 4898 expose, inheritAttrs, 4899 // assets 4900 components, directives, filters } = options; 4901 const checkDuplicateProperties = createDuplicateChecker() ; 4902 { 4903 const [propsOptions] = instance.propsOptions; 4904 if (propsOptions) { 4905 for (const key in propsOptions) { 4906 checkDuplicateProperties("Props" /* OptionTypes.PROPS */, key); 4907 } 4908 } 4909 } 4910 // options initialization order (to be consistent with Vue 2): 4911 // - props (already done outside of this function) 4912 // - inject 4913 // - methods 4914 // - data (deferred since it relies on `this` access) 4915 // - computed 4916 // - watch (deferred since it relies on `this` access) 4917 if (injectOptions) { 4918 resolveInjections(injectOptions, ctx, checkDuplicateProperties, instance.appContext.config.unwrapInjectedRef); 4919 } 4920 if (methods) { 4921 for (const key in methods) { 4922 const methodHandler = methods[key]; 4923 if (isFunction(methodHandler)) { 4924 // In dev mode, we use the `createRenderContext` function to define 4925 // methods to the proxy target, and those are read-only but 4926 // reconfigurable, so it needs to be redefined here 4927 { 4928 Object.defineProperty(ctx, key, { 4929 value: methodHandler.bind(publicThis), 4930 configurable: true, 4931 enumerable: true, 4932 writable: true 4933 }); 4934 } 4935 { 4936 checkDuplicateProperties("Methods" /* OptionTypes.METHODS */, key); 4937 } 4938 } 4939 else { 4940 warn$1(`Method "${key}" has type "${typeof methodHandler}" in the component definition. ` + 4941 `Did you reference the function correctly?`); 4942 } 4943 } 4944 } 4945 if (dataOptions) { 4946 if (!isFunction(dataOptions)) { 4947 warn$1(`The data option must be a function. ` + 4948 `Plain object usage is no longer supported.`); 4949 } 4950 const data = dataOptions.call(publicThis, publicThis);
vendor: 6,164 bytes, lines 4951-5107
4951 if (isPromise(data)) { 4952 warn$1(`data() returned a Promise - note data() cannot be async; If you ` + 4953 `intend to perform data fetching before component renders, use ` + 4954 `async setup() + <Suspense>.`); 4955 } 4956 if (!isObject(data)) { 4957 warn$1(`data() should return an object.`); 4958 } 4959 else { 4960 instance.data = reactive(data); 4961 { 4962 for (const key in data) { 4963 checkDuplicateProperties("Data" /* OptionTypes.DATA */, key); 4964 // expose data on ctx during dev 4965 if (!isReservedPrefix(key[0])) { 4966 Object.defineProperty(ctx, key, { 4967 configurable: true, 4968 enumerable: true, 4969 get: () => data[key], 4970 set: NOOP 4971 }); 4972 } 4973 } 4974 } 4975 } 4976 } 4977 // state initialization complete at this point - start caching access 4978 shouldCacheAccess = true; 4979 if (computedOptions) { 4980 for (const key in computedOptions) { 4981 const opt = computedOptions[key]; 4982 const get = isFunction(opt) 4983 ? opt.bind(publicThis, publicThis) 4984 : isFunction(opt.get) 4985 ? opt.get.bind(publicThis, publicThis) 4986 : NOOP; 4987 if (get === NOOP) { 4988 warn$1(`Computed property "${key}" has no getter.`); 4989 } 4990 const set = !isFunction(opt) && isFunction(opt.set) 4991 ? opt.set.bind(publicThis) 4992 : () => { 4993 warn$1(`Write operation failed: computed property "${key}" is readonly.`); 4994 } 4995 ; 4996 const c = computed$1({ 4997 get, 4998 set 4999 }); 5000 Object.defineProperty(ctx, key, { 5001 enumerable: true, 5002 configurable: true, 5003 get: () => c.value, 5004 set: v => (c.value = v) 5005 }); 5006 { 5007 checkDuplicateProperties("Computed" /* OptionTypes.COMPUTED */, key); 5008 } 5009 } 5010 } 5011 if (watchOptions) { 5012 for (const key in watchOptions) { 5013 createWatcher(watchOptions[key], ctx, publicThis, key); 5014 } 5015 } 5016 if (provideOptions) { 5017 const provides = isFunction(provideOptions) 5018 ? provideOptions.call(publicThis) 5019 : provideOptions; 5020 Reflect.ownKeys(provides).forEach(key => { 5021 provide(key, provides[key]); 5022 }); 5023 } 5024 if (created) { 5025 callHook(created, instance, "c" /* LifecycleHooks.CREATED */); 5026 } 5027 function registerLifecycleHook(register, hook) { 5028 if (isArray(hook)) { 5029 hook.forEach(_hook => register(_hook.bind(publicThis))); 5030 } 5031 else if (hook) { 5032 register(hook.bind(publicThis)); 5033 } 5034 } 5035 registerLifecycleHook(onBeforeMount, beforeMount); 5036 registerLifecycleHook(onMounted, mounted); 5037 registerLifecycleHook(onBeforeUpdate, beforeUpdate); 5038 registerLifecycleHook(onUpdated, updated); 5039 registerLifecycleHook(onActivated, activated); 5040 registerLifecycleHook(onDeactivated, deactivated); 5041 registerLifecycleHook(onErrorCaptured, errorCaptured); 5042 registerLifecycleHook(onRenderTracked, renderTracked); 5043 registerLifecycleHook(onRenderTriggered, renderTriggered); 5044 registerLifecycleHook(onBeforeUnmount, beforeUnmount); 5045 registerLifecycleHook(onUnmounted, unmounted); 5046 registerLifecycleHook(onServerPrefetch, serverPrefetch); 5047 if (isArray(expose)) { 5048 if (expose.length) { 5049 const exposed = instance.exposed || (instance.exposed = {}); 5050 expose.forEach(key => { 5051 Object.defineProperty(exposed, key, { 5052 get: () => publicThis[key], 5053 set: val => (publicThis[key] = val) 5054 }); 5055 }); 5056 } 5057 else if (!instance.exposed) { 5058 instance.exposed = {}; 5059 } 5060 } 5061 // options that are handled when creating the instance but also need to be 5062 // applied from mixins 5063 if (render && instance.render === NOOP) { 5064 instance.render = render; 5065 } 5066 if (inheritAttrs != null) { 5067 instance.inheritAttrs = inheritAttrs; 5068 } 5069 // asset options. 5070 if (components) 5071 instance.components = components; 5072 if (directives) 5073 instance.directives = directives; 5074 } 5075 function resolveInjections(injectOptions, ctx, checkDuplicateProperties = NOOP, unwrapRef = false) { 5076 if (isArray(injectOptions)) { 5077 injectOptions = normalizeInject(injectOptions); 5078 } 5079 for (const key in injectOptions) { 5080 const opt = injectOptions[key]; 5081 let injected; 5082 if (isObject(opt)) { 5083 if ('default' in opt) { 5084 injected = inject(opt.from || key, opt.default, true /* treat default function as factory */); 5085 } 5086 else { 5087 injected = inject(opt.from || key); 5088 } 5089 } 5090 else { 5091 injected = inject(opt); 5092 } 5093 if (isRef(injected)) { 5094 // TODO remove the check in 3.3 5095 if (unwrapRef) { 5096 Object.defineProperty(ctx, key, { 5097 enumerable: true, 5098 configurable: true, 5099 get: () => injected.value, 5100 set: v => (injected.value = v) 5101 }); 5102 } 5103 else { 5104 { 5105 warn$1(`injected property "${key}" is a ref and will be auto-unwrapped ` + 5106 `and no longer needs \`.value\` in the next minor release. ` + 5107 `To opt-in to the new behavior now, ` +
vendor: 7,159 bytes, lines 5108-5331
5108 `set \`app.config.unwrapInjectedRef = true\` (this config is ` + 5109 `temporary and will not be needed in the future.)`); 5110 } 5111 ctx[key] = injected; 5112 } 5113 } 5114 else { 5115 ctx[key] = injected; 5116 } 5117 { 5118 checkDuplicateProperties("Inject" /* OptionTypes.INJECT */, key); 5119 } 5120 } 5121 } 5122 function callHook(hook, instance, type) { 5123 callWithAsyncErrorHandling(isArray(hook) 5124 ? hook.map(h => h.bind(instance.proxy)) 5125 : hook.bind(instance.proxy), instance, type); 5126 } 5127 function createWatcher(raw, ctx, publicThis, key) { 5128 const getter = key.includes('.') 5129 ? createPathGetter(publicThis, key) 5130 : () => publicThis[key]; 5131 if (isString(raw)) { 5132 const handler = ctx[raw]; 5133 if (isFunction(handler)) { 5134 watch(getter, handler); 5135 } 5136 else { 5137 warn$1(`Invalid watch handler specified by key "${raw}"`, handler); 5138 } 5139 } 5140 else if (isFunction(raw)) { 5141 watch(getter, raw.bind(publicThis)); 5142 } 5143 else if (isObject(raw)) { 5144 if (isArray(raw)) { 5145 raw.forEach(r => createWatcher(r, ctx, publicThis, key)); 5146 } 5147 else { 5148 const handler = isFunction(raw.handler) 5149 ? raw.handler.bind(publicThis) 5150 : ctx[raw.handler]; 5151 if (isFunction(handler)) { 5152 watch(getter, handler, raw); 5153 } 5154 else { 5155 warn$1(`Invalid watch handler specified by key "${raw.handler}"`, handler); 5156 } 5157 } 5158 } 5159 else { 5160 warn$1(`Invalid watch option: "${key}"`, raw); 5161 } 5162 } 5163 /** 5164 * Resolve merged options and cache it on the component. 5165 * This is done only once per-component since the merging does not involve 5166 * instances. 5167 */ 5168 function resolveMergedOptions(instance) { 5169 const base = instance.type; 5170 const { mixins, extends: extendsOptions } = base; 5171 const { mixins: globalMixins, optionsCache: cache, config: { optionMergeStrategies } } = instance.appContext; 5172 const cached = cache.get(base); 5173 let resolved; 5174 if (cached) { 5175 resolved = cached; 5176 } 5177 else if (!globalMixins.length && !mixins && !extendsOptions) { 5178 { 5179 resolved = base; 5180 } 5181 } 5182 else { 5183 resolved = {}; 5184 if (globalMixins.length) { 5185 globalMixins.forEach(m => mergeOptions(resolved, m, optionMergeStrategies, true)); 5186 } 5187 mergeOptions(resolved, base, optionMergeStrategies); 5188 } 5189 if (isObject(base)) { 5190 cache.set(base, resolved); 5191 } 5192 return resolved; 5193 } 5194 function mergeOptions(to, from, strats, asMixin = false) { 5195 const { mixins, extends: extendsOptions } = from; 5196 if (extendsOptions) { 5197 mergeOptions(to, extendsOptions, strats, true); 5198 } 5199 if (mixins) { 5200 mixins.forEach((m) => mergeOptions(to, m, strats, true)); 5201 } 5202 for (const key in from) { 5203 if (asMixin && key === 'expose') { 5204 warn$1(`"expose" option is ignored when declared in mixins or extends. ` + 5205 `It should only be declared in the base component itself.`); 5206 } 5207 else { 5208 const strat = internalOptionMergeStrats[key] || (strats && strats[key]); 5209 to[key] = strat ? strat(to[key], from[key]) : from[key]; 5210 } 5211 } 5212 return to; 5213 } 5214 const internalOptionMergeStrats = { 5215 data: mergeDataFn, 5216 props: mergeObjectOptions, 5217 emits: mergeObjectOptions, 5218 // objects 5219 methods: mergeObjectOptions, 5220 computed: mergeObjectOptions, 5221 // lifecycle 5222 beforeCreate: mergeAsArray, 5223 created: mergeAsArray, 5224 beforeMount: mergeAsArray, 5225 mounted: mergeAsArray, 5226 beforeUpdate: mergeAsArray, 5227 updated: mergeAsArray, 5228 beforeDestroy: mergeAsArray, 5229 beforeUnmount: mergeAsArray, 5230 destroyed: mergeAsArray, 5231 unmounted: mergeAsArray, 5232 activated: mergeAsArray, 5233 deactivated: mergeAsArray, 5234 errorCaptured: mergeAsArray, 5235 serverPrefetch: mergeAsArray, 5236 // assets 5237 components: mergeObjectOptions, 5238 directives: mergeObjectOptions, 5239 // watch 5240 watch: mergeWatchOptions, 5241 // provide / inject 5242 provide: mergeDataFn, 5243 inject: mergeInject 5244 }; 5245 function mergeDataFn(to, from) { 5246 if (!from) { 5247 return to; 5248 } 5249 if (!to) { 5250 return from; 5251 } 5252 return function mergedDataFn() { 5253 return (extend)(isFunction(to) ? to.call(this, this) : to, isFunction(from) ? from.call(this, this) : from); 5254 }; 5255 } 5256 function mergeInject(to, from) { 5257 return mergeObjectOptions(normalizeInject(to), normalizeInject(from)); 5258 } 5259 function normalizeInject(raw) { 5260 if (isArray(raw)) { 5261 const res = {}; 5262 for (let i = 0; i < raw.length; i++) { 5263 res[raw[i]] = raw[i]; 5264 } 5265 return res; 5266 } 5267 return raw; 5268 } 5269 function mergeAsArray(to, from) { 5270 return to ? [...new Set([].concat(to, from))] : from; 5271 } 5272 function mergeObjectOptions(to, from) { 5273 return to ? extend(extend(Object.create(null), to), from) : from; 5274 } 5275 function mergeWatchOptions(to, from) { 5276 if (!to) 5277 return from; 5278 if (!from) 5279 return to; 5280 const merged = extend(Object.create(null), to); 5281 for (const key in from) { 5282 merged[key] = mergeAsArray(to[key], from[key]); 5283 } 5284 return merged; 5285 } 5286 5287 function initProps(instance, rawProps, isStateful, // result of bitwise flag comparison 5288 isSSR = false) { 5289 const props = {}; 5290 const attrs = {}; 5291 def(attrs, InternalObjectKey, 1); 5292 instance.propsDefaults = Object.create(null); 5293 setFullProps(instance, rawProps, props, attrs); 5294 // ensure all declared prop keys are present 5295 for (const key in instance.propsOptions[0]) { 5296 if (!(key in props)) { 5297 props[key] = undefined; 5298 } 5299 } 5300 // validation 5301 { 5302 validateProps(rawProps || {}, props, instance); 5303 } 5304 if (isStateful) { 5305 // stateful 5306 instance.props = isSSR ? props : shallowReactive(props); 5307 } 5308 else { 5309 if (!instance.type.props) { 5310 // functional w/ optional props, props === attrs 5311 instance.props = attrs; 5312 } 5313 else { 5314 // functional w/ declared props 5315 instance.props = props; 5316 } 5317 } 5318 instance.attrs = attrs; 5319 } 5320 function isInHmrContext(instance) { 5321 while (instance) { 5322 if (instance.type.__hmrId) 5323 return true; 5324 instance = instance.parent; 5325 } 5326 } 5327 function updateProps(instance, rawProps, rawPrevProps, optimized) { 5328 const { props, attrs, vnode: { patchFlag } } = instance; 5329 const rawCurrentProps = toRaw(props); 5330 const [options] = instance.propsOptions; 5331 let hasAttrsChanged = false;
5332 if ( 5333 // always force full diff in dev 5334 // - #1942 if hmr is enabled with sfc component 5335 // - vite#872 non-sfc component used by sfc component 5336 !(isInHmrContext(instance)) && 5337 (optimized || patchFlag > 0) && 5338 !(patchFlag & 16 /* PatchFlags.FULL_PROPS */)) { 5339 if (patchFlag & 8 /* PatchFlags.PROPS */) { 5340 // Compiler-generated props & no keys change, just set the updated 5341 // the props. 5342 const propsToUpdate = instance.vnode.dynamicProps; 5343 for (let i = 0; i < propsToUpdate.length; i++) { 5344 let key = propsToUpdate[i]; 5345 // skip if the prop key is a declared emit event listener 5346 if (isEmitListener(instance.emitsOptions, key)) { 5347 continue; 5348 } 5349 // PROPS flag guarantees rawProps to be non-null 5350 const value = rawProps[key]; 5351 if (options) { 5352 // attr / props separation was done on init and will be consistent 5353 // in this code path, so just check if attrs have it. 5354 if (hasOwn(attrs, key)) { 5355 if (value !== attrs[key]) { 5356 attrs[key] = value; 5357 hasAttrsChanged = true; 5358 } 5359 } 5360 else { 5361 const camelizedKey = camelize(key); 5362 props[camelizedKey] = resolvePropValue(options, rawCurrentProps, camelizedKey, value, instance, false /* isAbsent */); 5363 } 5364 } 5365 else { 5366 if (value !== attrs[key]) { 5367 attrs[key] = value; 5368 hasAttrsChanged = true; 5369 } 5370 } 5371 } 5372 } 5373 } 5374 else { 5375 // full props update. 5376 if (setFullProps(instance, rawProps, props, attrs)) { 5377 hasAttrsChanged = true; 5378 } 5379 // in case of dynamic props, check if we need to delete keys from 5380 // the props object 5381 let kebabKey; 5382 for (const key in rawCurrentProps) { 5383 if (!rawProps || 5384 // for camelCase 5385 (!hasOwn(rawProps, key) && 5386 // it's possible the original props was passed in as kebab-case 5387 // and converted to camelCase (#955) 5388 ((kebabKey = hyphenate(key)) === key || !hasOwn(rawProps, kebabKey)))) { 5389 if (options) { 5390 if (rawPrevProps && 5391 // for camelCase 5392 (rawPrevProps[key] !== undefined || 5393 // for kebab-case 5394 rawPrevProps[kebabKey] !== undefined)) { 5395 props[key] = resolvePropValue(options, rawCurrentProps, key, undefined, instance, true /* isAbsent */); 5396 } 5397 } 5398 else { 5399 delete props[key]; 5400 } 5401 } 5402 } 5403 // in the case of functional component w/o props declaration, props and 5404 // attrs point to the same object so it should already have been updated. 5405 if (attrs !== rawCurrentProps) { 5406 for (const key in attrs) { 5407 if (!rawProps || 5408 (!hasOwn(rawProps, key) && 5409 (!false ))) { 5410 delete attrs[key]; 5411 hasAttrsChanged = true; 5412 } 5413 } 5414 } 5415 } 5416 // trigger updates for $attrs in case it's used in component slots 5417 if (hasAttrsChanged) { 5418 trigger(instance, "set" /* TriggerOpTypes.SET */, '$attrs'); 5419 } 5420 { 5421 validateProps(rawProps || {}, props, instance); 5422 } 5423 } 5424 function setFullProps(instance, rawProps, props, attrs) { 5425 const [options, needCastKeys] = instance.propsOptions; 5426 let hasAttrsChanged = false;
vendor: 4,398 bytes, lines 5427-5546
5427 let rawCastValues; 5428 if (rawProps) { 5429 for (let key in rawProps) { 5430 // key, ref are reserved and never passed down 5431 if (isReservedProp(key)) { 5432 continue; 5433 } 5434 const value = rawProps[key]; 5435 // prop option names are camelized during normalization, so to support 5436 // kebab -> camel conversion here we need to camelize the key. 5437 let camelKey; 5438 if (options && hasOwn(options, (camelKey = camelize(key)))) { 5439 if (!needCastKeys || !needCastKeys.includes(camelKey)) { 5440 props[camelKey] = value; 5441 } 5442 else { 5443 (rawCastValues || (rawCastValues = {}))[camelKey] = value; 5444 } 5445 } 5446 else if (!isEmitListener(instance.emitsOptions, key)) { 5447 if (!(key in attrs) || value !== attrs[key]) { 5448 attrs[key] = value; 5449 hasAttrsChanged = true; 5450 } 5451 } 5452 } 5453 } 5454 if (needCastKeys) { 5455 const rawCurrentProps = toRaw(props); 5456 const castValues = rawCastValues || EMPTY_OBJ; 5457 for (let i = 0; i < needCastKeys.length; i++) { 5458 const key = needCastKeys[i]; 5459 props[key] = resolvePropValue(options, rawCurrentProps, key, castValues[key], instance, !hasOwn(castValues, key)); 5460 } 5461 } 5462 return hasAttrsChanged; 5463 } 5464 function resolvePropValue(options, props, key, value, instance, isAbsent) { 5465 const opt = options[key]; 5466 if (opt != null) { 5467 const hasDefault = hasOwn(opt, 'default'); 5468 // default values 5469 if (hasDefault && value === undefined) { 5470 const defaultValue = opt.default; 5471 if (opt.type !== Function && isFunction(defaultValue)) { 5472 const { propsDefaults } = instance; 5473 if (key in propsDefaults) { 5474 value = propsDefaults[key]; 5475 } 5476 else { 5477 setCurrentInstance(instance); 5478 value = propsDefaults[key] = defaultValue.call(null, props); 5479 unsetCurrentInstance(); 5480 } 5481 } 5482 else { 5483 value = defaultValue; 5484 } 5485 } 5486 // boolean casting 5487 if (opt[0 /* BooleanFlags.shouldCast */]) { 5488 if (isAbsent && !hasDefault) { 5489 value = false; 5490 } 5491 else if (opt[1 /* BooleanFlags.shouldCastTrue */] && 5492 (value === '' || value === hyphenate(key))) { 5493 value = true; 5494 } 5495 } 5496 } 5497 return value; 5498 } 5499 function normalizePropsOptions(comp, appContext, asMixin = false) { 5500 const cache = appContext.propsCache; 5501 const cached = cache.get(comp); 5502 if (cached) { 5503 return cached; 5504 } 5505 const raw = comp.props; 5506 const normalized = {}; 5507 const needCastKeys = []; 5508 // apply mixin/extends props 5509 let hasExtends = false; 5510 if (!isFunction(comp)) { 5511 const extendProps = (raw) => { 5512 hasExtends = true; 5513 const [props, keys] = normalizePropsOptions(raw, appContext, true); 5514 extend(normalized, props); 5515 if (keys) 5516 needCastKeys.push(...keys); 5517 }; 5518 if (!asMixin && appContext.mixins.length) { 5519 appContext.mixins.forEach(extendProps); 5520 } 5521 if (comp.extends) { 5522 extendProps(comp.extends); 5523 } 5524 if (comp.mixins) { 5525 comp.mixins.forEach(extendProps); 5526 } 5527 } 5528 if (!raw && !hasExtends) { 5529 if (isObject(comp)) { 5530 cache.set(comp, EMPTY_ARR); 5531 } 5532 return EMPTY_ARR; 5533 } 5534 if (isArray(raw)) { 5535 for (let i = 0; i < raw.length; i++) { 5536 if (!isString(raw[i])) { 5537 warn$1(`props must be strings when using array syntax.`, raw[i]); 5538 } 5539 const normalizedKey = camelize(raw[i]); 5540 if (validatePropName(normalizedKey)) { 5541 normalized[normalizedKey] = EMPTY_OBJ; 5542 } 5543 } 5544 } 5545 else if (raw) { 5546 if (!isObject(raw)) {
5547 warn$1(`invalid props options`, raw); 5548 } 5549 for (const key in raw) { 5550 const normalizedKey = camelize(key); 5551 if (validatePropName(normalizedKey)) { 5552 const opt = raw[key]; 5553 const prop = (normalized[normalizedKey] = 5554 isArray(opt) || isFunction(opt) ? { type: opt } : Object.assign({}, opt)); 5555 if (prop) { 5556 const booleanIndex = getTypeIndex(Boolean, prop.type); 5557 const stringIndex = getTypeIndex(String, prop.type); 5558 prop[0 /* BooleanFlags.shouldCast */] = booleanIndex > -1; 5559 prop[1 /* BooleanFlags.shouldCastTrue */] = 5560 stringIndex < 0 || booleanIndex < stringIndex; 5561 // if the prop needs boolean casting or default value 5562 if (booleanIndex > -1 || hasOwn(prop, 'default')) { 5563 needCastKeys.push(normalizedKey); 5564 } 5565 } 5566 } 5567 } 5568 } 5569 const res = [normalized, needCastKeys]; 5570 if (isObject(comp)) { 5571 cache.set(comp, res); 5572 } 5573 return res; 5574 } 5575 function validatePropName(key) { 5576 if (key[0] !== '$') { 5577 return true; 5578 } 5579 else { 5580 warn$1(`Invalid prop name: "${key}" is a reserved property.`); 5581 } 5582 return false; 5583 } 5584 // use function string name to check type constructors 5585 // so that it works across vms / iframes. 5586 function getType(ctor) { 5587 const match = ctor && ctor.toString().match(/^\s*function (\w+)/); 5588 return match ? match[1] : ctor === null ? 'null' : ''; 5589 } 5590 function isSameType(a, b) { 5591 return getType(a) === getType(b); 5592 } 5593 function getTypeIndex(type, expectedTypes) { 5594 if (isArray(expectedTypes)) { 5595 return expectedTypes.findIndex(t => isSameType(t, type)); 5596 } 5597 else if (isFunction(expectedTypes)) { 5598 return isSameType(expectedTypes, type) ? 0 : -1; 5599 } 5600 return -1; 5601 } 5602 /** 5603 * dev only 5604 */ 5605 function validateProps(rawProps, props, instance) { 5606 const resolvedValues = toRaw(props); 5607 const options = instance.propsOptions[0]; 5608 for (const key in options) { 5609 let opt = options[key]; 5610 if (opt == null) 5611 continue; 5612 validateProp(key, resolvedValues[key], opt, !hasOwn(rawProps, key) && !hasOwn(rawProps, hyphenate(key))); 5613 } 5614 } 5615 /** 5616 * dev only 5617 */ 5618 function validateProp(name, value, prop, isAbsent) { 5619 const { type, required, validator } = prop; 5620 // required! 5621 if (required && isAbsent) { 5622 warn$1('Missing required prop: "' + name + '"'); 5623 return; 5624 } 5625 // missing but optional 5626 if (value == null && !prop.required) { 5627 return; 5628 } 5629 // type check 5630 if (type != null && type !== true) { 5631 let isValid = false; 5632 const types = isArray(type) ? type : [type]; 5633 const expectedTypes = []; 5634 // value is valid as long as one of the specified types match 5635 for (let i = 0; i < types.length && !isValid; i++) { 5636 const { valid, expectedType } = assertType(value, types[i]); 5637 expectedTypes.push(expectedType || ''); 5638 isValid = valid; 5639 } 5640 if (!isValid) { 5641 warn$1(getInvalidTypeMessage(name, value, expectedTypes)); 5642 return; 5643 } 5644 } 5645 // custom validator 5646 if (validator && !validator(value)) { 5647 warn$1('Invalid prop: custom validator check failed for prop "' + name + '".'); 5648 } 5649 } 5650 const isSimpleType = /*#__PURE__*/ makeMap('String,Number,Boolean,Function,Symbol,BigInt'); 5651 /** 5652 * dev only 5653 */ 5654 function assertType(value, type) { 5655 let valid; 5656 const expectedType = getType(type); 5657 if (isSimpleType(expectedType)) { 5658 const t = typeof value; 5659 valid = t === expectedType.toLowerCase(); 5660 // for primitive wrapper objects 5661 if (!valid && t === 'object') { 5662 valid = value instanceof type; 5663 } 5664 } 5665 else if (expectedType === 'Object') { 5666 valid = isObject(value); 5667 } 5668 else if (expectedType === 'Array') { 5669 valid = isArray(value); 5670 } 5671 else if (expectedType === 'null') { 5672 valid = value === null; 5673 } 5674 else { 5675 valid = value instanceof type; 5676 } 5677 return { 5678 valid, 5679 expectedType 5680 }; 5681 } 5682 /** 5683 * dev only 5684 */ 5685 function getInvalidTypeMessage(name, value, expectedTypes) { 5686 let message = `Invalid prop: type check failed for prop "${name}".` + 5687 ` Expected ${expectedTypes.map(capitalize).join(' | ')}`; 5688 const expectedType = expectedTypes[0]; 5689 const receivedType = toRawType(value); 5690 const expectedValue = styleValue(value, expectedType); 5691 const receivedValue = styleValue(value, receivedType); 5692 // check if we need to specify expected value 5693 if (expectedTypes.length === 1 && 5694 isExplicable(expectedType) && 5695 !isBoolean(expectedType, receivedType)) { 5696 message += ` with value ${expectedValue}`; 5697 } 5698 message += `, got ${receivedType} `; 5699 // check if we need to specify received value 5700 if (isExplicable(receivedType)) { 5701 message += `with value ${receivedValue}.`; 5702 } 5703 return message; 5704 } 5705 /** 5706 * dev only 5707 */ 5708 function styleValue(value, type) { 5709 if (type === 'String') { 5710 return `"${value}"`; 5711 } 5712 else if (type === 'Number') { 5713 return `${Number(value)}`; 5714 } 5715 else { 5716 return `${value}`; 5717 } 5718 } 5719 /** 5720 * dev only 5721 */ 5722 function isExplicable(type) { 5723 const explicitTypes = ['string', 'number', 'boolean']; 5724 return explicitTypes.some(elem => type.toLowerCase() === elem); 5725 } 5726 /** 5727 * dev only 5728 */ 5729 function isBoolean(...args) { 5730 return args.some(elem => elem.toLowerCase() === 'boolean'); 5731 } 5732 5733 const isInternalKey = (key) => key[0] === '_' || key === '$stable'; 5734 const normalizeSlotValue = (value) => isArray(value) 5735 ? value.map(normalizeVNode) 5736 : [normalizeVNode(value)]; 5737 const normalizeSlot = (key, rawSlot, ctx) => { 5738 if (rawSlot._n) { 5739 // already normalized - #5353 5740 return rawSlot; 5741 } 5742 const normalized = withCtx((...args) => { 5743 if (true && currentInstance) { 5744 warn$1(`Slot "${key}" invoked outside of the render function: ` + 5745 `this will not track dependencies used in the slot. ` + 5746 `Invoke the slot function inside the render function instead.`); 5747 } 5748 return normalizeSlotValue(rawSlot(...args)); 5749 }, ctx); 5750 normalized._c = false;
5751 return normalized; 5752 }; 5753 const normalizeObjectSlots = (rawSlots, slots, instance) => { 5754 const ctx = rawSlots._ctx; 5755 for (const key in rawSlots) { 5756 if (isInternalKey(key)) 5757 continue; 5758 const value = rawSlots[key]; 5759 if (isFunction(value)) { 5760 slots[key] = normalizeSlot(key, value, ctx); 5761 } 5762 else if (value != null) { 5763 { 5764 warn$1(`Non-function value encountered for slot "${key}". ` + 5765 `Prefer function slots for better performance.`); 5766 } 5767 const normalized = normalizeSlotValue(value); 5768 slots[key] = () => normalized; 5769 } 5770 } 5771 }; 5772 const normalizeVNodeSlots = (instance, children) => { 5773 if (!isKeepAlive(instance.vnode) && 5774 !(false )) { 5775 warn$1(`Non-function value encountered for default slot. ` + 5776 `Prefer function slots for better performance.`); 5777 } 5778 const normalized = normalizeSlotValue(children); 5779 instance.slots.default = () => normalized; 5780 }; 5781 const initSlots = (instance, children) => { 5782 if (instance.vnode.shapeFlag & 32 /* ShapeFlags.SLOTS_CHILDREN */) { 5783 const type = children._; 5784 if (type) { 5785 // users can get the shallow readonly version of the slots object through `this.$slots`, 5786 // we should avoid the proxy object polluting the slots of the internal instance 5787 instance.slots = toRaw(children); 5788 // make compiler marker non-enumerable 5789 def(children, '_', type); 5790 } 5791 else { 5792 normalizeObjectSlots(children, (instance.slots = {})); 5793 } 5794 } 5795 else { 5796 instance.slots = {}; 5797 if (children) { 5798 normalizeVNodeSlots(instance, children); 5799 } 5800 } 5801 def(instance.slots, InternalObjectKey, 1); 5802 }; 5803 const updateSlots = (instance, children, optimized) => { 5804 const { vnode, slots } = instance; 5805 let needDeletionCheck = true; 5806 let deletionComparisonTarget = EMPTY_OBJ; 5807 if (vnode.shapeFlag & 32 /* ShapeFlags.SLOTS_CHILDREN */) { 5808 const type = children._; 5809 if (type) { 5810 // compiled slots. 5811 if (isHmrUpdating) { 5812 // Parent was HMR updated so slot content may have changed. 5813 // force update slots and mark instance for hmr as well 5814 extend(slots, children); 5815 } 5816 else if (optimized && type === 1 /* SlotFlags.STABLE */) { 5817 // compiled AND stable. 5818 // no need to update, and skip stale slots removal. 5819 needDeletionCheck = false; 5820 } 5821 else { 5822 // compiled but dynamic (v-if/v-for on slots) - update slots, but skip 5823 // normalization. 5824 extend(slots, children); 5825 // #2893 5826 // when rendering the optimized slots by manually written render function, 5827 // we need to delete the `slots._` flag if necessary to make subsequent updates reliable, 5828 // i.e. let the `renderSlot` create the bailed Fragment 5829 if (!optimized && type === 1 /* SlotFlags.STABLE */) { 5830 delete slots._; 5831 } 5832 } 5833 } 5834 else { 5835 needDeletionCheck = !children.$stable; 5836 normalizeObjectSlots(children, slots); 5837 }
5838 deletionComparisonTarget = children; 5839 } 5840 else if (children) { 5841 // non slot object children (direct value) passed to a component 5842 normalizeVNodeSlots(instance, children); 5843 deletionComparisonTarget = { default: 1 }; 5844 } 5845 // delete stale slots 5846 if (needDeletionCheck) { 5847 for (const key in slots) { 5848 if (!isInternalKey(key) && !(key in deletionComparisonTarget)) { 5849 delete slots[key]; 5850 } 5851 } 5852 } 5853 }; 5854 5855 function createAppContext() { 5856 return { 5857 app: null, 5858 config: { 5859 isNativeTag: NO, 5860 performance: false, 5861 globalProperties: {}, 5862 optionMergeStrategies: {}, 5863 errorHandler: undefined, 5864 warnHandler: undefined, 5865 compilerOptions: {} 5866 }, 5867 mixins: [], 5868 components: {}, 5869 directives: {}, 5870 provides: Object.create(null), 5871 optionsCache: new WeakMap(), 5872 propsCache: new WeakMap(), 5873 emitsCache: new WeakMap() 5874 }; 5875 } 5876 let uid = 0; 5877 function createAppAPI(render, hydrate) { 5878 return function createApp(rootComponent, rootProps = null) { 5879 if (!isFunction(rootComponent)) { 5880 rootComponent = Object.assign({}, rootComponent); 5881 } 5882 if (rootProps != null && !isObject(rootProps)) { 5883 warn$1(`root props passed to app.mount() must be an object.`); 5884 rootProps = null; 5885 } 5886 const context = createAppContext(); 5887 const installedPlugins = new Set(); 5888 let isMounted = false; 5889 const app = (context.app = { 5890 _uid: uid++, 5891 _component: rootComponent, 5892 _props: rootProps, 5893 _container: null, 5894 _context: context, 5895 _instance: null, 5896 version, 5897 get config() { 5898 return context.config; 5899 }, 5900 set config(v) { 5901 { 5902 warn$1(`app.config cannot be replaced. Modify individual options instead.`); 5903 } 5904 }, 5905 use(plugin, ...options) { 5906 if (installedPlugins.has(plugin)) { 5907 warn$1(`Plugin has already been applied to target app.`); 5908 } 5909 else if (plugin && isFunction(plugin.install)) { 5910 installedPlugins.add(plugin); 5911 plugin.install(app, ...options); 5912 } 5913 else if (isFunction(plugin)) { 5914 installedPlugins.add(plugin); 5915 plugin(app, ...options); 5916 } 5917 else { 5918 warn$1(`A plugin must either be a function or an object with an "install" ` + 5919 `function.`); 5920 } 5921 return app; 5922 }, 5923 mixin(mixin) { 5924 { 5925 if (!context.mixins.includes(mixin)) { 5926 context.mixins.push(mixin); 5927 } 5928 else { 5929 warn$1('Mixin has already been applied to target app' + 5930 (mixin.name ? `: ${mixin.name}` : '')); 5931 } 5932 } 5933 return app; 5934 }, 5935 component(name, component) { 5936 { 5937 validateComponentName(name, context.config); 5938 } 5939 if (!component) { 5940 return context.components[name]; 5941 } 5942 if (context.components[name]) { 5943 warn$1(`Component "${name}" has already been registered in target app.`); 5944 } 5945 context.components[name] = component; 5946 return app; 5947 }, 5948 directive(name, directive) { 5949 { 5950 validateDirectiveName(name); 5951 } 5952 if (!directive) { 5953 return context.directives[name]; 5954 } 5955 if (context.directives[name]) { 5956 warn$1(`Directive "${name}" has already been registered in target app.`); 5957 } 5958 context.directives[name] = directive; 5959 return app; 5960 }, 5961 mount(rootContainer, isHydrate, isSVG) { 5962 if (!isMounted) { 5963 // #5571 5964 if (rootContainer.__vue_app__) { 5965 warn$1(`There is already an app instance mounted on the host container.\n` + 5966 ` If you want to mount another app on the same host container,` + 5967 ` you need to unmount the previous app by calling \`app.unmount()\` first.`); 5968 } 5969 const vnode = createVNode(rootComponent, rootProps); 5970 // store app context on the root VNode. 5971 // this will be set on the root instance on initial mount. 5972 vnode.appContext = context; 5973 // HMR root reload 5974 { 5975 context.reload = () => { 5976 render(cloneVNode(vnode), rootContainer, isSVG); 5977 }; 5978 } 5979 if (isHydrate && hydrate) { 5980 hydrate(vnode, rootContainer); 5981 } 5982 else { 5983 render(vnode, rootContainer, isSVG); 5984 } 5985 isMounted = true; 5986 app._container = rootContainer; 5987 rootContainer.__vue_app__ = app; 5988 { 5989 app._instance = vnode.component; 5990 devtoolsInitApp(app, version); 5991 } 5992 return getExposeProxy(vnode.component) || vnode.component.proxy; 5993 } 5994 else { 5995 warn$1(`App has already been mounted.\n` + 5996 `If you want to remount the same app, move your app creation logic ` + 5997 `into a factory function and create fresh app instances for each ` + 5998 `mount - e.g. \`const createMyApp = () => createApp(App)\``); 5999 } 6000 }, 6001 unmount() { 6002 if (isMounted) { 6003 render(null, app._container); 6004 { 6005 app._instance = null; 6006 devtoolsUnmountApp(app); 6007 } 6008 delete app._container.__vue_app__; 6009 } 6010 else { 6011 warn$1(`Cannot unmount an app that is not mounted.`); 6012 } 6013 }, 6014 provide(key, value) { 6015 if (key in context.provides) { 6016 warn$1(`App already provides property with key "${String(key)}". ` + 6017 `It will be overwritten with the new value.`); 6018 } 6019 context.provides[key] = value; 6020 return app; 6021 } 6022 }); 6023 return app; 6024 }; 6025 } 6026 6027 /** 6028 * Function for handling a template ref 6029 */ 6030 function setRef(rawRef, oldRawRef, parentSuspense, vnode, isUnmount = false) { 6031 if (isArray(rawRef)) { 6032 rawRef.forEach((r, i) => setRef(r, oldRawRef && (isArray(oldRawRef) ? oldRawRef[i] : oldRawRef), parentSuspense, vnode, isUnmount)); 6033 return; 6034 } 6035 if (isAsyncWrapper(vnode) && !isUnmount) { 6036 // when mounting async components, nothing needs to be done, 6037 // because the template ref is forwarded to inner component 6038 return; 6039 } 6040 const refValue = vnode.shapeFlag & 4 /* ShapeFlags.STATEFUL_COMPONENT */ 6041 ? getExposeProxy(vnode.component) || vnode.component.proxy 6042 : vnode.el; 6043 const value = isUnmount ? null : refValue; 6044 const { i: owner, r: ref } = rawRef; 6045 if (!owner) { 6046 warn$1(`Missing ref owner context. ref cannot be used on hoisted vnodes. ` + 6047 `A vnode with ref must be created inside the render function.`); 6048 return; 6049 } 6050 const oldRef = oldRawRef && oldRawRef.r; 6051 const refs = owner.refs === EMPTY_OBJ ? (owner.refs = {}) : owner.refs; 6052 const setupState = owner.setupState; 6053 // dynamic ref changed. unset old ref
6054 if (oldRef != null && oldRef !== ref) { 6055 if (isString(oldRef)) { 6056 refs[oldRef] = null; 6057 if (hasOwn(setupState, oldRef)) { 6058 setupState[oldRef] = null; 6059 } 6060 } 6061 else if (isRef(oldRef)) { 6062 oldRef.value = null; 6063 } 6064 } 6065 if (isFunction(ref)) { 6066 callWithErrorHandling(ref, owner, 12 /* ErrorCodes.FUNCTION_REF */, [value, refs]); 6067 } 6068 else { 6069 const _isString = isString(ref); 6070 const _isRef = isRef(ref); 6071 if (_isString || _isRef) { 6072 const doSet = () => { 6073 if (rawRef.f) { 6074 const existing = _isString 6075 ? hasOwn(setupState, ref) 6076 ? setupState[ref] 6077 : refs[ref] 6078 : ref.value; 6079 if (isUnmount) { 6080 isArray(existing) && remove(existing, refValue); 6081 } 6082 else { 6083 if (!isArray(existing)) { 6084 if (_isString) { 6085 refs[ref] = [refValue]; 6086 if (hasOwn(setupState, ref)) { 6087 setupState[ref] = refs[ref]; 6088 } 6089 } 6090 else { 6091 ref.value = [refValue]; 6092 if (rawRef.k) 6093 refs[rawRef.k] = ref.value; 6094 } 6095 } 6096 else if (!existing.includes(refValue)) { 6097 existing.push(refValue); 6098 } 6099 } 6100 } 6101 else if (_isString) { 6102 refs[ref] = value; 6103 if (hasOwn(setupState, ref)) { 6104 setupState[ref] = value; 6105 } 6106 } 6107 else if (_isRef) { 6108 ref.value = value; 6109 if (rawRef.k) 6110 refs[rawRef.k] = value; 6111 } 6112 else { 6113 warn$1('Invalid template ref type:', ref, `(${typeof ref})`); 6114 } 6115 }; 6116 if (value) { 6117 doSet.id = -1; 6118 queuePostRenderEffect(doSet, parentSuspense); 6119 } 6120 else { 6121 doSet(); 6122 } 6123 } 6124 else { 6125 warn$1('Invalid template ref type:', ref, `(${typeof ref})`); 6126 } 6127 } 6128 } 6129 6130 let hasMismatch = false; 6131 const isSVGContainer = (container) => /svg/.test(container.namespaceURI) && container.tagName !== 'foreignObject'; 6132 const isComment = (node) => node.nodeType === 8 /* DOMNodeTypes.COMMENT */; 6133 // Note: hydration is DOM-specific 6134 // But we have to place it in core due to tight coupling with core - splitting 6135 // it out creates a ton of unnecessary complexity. 6136 // Hydration also depends on some renderer internal logic which needs to be 6137 // passed in via arguments. 6138 function createHydrationFunctions(rendererInternals) { 6139 const { mt: mountComponent, p: patch, o: { patchProp, createText, nextSibling, parentNode, remove, insert, createComment } } = rendererInternals; 6140 const hydrate = (vnode, container) => { 6141 if (!container.hasChildNodes()) { 6142 warn$1(`Attempting to hydrate existing markup but container is empty. ` + 6143 `Performing full mount instead.`); 6144 patch(null, vnode, container); 6145 flushPostFlushCbs(); 6146 container._vnode = vnode; 6147 return; 6148 } 6149 hasMismatch = false; 6150 hydrateNode(container.firstChild, vnode, null, null, null); 6151 flushPostFlushCbs(); 6152 container._vnode = vnode; 6153 if (hasMismatch && !false) { 6154 // this error should show up in production 6155 console.error(`Hydration completed but contains mismatches.`); 6156 } 6157 }; 6158 const hydrateNode = (node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized = false) => { 6159 const isFragmentStart = isComment(node) && node.data === '['; 6160 const onMismatch = () => handleMismatch(node, vnode, parentComponent, parentSuspense, slotScopeIds, isFragmentStart); 6161 const { type, ref, shapeFlag, patchFlag } = vnode; 6162 let domType = node.nodeType; 6163 vnode.el = node; 6164 if (patchFlag === -2 /* PatchFlags.BAIL */) { 6165 optimized = false;
6166 vnode.dynamicChildren = null; 6167 } 6168 let nextNode = null; 6169 switch (type) { 6170 case Text: 6171 if (domType !== 3 /* DOMNodeTypes.TEXT */) { 6172 // #5728 empty text node inside a slot can cause hydration failure 6173 // because the server rendered HTML won't contain a text node 6174 if (vnode.children === '') { 6175 insert((vnode.el = createText('')), parentNode(node), node); 6176 nextNode = node; 6177 } 6178 else { 6179 nextNode = onMismatch(); 6180 } 6181 } 6182 else { 6183 if (node.data !== vnode.children) { 6184 hasMismatch = true; 6185 warn$1(`Hydration text mismatch:` + 6186 `\n- Client: ${JSON.stringify(node.data)}` + 6187 `\n- Server: ${JSON.stringify(vnode.children)}`); 6188 node.data = vnode.children; 6189 } 6190 nextNode = nextSibling(node); 6191 } 6192 break; 6193 case Comment: 6194 if (domType !== 8 /* DOMNodeTypes.COMMENT */ || isFragmentStart) { 6195 nextNode = onMismatch(); 6196 } 6197 else { 6198 nextNode = nextSibling(node); 6199 } 6200 break; 6201 case Static: 6202 if (isFragmentStart) { 6203 // entire template is static but SSRed as a fragment 6204 node = nextSibling(node); 6205 domType = node.nodeType; 6206 } 6207 if (domType === 1 /* DOMNodeTypes.ELEMENT */ || domType === 3 /* DOMNodeTypes.TEXT */) { 6208 // determine anchor, adopt content 6209 nextNode = node; 6210 // if the static vnode has its content stripped during build, 6211 // adopt it from the server-rendered HTML. 6212 const needToAdoptContent = !vnode.children.length; 6213 for (let i = 0; i < vnode.staticCount; i++) { 6214 if (needToAdoptContent) 6215 vnode.children += 6216 nextNode.nodeType === 1 /* DOMNodeTypes.ELEMENT */ 6217 ? nextNode.outerHTML 6218 : nextNode.data; 6219 if (i === vnode.staticCount - 1) { 6220 vnode.anchor = nextNode; 6221 } 6222 nextNode = nextSibling(nextNode); 6223 } 6224 return isFragmentStart ? nextSibling(nextNode) : nextNode; 6225 } 6226 else { 6227 onMismatch(); 6228 } 6229 break; 6230 case Fragment: 6231 if (!isFragmentStart) { 6232 nextNode = onMismatch(); 6233 } 6234 else { 6235 nextNode = hydrateFragment(node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized); 6236 } 6237 break; 6238 default: 6239 if (shapeFlag & 1 /* ShapeFlags.ELEMENT */) { 6240 if (domType !== 1 /* DOMNodeTypes.ELEMENT */ || 6241 vnode.type.toLowerCase() !== 6242 node.tagName.toLowerCase()) { 6243 nextNode = onMismatch(); 6244 } 6245 else { 6246 nextNode = hydrateElement(node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized); 6247 } 6248 } 6249 else if (shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 6250 // when setting up the render effect, if the initial vnode already 6251 // has .el set, the component will perform hydration instead of mount 6252 // on its sub-tree. 6253 vnode.slotScopeIds = slotScopeIds; 6254 const container = parentNode(node); 6255 mountComponent(vnode, container, null, parentComponent, parentSuspense, isSVGContainer(container), optimized); 6256 // component may be async, so in the case of fragments we cannot rely 6257 // on component's rendered output to determine the end of the fragment 6258 // instead, we do a lookahead to find the end anchor node. 6259 nextNode = isFragmentStart 6260 ? locateClosingAsyncAnchor(node) 6261 : nextSibling(node); 6262 // #4293 teleport as component root 6263 if (nextNode && 6264 isComment(nextNode) && 6265 nextNode.data === 'teleport end') { 6266 nextNode = nextSibling(nextNode); 6267 } 6268 // #3787 6269 // if component is async, it may get moved / unmounted before its 6270 // inner component is loaded, so we need to give it a placeholder 6271 // vnode that matches its adopted DOM. 6272 if (isAsyncWrapper(vnode)) { 6273 let subTree; 6274 if (isFragmentStart) { 6275 subTree = createVNode(Fragment); 6276 subTree.anchor = nextNode 6277 ? nextNode.previousSibling 6278 : container.lastChild; 6279 } 6280 else { 6281 subTree = 6282 node.nodeType === 3 ? createTextVNode('') : createVNode('div'); 6283 } 6284 subTree.el = node; 6285 vnode.component.subTree = subTree; 6286 } 6287 } 6288 else if (shapeFlag & 64 /* ShapeFlags.TELEPORT */) { 6289 if (domType !== 8 /* DOMNodeTypes.COMMENT */) { 6290 nextNode = onMismatch(); 6291 } 6292 else { 6293 nextNode = vnode.type.hydrate(node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized, rendererInternals, hydrateChildren); 6294 } 6295 } 6296 else if (shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 6297 nextNode = vnode.type.hydrate(node, vnode, parentComponent, parentSuspense, isSVGContainer(parentNode(node)), slotScopeIds, optimized, rendererInternals, hydrateNode); 6298 } 6299 else { 6300 warn$1('Invalid HostVNode type:', type, `(${typeof type})`); 6301 } 6302 } 6303 if (ref != null) { 6304 setRef(ref, null, parentSuspense, vnode); 6305 } 6306 return nextNode; 6307 }; 6308 const hydrateElement = (el, vnode, parentComponent, parentSuspense, slotScopeIds, optimized) => { 6309 optimized = optimized || !!vnode.dynamicChildren; 6310 const { type, props, patchFlag, shapeFlag, dirs } = vnode; 6311 // #4006 for form elements with non-string v-model value bindings 6312 // e.g. <option :value="obj">, <input type="checkbox" :true-value="1"> 6313 const forcePatchValue = (type === 'input' && dirs) || type === 'option';
6314 // skip props & children if this is hoisted static nodes 6315 // #5405 in dev, always hydrate children for HMR 6316 { 6317 if (dirs) { 6318 invokeDirectiveHook(vnode, null, parentComponent, 'created'); 6319 } 6320 // props 6321 if (props) { 6322 if (forcePatchValue || 6323 !optimized || 6324 patchFlag & (16 /* PatchFlags.FULL_PROPS */ | 32 /* PatchFlags.HYDRATE_EVENTS */)) { 6325 for (const key in props) { 6326 if ((forcePatchValue && key.endsWith('value')) || 6327 (isOn(key) && !isReservedProp(key))) { 6328 patchProp(el, key, null, props[key], false, undefined, parentComponent); 6329 } 6330 } 6331 } 6332 else if (props.onClick) { 6333 // Fast path for click listeners (which is most often) to avoid 6334 // iterating through props. 6335 patchProp(el, 'onClick', null, props.onClick, false, undefined, parentComponent); 6336 } 6337 } 6338 // vnode / directive hooks 6339 let vnodeHooks; 6340 if ((vnodeHooks = props && props.onVnodeBeforeMount)) { 6341 invokeVNodeHook(vnodeHooks, parentComponent, vnode); 6342 } 6343 if (dirs) { 6344 invokeDirectiveHook(vnode, null, parentComponent, 'beforeMount'); 6345 } 6346 if ((vnodeHooks = props && props.onVnodeMounted) || dirs) { 6347 queueEffectWithSuspense(() => { 6348 vnodeHooks && invokeVNodeHook(vnodeHooks, parentComponent, vnode); 6349 dirs && invokeDirectiveHook(vnode, null, parentComponent, 'mounted'); 6350 }, parentSuspense); 6351 } 6352 // children 6353 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */ && 6354 // skip if element has innerHTML / textContent 6355 !(props && (props.innerHTML || props.textContent))) { 6356 let next = hydrateChildren(el.firstChild, vnode, el, parentComponent, parentSuspense, slotScopeIds, optimized); 6357 let hasWarned = false; 6358 while (next) { 6359 hasMismatch = true; 6360 if (!hasWarned) { 6361 warn$1(`Hydration children mismatch in <${vnode.type}>: ` + 6362 `server rendered element contains more child nodes than client vdom.`); 6363 hasWarned = true; 6364 } 6365 // The SSRed DOM contains more nodes than it should. Remove them. 6366 const cur = next; 6367 next = next.nextSibling; 6368 remove(cur); 6369 } 6370 } 6371 else if (shapeFlag & 8 /* ShapeFlags.TEXT_CHILDREN */) { 6372 if (el.textContent !== vnode.children) { 6373 hasMismatch = true; 6374 warn$1(`Hydration text content mismatch in <${vnode.type}>:\n` + 6375 `- Client: ${el.textContent}\n` + 6376 `- Server: ${vnode.children}`); 6377 el.textContent = vnode.children; 6378 } 6379 } 6380 } 6381 return el.nextSibling; 6382 }; 6383 const hydrateChildren = (node, parentVNode, container, parentComponent, parentSuspense, slotScopeIds, optimized) => { 6384 optimized = optimized || !!parentVNode.dynamicChildren; 6385 const children = parentVNode.children; 6386 const l = children.length; 6387 let hasWarned = false; 6388 for (let i = 0; i < l; i++) { 6389 const vnode = optimized 6390 ? children[i] 6391 : (children[i] = normalizeVNode(children[i])); 6392 if (node) { 6393 node = hydrateNode(node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized); 6394 } 6395 else if (vnode.type === Text && !vnode.children) { 6396 continue; 6397 } 6398 else { 6399 hasMismatch = true; 6400 if (!hasWarned) { 6401 warn$1(`Hydration children mismatch in <${container.tagName.toLowerCase()}>: ` + 6402 `server rendered element contains fewer child nodes than client vdom.`); 6403 hasWarned = true; 6404 } 6405 // the SSRed DOM didn't contain enough nodes. Mount the missing ones. 6406 patch(null, vnode, container, null, parentComponent, parentSuspense, isSVGContainer(container), slotScopeIds); 6407 } 6408 } 6409 return node; 6410 }; 6411 const hydrateFragment = (node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized) => { 6412 const { slotScopeIds: fragmentSlotScopeIds } = vnode; 6413 if (fragmentSlotScopeIds) { 6414 slotScopeIds = slotScopeIds 6415 ? slotScopeIds.concat(fragmentSlotScopeIds) 6416 : fragmentSlotScopeIds; 6417 } 6418 const container = parentNode(node); 6419 const next = hydrateChildren(nextSibling(node), vnode, container, parentComponent, parentSuspense, slotScopeIds, optimized); 6420 if (next && isComment(next) && next.data === ']') { 6421 return nextSibling((vnode.anchor = next)); 6422 } 6423 else { 6424 // fragment didn't hydrate successfully, since we didn't get a end anchor 6425 // back. This should have led to node/children mismatch warnings. 6426 hasMismatch = true;
6427 // since the anchor is missing, we need to create one and insert it 6428 insert((vnode.anchor = createComment(`]`)), container, next); 6429 return next; 6430 } 6431 }; 6432 const handleMismatch = (node, vnode, parentComponent, parentSuspense, slotScopeIds, isFragment) => { 6433 hasMismatch = true; 6434 warn$1(`Hydration node mismatch:\n- Client vnode:`, vnode.type, `\n- Server rendered DOM:`, node, node.nodeType === 3 /* DOMNodeTypes.TEXT */ 6435 ? `(text)` 6436 : isComment(node) && node.data === '[' 6437 ? `(start of fragment)` 6438 : ``); 6439 vnode.el = null; 6440 if (isFragment) { 6441 // remove excessive fragment nodes 6442 const end = locateClosingAsyncAnchor(node); 6443 while (true) { 6444 const next = nextSibling(node); 6445 if (next && next !== end) { 6446 remove(next); 6447 } 6448 else { 6449 break; 6450 } 6451 } 6452 } 6453 const next = nextSibling(node); 6454 const container = parentNode(node); 6455 remove(node); 6456 patch(null, vnode, container, next, parentComponent, parentSuspense, isSVGContainer(container), slotScopeIds); 6457 return next; 6458 }; 6459 const locateClosingAsyncAnchor = (node) => { 6460 let match = 0; 6461 while (node) { 6462 node = nextSibling(node); 6463 if (node && isComment(node)) { 6464 if (node.data === '[') 6465 match++; 6466 if (node.data === ']') { 6467 if (match === 0) { 6468 return nextSibling(node); 6469 } 6470 else { 6471 match--; 6472 } 6473 } 6474 } 6475 } 6476 return node; 6477 }; 6478 return [hydrate, hydrateNode]; 6479 } 6480 6481 /* eslint-disable no-restricted-globals */ 6482 let supported; 6483 let perf; 6484 function startMeasure(instance, type) { 6485 if (instance.appContext.config.performance && isSupported()) { 6486 perf.mark(`vue-${type}-${instance.uid}`); 6487 } 6488 { 6489 devtoolsPerfStart(instance, type, isSupported() ? perf.now() : Date.now()); 6490 } 6491 } 6492 function endMeasure(instance, type) { 6493 if (instance.appContext.config.performance && isSupported()) { 6494 const startTag = `vue-${type}-${instance.uid}`; 6495 const endTag = startTag + `:end`; 6496 perf.mark(endTag); 6497 perf.measure(`<${formatComponentName(instance, instance.type)}> ${type}`, startTag, endTag); 6498 perf.clearMarks(startTag); 6499 perf.clearMarks(endTag); 6500 } 6501 { 6502 devtoolsPerfEnd(instance, type, isSupported() ? perf.now() : Date.now()); 6503 } 6504 } 6505 function isSupported() { 6506 if (supported !== undefined) { 6507 return supported; 6508 } 6509 if (typeof window !== 'undefined' && window.performance) { 6510 supported = true; 6511 perf = window.performance; 6512 } 6513 else { 6514 supported = false; 6515 } 6516 return supported; 6517 } 6518 6519 const queuePostRenderEffect = queueEffectWithSuspense 6520 ; 6521 /** 6522 * The createRenderer function accepts two generic arguments: 6523 * HostNode and HostElement, corresponding to Node and Element types in the 6524 * host environment. For example, for runtime-dom, HostNode would be the DOM 6525 * `Node` interface and HostElement would be the DOM `Element` interface. 6526 * 6527 * Custom renderers can pass in the platform specific types like this: 6528 * 6529 * ``` js 6530 * const { render, createApp } = createRenderer<Node, Element>({ 6531 * patchProp, 6532 * ...nodeOps 6533 * }) 6534 * ``` 6535 */ 6536 function createRenderer(options) { 6537 return baseCreateRenderer(options); 6538 } 6539 // Separate API for creating hydration-enabled renderer. 6540 // Hydration logic is only used when calling this function, making it 6541 // tree-shakable. 6542 function createHydrationRenderer(options) { 6543 return baseCreateRenderer(options, createHydrationFunctions); 6544 } 6545 // implementation 6546 function baseCreateRenderer(options, createHydrationFns) { 6547 const target = getGlobalThis(); 6548 target.__VUE__ = true; 6549 { 6550 setDevtoolsHook(target.__VUE_DEVTOOLS_GLOBAL_HOOK__, target); 6551 } 6552 const { insert: hostInsert, remove: hostRemove, patchProp: hostPatchProp, createElement: hostCreateElement, createText: hostCreateText, createComment: hostCreateComment, setText: hostSetText, setElementText: hostSetElementText, parentNode: hostParentNode, nextSibling: hostNextSibling, setScopeId: hostSetScopeId =
6552NOOP, insertStaticContent: hostInsertStaticContent } = options; 6553 // Note: functions inside this closure should use `const xxx = () => {}` 6554 // style in order to prevent being inlined by minifiers. 6555 const patch = (n1, n2, container, anchor = null, parentComponent = null, parentSuspense = null, isSVG = false, slotScopeIds = null, optimized = isHmrUpdating ? false : !!n2.dynamicChildren) => { 6556 if (n1 === n2) { 6557 return; 6558 } 6559 // patching & not same type, unmount old tree 6560 if (n1 && !isSameVNodeType(n1, n2)) { 6561 anchor = getNextHostNode(n1); 6562 unmount(n1, parentComponent, parentSuspense, true); 6563 n1 = null; 6564 } 6565 if (n2.patchFlag === -2 /* PatchFlags.BAIL */) { 6566 optimized = false; 6567 n2.dynamicChildren = null; 6568 } 6569 const { type, ref, shapeFlag } = n2; 6570 switch (type) { 6571 case Text: 6572 processText(n1, n2, container, anchor); 6573 break; 6574 case Comment: 6575 processCommentNode(n1, n2, container, anchor); 6576 break; 6577 case Static: 6578 if (n1 == null) { 6579 mountStaticNode(n2, container, anchor, isSVG); 6580 } 6581 else { 6582 patchStaticNode(n1, n2, container, isSVG); 6583 } 6584 break; 6585 case Fragment: 6586 processFragment(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6587 break; 6588 default: 6589 if (shapeFlag & 1 /* ShapeFlags.ELEMENT */) { 6590 processElement(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6591 } 6592 else if (shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 6593 processComponent(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6594 } 6595 else if (shapeFlag & 64 /* ShapeFlags.TELEPORT */) { 6596 type.process(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, internals); 6597 } 6598 else if (shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 6599 type.process(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, internals); 6600 } 6601 else { 6602 warn$1('Invalid VNode type:', type, `(${typeof type})`); 6603 } 6604 } 6605 // set ref 6606 if (ref != null && parentComponent) { 6607 setRef(ref, n1 && n1.ref, parentSuspense, n2 || n1, !n2); 6608 } 6609 }; 6610 const processText = (n1, n2, container, anchor) => { 6611 if (n1 == null) { 6612 hostInsert((n2.el = hostCreateText(n2.children)), container, anchor); 6613 } 6614 else { 6615 const el = (n2.el = n1.el); 6616 if (n2.children !== n1.children) { 6617 hostSetText(el, n2.children); 6618 } 6619 } 6620 }; 6621 const processCommentNode = (n1, n2, container, anchor) => { 6622 if (n1 == null) { 6623 hostInsert((n2.el = hostCreateComment(n2.children || '')), container, anchor); 6624 } 6625 else { 6626 // there's no support for dynamic comments 6627 n2.el = n1.el; 6628 } 6629 }; 6630 const mountStaticNode = (n2, container, anchor, isSVG) => { 6631 [n2.el, n2.anchor] = hostInsertStaticContent(n2.children, container, anchor, isSVG, n2.el, n2.anchor); 6632 }; 6633 /** 6634 * Dev / HMR only 6635 */ 6636 const patchStaticNode = (n1, n2, container, isSVG) => { 6637 // static nodes are only patched during dev for HMR 6638 if (n2.children !== n1.children) { 6639 const anchor = hostNextSibling(n1.anchor); 6640 // remove existing 6641 removeStaticNode(n1); 6642 [n2.el, n2.anchor] = hostInsertStaticContent(n2.children, container, anchor, isSVG); 6643 } 6644 else { 6645 n2.el = n1.el; 6646 n2.anchor = n1.anchor; 6647 } 6648 }; 6649 const moveStaticNode = ({ el, anchor }, container, nextSibling) => { 6650 let next; 6651 while (el && el !== anchor) { 6652 next = hostNextSibling(el); 6653 hostInsert(el, container, nextSibling); 6654 el = next; 6655 } 6656 hostInsert(anchor, container, nextSibling); 6657 }; 6658 const removeStaticNode = ({ el, anchor }) => { 6659 let next; 6660 while (el && el !== anchor) { 6661 next = hostNextSibling(el); 6662 hostRemove(el); 6663 el = next; 6664 } 6665 hostRemove(anchor); 6666 }; 6667 const processElement = (n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 6668 isSVG = isSVG || n2.type === 'svg'; 6669 if (n1 == null) { 6670 mountElement(n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6671 } 6672 else { 6673 patchElement(n1, n2, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6674 } 6675 }; 6676 const mountElement = (vnode, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 6677 let el; 6678 let vnodeHook; 6679 const { type, props, shapeFlag, transition, dirs } = vnode; 6680 el = vnode.el = hostCreateElement(vnode.type, isSVG, props && props.is, props); 6681 // mount children first, since some props may rely on child content 6682 // being already rendered, e.g. `<select value>` 6683 if (shapeFlag & 8 /* ShapeFlags.TEXT_CHILDREN */) { 6684 hostSetElementText(el, vnode.children); 6685 } 6686 else if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 6687 mountChildren(vnode.children, el, null, parentComponent, parentSuspense, isSVG && type !== 'foreignObject', slotScopeIds, optimized); 6688 } 6689 if (dirs) { 6690 invokeDirectiveHook(vnode, null, parentComponent, 'created'); 6691 } 6692 // props 6693 if (props) { 6694 for (const key in props) { 6695 if (key !== 'value' && !isReservedProp(key)) { 6696 hostPatchProp(el, key, null, props[key], isSVG, vnode.children, parentComponent, parentSuspense, unmountChildren); 6697 } 6698 } 6699 /** 6700 * Special case for setting value on DOM elements: 6701 * - it can be order-sensitive (e.g. should be set *after* min/max, #2325, #4024) 6702 * - it needs to be forced (#1471) 6703 * #2353 proposes adding another renderer option to configure this, but
6704 * the properties affects are so finite it is worth special casing it 6705 * here to reduce the complexity. (Special casing it also should not 6706 * affect non-DOM renderers) 6707 */ 6708 if ('value' in props) { 6709 hostPatchProp(el, 'value', null, props.value); 6710 } 6711 if ((vnodeHook = props.onVnodeBeforeMount)) { 6712 invokeVNodeHook(vnodeHook, parentComponent, vnode); 6713 } 6714 } 6715 // scopeId 6716 setScopeId(el, vnode, vnode.scopeId, slotScopeIds, parentComponent); 6717 { 6718 Object.defineProperty(el, '__vnode', { 6719 value: vnode, 6720 enumerable: false 6721 }); 6722 Object.defineProperty(el, '__vueParentComponent', { 6723 value: parentComponent, 6724 enumerable: false 6725 }); 6726 } 6727 if (dirs) { 6728 invokeDirectiveHook(vnode, null, parentComponent, 'beforeMount'); 6729 } 6730 // #1583 For inside suspense + suspense not resolved case, enter hook should call when suspense resolved 6731 // #1689 For inside suspense + suspense resolved case, just call it 6732 const needCallTransitionHooks = (!parentSuspense || (parentSuspense && !parentSuspense.pendingBranch)) && 6733 transition && 6734 !transition.persisted; 6735 if (needCallTransitionHooks) { 6736 transition.beforeEnter(el); 6737 } 6738 hostInsert(el, container, anchor); 6739 if ((vnodeHook = props && props.onVnodeMounted) || 6740 needCallTransitionHooks || 6741 dirs) { 6742 queuePostRenderEffect(() => { 6743 vnodeHook && invokeVNodeHook(vnodeHook, parentComponent, vnode); 6744 needCallTransitionHooks && transition.enter(el); 6745 dirs && invokeDirectiveHook(vnode, null, parentComponent, 'mounted'); 6746 }, parentSuspense); 6747 } 6748 }; 6749 const setScopeId = (el, vnode, scopeId, slotScopeIds, parentComponent) => { 6750 if (scopeId) { 6751 hostSetScopeId(el, scopeId); 6752 } 6753 if (slotScopeIds) { 6754 for (let i = 0; i < slotScopeIds.length; i++) { 6755 hostSetScopeId(el, slotScopeIds[i]); 6756 } 6757 } 6758 if (parentComponent) { 6759 let subTree = parentComponent.subTree; 6760 if (subTree.patchFlag > 0 && 6761 subTree.patchFlag & 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */) { 6762 subTree = 6763 filterSingleRoot(subTree.children) || subTree; 6764 } 6765 if (vnode === subTree) { 6766 const parentVNode = parentComponent.vnode; 6767 setScopeId(el, parentVNode, parentVNode.scopeId, parentVNode.slotScopeIds, parentComponent.parent); 6768 } 6769 } 6770 }; 6771 const mountChildren = (children, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, start = 0) => { 6772 for (let i = start; i < children.length; i++) { 6773 const child = (children[i] = optimized 6774 ? cloneIfMounted(children[i]) 6775 : normalizeVNode(children[i])); 6776 patch(null, child, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6777 } 6778 }; 6779 const patchElement = (n1, n2, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 6780 const el = (n2.el = n1.el); 6781 let { patchFlag, dynamicChildren, dirs } = n2; 6782 // #1426 take the old vnode's patch flag into account since user may clone a 6783 // compiler-generated vnode, which de-opts to FULL_PROPS 6784 patchFlag |= n1.patchFlag & 16 /* PatchFlags.FULL_PROPS */; 6785 const oldProps = n1.props || EMPTY_OBJ; 6786 const newProps = n2.props || EMPTY_OBJ; 6787 let vnodeHook; 6788 // disable recurse in beforeUpdate hooks 6789 parentComponent && toggleRecurse(parentComponent, false); 6790 if ((vnodeHook = newProps.onVnodeBeforeUpdate)) { 6791 invokeVNodeHook(vnodeHook, parentComponent, n2, n1); 6792 } 6793 if (dirs) { 6794 invokeDirectiveHook(n2, n1, parentComponent, 'beforeUpdate'); 6795 } 6796 parentComponent && toggleRecurse(parentComponent, true); 6797 if (isHmrUpdating) { 6798 // HMR updated, force full diff 6799 patchFlag = 0; 6800 optimized = false;
vendor: 5,096 bytes, lines 6801-6891
6801 dynamicChildren = null; 6802 } 6803 const areChildrenSVG = isSVG && n2.type !== 'foreignObject'; 6804 if (dynamicChildren) { 6805 patchBlockChildren(n1.dynamicChildren, dynamicChildren, el, parentComponent, parentSuspense, areChildrenSVG, slotScopeIds); 6806 if (parentComponent && parentComponent.type.__hmrId) { 6807 traverseStaticChildren(n1, n2); 6808 } 6809 } 6810 else if (!optimized) { 6811 // full diff 6812 patchChildren(n1, n2, el, null, parentComponent, parentSuspense, areChildrenSVG, slotScopeIds, false); 6813 } 6814 if (patchFlag > 0) { 6815 // the presence of a patchFlag means this element's render code was 6816 // generated by the compiler and can take the fast path. 6817 // in this path old node and new node are guaranteed to have the same shape 6818 // (i.e. at the exact same position in the source template) 6819 if (patchFlag & 16 /* PatchFlags.FULL_PROPS */) { 6820 // element props contain dynamic keys, full diff needed 6821 patchProps(el, n2, oldProps, newProps, parentComponent, parentSuspense, isSVG); 6822 } 6823 else { 6824 // class 6825 // this flag is matched when the element has dynamic class bindings. 6826 if (patchFlag & 2 /* PatchFlags.CLASS */) { 6827 if (oldProps.class !== newProps.class) { 6828 hostPatchProp(el, 'class', null, newProps.class, isSVG); 6829 } 6830 } 6831 // style 6832 // this flag is matched when the element has dynamic style bindings 6833 if (patchFlag & 4 /* PatchFlags.STYLE */) { 6834 hostPatchProp(el, 'style', oldProps.style, newProps.style, isSVG); 6835 } 6836 // props 6837 // This flag is matched when the element has dynamic prop/attr bindings 6838 // other than class and style. The keys of dynamic prop/attrs are saved for 6839 // faster iteration. 6840 // Note dynamic keys like :[foo]="bar" will cause this optimization to 6841 // bail out and go through a full diff because we need to unset the old key 6842 if (patchFlag & 8 /* PatchFlags.PROPS */) { 6843 // if the flag is present then dynamicProps must be non-null 6844 const propsToUpdate = n2.dynamicProps; 6845 for (let i = 0; i < propsToUpdate.length; i++) { 6846 const key = propsToUpdate[i]; 6847 const prev = oldProps[key]; 6848 const next = newProps[key]; 6849 // #1471 force patch value 6850 if (next !== prev || key === 'value') { 6851 hostPatchProp(el, key, prev, next, isSVG, n1.children, parentComponent, parentSuspense, unmountChildren); 6852 } 6853 } 6854 } 6855 } 6856 // text 6857 // This flag is matched when the element has only dynamic text children. 6858 if (patchFlag & 1 /* PatchFlags.TEXT */) { 6859 if (n1.children !== n2.children) { 6860 hostSetElementText(el, n2.children); 6861 } 6862 } 6863 } 6864 else if (!optimized && dynamicChildren == null) { 6865 // unoptimized, full diff 6866 patchProps(el, n2, oldProps, newProps, parentComponent, parentSuspense, isSVG); 6867 } 6868 if ((vnodeHook = newProps.onVnodeUpdated) || dirs) { 6869 queuePostRenderEffect(() => { 6870 vnodeHook && invokeVNodeHook(vnodeHook, parentComponent, n2, n1); 6871 dirs && invokeDirectiveHook(n2, n1, parentComponent, 'updated'); 6872 }, parentSuspense); 6873 } 6874 }; 6875 // The fast path for blocks. 6876 const patchBlockChildren = (oldChildren, newChildren, fallbackContainer, parentComponent, parentSuspense, isSVG, slotScopeIds) => { 6877 for (let i = 0; i < newChildren.length; i++) { 6878 const oldVNode = oldChildren[i]; 6879 const newVNode = newChildren[i]; 6880 // Determine the container (parent element) for the patch. 6881 const container = 6882 // oldVNode may be an errored async setup() component inside Suspense 6883 // which will not have a mounted element 6884 oldVNode.el && 6885 // - In the case of a Fragment, we need to provide the actual parent 6886 // of the Fragment itself so it can move its children. 6887 (oldVNode.type === Fragment || 6888 // - In the case of different nodes, there is going to be a replacement 6889 // which also requires the correct parent container 6890 !isSameVNodeType(oldVNode, newVNode) || 6891 // - In the case of a component, it could contain anything.
6892 oldVNode.shapeFlag & (6 /* ShapeFlags.COMPONENT */ | 64 /* ShapeFlags.TELEPORT */)) 6893 ? hostParentNode(oldVNode.el) 6894 : // In other cases, the parent container is not actually used so we 6895 // just pass the block element here to avoid a DOM parentNode call. 6896 fallbackContainer; 6897 patch(oldVNode, newVNode, container, null, parentComponent, parentSuspense, isSVG, slotScopeIds, true); 6898 } 6899 }; 6900 const patchProps = (el, vnode, oldProps, newProps, parentComponent, parentSuspense, isSVG) => { 6901 if (oldProps !== newProps) { 6902 if (oldProps !== EMPTY_OBJ) { 6903 for (const key in oldProps) { 6904 if (!isReservedProp(key) && !(key in newProps)) { 6905 hostPatchProp(el, key, oldProps[key], null, isSVG, vnode.children, parentComponent, parentSuspense, unmountChildren); 6906 } 6907 } 6908 } 6909 for (const key in newProps) { 6910 // empty string is not valid prop 6911 if (isReservedProp(key)) 6912 continue; 6913 const next = newProps[key]; 6914 const prev = oldProps[key]; 6915 // defer patching value 6916 if (next !== prev && key !== 'value') { 6917 hostPatchProp(el, key, prev, next, isSVG, vnode.children, parentComponent, parentSuspense, unmountChildren); 6918 } 6919 } 6920 if ('value' in newProps) { 6921 hostPatchProp(el, 'value', oldProps.value, newProps.value); 6922 } 6923 } 6924 }; 6925 const processFragment = (n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 6926 const fragmentStartAnchor = (n2.el = n1 ? n1.el : hostCreateText('')); 6927 const fragmentEndAnchor = (n2.anchor = n1 ? n1.anchor : hostCreateText('')); 6928 let { patchFlag, dynamicChildren, slotScopeIds: fragmentSlotScopeIds } = n2; 6929 if (// #5523 dev root fragment may inherit directives 6930 (isHmrUpdating || patchFlag & 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */)) { 6931 // HMR updated / Dev root fragment (w/ comments), force full diff 6932 patchFlag = 0; 6933 optimized = false; 6934 dynamicChildren = null; 6935 } 6936 // check if this is a slot fragment with :slotted scope ids 6937 if (fragmentSlotScopeIds) { 6938 slotScopeIds = slotScopeIds 6939 ? slotScopeIds.concat(fragmentSlotScopeIds) 6940 : fragmentSlotScopeIds; 6941 } 6942 if (n1 == null) { 6943 hostInsert(fragmentStartAnchor, container, anchor); 6944 hostInsert(fragmentEndAnchor, container, anchor); 6945 // a fragment can only have array children 6946 // since they are either generated by the compiler, or implicitly created 6947 // from arrays. 6948 mountChildren(n2.children, container, fragmentEndAnchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6949 } 6950 else { 6951 if (patchFlag > 0 && 6952 patchFlag & 64 /* PatchFlags.STABLE_FRAGMENT */ && 6953 dynamicChildren && 6954 // #2715 the previous fragment could've been a BAILed one as a result 6955 // of renderSlot() with no valid children 6956 n1.dynamicChildren) { 6957 // a stable fragment (template root or <template v-for>) doesn't need to 6958 // patch children order, but it may contain dynamicChildren. 6959 patchBlockChildren(n1.dynamicChildren, dynamicChildren, container, parentComponent, parentSuspense, isSVG, slotScopeIds); 6960 if (parentComponent && parentComponent.type.__hmrId) { 6961 traverseStaticChildren(n1, n2); 6962 } 6963 else if ( 6964 // #2080 if the stable fragment has a key, it's a <template v-for> that may 6965 // get moved around. Make sure all root level vnodes inherit el. 6966 // #2134 or if it's a component root, it may al
6966so get moved around 6967 // as the component is being moved. 6968 n2.key != null || 6969 (parentComponent && n2 === parentComponent.subTree)) { 6970 traverseStaticChildren(n1, n2, true /* shallow */); 6971 } 6972 } 6973 else { 6974 // keyed / unkeyed, or manual fragments. 6975 // for keyed & unkeyed, since they are compiler generated from v-for, 6976 // each child is guaranteed to be a block so the fragment will never 6977 // have dynamicChildren. 6978 patchChildren(n1, n2, container, fragmentEndAnchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 6979 } 6980 } 6981 }; 6982 const processComponent = (n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 6983 n2.slotScopeIds = slotScopeIds; 6984 if (n1 == null) { 6985 if (n2.shapeFlag & 512 /* ShapeFlags.COMPONENT_KEPT_ALIVE */) { 6986 parentComponent.ctx.activate(n2, container, anchor, isSVG, optimized); 6987 } 6988 else { 6989 mountComponent(n2, container, anchor, parentComponent, parentSuspense, isSVG, optimized); 6990 } 6991 } 6992 else { 6993 updateComponent(n1, n2, optimized); 6994 } 6995 }; 6996 const mountComponent = (initialVNode, container, anchor, parentComponent, parentSuspense, isSVG, optimized) => { 6997 const instance = (initialVNode.component = createComponentInstance(initialVNode, parentComponent, parentSuspense)); 6998 if (instance.type.__hmrId) { 6999 registerHMR(instance); 7000 } 7001 { 7002 pushWarningContext(initialVNode); 7003 startMeasure(instance, `mount`); 7004 } 7005 // inject renderer internals for keepAlive 7006 if (isKeepAlive(initialVNode)) { 7007 instance.ctx.renderer = internals; 7008 } 7009 // resolve props and slots for setup context 7010 { 7011 { 7012 startMeasure(instance, `init`); 7013 } 7014 setupComponent(instance); 7015 { 7016 endMeasure(instance, `init`); 7017 } 7018 } 7019 // setup() is async. This component relies on async logic to be resolved 7020 // before proceeding 7021 if (instance.asyncDep) { 7022 parentSuspense && parentSuspense.registerDep(instance, setupRenderEffect); 7023 // Give it a placeholder if this is not hydration 7024 // TODO handle self-defined fallback 7025 if (!initialVNode.el) { 7026 const placeholder = (instance.subTree = createVNode(Comment)); 7027 processCommentNode(null, placeholder, container, anchor); 7028 } 7029 return; 7030 } 7031 setupRenderEffect(instance, initialVNode, container, anchor, parentSuspense, isSVG, optimized); 7032 { 7033 popWarningContext(); 7034 endMeasure(instance, `mount`); 7035 } 7036 }; 7037 const updateComponent = (n1, n2, optimized) => { 7038 const instance = (n2.component = n1.component); 7039 if (shouldUpdateComponent(n1, n2, optimized)) { 7040 if (instance.asyncDep && 7041 !instance.asyncResolved) { 7042 // async & still pending - just update props and slots 7043 // since the component's reactive effect for render isn't set-up yet 7044 { 7045 pushWarningContext(n2); 7046 } 7047 updateComponentPreRender(instance, n2, optimized); 7048 { 7049 popWarningContext(); 7050 } 7051 return; 7052 } 7053 else { 7054 // normal update 7055 instance.next = n2; 7056 // in case the child component is also queued, remove it to avoid 7057 // double updating the same child component in the same flush. 7058 invalidateJob(instance.update); 7059 // instance.update is the reactive effect.
vendor: 20,630 bytes, lines 7060-7513
7060 instance.update(); 7061 } 7062 } 7063 else { 7064 // no update needed. just copy over properties 7065 n2.el = n1.el; 7066 instance.vnode = n2; 7067 } 7068 }; 7069 const setupRenderEffect = (instance, initialVNode, container, anchor, parentSuspense, isSVG, optimized) => { 7070 const componentUpdateFn = () => { 7071 if (!instance.isMounted) { 7072 let vnodeHook; 7073 const { el, props } = initialVNode; 7074 const { bm, m, parent } = instance; 7075 const isAsyncWrapperVNode = isAsyncWrapper(initialVNode); 7076 toggleRecurse(instance, false); 7077 // beforeMount hook 7078 if (bm) { 7079 invokeArrayFns(bm); 7080 } 7081 // onVnodeBeforeMount 7082 if (!isAsyncWrapperVNode && 7083 (vnodeHook = props && props.onVnodeBeforeMount)) { 7084 invokeVNodeHook(vnodeHook, parent, initialVNode); 7085 } 7086 toggleRecurse(instance, true); 7087 if (el && hydrateNode) { 7088 // vnode has adopted host node - perform hydration instead of mount. 7089 const hydrateSubTree = () => { 7090 { 7091 startMeasure(instance, `render`); 7092 } 7093 instance.subTree = renderComponentRoot(instance); 7094 { 7095 endMeasure(instance, `render`); 7096 } 7097 { 7098 startMeasure(instance, `hydrate`); 7099 } 7100 hydrateNode(el, instance.subTree, instance, parentSuspense, null); 7101 { 7102 endMeasure(instance, `hydrate`); 7103 } 7104 }; 7105 if (isAsyncWrapperVNode) { 7106 initialVNode.type.__asyncLoader().then( 7107 // note: we are moving the render call into an async callback, 7108 // which means it won't track dependencies - but it's ok because 7109 // a server-rendered async wrapper is already in resolved state 7110 // and it will never need to change. 7111 () => !instance.isUnmounted && hydrateSubTree()); 7112 } 7113 else { 7114 hydrateSubTree(); 7115 } 7116 } 7117 else { 7118 { 7119 startMeasure(instance, `render`); 7120 } 7121 const subTree = (instance.subTree = renderComponentRoot(instance)); 7122 { 7123 endMeasure(instance, `render`); 7124 } 7125 { 7126 startMeasure(instance, `patch`); 7127 } 7128 patch(null, subTree, container, anchor, instance, parentSuspense, isSVG); 7129 { 7130 endMeasure(instance, `patch`); 7131 } 7132 initialVNode.el = subTree.el; 7133 } 7134 // mounted hook 7135 if (m) { 7136 queuePostRenderEffect(m, parentSuspense); 7137 } 7138 // onVnodeMounted 7139 if (!isAsyncWrapperVNode && 7140 (vnodeHook = props && props.onVnodeMounted)) { 7141 const scopedInitialVNode = initialVNode; 7142 queuePostRenderEffect(() => invokeVNodeHook(vnodeHook, parent, scopedInitialVNode), parentSuspense); 7143 } 7144 // activated hook for keep-alive roots. 7145 // #1742 activated hook must be accessed after first render 7146 // since the hook may be injected by a child keep-alive 7147 if (initialVNode.shapeFlag & 256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */ || 7148 (parent && 7149 isAsyncWrapper(parent.vnode) && 7150 parent.vnode.shapeFlag & 256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */)) { 7151 instance.a && queuePostRenderEffect(instance.a, parentSuspense); 7152 } 7153 instance.isMounted = true; 7154 { 7155 devtoolsComponentAdded(instance); 7156 } 7157 // #2458: deference mount-only object parameters to prevent memleaks 7158 initialVNode = container = anchor = null; 7159 } 7160 else { 7161 // updateComponent 7162 // This is triggered by mutation of component's own state (next: null) 7163 // OR parent calling processComponent (next: VNode) 7164 let { next, bu, u, parent, vnode } = instance; 7165 let originNext = next; 7166 let vnodeHook; 7167 { 7168 pushWarningContext(next || instance.vnode); 7169 } 7170 // Disallow component effect recursion during pre-lifecycle hooks. 7171 toggleRecurse(instance, false); 7172 if (next) { 7173 next.el = vnode.el; 7174 updateComponentPreRender(instance, next, optimized); 7175 } 7176 else { 7177 next = vnode; 7178 } 7179 // beforeUpdate hook 7180 if (bu) { 7181 invokeArrayFns(bu); 7182 } 7183 // onVnodeBeforeUpdate 7184 if ((vnodeHook = next.props && next.props.onVnodeBeforeUpdate)) { 7185 invokeVNodeHook(vnodeHook, parent, next, vnode); 7186 } 7187 toggleRecurse(instance, true); 7188 // render 7189 { 7190 startMeasure(instance, `render`); 7191 } 7192 const nextTree = renderComponentRoot(instance); 7193 { 7194 endMeasure(instance, `render`); 7195 } 7196 const prevTree = instance.subTree; 7197 instance.subTree = nextTree; 7198 { 7199 startMeasure(instance, `patch`); 7200 } 7201 patch(prevTree, nextTree, 7202 // parent may have changed if it's in a teleport 7203 hostParentNode(prevTree.el), 7204 // anchor may have changed if it's in a fragment 7205 getNextHostNode(prevTree), instance, parentSuspense, isSVG); 7206 { 7207 endMeasure(instance, `patch`); 7208 } 7209 next.el = nextTree.el; 7210 if (originNext === null) { 7211 // self-triggered update. In case of HOC, update parent component 7212 // vnode el. HOC is indicated by parent instance's subTree pointing 7213 // to child component's vnode 7214 updateHOCHostEl(instance, nextTree.el); 7215 } 7216 // updated hook 7217 if (u) { 7218 queuePostRenderEffect(u, parentSuspense); 7219 } 7220 // onVnodeUpdated 7221 if ((vnodeHook = next.props && next.props.onVnodeUpdated)) { 7222 queuePostRenderEffect(() => invokeVNodeHook(vnodeHook, parent, next, vnode), parentSuspense); 7223 } 7224 { 7225 devtoolsComponentUpdated(instance); 7226 } 7227 { 7228 popWarningContext(); 7229 } 7230 } 7231 }; 7232 // create reactive effect for rendering 7233 const effect = (instance.effect = new ReactiveEffect(componentUpdateFn, () => queueJob(update), instance.scope // track it in component's effect scope 7234 )); 7235 const update = (instance.update = () => effect.run()); 7236 update.id = instance.uid; 7237 // allowRecurse 7238 // #1801, #2043 component render effects should allow recursive updates 7239 toggleRecurse(instance, true); 7240 { 7241 effect.onTrack = instance.rtc 7242 ? e => invokeArrayFns(instance.rtc, e) 7243 : void 0; 7244 effect.onTrigger = instance.rtg 7245 ? e => invokeArrayFns(instance.rtg, e) 7246 : void 0; 7247 update.ownerInstance = instance; 7248 } 7249 update(); 7250 }; 7251 const updateComponentPreRender = (instance, nextVNode, optimized) => { 7252 nextVNode.component = instance; 7253 const prevProps = instance.vnode.props; 7254 instance.vnode = nextVNode; 7255 instance.next = null; 7256 updateProps(instance, nextVNode.props, prevProps, optimized); 7257 updateSlots(instance, nextVNode.children, optimized); 7258 pauseTracking(); 7259 // props update may have triggered pre-flush watchers. 7260 // flush them before the render update. 7261 flushPreFlushCbs(); 7262 resetTracking(); 7263 }; 7264 const patchChildren = (n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized = false) => { 7265 const c1 = n1 && n1.children; 7266 const prevShapeFlag = n1 ? n1.shapeFlag : 0; 7267 const c2 = n2.children; 7268 const { patchFlag, shapeFlag } = n2; 7269 // fast path 7270 if (patchFlag > 0) { 7271 if (patchFlag & 128 /* PatchFlags.KEYED_FRAGMENT */) { 7272 // this could be either fully-keyed or mixed (some keyed some not) 7273 // presence of patchFlag means children are guaranteed to be arrays 7274 patchKeyedChildren(c1, c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7275 return; 7276 } 7277 else if (patchFlag & 256 /* PatchFlags.UNKEYED_FRAGMENT */) { 7278 // unkeyed 7279 patchUnkeyedChildren(c1, c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7280 return; 7281 } 7282 } 7283 // children has 3 possibilities: text, array or no children. 7284 if (shapeFlag & 8 /* ShapeFlags.TEXT_CHILDREN */) { 7285 // text children fast path 7286 if (prevShapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7287 unmountChildren(c1, parentComponent, parentSuspense); 7288 } 7289 if (c2 !== c1) { 7290 hostSetElementText(container, c2); 7291 } 7292 } 7293 else { 7294 if (prevShapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7295 // prev children was array 7296 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7297 // two arrays, cannot assume anything, do full diff 7298 patchKeyedChildren(c1, c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7299 } 7300 else { 7301 // no new children, just unmount old 7302 unmountChildren(c1, parentComponent, parentSuspense, true); 7303 } 7304 } 7305 else { 7306 // prev children was text OR null 7307 // new children is array OR null 7308 if (prevShapeFlag & 8 /* ShapeFlags.TEXT_CHILDREN */) { 7309 hostSetElementText(container, ''); 7310 } 7311 // mount new if array 7312 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7313 mountChildren(c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7314 } 7315 } 7316 } 7317 }; 7318 const patchUnkeyedChildren = (c1, c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 7319 c1 = c1 || EMPTY_ARR; 7320 c2 = c2 || EMPTY_ARR; 7321 const oldLength = c1.length; 7322 const newLength = c2.length; 7323 const commonLength = Math.min(oldLength, newLength); 7324 let i; 7325 for (i = 0; i < commonLength; i++) { 7326 const nextChild = (c2[i] = optimized 7327 ? cloneIfMounted(c2[i]) 7328 : normalizeVNode(c2[i])); 7329 patch(c1[i], nextChild, container, null, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7330 } 7331 if (oldLength > newLength) { 7332 // remove old 7333 unmountChildren(c1, parentComponent, parentSuspense, true, false, commonLength); 7334 } 7335 else { 7336 // mount new 7337 mountChildren(c2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, commonLength); 7338 } 7339 }; 7340 // can be all-keyed or mixed 7341 const patchKeyedChildren = (c1, c2, container, parentAnchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized) => { 7342 let i = 0; 7343 const l2 = c2.length; 7344 let e1 = c1.length - 1; // prev ending index 7345 let e2 = l2 - 1; // next ending index 7346 // 1. sync from start 7347 // (a b) c 7348 // (a b) d e 7349 while (i <= e1 && i <= e2) { 7350 const n1 = c1[i]; 7351 const n2 = (c2[i] = optimized 7352 ? cloneIfMounted(c2[i]) 7353 : normalizeVNode(c2[i])); 7354 if (isSameVNodeType(n1, n2)) { 7355 patch(n1, n2, container, null, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7356 } 7357 else { 7358 break; 7359 } 7360 i++; 7361 } 7362 // 2. sync from end 7363 // a (b c) 7364 // d e (b c) 7365 while (i <= e1 && i <= e2) { 7366 const n1 = c1[e1]; 7367 const n2 = (c2[e2] = optimized 7368 ? cloneIfMounted(c2[e2]) 7369 : normalizeVNode(c2[e2])); 7370 if (isSameVNodeType(n1, n2)) { 7371 patch(n1, n2, container, null, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7372 } 7373 else { 7374 break; 7375 } 7376 e1--; 7377 e2--; 7378 } 7379 // 3. common sequence + mount 7380 // (a b) 7381 // (a b) c 7382 // i = 2, e1 = 1, e2 = 2 7383 // (a b) 7384 // c (a b) 7385 // i = 0, e1 = -1, e2 = 0 7386 if (i > e1) { 7387 if (i <= e2) { 7388 const nextPos = e2 + 1; 7389 const anchor = nextPos < l2 ? c2[nextPos].el : parentAnchor; 7390 while (i <= e2) { 7391 patch(null, (c2[i] = optimized 7392 ? cloneIfMounted(c2[i]) 7393 : normalizeVNode(c2[i])), container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7394 i++; 7395 } 7396 } 7397 } 7398 // 4. common sequence + unmount 7399 // (a b) c 7400 // (a b) 7401 // i = 2, e1 = 2, e2 = 1 7402 // a (b c) 7403 // (b c) 7404 // i = 0, e1 = 0, e2 = -1 7405 else if (i > e2) { 7406 while (i <= e1) { 7407 unmount(c1[i], parentComponent, parentSuspense, true); 7408 i++; 7409 } 7410 } 7411 // 5. unknown sequence 7412 // [i ... e1 + 1]: a b [c d e] f g 7413 // [i ... e2 + 1]: a b [e d c h] f g 7414 // i = 2, e1 = 4, e2 = 5 7415 else { 7416 const s1 = i; // prev starting index 7417 const s2 = i; // next starting index 7418 // 5.1 build key:index map for newChildren 7419 const keyToNewIndexMap = new Map(); 7420 for (i = s2; i <= e2; i++) { 7421 const nextChild = (c2[i] = optimized 7422 ? cloneIfMounted(c2[i]) 7423 : normalizeVNode(c2[i])); 7424 if (nextChild.key != null) { 7425 if (keyToNewIndexMap.has(nextChild.key)) { 7426 warn$1(`Duplicate keys found during update:`, JSON.stringify(nextChild.key), `Make sure keys are unique.`); 7427 } 7428 keyToNewIndexMap.set(nextChild.key, i); 7429 } 7430 } 7431 // 5.2 loop through old children left to be patched and try to patch 7432 // matching nodes & remove nodes that are no longer present 7433 let j; 7434 let patched = 0; 7435 const toBePatched = e2 - s2 + 1; 7436 let moved = false; 7437 // used to track whether any node has moved 7438 let maxNewIndexSoFar = 0; 7439 // works as Map<newIndex, oldIndex> 7440 // Note that oldIndex is offset by +1 7441 // and oldIndex = 0 is a special value indicating the new node has 7442 // no corresponding old node. 7443 // used for determining longest stable subsequence 7444 const newIndexToOldIndexMap = new Array(toBePatched); 7445 for (i = 0; i < toBePatched; i++) 7446 newIndexToOldIndexMap[i] = 0; 7447 for (i = s1; i <= e1; i++) { 7448 const prevChild = c1[i]; 7449 if (patched >= toBePatched) { 7450 // all new children have been patched so this can only be a removal 7451 unmount(prevChild, parentComponent, parentSuspense, true); 7452 continue; 7453 } 7454 let newIndex; 7455 if (prevChild.key != null) { 7456 newIndex = keyToNewIndexMap.get(prevChild.key); 7457 } 7458 else { 7459 // key-less node, try to locate a key-less node of the same type 7460 for (j = s2; j <= e2; j++) { 7461 if (newIndexToOldIndexMap[j - s2] === 0 && 7462 isSameVNodeType(prevChild, c2[j])) { 7463 newIndex = j; 7464 break; 7465 } 7466 } 7467 } 7468 if (newIndex === undefined) { 7469 unmount(prevChild, parentComponent, parentSuspense, true); 7470 } 7471 else { 7472 newIndexToOldIndexMap[newIndex - s2] = i + 1; 7473 if (newIndex >= maxNewIndexSoFar) { 7474 maxNewIndexSoFar = newIndex; 7475 } 7476 else { 7477 moved = true; 7478 } 7479 patch(prevChild, c2[newIndex], container, null, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7480 patched++; 7481 } 7482 } 7483 // 5.3 move and mount 7484 // generate longest stable subsequence only when nodes have moved 7485 const increasingNewIndexSequence = moved 7486 ? getSequence(newIndexToOldIndexMap) 7487 : EMPTY_ARR; 7488 j = increasingNewIndexSequence.length - 1; 7489 // looping backwards so that we can use last patched node as anchor 7490 for (i = toBePatched - 1; i >= 0; i--) { 7491 const nextIndex = s2 + i; 7492 const nextChild = c2[nextIndex]; 7493 const anchor = nextIndex + 1 < l2 ? c2[nextIndex + 1].el : parentAnchor; 7494 if (newIndexToOldIndexMap[i] === 0) { 7495 // mount new 7496 patch(null, nextChild, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7497 } 7498 else if (moved) { 7499 // move if: 7500 // There is no stable subsequence (e.g. a reverse) 7501 // OR current node is not among the stable sequence 7502 if (j < 0 || i !== increasingNewIndexSequence[j]) { 7503 move(nextChild, container, anchor, 2 /* MoveType.REORDER */); 7504 } 7505 else { 7506 j--; 7507 } 7508 } 7509 } 7510 } 7511 }; 7512 const move = (vnode, container, anchor, moveType, parentSuspense = null) => { 7513 const { el, type, transition, children, shapeFlag } = vnode;
7514 if (shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 7515 move(vnode.component.subTree, container, anchor, moveType); 7516 return; 7517 } 7518 if (shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 7519 vnode.suspense.move(container, anchor, moveType); 7520 return; 7521 } 7522 if (shapeFlag & 64 /* ShapeFlags.TELEPORT */) { 7523 type.move(vnode, container, anchor, internals); 7524 return; 7525 } 7526 if (type === Fragment) { 7527 hostInsert(el, container, anchor); 7528 for (let i = 0; i < children.length; i++) { 7529 move(children[i], container, anchor, moveType); 7530 } 7531 hostInsert(vnode.anchor, container, anchor); 7532 return; 7533 } 7534 if (type === Static) { 7535 moveStaticNode(vnode, container, anchor); 7536 return; 7537 } 7538 // single nodes 7539 const needTransition = moveType !== 2 /* MoveType.REORDER */ && 7540 shapeFlag & 1 /* ShapeFlags.ELEMENT */ && 7541 transition; 7542 if (needTransition) { 7543 if (moveType === 0 /* MoveType.ENTER */) { 7544 transition.beforeEnter(el); 7545 hostInsert(el, container, anchor); 7546 queuePostRenderEffect(() => transition.enter(el), parentSuspense); 7547 } 7548 else { 7549 const { leave, delayLeave, afterLeave } = transition; 7550 const remove = () => hostInsert(el, container, anchor); 7551 const performLeave = () => { 7552 leave(el, () => { 7553 remove(); 7554 afterLeave && afterLeave(); 7555 }); 7556 }; 7557 if (delayLeave) { 7558 delayLeave(el, remove, performLeave); 7559 } 7560 else { 7561 performLeave(); 7562 } 7563 } 7564 } 7565 else { 7566 hostInsert(el, container, anchor); 7567 } 7568 }; 7569 const unmount = (vnode, parentComponent, parentSuspense, doRemove = false, optimized = false) => { 7570 const { type, props, ref, children, dynamicChildren, shapeFlag, patchFlag, dirs } = vnode; 7571 // unset ref 7572 if (ref != null) { 7573 setRef(ref, null, parentSuspense, vnode, true); 7574 } 7575 if (shapeFlag & 256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */) { 7576 parentComponent.ctx.deactivate(vnode); 7577 return; 7578 } 7579 const shouldInvokeDirs = shapeFlag & 1 /* ShapeFlags.ELEMENT */ && dirs; 7580 const shouldInvokeVnodeHook = !isAsyncWrapper(vnode); 7581 let vnodeHook; 7582 if (shouldInvokeVnodeHook && 7583 (vnodeHook = props && props.onVnodeBeforeUnmount)) { 7584 invokeVNodeHook(vnodeHook, parentComponent, vnode); 7585 } 7586 if (shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 7587 unmountComponent(vnode.component, parentSuspense, doRemove); 7588 } 7589 else { 7590 if (shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 7591 vnode.suspense.unmount(parentSuspense, doRemove); 7592 return; 7593 } 7594 if (shouldInvokeDirs) { 7595 invokeDirectiveHook(vnode, null, parentComponent, 'beforeUnmount'); 7596 } 7597 if (shapeFlag & 64 /* ShapeFlags.TELEPORT */) { 7598 vnode.type.remove(vnode, parentComponent, parentSuspense, optimized, internals, doRemove); 7599 } 7600 else if (dynamicChildren && 7601 // #1153: fast path should not be taken for non-stable (v-for) fragments 7602 (type !== Fragment || 7603 (patchFlag > 0 && patchFlag & 64 /* PatchFlags.STABLE_FRAGMENT */))) { 7604 // fast path for block nodes: only need to unmount dynamic children. 7605 unmountChildren(dynamicChildren, parentComponent, parentSuspense, false, true); 7606 } 7607 else if ((type === Fragment && 7608 patchFlag & 7609 (128 /* PatchFlags.KEYED_FRAGMENT */ | 256 /* PatchFlags.UNKEYED_FRAGMENT */)) || 7610 (!optimized && shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */)) { 7611 unmountChildren(children, parentComponent, parentSuspense); 7612 } 7613 if (doRemove) { 7614 remove(vnode); 7615 } 7616 } 7617 if ((shouldInvokeVnodeHook && 7618 (vnodeHook = props && props.onVnodeUnmounted)) || 7619 shouldInvokeDirs) { 7620 queuePostRenderEffect(() => { 7621 vnodeHook && invokeVNodeHook(vnodeHook, parentComponent, vnode); 7622 shouldInvokeDirs && 7623 invokeDirectiveHook(vnode, null, parentComponent, 'unmounted'); 7624 }, parentSuspense); 7625 } 7626 }; 7627 const remove = vnode => { 7628 const { type, el, anchor, transition } = vnode; 7629 if (type === Fragment) { 7630 if (vnode.patchFlag > 0 && 7631 vnode.patchFlag & 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */ && 7632 transition && 7633 !transition.persisted) {
7634 vnode.children.forEach(child => { 7635 if (child.type === Comment) { 7636 hostRemove(child.el); 7637 } 7638 else { 7639 remove(child); 7640 } 7641 }); 7642 } 7643 else { 7644 removeFragment(el, anchor); 7645 } 7646 return; 7647 } 7648 if (type === Static) { 7649 removeStaticNode(vnode); 7650 return; 7651 } 7652 const performRemove = () => { 7653 hostRemove(el); 7654 if (transition && !transition.persisted && transition.afterLeave) { 7655 transition.afterLeave(); 7656 } 7657 }; 7658 if (vnode.shapeFlag & 1 /* ShapeFlags.ELEMENT */ && 7659 transition && 7660 !transition.persisted) { 7661 const { leave, delayLeave } = transition; 7662 const performLeave = () => leave(el, performRemove); 7663 if (delayLeave) { 7664 delayLeave(vnode.el, performRemove, performLeave); 7665 } 7666 else { 7667 performLeave(); 7668 } 7669 } 7670 else { 7671 performRemove(); 7672 } 7673 }; 7674 const removeFragment = (cur, end) => { 7675 // For fragments, directly remove all contained DOM nodes. 7676 // (fragment child nodes cannot have transition) 7677 let next; 7678 while (cur !== end) { 7679 next = hostNextSibling(cur); 7680 hostRemove(cur); 7681 cur = next; 7682 } 7683 hostRemove(end); 7684 }; 7685 const unmountComponent = (instance, parentSuspense, doRemove) => { 7686 if (instance.type.__hmrId) { 7687 unregisterHMR(instance); 7688 } 7689 const { bum, scope, update, subTree, um } = instance; 7690 // beforeUnmount hook 7691 if (bum) { 7692 invokeArrayFns(bum); 7693 } 7694 // stop effects in component scope 7695 scope.stop(); 7696 // update may be null if a component is unmounted before its async 7697 // setup has resolved. 7698 if (update) { 7699 // so that scheduler will no longer invoke it 7700 update.active = false; 7701 unmount(subTree, instance, parentSuspense, doRemove); 7702 } 7703 // unmounted hook 7704 if (um) { 7705 queuePostRenderEffect(um, parentSuspense); 7706 } 7707 queuePostRenderEffect(() => { 7708 instance.isUnmounted = true; 7709 }, parentSuspense); 7710 // A component with async dep inside a pending suspense is unmounted before 7711 // its async dep resolves. This should remove the dep from the suspense, and 7712 // cause the suspense to resolve immediately if that was the last dep. 7713 if (parentSuspense && 7714 parentSuspense.pendingBranch && 7715 !parentSuspense.isUnmounted && 7716 instance.asyncDep && 7717 !instance.asyncResolved && 7718 instance.suspenseId === parentSuspense.pendingId) { 7719 parentSuspense.deps--; 7720 if (parentSuspense.deps === 0) { 7721 parentSuspense.resolve(); 7722 } 7723 } 7724 { 7725 devtoolsComponentRemoved(instance); 7726 } 7727 }; 7728 const unmountChildren = (children, parentComponent, parentSuspense, doRemove = false, optimized = false, start = 0) => { 7729 for (let i = start; i < children.length; i++) { 7730 unmount(children[i], parentComponent, parentSuspense, doRemove, optimized); 7731 } 7732 }; 7733 const getNextHostNode = vnode => { 7734 if (vnode.shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 7735 return getNextHostNode(vnode.component.subTree); 7736 } 7737 if (vnode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 7738 return vnode.suspense.next(); 7739 } 7740 return hostNextSibling((vnode.anchor || vnode.el)); 7741 }; 7742 const render = (vnode, container, isSVG) => { 7743 if (vnode == null) { 7744 if (container._vnode) { 7745 unmount(container._vnode, null, null, true); 7746 } 7747 } 7748 else { 7749 patch(container._vnode || null, vnode, container, null, null, null, isSVG); 7750 } 7751 flushPreFlushCbs(); 7752 flushPostFlushCbs(); 7753 container._vnode = vnode; 7754 }; 7755 const internals = { 7756 p: patch, 7757 um: unmount, 7758 m: move, 7759 r: remove, 7760 mt: mountComponent, 7761 mc: mountChildren, 7762 pc: patchChildren, 7763 pbc: patchBlockChildren, 7764 n: getNextHostNode, 7765 o: options 7766 }; 7767 let hydrate; 7768 let hydrateNode; 7769 if (createHydrationFns) { 7770 [hydrate, hydrateNode] = createHydrationFns(internals); 7771 } 7772 return { 7773 render, 7774 hydrate, 7775 createApp: createAppAPI(render, hydrate) 7776 }; 7777 } 7778 function toggleRecurse({ effect, update }, allowed) { 7779 effect.allowRecurse = update.allowRecurse = allowed; 7780 } 7781 /** 7782 * #1156 7783 * When a component is HMR-enabled, we need to make sure that all static no
7783des 7784 * inside a block also inherit the DOM element from the previous tree so that 7785 * HMR updates (which are full updates) can retrieve the element for patching. 7786 * 7787 * #2080 7788 * Inside keyed `template` fragment static children, if a fragment is moved, 7789 * the children will always be moved. Therefore, in order to ensure correct move 7790 * position, el should be inherited from previous nodes. 7791 */ 7792 function traverseStaticChildren(n1, n2, shallow = false) { 7793 const ch1 = n1.children; 7794 const ch2 = n2.children; 7795 if (isArray(ch1) && isArray(ch2)) { 7796 for (let i = 0; i < ch1.length; i++) { 7797 // this is only called in the optimized path so array children are 7798 // guaranteed to be vnodes 7799 const c1 = ch1[i]; 7800 let c2 = ch2[i]; 7801 if (c2.shapeFlag & 1 /* ShapeFlags.ELEMENT */ && !c2.dynamicChildren) { 7802 if (c2.patchFlag <= 0 || c2.patchFlag === 32 /* PatchFlags.HYDRATE_EVENTS */) { 7803 c2 = ch2[i] = cloneIfMounted(ch2[i]); 7804 c2.el = c1.el; 7805 } 7806 if (!shallow) 7807 traverseStaticChildren(c1, c2); 7808 } 7809 // #6852 also inherit for text nodes 7810 if (c2.type === Text) { 7811 c2.el = c1.el; 7812 } 7813 // also inherit for comment nodes, but not placeholders (e.g. v-if which 7814 // would have received .el during block patch) 7815 if (c2.type === Comment && !c2.el) { 7816 c2.el = c1.el; 7817 } 7818 } 7819 } 7820 } 7821 // https://en.wikipedia.org/wiki/Longest_increasing_subsequence 7822 function getSequence(arr) { 7823 const p = arr.slice(); 7824 const result = [0]; 7825 let i, j, u, v, c; 7826 const len = arr.length; 7827 for (i = 0; i < len; i++) { 7828 const arrI = arr[i]; 7829 if (arrI !== 0) { 7830 j = result[result.length - 1]; 7831 if (arr[j] < arrI) { 7832 p[i] = j; 7833 result.push(i); 7834 continue; 7835 } 7836 u = 0; 7837 v = result.length - 1; 7838 while (u < v) { 7839 c = (u + v) >> 1; 7840 if (arr[result[c]] < arrI) { 7841 u = c + 1; 7842 } 7843 else { 7844 v = c; 7845 } 7846 } 7847 if (arrI < arr[result[u]]) { 7848 if (u > 0) { 7849 p[i] = result[u - 1]; 7850 } 7851 result[u] = i; 7852 } 7853 } 7854 } 7855 u = result.length; 7856 v = result[u - 1]; 7857 while (u-- > 0) { 7858 result[u] = v; 7859 v = p[v]; 7860 } 7861 return result; 7862 } 7863 7864 const isTeleport = (type) => type.__isTeleport; 7865 const isTeleportDisabled = (props) => props && (props.disabled || props.disabled === ''); 7866 const isTargetSVG = (target) => typeof SVGElement !== 'undefined' && target instanceof SVGElement; 7867 const resolveTarget = (props, select) => { 7868 const targetSelector = props && props.to; 7869 if (isString(targetSelector)) { 7870 if (!select) { 7871 warn$1(`Current renderer does not support string target for Teleports. ` + 7872 `(missing querySelector renderer option)`); 7873 return null; 7874 } 7875 else { 7876 const target = select(targetSelector); 7877 if (!target) { 7878 warn$1(`Failed to locate Teleport target with selector "${targetSelector}". ` + 7879 `Note the target element must exist before the component is mounted - ` + 7880 `i.e. the target cannot be rendered by the component itself, and ` + 7881 `ideally should be outside of the entire Vue component tree.`); 7882 } 7883 return target; 7884 } 7885 } 7886 else { 7887 if (!targetSelector && !isTeleportDisabled(props)) { 7888 warn$1(`Invalid Teleport target: ${targetSelector}`); 7889 } 7890 return targetSelector; 7891 } 7892 }; 7893 const TeleportImpl = { 7894 __isTeleport: true, 7895 process(n1, n2, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized, internals) { 7896 const { mc: mountChildren, pc: patchChildren, pbc: patchBlockChildren, o: { insert, querySelector, createText, createComment } } = internals; 7897 const disabled = isTeleportDisabled(n2.props); 7898 let { shapeFlag, children, dynamicChildren } = n2; 7899 // #3302 7900 // HMR updated, force full diff 7901 if (isHmrUpdating) { 7902 optimized = false;
7903 dynamicChildren = null; 7904 } 7905 if (n1 == null) { 7906 // insert anchors in the main view 7907 const placeholder = (n2.el = createComment('teleport start') 7908 ); 7909 const mainAnchor = (n2.anchor = createComment('teleport end') 7910 ); 7911 insert(placeholder, container, anchor); 7912 insert(mainAnchor, container, anchor); 7913 const target = (n2.target = resolveTarget(n2.props, querySelector)); 7914 const targetAnchor = (n2.targetAnchor = createText('')); 7915 if (target) { 7916 insert(targetAnchor, target); 7917 // #2652 we could be teleporting from a non-SVG tree into an SVG tree 7918 isSVG = isSVG || isTargetSVG(target); 7919 } 7920 else if (!disabled) { 7921 warn$1('Invalid Teleport target on mount:', target, `(${typeof target})`); 7922 } 7923 const mount = (container, anchor) => { 7924 // Teleport *always* has Array children. This is enforced in both the 7925 // compiler and vnode children normalization. 7926 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7927 mountChildren(children, container, anchor, parentComponent, parentSuspense, isSVG, slotScopeIds, optimized); 7928 } 7929 }; 7930 if (disabled) { 7931 mount(container, mainAnchor); 7932 } 7933 else if (target) { 7934 mount(target, targetAnchor); 7935 } 7936 } 7937 else { 7938 // update content 7939 n2.el = n1.el; 7940 const mainAnchor = (n2.anchor = n1.anchor); 7941 const target = (n2.target = n1.target); 7942 const targetAnchor = (n2.targetAnchor = n1.targetAnchor); 7943 const wasDisabled = isTeleportDisabled(n1.props); 7944 const currentContainer = wasDisabled ? container : target; 7945 const currentAnchor = wasDisabled ? mainAnchor : targetAnchor; 7946 isSVG = isSVG || isTargetSVG(target); 7947 if (dynamicChildren) { 7948 // fast path when the teleport happens to be a block root 7949 patchBlockChildren(n1.dynamicChildren, dynamicChildren, currentContainer, parentComponent, parentSuspense, isSVG, slotScopeIds); 7950 // even in block tree mode we need to make sure all root-level nodes 7951 // in the teleport inherit previous DOM references so that they can 7952 // be moved in future patches. 7953 traverseStaticChildren(n1, n2, true); 7954 } 7955 else if (!optimized) { 7956 patchChildren(n1, n2, currentContainer, currentAnchor, parentComponent, parentSuspense, isSVG, slotScopeIds, false); 7957 } 7958 if (disabled) { 7959 if (!wasDisabled) { 7960 // enabled -> disabled 7961 // move into main container 7962 moveTeleport(n2, container, mainAnchor, internals, 1 /* TeleportMoveTypes.TOGGLE */); 7963 } 7964 } 7965 else { 7966 // target changed 7967 if ((n2.props && n2.props.to) !== (n1.props && n1.props.to)) { 7968 const nextTarget = (n2.target = resolveTarget(n2.props, querySelector)); 7969 if (nextTarget) { 7970 moveTeleport(n2, nextTarget, null, internals, 0 /* TeleportMoveTypes.TARGET_CHANGE */); 7971 } 7972 else { 7973 warn$1('Invalid Teleport target on update:', target, `(${typeof target})`); 7974 } 7975 } 7976 else if (wasDisabled) { 7977 // disabled -> enabled 7978 // move into teleport target 7979 moveTeleport(n2, target, targetAnchor, internals, 1 /* TeleportMoveTypes.TOGGLE */); 7980 } 7981 } 7982 } 7983 updateCssVars(n2); 7984 }, 7985 remove(vnode, parentComponent, parentSuspense, optimized, { um: unmount, o: { remove: hostRemove } }, doRemove) { 7986 const { shapeFlag, children, anchor, targetAnchor, target, props } = vnode; 7987 if (target) { 7988 hostRemove(targetAnchor); 7989 } 7990 // an unmounted teleport should always remove its children if not disabled 7991 if (doRemove || !isTeleportDisabled(props)) { 7992 hostRemove(anchor); 7993 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 7994 for (let i = 0; i < children.length; i++) { 7995 const child = children[i]; 7996 unmount(child, parentComponent, parentSuspense, true, !!child.dynamicChildren); 7997 } 7998 } 7999 } 8000 }, 8001 move: moveTeleport, 8002 hydrate: hydrateTeleport 8003 }; 8004 function moveTeleport(vnode, container, parentAnchor, { o: { insert }, m: move }, moveType = 2 /* TeleportMoveTypes.REORDER */) { 8005 // move target anchor if this is a target change. 8006 if (moveType === 0 /* TeleportMoveTypes.TARGET_CHANGE */) { 8007 insert(vnode.targetAnchor, container, parentAnchor); 8008 } 8009 const { el, anchor, shapeFlag, children, props } = vnode; 8010 const isReorder = moveType === 2 /* TeleportMoveTypes.REORDER */; 8011 // move main view anchor if this is a re-order. 8012 if (isReorder) { 8013 insert(el, container, parentAnchor); 8014 } 8015 // if this is a re-order and teleport is enabled (content is in target) 8016 // do not move children. So the opposite is: only move children if this 8017 // is not a reorder, or the teleport is disabled 8018 if (!isReorder || isTeleportDisabled(props)) { 8019 // Teleport has either Array children or no children. 8020 if (shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 8021 for (let i = 0; i < children.length; i++) { 8022 move(children[i], container, parentAnchor, 2 /* MoveType.REORDER */); 8023 } 8024 } 8025 } 8026 // move main view anchor if this is a re-order. 8027 if (isReorder) { 8028 insert(anchor, container, parentAnchor); 8029 } 8030 } 8031 function hydrateTeleport(node, vnode, parentComponent, parentSuspense, slotScopeIds, optimized, { o: { nextSibling, parentNode, querySelector } }, hydrateChildren) { 8032 const target = (vnode.target = resolveTarget(vnode.props, querySelector)); 8033 if (target) { 8034 // if multiple teleports rendered to the same target element, we need to 8035 // pick up from where the last teleport finished instead of the first node 8036 const targetNode = target._lpa || target.firstChild; 8037 if (vnode.shapeFlag & 16 /* ShapeFlags.ARRAY_CHILDREN */) { 8038 if (isTeleportDisabled(vnode.props)) { 8039 vnode.anchor = hydrateChildren(nextSibling(node), vnode, parentNode(node), parentComponent, parentSuspense, slotScopeIds, optimized); 8040 vnode.targetAnchor = targetNode;
8041 } 8042 else { 8043 vnode.anchor = nextSibling(node); 8044 // lookahead until we find the target anchor 8045 // we cannot rely on return value of hydrateChildren() because there 8046 // could be nested teleports 8047 let targetAnchor = targetNode; 8048 while (targetAnchor) { 8049 targetAnchor = nextSibling(targetAnchor); 8050 if (targetAnchor && 8051 targetAnchor.nodeType === 8 && 8052 targetAnchor.data === 'teleport anchor') { 8053 vnode.targetAnchor = targetAnchor; 8054 target._lpa = 8055 vnode.targetAnchor && nextSibling(vnode.targetAnchor); 8056 break; 8057 } 8058 } 8059 hydrateChildren(targetNode, vnode, target, parentComponent, parentSuspense, slotScopeIds, optimized); 8060 } 8061 } 8062 updateCssVars(vnode); 8063 } 8064 return vnode.anchor && nextSibling(vnode.anchor); 8065 } 8066 // Force-casted public typing for h and TSX props inference 8067 const Teleport = TeleportImpl; 8068 function updateCssVars(vnode) { 8069 // presence of .ut method indicates owner component uses css vars. 8070 // code path here can assume browser environment. 8071 const ctx = vnode.ctx; 8072 if (ctx && ctx.ut) { 8073 let node = vnode.children[0].el; 8074 while (node !== vnode.targetAnchor) { 8075 if (node.nodeType === 1) 8076 node.setAttribute('data-v-owner', ctx.uid); 8077 node = node.nextSibling; 8078 } 8079 ctx.ut(); 8080 } 8081 } 8082 8083 const Fragment = Symbol('Fragment' ); 8084 const Text = Symbol('Text' ); 8085 const Comment = Symbol('Comment' ); 8086 const Static = Symbol('Static' ); 8087 // Since v-if and v-for are the two possible ways node structure can dynamically 8088 // change, once we consider v-if branches and each v-for fragment a block, we 8089 // can divide a template into nested blocks, and within each block the node 8090 // structure would be stable. This allows us to skip most children diffing 8091 // and only worry about the dynamic nodes (indicated by patch flags). 8092 const blockStack = []; 8093 let currentBlock = null; 8094 /** 8095 * Open a block. 8096 * This must be called before `createBlock`. It cannot be part of `createBlock` 8097 * because the children of the block are evaluated before `createBlock` itself 8098 * is called. The generated code typically looks like this: 8099 * 8100 * ```js 8101 * function render() { 8102 * return (openBlock(),createBlock('div', null, [...])) 8103 * } 8104 * ``` 8105 * disableTracking is true when creating a v-for fragment block, since a v-for 8106 * fragment always diffs its children. 8107 * 8108 * @private 8109 */ 8110 function openBlock(disableTracking = false) { 8111 blockStack.push((currentBlock = disableTracking ? null : [])); 8112 } 8113 function closeBlock() { 8114 blockStack.pop(); 8115 currentBlock = blockStack[blockStack.length - 1] || null; 8116 } 8117 // Whether we should be tracking dynamic child nodes inside a block. 8118 // Only tracks when this value is > 0 8119 // We are not using a simple boolean because this value may need to be 8120 // incremented/decremented by nested usage of v-once (see below) 8121 let isBlockTreeEnabled = 1; 8122 /** 8123 * Block tracking sometimes needs to be disabled, for example during the 8124 * creation of a tree that needs to be cached by v-once. The compiler generates 8125 * code like this: 8126 * 8127 * ``` js 8128 * _cache[1] || ( 8129 * setBlockTracking(-1), 8130 * _cache[1] = createVNode(...), 8131 * setBlockTracking(1), 8132 * _cache[1] 8133 * ) 8134 * ``` 8135 * 8136 * @private 8137 */ 8138 function setBlockTracking(value) { 8139 isBlockTreeEnabled += value; 8140 } 8141 function setupBlock(vnode) { 8142 // save current block children on the block vnode 8143 vnode.dynamicChildren = 8144 isBlockTreeEnabled > 0 ? currentBlock || EMPTY_ARR : null; 8145 // close block 8146 closeBlock(); 8147 // a block is always going to be patched, so track it as a child of its 8148 // parent block 8149 if (isBlockTreeEnabled > 0 && currentBlock) {
8150 currentBlock.push(vnode); 8151 } 8152 return vnode; 8153 } 8154 /** 8155 * @private 8156 */ 8157 function createElementBlock(type, props, children, patchFlag, dynamicProps, shapeFlag) { 8158 return setupBlock(createBaseVNode(type, props, children, patchFlag, dynamicProps, shapeFlag, true /* isBlock */)); 8159 } 8160 /** 8161 * Create a block root vnode. Takes the same exact arguments as `createVNode`. 8162 * A block root keeps track of dynamic nodes within the block in the 8163 * `dynamicChildren` array. 8164 * 8165 * @private 8166 */ 8167 function createBlock(type, props, children, patchFlag, dynamicProps) { 8168 return setupBlock(createVNode(type, props, children, patchFlag, dynamicProps, true /* isBlock: prevent a block from tracking itself */)); 8169 } 8170 function isVNode(value) { 8171 return value ? value.__v_isVNode === true : false; 8172 } 8173 function isSameVNodeType(n1, n2) { 8174 if (n2.shapeFlag & 6 /* ShapeFlags.COMPONENT */ && 8175 hmrDirtyComponents.has(n2.type)) { 8176 // #7042, ensure the vnode being unmounted during HMR 8177 // bitwise operations to remove keep alive flags 8178 n1.shapeFlag &= ~256 /* ShapeFlags.COMPONENT_SHOULD_KEEP_ALIVE */; 8179 n2.shapeFlag &= ~512 /* ShapeFlags.COMPONENT_KEPT_ALIVE */; 8180 // HMR only: if the component has been hot-updated, force a reload. 8181 return false; 8182 } 8183 return n1.type === n2.type && n1.key === n2.key; 8184 } 8185 let vnodeArgsTransformer; 8186 /** 8187 * Internal API for registering an arguments transform for createVNode 8188 * used for creating stubs in the test-utils 8189 * It is *internal* but needs to be exposed for test-utils to pick up proper 8190 * typings 8191 */ 8192 function transformVNodeArgs(transformer) { 8193 vnodeArgsTransformer = transformer; 8194 } 8195 const createVNodeWithArgsTransform = (...args) => { 8196 return _createVNode(...(vnodeArgsTransformer 8197 ? vnodeArgsTransformer(args, currentRenderingInstance) 8198 : args)); 8199 }; 8200 const InternalObjectKey = `__vInternal`; 8201 const normalizeKey = ({ key }) => key != null ? key : null; 8202 const normalizeRef = ({ ref, ref_key, ref_for }) => { 8203 return (ref != null 8204 ? isString(ref) || isRef(ref) || isFunction(ref) 8205 ? { i: currentRenderingInstance, r: ref, k: ref_key, f: !!ref_for } 8206 : ref 8207 : null); 8208 }; 8209 function createBaseVNode(type, props = null, children = null, patchFlag = 0, dynamicProps = null, shapeFlag = type === Fragment ? 0 : 1 /* ShapeFlags.ELEMENT */, isBlockNode = false, needFullChildrenNormalization = false) { 8210 const vnode = { 8211 __v_isVNode: true, 8212 __v_skip: true, 8213 type, 8214 props, 8215 key: props && normalizeKey(props), 8216 ref: props && normalizeRef(props), 8217 scopeId: currentScopeId, 8218 slotScopeIds: null, 8219 children, 8220 component: null, 8221 suspense: null, 8222 ssContent: null, 8223 ssFallback: null, 8224 dirs: null, 8225 transition: null, 8226 el: null, 8227 anchor: null, 8228 target: null, 8229 targetAnchor: null, 8230 staticCount: 0, 8231 shapeFlag, 8232 patchFlag, 8233 dynamicProps, 8234 dynamicChildren: null, 8235 appContext: null, 8236 ctx: currentRenderingInstance 8237 }; 8238 if (needFullChildrenNormalization) { 8239 normalizeChildren(vnode, children); 8240 // normalize suspense children 8241 if (shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 8242 type.normalize(vnode); 8243 } 8244 } 8245 else if (children) { 8246 // compiled element vnode - if children is passed, only possible types are 8247 // string or Array. 8248 vnode.shapeFlag |= isString(children) 8249 ? 8 /* ShapeFlags.TEXT_CHILDREN */ 8250 : 16 /* ShapeFlags.ARRAY_CHILDREN */; 8251 } 8252 // validate key 8253 if (vnode.key !== vnode.key) { 8254 warn$1(`VNode created with invalid key (NaN). VNode type:`, vnode.type); 8255 } 8256 // track vnode for block tree 8257 if (isBlockTreeEnabled > 0 && 8258 // avoid a block node from tracking itself 8259 !isBlockNode && 8260 // has current parent block 8261 currentBlock && 8262 // presence of a patch flag indicates this node needs patching on updates. 8263 // component nodes also should always be patched, because even if the 8264 // component doesn't need to update, it needs to persist the instance on to 8265 // the next vnode so that it can be properly unmounted later. 8266 (vnode.patchFlag >
vendor: 6,037 bytes, lines 8266-8396
8266 0 || shapeFlag & 6 /* ShapeFlags.COMPONENT */) && 8267 // the EVENTS flag is only for hydration and if it is the only flag, the 8268 // vnode should not be considered dynamic due to handler caching. 8269 vnode.patchFlag !== 32 /* PatchFlags.HYDRATE_EVENTS */) { 8270 currentBlock.push(vnode); 8271 } 8272 return vnode; 8273 } 8274 const createVNode = (createVNodeWithArgsTransform ); 8275 function _createVNode(type, props = null, children = null, patchFlag = 0, dynamicProps = null, isBlockNode = false) { 8276 if (!type || type === NULL_DYNAMIC_COMPONENT) { 8277 if (!type) { 8278 warn$1(`Invalid vnode type when creating vnode: ${type}.`); 8279 } 8280 type = Comment; 8281 } 8282 if (isVNode(type)) { 8283 // createVNode receiving an existing vnode. This happens in cases like 8284 // <component :is="vnode"/> 8285 // #2078 make sure to merge refs during the clone instead of overwriting it 8286 const cloned = cloneVNode(type, props, true /* mergeRef: true */); 8287 if (children) { 8288 normalizeChildren(cloned, children); 8289 } 8290 if (isBlockTreeEnabled > 0 && !isBlockNode && currentBlock) { 8291 if (cloned.shapeFlag & 6 /* ShapeFlags.COMPONENT */) { 8292 currentBlock[currentBlock.indexOf(type)] = cloned; 8293 } 8294 else { 8295 currentBlock.push(cloned); 8296 } 8297 } 8298 cloned.patchFlag |= -2 /* PatchFlags.BAIL */; 8299 return cloned; 8300 } 8301 // class component normalization. 8302 if (isClassComponent(type)) { 8303 type = type.__vccOpts; 8304 } 8305 // class & style normalization. 8306 if (props) { 8307 // for reactive or proxy objects, we need to clone it to enable mutation. 8308 props = guardReactiveProps(props); 8309 let { class: klass, style } = props; 8310 if (klass && !isString(klass)) { 8311 props.class = normalizeClass(klass); 8312 } 8313 if (isObject(style)) { 8314 // reactive state objects need to be cloned since they are likely to be 8315 // mutated 8316 if (isProxy(style) && !isArray(style)) { 8317 style = extend({}, style); 8318 } 8319 props.style = normalizeStyle(style); 8320 } 8321 } 8322 // encode the vnode type information into a bitmap 8323 const shapeFlag = isString(type) 8324 ? 1 /* ShapeFlags.ELEMENT */ 8325 : isSuspense(type) 8326 ? 128 /* ShapeFlags.SUSPENSE */ 8327 : isTeleport(type) 8328 ? 64 /* ShapeFlags.TELEPORT */ 8329 : isObject(type) 8330 ? 4 /* ShapeFlags.STATEFUL_COMPONENT */ 8331 : isFunction(type) 8332 ? 2 /* ShapeFlags.FUNCTIONAL_COMPONENT */ 8333 : 0; 8334 if (shapeFlag & 4 /* ShapeFlags.STATEFUL_COMPONENT */ && isProxy(type)) { 8335 type = toRaw(type); 8336 warn$1(`Vue received a Component which was made a reactive object. This can ` + 8337 `lead to unnecessary performance overhead, and should be avoided by ` + 8338 `marking the component with \`markRaw\` or using \`shallowRef\` ` + 8339 `instead of \`ref\`.`, `\nComponent that was made reactive: `, type); 8340 } 8341 return createBaseVNode(type, props, children, patchFlag, dynamicProps, shapeFlag, isBlockNode, true); 8342 } 8343 function guardReactiveProps(props) { 8344 if (!props) 8345 return null; 8346 return isProxy(props) || InternalObjectKey in props 8347 ? extend({}, props) 8348 : props; 8349 } 8350 function cloneVNode(vnode, extraProps, mergeRef = false) { 8351 // This is intentionally NOT using spread or extend to avoid the runtime 8352 // key enumeration cost. 8353 const { props, ref, patchFlag, children } = vnode; 8354 const mergedProps = extraProps ? mergeProps(props || {}, extraProps) : props; 8355 const cloned = { 8356 __v_isVNode: true, 8357 __v_skip: true, 8358 type: vnode.type, 8359 props: mergedProps, 8360 key: mergedProps && normalizeKey(mergedProps), 8361 ref: extraProps && extraProps.ref 8362 ? // #2078 in the case of <component :is="vnode" ref="extra"/> 8363 // if the vnode itself already has a ref, cloneVNode will need to merge 8364 // the refs so the single vnode can be set on multiple refs 8365 mergeRef && ref 8366 ? isArray(ref) 8367 ? ref.concat(normalizeRef(extraProps)) 8368 : [ref, normalizeRef(extraProps)] 8369 : normalizeRef(extraProps) 8370 : ref, 8371 scopeId: vnode.scopeId, 8372 slotScopeIds: vnode.slotScopeIds, 8373 children: patchFlag === -1 /* PatchFlags.HOISTED */ && isArray(children) 8374 ? children.map(deepCloneVNode) 8375 : children, 8376 target: vnode.target, 8377 targetAnchor: vnode.targetAnchor, 8378 staticCount: vnode.staticCount, 8379 shapeFlag: vnode.shapeFlag, 8380 // if the vnode is cloned with extra props, we can no longer assume its 8381 // existing patch flag to be reliable and need to add the FULL_PROPS flag. 8382 // note: preserve flag for fragments since they use the flag for children 8383 // fast paths only. 8384 patchFlag: extraProps && vnode.type !== Fragment 8385 ? patchFlag === -1 // hoisted node 8386 ? 16 /* PatchFlags.FULL_PROPS */ 8387 : patchFlag | 16 /* PatchFlags.FULL_PROPS */ 8388 : patchFlag, 8389 dynamicProps: vnode.dynamicProps, 8390 dynamicChildren: vnode.dynamicChildren, 8391 appContext: vnode.appContext, 8392 dirs: vnode.dirs, 8393 transition: vnode.transition, 8394 // These should technically only be non-null on mounted VNodes. However, 8395 // they *should* be copied for kept-alive vnodes. So we just always copy 8396 // them since them being non-null during a mount doesn't affect the logic as
vendor: 5,338 bytes, lines 8397-8543
8397 // they will simply be overwritten. 8398 component: vnode.component, 8399 suspense: vnode.suspense, 8400 ssContent: vnode.ssContent && cloneVNode(vnode.ssContent), 8401 ssFallback: vnode.ssFallback && cloneVNode(vnode.ssFallback), 8402 el: vnode.el, 8403 anchor: vnode.anchor, 8404 ctx: vnode.ctx 8405 }; 8406 return cloned; 8407 } 8408 /** 8409 * Dev only, for HMR of hoisted vnodes reused in v-for 8410 * https://github.com/vitejs/vite/issues/2022 8411 */ 8412 function deepCloneVNode(vnode) { 8413 const cloned = cloneVNode(vnode); 8414 if (isArray(vnode.children)) { 8415 cloned.children = vnode.children.map(deepCloneVNode); 8416 } 8417 return cloned; 8418 } 8419 /** 8420 * @private 8421 */ 8422 function createTextVNode(text = ' ', flag = 0) { 8423 return createVNode(Text, null, text, flag); 8424 } 8425 /** 8426 * @private 8427 */ 8428 function createStaticVNode(content, numberOfNodes) { 8429 // A static vnode can contain multiple stringified elements, and the number 8430 // of elements is necessary for hydration. 8431 const vnode = createVNode(Static, null, content); 8432 vnode.staticCount = numberOfNodes; 8433 return vnode; 8434 } 8435 /** 8436 * @private 8437 */ 8438 function createCommentVNode(text = '', 8439 // when used as the v-else branch, the comment node must be created as a 8440 // block to ensure correct updates. 8441 asBlock = false) { 8442 return asBlock 8443 ? (openBlock(), createBlock(Comment, null, text)) 8444 : createVNode(Comment, null, text); 8445 } 8446 function normalizeVNode(child) { 8447 if (child == null || typeof child === 'boolean') { 8448 // empty placeholder 8449 return createVNode(Comment); 8450 } 8451 else if (isArray(child)) { 8452 // fragment 8453 return createVNode(Fragment, null, 8454 // #3666, avoid reference pollution when reusing vnode 8455 child.slice()); 8456 } 8457 else if (typeof child === 'object') { 8458 // already vnode, this should be the most common since compiled templates 8459 // always produce all-vnode children arrays 8460 return cloneIfMounted(child); 8461 } 8462 else { 8463 // strings and numbers 8464 return createVNode(Text, null, String(child)); 8465 } 8466 } 8467 // optimized normalization for template-compiled render fns 8468 function cloneIfMounted(child) { 8469 return (child.el === null && child.patchFlag !== -1 /* PatchFlags.HOISTED */) || 8470 child.memo 8471 ? child 8472 : cloneVNode(child); 8473 } 8474 function normalizeChildren(vnode, children) { 8475 let type = 0; 8476 const { shapeFlag } = vnode; 8477 if (children == null) { 8478 children = null; 8479 } 8480 else if (isArray(children)) { 8481 type = 16 /* ShapeFlags.ARRAY_CHILDREN */; 8482 } 8483 else if (typeof children === 'object') { 8484 if (shapeFlag & (1 /* ShapeFlags.ELEMENT */ | 64 /* ShapeFlags.TELEPORT */)) { 8485 // Normalize slot to plain children for plain element and Teleport 8486 const slot = children.default; 8487 if (slot) { 8488 // _c marker is added by withCtx() indicating this is a compiled slot 8489 slot._c && (slot._d = false); 8490 normalizeChildren(vnode, slot()); 8491 slot._c && (slot._d = true); 8492 } 8493 return; 8494 } 8495 else { 8496 type = 32 /* ShapeFlags.SLOTS_CHILDREN */; 8497 const slotFlag = children._; 8498 if (!slotFlag && !(InternalObjectKey in children)) { 8499 children._ctx = currentRenderingInstance; 8500 } 8501 else if (slotFlag === 3 /* SlotFlags.FORWARDED */ && currentRenderingInstance) { 8502 // a child component receives forwarded slots from the parent. 8503 // its slot type is determined by its parent's slot type. 8504 if (currentRenderingInstance.slots._ === 1 /* SlotFlags.STABLE */) { 8505 children._ = 1 /* SlotFlags.STABLE */; 8506 } 8507 else { 8508 children._ = 2 /* SlotFlags.DYNAMIC */; 8509 vnode.patchFlag |= 1024 /* PatchFlags.DYNAMIC_SLOTS */; 8510 } 8511 } 8512 } 8513 } 8514 else if (isFunction(children)) { 8515 children = { default: children, _ctx: currentRenderingInstance }; 8516 type = 32 /* ShapeFlags.SLOTS_CHILDREN */; 8517 } 8518 else { 8519 children = String(children); 8520 // force teleport children to array so it can be moved around 8521 if (shapeFlag & 64 /* ShapeFlags.TELEPORT */) { 8522 type = 16 /* ShapeFlags.ARRAY_CHILDREN */; 8523 children = [createTextVNode(children)]; 8524 } 8525 else { 8526 type = 8 /* ShapeFlags.TEXT_CHILDREN */; 8527 } 8528 } 8529 vnode.children = children; 8530 vnode.shapeFlag |= type; 8531 } 8532 function mergeProps(...args) { 8533 const ret = {}; 8534 for (let i = 0; i < args.length; i++) { 8535 const toMerge = args[i]; 8536 for (const key in toMerge) { 8537 if (key === 'class') { 8538 if (ret.class !== toMerge.class) { 8539 ret.class = normalizeClass([ret.class, toMerge.class]); 8540 } 8541 } 8542 else if (key === 'style') { 8543 ret.style = normalizeStyle([ret.style, toMerge.
8543style]); 8544 } 8545 else if (isOn(key)) { 8546 const existing = ret[key]; 8547 const incoming = toMerge[key]; 8548 if (incoming && 8549 existing !== incoming && 8550 !(isArray(existing) && existing.includes(incoming))) { 8551 ret[key] = existing 8552 ? [].concat(existing, incoming) 8553 : incoming; 8554 } 8555 } 8556 else if (key !== '') { 8557 ret[key] = toMerge[key]; 8558 } 8559 } 8560 } 8561 return ret; 8562 } 8563 function invokeVNodeHook(hook, instance, vnode, prevVNode = null) { 8564 callWithAsyncErrorHandling(hook, instance, 7 /* ErrorCodes.VNODE_HOOK */, [ 8565 vnode, 8566 prevVNode 8567 ]); 8568 } 8569 8570 const emptyAppContext = createAppContext(); 8571 let uid$1 = 0; 8572 function createComponentInstance(vnode, parent, suspense) { 8573 const type = vnode.type; 8574 // inherit parent app context - or - if root, adopt from root vnode 8575 const appContext = (parent ? parent.appContext : vnode.appContext) || emptyAppContext; 8576 const instance = { 8577 uid: uid$1++, 8578 vnode, 8579 type, 8580 parent, 8581 appContext, 8582 root: null, 8583 next: null, 8584 subTree: null, 8585 effect: null, 8586 update: null, 8587 scope: new EffectScope(true /* detached */), 8588 render: null, 8589 proxy: null, 8590 exposed: null, 8591 exposeProxy: null, 8592 withProxy: null, 8593 provides: parent ? parent.provides : Object.create(appContext.provides), 8594 accessCache: null, 8595 renderCache: [], 8596 // local resolved assets 8597 components: null, 8598 directives: null, 8599 // resolved props and emits options 8600 propsOptions: normalizePropsOptions(type, appContext), 8601 emitsOptions: normalizeEmitsOptions(type, appContext), 8602 // emit 8603 emit: null, 8604 emitted: null, 8605 // props default value 8606 propsDefaults: EMPTY_OBJ, 8607 // inheritAttrs 8608 inheritAttrs: type.inheritAttrs, 8609 // state 8610 ctx: EMPTY_OBJ, 8611 data: EMPTY_OBJ, 8612 props: EMPTY_OBJ, 8613 attrs: EMPTY_OBJ, 8614 slots: EMPTY_OBJ, 8615 refs: EMPTY_OBJ, 8616 setupState: EMPTY_OBJ, 8617 setupContext: null, 8618 // suspense related 8619 suspense, 8620 suspenseId: suspense ? suspense.pendingId : 0, 8621 asyncDep: null, 8622 asyncResolved: false, 8623 // lifecycle hooks 8624 // not using enums here because it results in computed properties 8625 isMounted: false, 8626 isUnmounted: false, 8627 isDeactivated: false, 8628 bc: null, 8629 c: null, 8630 bm: null, 8631 m: null, 8632 bu: null, 8633 u: null, 8634 um: null, 8635 bum: null, 8636 da: null, 8637 a: null, 8638 rtg: null, 8639 rtc: null, 8640 ec: null, 8641 sp: null 8642 }; 8643 { 8644 instance.ctx = createDevRenderContext(instance); 8645 } 8646 instance.root = parent ? parent.root : instance; 8647 instance.emit = emit$1.bind(null, instance); 8648 // apply custom element special handling 8649 if (vnode.ce) { 8650 vnode.ce(instance); 8651 } 8652 return instance; 8653 } 8654 let currentInstance = null; 8655 const getCurrentInstance = () => currentInstance || currentRenderingInstance; 8656 const setCurrentInstance = (instance) => { 8657 currentInstance = instance; 8658 instance.scope.on(); 8659 }; 8660 const unsetCurrentInstance = () => { 8661 currentInstance && currentInstance.scope.off(); 8662 currentInstance = null; 8663 }; 8664 const isBuiltInTag = /*#__PURE__*/ makeMap('slot,component'); 8665 function validateComponentName(name, config) { 8666 const appIsNativeTag = config.isNativeTag || NO; 8667 if (isBuiltInTag(name) || appIsNativeTag(name)) { 8668 warn$1('Do not use built-in or reserved HTML elements as component id: ' + name); 8669 } 8670 } 8671 function isStatefulComponent(instance) { 8672 return instance.vnode.shapeFlag & 4 /* ShapeFlags.STATEFUL_COMPONENT */; 8673 } 8674 let isInSSRComponentSetup = false;
8675 function setupComponent(instance, isSSR = false) { 8676 isInSSRComponentSetup = isSSR; 8677 const { props, children } = instance.vnode; 8678 const isStateful = isStatefulComponent(instance); 8679 initProps(instance, props, isStateful, isSSR); 8680 initSlots(instance, children); 8681 const setupResult = isStateful 8682 ? setupStatefulComponent(instance, isSSR) 8683 : undefined; 8684 isInSSRComponentSetup = false; 8685 return setupResult; 8686 } 8687 function setupStatefulComponent(instance, isSSR) { 8688 var _a; 8689 const Component = instance.type; 8690 { 8691 if (Component.name) { 8692 validateComponentName(Component.name, instance.appContext.config); 8693 } 8694 if (Component.components) { 8695 const names = Object.keys(Component.components); 8696 for (let i = 0; i < names.length; i++) { 8697 validateComponentName(names[i], instance.appContext.config); 8698 } 8699 } 8700 if (Component.directives) { 8701 const names = Object.keys(Component.directives); 8702 for (let i = 0; i < names.length; i++) { 8703 validateDirectiveName(names[i]); 8704 } 8705 } 8706 if (Component.compilerOptions && isRuntimeOnly()) { 8707 warn$1(`"compilerOptions" is only supported when using a build of Vue that ` + 8708 `includes the runtime compiler. Since you are using a runtime-only ` + 8709 `build, the options should be passed via your build tool config instead.`); 8710 } 8711 } 8712 // 0. create render proxy property access cache 8713 instance.accessCache = Object.create(null); 8714 // 1. create public instance / render proxy 8715 // also mark it raw so it's never observed 8716 instance.proxy = markRaw(new Proxy(instance.ctx, PublicInstanceProxyHandlers)); 8717 { 8718 exposePropsOnRenderContext(instance); 8719 } 8720 // 2. call setup() 8721 const { setup } = Component; 8722 if (setup) { 8723 const setupContext = (instance.setupContext = 8724 setup.length > 1 ? createSetupContext(instance) : null); 8725 setCurrentInstance(instance); 8726 pauseTracking(); 8727 const setupResult = callWithErrorHandling(setup, instance, 0 /* ErrorCodes.SETUP_FUNCTION */, [shallowReadonly(instance.props) , setupContext]); 8728 resetTracking(); 8729 unsetCurrentInstance(); 8730 if (isPromise(setupResult)) { 8731 setupResult.then(unsetCurrentInstance, unsetCurrentInstance); 8732 if (isSSR) { 8733 // return the promise so server-renderer can wait on it 8734 return setupResult 8735 .then((resolvedResult) => { 8736 handleSetupResult(instance, resolvedResult, isSSR); 8737 }) 8738 .catch(e => { 8739 handleError(e, instance, 0 /* ErrorCodes.SETUP_FUNCTION */); 8740 }); 8741 } 8742 else { 8743 // async setup returned Promise. 8744 // bail here and wait for re-entry. 8745 instance.asyncDep = setupResult; 8746 if (!instance.suspense) { 8747 const name = (_a = Component.name) !== null && _a !== void 0 ? _a : 'Anonymous'; 8748 warn$1(`Component <${name}>: setup function returned a promise, but no ` + 8749 `<Suspense> boundary was found in the parent component tree. ` + 8750 `A component with async setup() must be nested in a <Suspense> ` + 8751 `in order to be rendered.`); 8752 } 8753 } 8754 } 8755 else { 8756 handleSetupResult(instance, setupResult, isSSR); 8757 } 8758 } 8759 else { 8760 finishComponentSetup(instance, isSSR); 8761 } 8762 } 8763 function handleSetupResult(instance, setupResult, isSSR) { 8764 if (isFunction(setupResult)) { 8765 // setup returned an inline render function 8766 { 8767 instance.render = setupResult; 8768 } 8769 } 8770 else if (isObject(setupResult)) { 8771 if (isVNode(setupResult)) { 8772 warn$1(`setup() should not return VNodes directly - ` + 8773 `return a render function instead.`); 8774 } 8775 // setup returned bindings. 8776 // assuming a render function compiled from template is present. 8777 { 8778 instance.devtoolsRawSetupState = setupResult; 8779 } 8780 instance.setupState = proxyRefs(setupResult); 8781 { 8782 exposeSetupStateOnRenderContext(instance); 8783 } 8784 } 8785 else if (setupResult !== undefined) { 8786 warn$1(`setup() should return an object. Received: ${setupResult === null ? 'null' : typeof setupResult}`); 8787 } 8788 finishComponentSetup(instance, isSSR); 8789 } 8790 let compile; 8791 let installWithProxy; 8792 /** 8793 * For runtime-dom to register the compiler. 8794 * Note the exported method uses any to avoid d.ts relying on the compiler types. 8795 */ 8796 function registerRuntimeCompiler(_compile) { 8797 compile = _compile; 8798 installWithProxy = i => { 8799 if (i.render._rc) { 8800 i.withProxy = new Proxy(i.ctx, RuntimeCompiledPublicInstanceProxyHandlers); 8801 } 8802 }; 8803 } 8804 // dev only 8805 const isRuntimeOnly = () => !compile; 8806 function finishComponentSetup(instance, isSSR, skipOptions) { 8807 const Component = instance.type; 8808 // template / render function normalization 8809 // could be already set when returned from setup() 8810 if (!instance.render) { 8811 // only do on-the-fly compile if not in SSR - SSR on-the-fly compilation 8812 // is done by server-renderer 8813 if (!isSSR && compile && !Component.render) { 8814 const template = Component.template || 8815 resolveMergedOptions(instance).template; 8816 if (template) { 8817 { 8818 startMeasure(instance, `compile`); 8819 } 8820 const { isCustomElement, compilerOptions } = instance.appContext.config; 8821 const { delimiters, compilerOptions: componentCompilerOptions } = Component; 8822 const finalCompilerOptions = extend(extend({ 8823 isCustomElement, 8824 delimiters 8825 }, compilerOptions), componentCompilerOptions); 8826 Component.render = compile(template, finalCompilerOptions); 8827 { 8828 endMeasure(instance, `compile`); 8829 } 8830 } 8831 } 8832 instance.render = (Component.render || NOOP); 8833 // for runtime-compiled render functions using `with` blocks, the render 8834 // proxy used needs a different `has` handler which is more performant and 8835 // also only allows a whitelist of globals to fallthrough. 8836 if (installWithProxy) { 8837 installWithProxy(instance); 8838 } 8839 } 8840 // support for 2.x options 8841 { 8842 setCurrentInstance(instance); 8843 pauseTracking(); 8844 applyOptions(instance); 8845 resetTracking(); 8846 unsetCurrentInstance(); 8847 } 8848 // warn missing template/render 8849 // the runtime compilation of template in SSR is done by server-render 8850 if (!Component.render && instance.render === NOOP && !isSSR) { 8851 /* istanbul ignore if */ 8852 if (!compile && Component.template) { 8853 warn$1(`Component provided template option but ` + 8854 `runtime compilation is not supported in this build of Vue.` + 8855 (` Use "vue.global.js" instead.` 8856 ) /* should not happen */); 8857 } 8858 else { 8859 warn$1(`Component is missing template or render function.`); 8860 } 8861 } 8862 } 8863 function createAttrsProxy(instance) { 8864 return new Proxy(instance.attrs, { 8865 get(target, key) { 8866 markAttrsAccessed(); 8867 track(instance, "get" /* TrackOpTypes.GET */, '$attrs'); 8868 return target[key]; 8869 }, 8870 set() { 8871 warn$1(`setupContext.attrs is readonly.`); 8872 return false;
8873 }, 8874 deleteProperty() { 8875 warn$1(`setupContext.attrs is readonly.`); 8876 return false; 8877 } 8878 } 8879 ); 8880 } 8881 function createSetupContext(instance) { 8882 const expose = exposed => { 8883 if (instance.exposed) { 8884 warn$1(`expose() should be called only once per setup().`); 8885 } 8886 instance.exposed = exposed || {}; 8887 }; 8888 let attrs; 8889 { 8890 // We use getters in dev in case libs like test-utils overwrite instance 8891 // properties (overwrites should not be done in prod) 8892 return Object.freeze({ 8893 get attrs() { 8894 return attrs || (attrs = createAttrsProxy(instance)); 8895 }, 8896 get slots() { 8897 return shallowReadonly(instance.slots); 8898 }, 8899 get emit() { 8900 return (event, ...args) => instance.emit(event, ...args); 8901 }, 8902 expose 8903 }); 8904 } 8905 } 8906 function getExposeProxy(instance) { 8907 if (instance.exposed) { 8908 return (instance.exposeProxy || 8909 (instance.exposeProxy = new Proxy(proxyRefs(markRaw(instance.exposed)), { 8910 get(target, key) { 8911 if (key in target) { 8912 return target[key]; 8913 } 8914 else if (key in publicPropertiesMap) { 8915 return publicPropertiesMap[key](instance); 8916 } 8917 }, 8918 has(target, key) { 8919 return key in target || key in publicPropertiesMap; 8920 } 8921 }))); 8922 } 8923 } 8924 const classifyRE = /(?:^|[-_])(\w)/g; 8925 const classify = (str) => str.replace(classifyRE, c => c.toUpperCase()).replace(/[-_]/g, ''); 8926 function getComponentName(Component, includeInferred = true) { 8927 return isFunction(Component) 8928 ? Component.displayName || Component.name 8929 : Component.name || (includeInferred && Component.__name); 8930 } 8931 /* istanbul ignore next */ 8932 function formatComponentName(instance, Component, isRoot = false) { 8933 let name = getComponentName(Component); 8934 if (!name && Component.__file) { 8935 const match = Component.__file.match(/([^/\\]+)\.\w+$/); 8936 if (match) { 8937 name = match[1]; 8938 } 8939 } 8940 if (!name && instance && instance.parent) { 8941 // try to infer the name based on reverse resolution 8942 const inferFromRegistry = (registry) => { 8943 for (const key in registry) { 8944 if (registry[key] === Component) { 8945 return key; 8946 } 8947 } 8948 }; 8949 name = 8950 inferFromRegistry(instance.components || 8951 instance.parent.type.components) || inferFromRegistry(instance.appContext.components); 8952 } 8953 return name ? classify(name) : isRoot ? `App` : `Anonymous`; 8954 } 8955 function isClassComponent(value) { 8956 return isFunction(value) && '__vccOpts' in value; 8957 } 8958 8959 const computed$1 = ((getterOrOptions, debugOptions) => { 8960 // @ts-ignore 8961 return computed(getterOrOptions, debugOptions, isInSSRComponentSetup); 8962 }); 8963 8964 // dev only 8965 const warnRuntimeUsage = (method) => warn$1(`${method}() is a compiler-hint helper that is only usable inside ` + 8966 `<script setup> of a single file component. Its arguments should be ` + 8967 `compiled away and passing it at runtime has no effect.`); 8968 // implementation 8969 function defineProps() { 8970 { 8971 warnRuntimeUsage(`defineProps`); 8972 } 8973 return null; 8974 } 8975 // implementation 8976 function defineEmits() { 8977 { 8978 warnRuntimeUsage(`defineEmits`); 8979 } 8980 return null; 8981 } 8982 /** 8983 * Vue `<script setup>` compiler macro for declaring a component's exposed 8984 * instance properties when it is accessed by a parent component via template 8985 * refs. 8986 * 8987 * `<script setup>` components are closed by default - i.e. variables inside 8988 * the `<script setup>` scope is not exposed to parent unless explicitly exposed 8989 * via `defineExpose`. 8990 * 8991 * This is only usable inside `<script setup>`, is compiled away in the 8992 * output and should **not** be actually called at runtime. 8993 */ 8994 function defineExpose(exposed) { 8995 { 8996 warnRuntimeUsage(`defineExpose`); 8997 } 8998 } 8999 /** 9000 * Vue `<script setup>` compiler macro for providing props default values when 9001 * using type-based `defineProps` declaration. 9002 * 9003 * Example usage: 9004 * ```ts 9005 * withDefaults(defineProps<{ 9006 * size?: number 9007 * labels?: string[] 9008 * }>(), { 9009 * size: 3, 9010 * labels: () => ['default label'] 9011 * }) 9012 * ``` 9013 * 9014 * This is only usable inside `<script setup>`, is compiled away in the output 9015 * and should **not** be actually called at runtime. 9016 */ 9017 function withDefaults(props, defaults) { 9018 { 9019 warnRuntimeUsage(`withDefaults`); 9020 } 9021 return null; 9022 } 9023 function useSlots() { 9024 return getContext().slots; 9025 } 9026 function useAttrs() { 9027 return getContext().attrs; 9028 } 9029 function getContext() { 9030 const i = getCurrentInstance(); 9031 if (!i) { 9032 warn$1(`useContext() called without active instance.`); 9033 } 9034 return i.setupContext || (i.setupContext = createSetupContext(i)); 9035 } 9036 /** 9037 * Runtime helper for merging default declarations. Imported by compiled code 9038 * only. 9039 * @internal 9040 */ 9041 function mergeDefaults(raw, defaults) { 9042 const props = isArray(raw) 9043 ? raw.reduce((normalized, p) => ((normalized[p] = {}), normalized), {}) 9044 : raw; 9045 for (const key in defaults) { 9046 const opt = props[key]; 9047 if (opt) { 9048 if (isArray(opt) || isFunction(opt)) { 9049 props[key] = { type: opt, default: defaults[key] }; 9050 } 9051 else { 9052 opt.default = defaults[key]; 9053 } 9054 } 9055 else if (opt === null) { 9056 props[key] = { default: defaults[key] }; 9057 } 9058 else { 9059 warn$1(`props default key "${key}" has no corresponding declaration.`); 9060 } 9061 } 9062 return props; 9063 } 9064 /** 9065 * Used to create a proxy for the rest element when destructuring props with 9066 * defineProps(). 9067 * @internal 9068 */ 9069 function createPropsRestProxy(props, excludedKeys) { 9070 const ret = {}; 9071 for (const key in props) { 9072 if (!excludedKeys.includes(key)) { 9073 Object.defineProperty(ret, key, { 9074 enumerable: true, 9075 get: () => props[key] 9076 }); 9077 } 9078 } 9079 return ret; 9080 } 9081 /** 9082 * `<script setup>` helper for persisting the current instance context over 9083 * async/await flows. 9084 * 9085 * `@vue/compiler-sfc` converts the following: 9086 * 9087 * ```ts 9088 * const x = await foo() 9089 * ``` 9090 * 9091 * into: 9092 * 9093 * ```ts 9094 * let __temp, __restore 9095 * const x = (([__temp, __restore] = withAsyncContext(() =>
9095 foo())),__temp=await __temp,__restore(),__temp) 9096 * ``` 9097 * @internal 9098 */ 9099 function withAsyncContext(getAwaitable) { 9100 const ctx = getCurrentInstance(); 9101 if (!ctx) { 9102 warn$1(`withAsyncContext called without active current instance. ` + 9103 `This is likely a bug.`); 9104 } 9105 let awaitable = getAwaitable(); 9106 unsetCurrentInstance(); 9107 if (isPromise(awaitable)) { 9108 awaitable = awaitable.catch(e => { 9109 setCurrentInstance(ctx); 9110 throw e; 9111 }); 9112 } 9113 return [awaitable, () => setCurrentInstance(ctx)]; 9114 } 9115 9116 // Actual implementation 9117 function h(type, propsOrChildren, children) { 9118 const l = arguments.length; 9119 if (l === 2) { 9120 if (isObject(propsOrChildren) && !isArray(propsOrChildren)) { 9121 // single vnode without props 9122 if (isVNode(propsOrChildren)) { 9123 return createVNode(type, null, [propsOrChildren]); 9124 } 9125 // props without children 9126 return createVNode(type, propsOrChildren); 9127 } 9128 else { 9129 // omit props 9130 return createVNode(type, null, propsOrChildren); 9131 } 9132 } 9133 else { 9134 if (l > 3) { 9135 children = Array.prototype.slice.call(arguments, 2); 9136 } 9137 else if (l === 3 && isVNode(children)) { 9138 children = [children]; 9139 } 9140 return createVNode(type, propsOrChildren, children); 9141 } 9142 } 9143 9144 const ssrContextKey = Symbol(`ssrContext` ); 9145 const useSSRContext = () => { 9146 { 9147 warn$1(`useSSRContext() is not supported in the global build.`); 9148 } 9149 }; 9150 9151 function initCustomFormatter() { 9152 /* eslint-disable no-restricted-globals */ 9153 if (typeof window === 'undefined') { 9154 return; 9155 } 9156 const vueStyle = { style: 'color:#3ba776' }; 9157 const numberStyle = { style: 'color:#0b1bc9' }; 9158 const stringStyle = { style: 'color:#b62e24' }; 9159 const keywordStyle = { style: 'color:#9d288c' }; 9160 // custom formatter for Chrome 9161 // https://www.mattzeunert.com/2016/02/19/custom-chrome-devtools-object-formatters.html 9162 const formatter = { 9163 header(obj) { 9164 // TODO also format ComponentPublicInstance & ctx.slots/attrs in setup 9165 if (!isObject(obj)) { 9166 return null; 9167 } 9168 if (obj.__isVue) { 9169 return ['div', vueStyle, `VueInstance`]; 9170 } 9171 else if (isRef(obj)) { 9172 return [ 9173 'div', 9174 {}, 9175 ['span', vueStyle, genRefFlag(obj)], 9176 '<', 9177 formatValue(obj.value), 9178 `>` 9179 ]; 9180 } 9181 else if (isReactive(obj)) { 9182 return [ 9183 'div', 9184 {}, 9185 ['span', vueStyle, isShallow(obj) ? 'ShallowReactive' : 'Reactive'], 9186 '<', 9187 formatValue(obj), 9188 `>${isReadonly(obj) ? ` (readonly)` : ``}` 9189 ]; 9190 } 9191 else if (isReadonly(obj)) { 9192 return [ 9193 'div', 9194 {}, 9195 ['span', vueStyle, isShallow(obj) ? 'ShallowReadonly' : 'Readonly'], 9196 '<', 9197 formatValue(obj), 9198 '>' 9199 ]; 9200 } 9201 return null; 9202 }, 9203 hasBody(obj) { 9204 return obj && obj.__isVue; 9205 }, 9206 body(obj) { 9207 if (obj && obj.__isVue) { 9208 return [ 9209 'div', 9210 {}, 9211 ...formatInstance(obj.$) 9212 ]; 9213 } 9214 } 9215 }; 9216 function formatInstance(instance) { 9217 const blocks = []; 9218 if (instance.type.props && instance.props) { 9219 blocks.push(createInstanceBlock('props', toRaw(instance.props))); 9220 } 9221 if (instance.setupState !== EMPTY_OBJ) { 9222 blocks.push(createInstanceBlock('setup', instance.setupState)); 9223 } 9224 if (instance.data !== EMPTY_OBJ) { 9225 blocks.push(createInstanceBlock('data', toRaw(instance.data))); 9226 } 9227 const computed = extractKeys(instance, 'computed'); 9228 if (computed) { 9229 blocks.push(createInstanceBlock('computed', computed)); 9230 } 9231 const injected = extractKeys(instance, 'inject'); 9232 if (injected) { 9233 blocks.push(createInstanceBlock('injected', injected)); 9234 } 9235 blocks.push([ 9236 'div', 9237 {}, 9238 [ 9239 'span', 9240 { 9241 style: keywordStyle.style + ';opacity:0.66' 9242 }, 9243 '$ (internal): ' 9244 ], 9245 ['object', { object: instance }] 9246 ]); 9247 return blocks; 9248 } 9249 function createInstanceBlock(type, target) { 9250 target = extend({}, target); 9251 if (!Object.keys(target).length) { 9252 return ['span', {}]; 9253 } 9254 return [ 9255 'div', 9256 { style: 'line-height:1.25em;margin-bottom:0.6em' }, 9257 [ 9258 'div', 9259 { 9260 style: 'color:#476582' 9261 }, 9262 type 9263 ], 9264 [ 9265 'div', 9266 { 9267 style: 'padding-left:1.25em' 9268 }, 9269 ...Object.keys(target).map(key => { 9270 return [ 9271 'div', 9272 {}, 9273 ['span', keywordStyle, key + ': '], 9274 formatValue(target[key], false) 9275 ]; 9276 }) 9277 ] 9278 ]; 9279 } 9280 function formatValue(v, asRaw = true) { 9281 if (typeof v === 'number') { 9282 return ['span', numberStyle, v]; 9283 } 9284 else if (typeof v === 'string') { 9285 return ['span', stringStyle, JSON.stringify(v)]; 9286 } 9287 else if (typeof v === 'boolean') { 9288 return ['span', keywordStyle, v]; 9289 } 9290 else if (isObject(v)) { 9291 return ['object', { object: asRaw ? toRaw(v) : v }]; 9292 } 9293 else { 9294 return ['span', stringStyle, String(v)]; 9295 } 9296 } 9297 function extractKeys(instance, type) { 9298 const Comp = instance.type; 9299 if (isFunction(Comp)) { 9300 return; 9301 } 9302 const extracted = {}; 9303 for (const key in instance.ctx) { 9304 if (isKeyOfType(Comp, key, type)) { 9305 extracted[key] = instance.ctx[key]; 9306 } 9307 } 9308 return extracted; 9309 } 9310 function isKeyOfType(Comp, key, type) { 9311 const opts = Comp[type]; 9312 if ((isArray(opts) && opts.includes(key)) || 9313 (isObject(opts) && key in opts)) { 9314 return true; 9315 } 9316 if (Comp.extends && isKeyOfType(Comp.extends, key, type)) { 9317 return true; 9318 } 9319 if (Comp.mixins && Comp.mixins.some(m => isKeyOfType(m, key, type))) { 9320 return true; 9321 } 9322 } 9323 function genRefFlag(v) { 9324 if (isShallow(v)) { 9325 return `ShallowRef`; 9326 } 9327 if (v.effect) { 9328 return `ComputedRef`; 9329 } 9330 return `Ref`; 9331 } 9332 if (window.devtoolsFormatters) { 9333 window.devtoolsFormatters.push(formatter); 9334 } 9335 else { 9336 window.devtoolsFormatters = [formatter]; 9337 } 9338 } 9339 9340 function withMemo(memo, render, cache, index) {
9341 const cached = cache[index]; 9342 if (cached && isMemoSame(cached, memo)) { 9343 return cached; 9344 } 9345 const ret = render(); 9346 // shallow clone 9347 ret.memo = memo.slice(); 9348 return (cache[index] = ret); 9349 } 9350 function isMemoSame(cached, memo) { 9351 const prev = cached.memo; 9352 if (prev.length != memo.length) { 9353 return false; 9354 } 9355 for (let i = 0; i < prev.length; i++) { 9356 if (hasChanged(prev[i], memo[i])) { 9357 return false; 9358 } 9359 } 9360 // make sure to let parent block track it when returning cached 9361 if (isBlockTreeEnabled > 0 && currentBlock) { 9362 currentBlock.push(cached); 9363 } 9364 return true; 9365 } 9366 9367 // Core API ------------------------------------------------------------------ 9368 const version = "3.2.45"; 9369 /** 9370 * SSR utils for \@vue/server-renderer. Only exposed in ssr-possible builds. 9371 * @internal 9372 */ 9373 const ssrUtils = (null); 9374 /** 9375 * @internal only exposed in compat builds 9376 */ 9377 const resolveFilter = null; 9378 /** 9379 * @internal only exposed in compat builds. 9380 */ 9381 const compatUtils = (null); 9382 9383 const svgNS = 'http://www.w3.org/2000/svg'; 9384 const doc = (typeof document !== 'undefined' ? document : null); 9385 const templateContainer = doc && /*#__PURE__*/ doc.createElement('template'); 9386 const nodeOps = { 9387 insert: (child, parent, anchor) => { 9388 parent.insertBefore(child, anchor || null); 9389 }, 9390 remove: child => { 9391 const parent = child.parentNode; 9392 if (parent) { 9393 parent.removeChild(child); 9394 } 9395 }, 9396 createElement: (tag, isSVG, is, props) => { 9397 const el = isSVG 9398 ? doc.createElementNS(svgNS, tag) 9399 : doc.createElement(tag, is ? { is } : undefined); 9400 if (tag === 'select' && props && props.multiple != null) { 9401 el.setAttribute('multiple', props.multiple); 9402 } 9403 return el; 9404 }, 9405 createText: text => doc.createTextNode(text), 9406 createComment: text => doc.createComment(text), 9407 setText: (node, text) => { 9408 node.nodeValue = text; 9409 }, 9410 setElementText: (el, text) => { 9411 el.textContent = text; 9412 }, 9413 parentNode: node => node.parentNode,
9414 nextSibling: node => node.nextSibling, 9415 querySelector: selector => doc.querySelector(selector), 9416 setScopeId(el, id) { 9417 el.setAttribute(id, ''); 9418 }, 9419 // __UNSAFE__ 9420 // Reason: innerHTML. 9421 // Static content here can only come from compiled templates. 9422 // As long as the user only uses trusted templates, this is safe. 9423 insertStaticContent(content, parent, anchor, isSVG, start, end) { 9424 // <parent> before | first ... last | anchor </parent> 9425 const before = anchor ? anchor.previousSibling : parent.lastChild; 9426 // #5308 can only take cached path if: 9427 // - has a single root node 9428 // - nextSibling info is still available 9429 if (start && (start === end || start.nextSibling)) { 9430 // cached 9431 while (true) { 9432 parent.insertBefore(start.cloneNode(true), anchor); 9433 if (start === end || !(start = start.nextSibling)) 9434 break; 9435 } 9436 } 9437 else { 9438 // fresh insert 9439 templateContainer.innerHTML = isSVG ? `<svg>${content}</svg>` : content; 9440 const template = templateContainer.content; 9441 if (isSVG) { 9442 // remove outer svg wrapper 9443 const wrapper = template.firstChild; 9444 while (wrapper.firstChild) { 9445 template.appendChild(wrapper.firstChild); 9446 } 9447 template.removeChild(wrapper); 9448 } 9449 parent.insertBefore(template, anchor); 9450 } 9451 return [ 9452 // first 9453 before ? before.nextSibling : parent.firstChild, 9454 // last 9455 anchor ? anchor.previousSibling : parent.lastChild 9456 ]; 9457 } 9458 }; 9459 9460 // compiler should normalize class + :class bindings on the same element 9461 // into a single binding ['staticClass', dynamic] 9462 function patchClass(el, value, isSVG) { 9463 // directly setting className should be faster than setAttribute in theory 9464 // if this is an element during a transition, take the temporary transition 9465 // classes into account. 9466 const transitionClasses = el._vtc; 9467 if (transitionClasses) { 9468 value = (value ? [value, ...transitionClasses] : [...transitionClasses]).join(' '); 9469 } 9470 if (value == null) { 9471 el.removeAttribute('class'); 9472 } 9473 else if (isSVG) { 9474 el.setAttribute('class', value); 9475 } 9476 else { 9477 el.className = value; 9478 } 9479 } 9480 9481 function patchStyle(el, prev, next) { 9482 const style = el.style; 9483 const isCssString = isString(next); 9484 if (next && !isCssString) { 9485 for (const key in next) { 9486 setStyle(style, key, next[key]); 9487 } 9488 if (prev && !isString(prev)) { 9489 for (const key in prev) { 9490 if (next[key] == null) { 9491 setStyle(style, key, ''); 9492 } 9493 } 9494 } 9495 } 9496 else { 9497 const currentDisplay = style.display; 9498 if (isCssString) { 9499 if (prev !== next) { 9500 style.cssText = next; 9501 } 9502 } 9503 else if (prev) { 9504 el.removeAttribute('style'); 9505 } 9506 // indicates that the `display` of the element is controlled by `v-show`, 9507 // so we always keep the current `display` value regardless of the `style` 9508 // value, thus handing over control to `v-show`. 9509 if ('_vod' in el) { 9510 style.display = currentDisplay; 9511 } 9512 } 9513 } 9514 const semicolonRE = /[^\\];\s*$/; 9515 const importantRE = /\s*!important$/; 9516 function setStyle(style, name, val) { 9517 if (isArray(val)) { 9518 val.forEach(v => setStyle(style, name, v)); 9519 } 9520 else { 9521 if (val == null) 9522 val = ''; 9523 { 9524 if (semicolonRE.test(val)) { 9525 warn$1(`Unexpected semicolon at the end of '${name}' style value: '${val}'`); 9526 } 9527 } 9528 if (name.startsWith('--')) { 9529 // custom property definition 9530 style.setProperty(name, val); 9531 } 9532 else { 9533 const prefixed = autoPrefix(style, name); 9534 if (importantRE.test(val)) { 9535 // !important 9536 style.setProperty(hyphenate(prefixed), val.replace(importantRE, ''), 'important'); 9537 } 9538 else { 9539 style[prefixed] = val; 9540 } 9541 } 9542 } 9543 } 9544 const prefixes = ['Webkit', 'Moz', 'ms']; 9545 const prefixCache = {}; 9546 function autoPrefix(style, rawName) { 9547 const cached = prefixCache[rawName]; 9548 if (cached) { 9549 return cached; 9550 } 9551 let name = camelize(rawName); 9552 if (name !== 'filter' && name in style) { 9553 return (prefixCache[rawName] = name); 9554 } 9555 name = capitalize(name); 9556 for (let i = 0; i < prefixes.length; i++) { 9557 const prefixed = prefixes[i] + name; 9558 if (prefixed in style) { 9559 return (prefixCache[rawName] = prefixed); 9560 } 9561 } 9562 return rawName; 9563 } 9564 9565 const xlinkNS = 'http://www.w3.org/1999/xlink'; 9566 function patchAttr(el, key, value, isSVG, instance) { 9567 if (isSVG && key.startsWith('xlink:')) { 9568 if (value == null) { 9569 el.removeAttributeNS(xlinkNS, key.slice(6, key.length)); 9570 } 9571 else { 9572 el.setAttributeNS(xlinkNS, key, value); 9573 } 9574 } 9575 else { 9576 // note we are only checking boolean attributes that don't have a 9577 // corresponding dom prop of the same name here. 9578 const isBoolean = isSpecialBooleanAttr(key); 9579 if (value == null || (isBoolean && !includeBooleanAttr(value))) { 9580 el.removeAttribute(key); 9581 } 9582 else { 9583 el.setAttribute(key, isBoolean ? '' : value); 9584 } 9585 } 9586 } 9587 9588 // __UNSAFE__ 9589 // functions. The user is responsible for using them with only trusted content. 9590 function patchDOMProp(el, key, value, 9591 // the following args are passed only due to potential innerHTML/textContent 9592 // overriding existing VNodes, in which case the old tree must be properly 9593 // unmounted. 9594 prevChildren, parentComponent, parentSuspense, unmountChildren) {
9595 if (key === 'innerHTML' || key === 'textContent') { 9596 if (prevChildren) { 9597 unmountChildren(prevChildren, parentComponent, parentSuspense); 9598 } 9599 el[key] = value == null ? '' : value; 9600 return; 9601 } 9602 if (key === 'value' && 9603 el.tagName !== 'PROGRESS' && 9604 // custom elements may use _value internally 9605 !el.tagName.includes('-')) { 9606 // store value as _value as well since 9607 // non-string values will be stringified. 9608 el._value = value; 9609 const newValue = value == null ? '' : value; 9610 if (el.value !== newValue || 9611 // #4956: always set for OPTION elements because its value falls back to 9612 // textContent if no value attribute is present. And setting .value for 9613 // OPTION has no side effect 9614 el.tagName === 'OPTION') { 9615 el.value = newValue; 9616 } 9617 if (value == null) { 9618 el.removeAttribute(key); 9619 } 9620 return; 9621 } 9622 let needRemove = false; 9623 if (value === '' || value == null) { 9624 const type = typeof el[key]; 9625 if (type === 'boolean') { 9626 // e.g. <select multiple> compiles to { multiple: '' } 9627 value = includeBooleanAttr(value); 9628 } 9629 else if (value == null && type === 'string') { 9630 // e.g. <div :id="null"> 9631 value = ''; 9632 needRemove = true; 9633 } 9634 else if (type === 'number') { 9635 // e.g. <img :width="null"> 9636 value = 0; 9637 needRemove = true; 9638 } 9639 } 9640 // some properties perform value validation and throw, 9641 // some properties has getter, no setter, will error in 'use strict' 9642 // eg. <select :type="null"></select> <select :willValidate="null"></select> 9643 try { 9644 el[key] = value; 9645 } 9646 catch (e) { 9647 // do not warn if value is auto-coerced from nullish values 9648 if (!needRemove) { 9649 warn$1(`Failed setting prop "${key}" on <${el.tagName.toLowerCase()}>: ` + 9650 `value ${value} is invalid.`, e); 9651 } 9652 } 9653 needRemove && el.removeAttribute(key); 9654 } 9655 9656 function addEventListener(el, event, handler, options) { 9657 el.addEventListener(event, handler, options); 9658 } 9659 function removeEventListener(el, event, handler, options) { 9660 el.removeEventListener(event, handler, options); 9661 } 9662 function patchEvent(el, rawName, prevValue, nextValue, instance = null) { 9663 // vei = vue event invokers 9664 const invokers = el._vei || (el._vei = {}); 9665 const existingInvoker = invokers[rawName];
9666 if (nextValue && existingInvoker) { 9667 // patch 9668 existingInvoker.value = nextValue; 9669 } 9670 else { 9671 const [name, options] = parseName(rawName); 9672 if (nextValue) { 9673 // add 9674 const invoker = (invokers[rawName] = createInvoker(nextValue, instance)); 9675 addEventListener(el, name, invoker, options); 9676 } 9677 else if (existingInvoker) { 9678 // remove 9679 removeEventListener(el, name, existingInvoker, options); 9680 invokers[rawName] = undefined; 9681 } 9682 } 9683 } 9684 const optionsModifierRE = /(?:Once|Passive|Capture)$/; 9685 function parseName(name) { 9686 let options; 9687 if (optionsModifierRE.test(name)) { 9688 options = {}; 9689 let m; 9690 while ((m = name.match(optionsModifierRE))) { 9691 name = name.slice(0, name.length - m[0].length); 9692 options[m[0].toLowerCase()] = true; 9693 } 9694 } 9695 const event = name[2] === ':' ? name.slice(3) : hyphenate(name.slice(2)); 9696 return [event, options]; 9697 } 9698 // To avoid the overhead of repeatedly calling Date.now(), we cache 9699 // and use the same timestamp for all event listeners attached in the same tick. 9700 let cachedNow = 0; 9701 const p = /*#__PURE__*/ Promise.resolve(); 9702 const getNow = () => cachedNow || (p.then(() => (cachedNow = 0)), (cachedNow = Date.now())); 9703 function createInvoker(initialValue, instance) { 9704 const invoker = (e) => { 9705 // async edge case vuejs/vue#6566 9706 // inner click event triggers patch, event handler 9707 // attached to outer element during patch, and triggered again. This 9708 // happens because browsers fire microtask ticks between event propagation. 9709 // this no longer happens for templates in Vue 3, but could still be 9710 // theoretically possible for hand-written render functions. 9711 // the solution: we save the timestamp when a handler is attached, 9712 // and also attach the timestamp to any event that was handled by vue 9713 // for the first time (to avoid inconsistent event timestamp implementations 9714 // or events fired from iframes, e.g. #2513) 9715 // The handler would only fire if the event passed to it was fired 9716 // AFTER it was attached. 9717 if (!e._vts) { 9718 e._vts = Date.now(); 9719 } 9720 else if (e._vts <= invoker.attached) { 9721 return; 9722 } 9723 callWithAsyncErrorHandling(patchStopImmediatePropagation(e, invoker.value), instance, 5 /* ErrorCodes.NATIVE_EVENT_HANDLER */, [e]); 9724 }; 9725 invoker.value = initialValue; 9726 invoker.attached = getNow(); 9727 return invoker; 9728 } 9729 function patchStopImmediatePropagation(e, value) { 9730 if (isArray(value)) { 9731 const originalStop = e.stopImmediatePropagation; 9732 e.stopImmediatePropagation = () => { 9733 originalStop.call(e); 9734 e._stopped = true; 9735 }; 9736 return value.map(fn => (e) => !e._stopped && fn && fn(e)); 9737 } 9738 else { 9739 return value; 9740 } 9741 } 9742 9743 const nativeOnRE = /^on[a-z]/; 9744 const patchProp = (el, key, prevValue, nextValue, isSVG = false, prevChildren, parentComponent, parentSuspense, unmountChildren) => { 9745 if (key === 'class') { 9746 patchClass(el, nextValue, isSVG); 9747 } 9748 else if (key === 'style') { 9749 patchStyle(el, prevValue, nextValue); 9750 } 9751 else if (isOn(key)) { 9752 // ignore v-model listeners 9753 if (!isModelListener(key)) { 9754 patchEvent(el, key, prevValue, nextValue, parentComponent); 9755 } 9756 } 9757 else if (key[0] === '.' 9758 ? ((key = key.slice(1)), true) 9759 : key[0] === '^' 9760 ? ((key = key.slice(1)), false) 9761 : shouldSetAsProp(el, key, nextValue, isSVG)) { 9762 patchDOMProp(el, key, nextValue, prevChildren, parentComponent, parentSuspense, unmountChildren); 9763 } 9764 else { 9765 // special case for <input v-model type="checkbox"> with 9766 // :true-value & :false-value 9767 // store value as dom properties since non-string values will be 9768 // stringified. 9769 if (key === 'true-value') { 9770 el._trueValue = nextValue; 9771 } 9772 else if (key === 'false-value') { 9773 el._falseValue = nextValue; 9774 } 9775 patchAttr(el, key, nextValue, isSVG); 9776 } 9777 }; 9778 function shouldSetAsProp(el, key, value, isSVG) { 9779 if (isSVG) { 9780 // most keys must be set as attribute on svg elements to work 9781 // ...except innerHTML & textContent
9782 if (key === 'innerHTML' || key === 'textContent') { 9783 return true; 9784 } 9785 // or native onclick with function values 9786 if (key in el && nativeOnRE.test(key) && isFunction(value)) { 9787 return true; 9788 } 9789 return false; 9790 } 9791 // these are enumerated attrs, however their corresponding DOM properties 9792 // are actually booleans - this leads to setting it with a string "false" 9793 // value leading it to be coerced to `true`, so we need to always treat 9794 // them as attributes. 9795 // Note that `contentEditable` doesn't have this problem: its DOM 9796 // property is also enumerated string values. 9797 if (key === 'spellcheck' || key === 'draggable' || key === 'translate') { 9798 return false; 9799 } 9800 // #1787, #2840 form property on form elements is readonly and must be set as 9801 // attribute. 9802 if (key === 'form') { 9803 return false; 9804 } 9805 // #1526 <input list> must be set as attribute 9806 if (key === 'list' && el.tagName === 'INPUT') { 9807 return false; 9808 } 9809 // #2766 <textarea type> must be set as attribute 9810 if (key === 'type' && el.tagName === 'TEXTAREA') { 9811 return false; 9812 } 9813 // native onclick with string value, must be set as attribute 9814 if (nativeOnRE.test(key) && isString(value)) { 9815 return false; 9816 } 9817 return key in el; 9818 } 9819 9820 function defineCustomElement(options, hydrate) { 9821 const Comp = defineComponent(options); 9822 class VueCustomElement extends VueElement { 9823 constructor(initialProps) { 9824 super(Comp, initialProps, hydrate); 9825 } 9826 } 9827 VueCustomElement.def = Comp; 9828 return VueCustomElement; 9829 } 9830 const defineSSRCustomElement = ((options) => { 9831 // @ts-ignore 9832 return defineCustomElement(options, hydrate); 9833 }); 9834 const BaseClass = (typeof HTMLElement !== 'undefined' ? HTMLElement : class { 9835 }); 9836 class VueElement extends BaseClass { 9837 constructor(_def, _props = {}, hydrate) { 9838 super(); 9839 this._def = _def; 9840 this._props = _props; 9841 /** 9842 * @internal 9843 */ 9844 this._instance = null; 9845 this._connected = false; 9846 this._resolved = false; 9847 this._numberProps = null; 9848 if (this.shadowRoot && hydrate) { 9849 hydrate(this._createVNode(), this.shadowRoot); 9850 } 9851 else { 9852 if (this.shadowRoot) { 9853 warn$1(`Custom element has pre-rendered declarative shadow root but is not ` + 9854 `defined as hydratable. Use \`defineSSRCustomElement\`.`); 9855 } 9856 this.attachShadow({ mode: 'open' }); 9857 if (!this._def.__asyncLoader) { 9858 // for sync component defs we can immediately resolve props 9859 this._resolveProps(this._def); 9860 } 9861 } 9862 } 9863 connectedCallback() { 9864 this._connected = true; 9865 if (!this._instance) { 9866 if (this._resolved) { 9867 this._update(); 9868 } 9869 else { 9870 this._resolveDef(); 9871 } 9872 } 9873 } 9874 disconnectedCallback() { 9875 this._connected = false; 9876 nextTick(() => { 9877 if (!this._connected) { 9878 render(null, this.shadowRoot); 9879 this._instance = null; 9880 } 9881 }); 9882 } 9883 /** 9884 * resolve inner component definition (handle possible async component) 9885 */ 9886 _resolveDef() { 9887 this._resolved = true; 9888 // set initial attrs 9889 for (let i = 0; i < this.attributes.length; i++) { 9890 this._setAttr(this.attributes[i].name); 9891 } 9892 // watch future attr changes 9893 new MutationObserver(mutations => { 9894 for (const m of mutations) { 9895 this._setAttr(m.attributeName); 9896 } 9897 }).observe(this, { attributes: true }); 9898 const resolve = (def, isAsync = false) => { 9899 const { props, styles } = def; 9900 // cast Number-type props set before resolve 9901 let numberProps; 9902 if (props && !isArray(props)) { 9903 for (const key in props) { 9904 const opt = props[key]; 9905 if (opt === Number || (opt && opt.type === Number)) { 9906 if (key in this._props) { 9907 this._props[key] = toNumber(this._props[key]); 9908 } 9909 (numberProps || (numberProps = Object.create(null)))[
9909camelize(key)] = true; 9910 } 9911 } 9912 } 9913 this._numberProps = numberProps; 9914 if (isAsync) { 9915 // defining getter/setters on prototype 9916 // for sync defs, this already happened in the constructor 9917 this._resolveProps(def); 9918 } 9919 // apply CSS 9920 this._applyStyles(styles); 9921 // initial render 9922 this._update(); 9923 }; 9924 const asyncDef = this._def.__asyncLoader; 9925 if (asyncDef) { 9926 asyncDef().then(def => resolve(def, true)); 9927 } 9928 else { 9929 resolve(this._def); 9930 } 9931 } 9932 _resolveProps(def) { 9933 const { props } = def; 9934 const declaredPropKeys = isArray(props) ? props : Object.keys(props || {}); 9935 // check if there are props set pre-upgrade or connect 9936 for (const key of Object.keys(this)) { 9937 if (key[0] !== '_' && declaredPropKeys.includes(key)) { 9938 this._setProp(key, this[key], true, false); 9939 } 9940 } 9941 // defining getter/setters on prototype 9942 for (const key of declaredPropKeys.map(camelize)) { 9943 Object.defineProperty(this, key, { 9944 get() { 9945 return this._getProp(key); 9946 }, 9947 set(val) { 9948 this._setProp(key, val); 9949 } 9950 }); 9951 } 9952 } 9953 _setAttr(key) { 9954 let value = this.getAttribute(key); 9955 const camelKey = camelize(key); 9956 if (this._numberProps && this._numberProps[camelKey]) { 9957 value = toNumber(value); 9958 } 9959 this._setProp(camelKey, value, false); 9960 } 9961 /** 9962 * @internal 9963 */ 9964 _getProp(key) { 9965 return this._props[key]; 9966 } 9967 /** 9968 * @internal 9969 */ 9970 _setProp(key, val, shouldReflect = true, shouldUpdate = true) { 9971 if (val !== this._props[key]) { 9972 this._props[key] = val; 9973 if (shouldUpdate && this._instance) { 9974 this._update(); 9975 } 9976 // reflect 9977 if (shouldReflect) { 9978 if (val === true) { 9979 this.setAttribute(hyphenate(key), ''); 9980 } 9981 else if (typeof val === 'string' || typeof val === 'number') { 9982 this.setAttribute(hyphenate(key), val + ''); 9983 } 9984 else if (!val) { 9985 this.removeAttribute(hyphenate(key)); 9986 } 9987 } 9988 } 9989 } 9990 _update() { 9991 render(this._createVNode(), this.shadowRoot); 9992 } 9993 _createVNode() { 9994 const vnode = createVNode(this._def, extend({}, this._props)); 9995 if (!this._instance) { 9996 vnode.ce = instance => { 9997 this._instance = instance; 9998 instance.isCE = true; 9999 // HMR 10000 { 10001 instance.ceReload = newStyles => { 10002 // always reset styles 10003 if (this._styles) { 10004 this._styles.forEach(s => this.shadowRoot.removeChild(s)); 10005 this._styles.length = 0; 10006 } 10007 this._applyStyles(newStyles); 10008 this._instance = null; 10009 this._update(); 10010 }; 10011 } 10012 const dispatch = (event, args) => { 10013 this.dispatchEvent(new CustomEvent(event, { 10014 detail: args 10015 })); 10016 }; 10017 // intercept emit 10018 instance.emit = (event, ...args) => { 10019 // dispatch both the raw and hyphenated versions of an event 10020 // to match Vue behavior 10021 dispatch(event, args); 10022 if (hyphenate(event) !== event) { 10023 dispatch(hyphenate(event), args); 10024 } 10025 }; 10026 // locate nearest Vue custom element parent for provide/inject 10027 let parent = this; 10028 while ((parent = 10029 parent && (parent.parentNode || parent.host))) { 10030 if (parent instanceof VueElement) { 10031 instance.parent = parent._instance; 10032 instance.provides = parent._instance.provides; 10033 break; 10034 } 10035 } 10036 }; 10037 } 10038 return vnode; 10039 } 10040 _applyStyles(styles) { 10041 if (styles) {
10042 styles.forEach(css => { 10043 const s = document.createElement('style'); 10044 s.textContent = css; 10045 this.shadowRoot.appendChild(s); 10046 // record for HMR 10047 { 10048 (this._styles || (this._styles = [])).push(s); 10049 } 10050 }); 10051 } 10052 } 10053 } 10054 10055 function useCssModule(name = '$style') { 10056 /* istanbul ignore else */ 10057 { 10058 { 10059 warn$1(`useCssModule() is not supported in the global build.`); 10060 } 10061 return EMPTY_OBJ; 10062 } 10063 } 10064 10065 /** 10066 * Runtime helper for SFC's CSS variable injection feature. 10067 * @private 10068 */ 10069 function useCssVars(getter) { 10070 const instance = getCurrentInstance(); 10071 /* istanbul ignore next */ 10072 if (!instance) { 10073 warn$1(`useCssVars is called without current active component instance.`); 10074 return; 10075 } 10076 const updateTeleports = (instance.ut = (vars = getter(instance.proxy)) => { 10077 Array.from(document.querySelectorAll(`[data-v-owner="${instance.uid}"]`)).forEach(node => setVarsOnNode(node, vars)); 10078 }); 10079 const setVars = () => { 10080 const vars = getter(instance.proxy); 10081 setVarsOnVNode(instance.subTree, vars); 10082 updateTeleports(vars); 10083 }; 10084 watchPostEffect(setVars); 10085 onMounted(() => { 10086 const ob = new MutationObserver(setVars); 10087 ob.observe(instance.subTree.el.parentNode, { childList: true }); 10088 onUnmounted(() => ob.disconnect()); 10089 }); 10090 } 10091 function setVarsOnVNode(vnode, vars) { 10092 if (vnode.shapeFlag & 128 /* ShapeFlags.SUSPENSE */) { 10093 const suspense = vnode.suspense; 10094 vnode = suspense.activeBranch; 10095 if (suspense.pendingBranch && !suspense.isHydrating) { 10096 suspense.effects.push(() => { 10097 setVarsOnVNode(suspense.activeBranch, vars); 10098 }); 10099 } 10100 } 10101 // drill down HOCs until it's a non-component vnode 10102 while (vnode.component) { 10103 vnode = vnode.component.subTree; 10104 } 10105 if (vnode.shapeFlag & 1 /* ShapeFlags.ELEMENT */ && vnode.el) { 10106 setVarsOnNode(vnode.el, vars); 10107 } 10108 else if (vnode.type === Fragment) { 10109 vnode.children.forEach(c => setVarsOnVNode(c, vars)); 10110 } 10111 else if (vnode.type === Static) { 10112 let { el, anchor } = vnode; 10113 while (el) { 10114 setVarsOnNode(el, vars); 10115 if (el === anchor) 10116 break; 10117 el = el.nextSibling; 10118 } 10119 } 10120 } 10121 function setVarsOnNode(el, vars) { 10122 if (el.nodeType === 1) { 10123 const style = el.style; 10124 for (const key in vars) { 10125 style.setProperty(`--${key}`, vars[key]); 10126 } 10127 } 10128 } 10129 10130 const TRANSITION = 'transition'; 10131 const ANIMATION = 'animation'; 10132 // DOM Transition is a higher-order-component based on the platform-agnostic 10133 // base Transition component, with DOM-specific logic. 10134 const Transition = (props, { slots }) => h(BaseTransition, resolveTransitionProps(props), slots); 10135 Transition.displayName = 'Transition'; 10136 const DOMTransitionPropsValidators = { 10137 name: String, 10138 type: String, 10139 css: { 10140 type: Boolean, 10141 default: true 10142 }, 10143 duration: [String, Number, Object], 10144 enterFromClass: String, 10145 enterActiveClass: String, 10146 enterToClass: String, 10147 appearFromClass: String, 10148 appearActiveClass: String, 10149 appearToClass: String, 10150 leaveFromClass: String, 10151 leaveActiveClass: String, 10152 leaveToClass: String 10153 }; 10154 const TransitionPropsValidators = (Transition.props = 10155 /*#__PURE__*/ extend({}, BaseTransition.props, DOMTransitionPropsValidators)); 10156 /** 10157 * #3227 Incoming hooks may be merged into arrays when wrapping Transition 10158 * with custom HOCs. 10159 */ 10160 const callHook$1 = (hook, args = []) => { 10161 if (isArray(hook)) { 10162 hook.forEach(h => h(...args)); 10163 } 10164 else if (hook) { 10165 hook(...args); 10166 } 10167 }; 10168 /** 10169 * Check if a hook expects a callback (2nd arg), which means the user 10170 * intends to explicitly control the end of the transition. 10171 */ 10172 const hasExplicitCallback = (hook) => { 10173 return hook 10174 ? isArray(hook) 10175 ? hook.some(h => h.length > 1) 10176 : hook.length > 1 10177 : false;
vendor: 4,229 bytes, lines 10178-10274
10178 }; 10179 function resolveTransitionProps(rawProps) { 10180 const baseProps = {}; 10181 for (const key in rawProps) { 10182 if (!(key in DOMTransitionPropsValidators)) { 10183 baseProps[key] = rawProps[key]; 10184 } 10185 } 10186 if (rawProps.css === false) { 10187 return baseProps; 10188 } 10189 const { name = 'v', type, duration, enterFromClass = `${name}-enter-from`, enterActiveClass = `${name}-enter-active`, enterToClass = `${name}-enter-to`, appearFromClass = enterFromClass, appearActiveClass = enterActiveClass, appearToClass = enterToClass, leaveFromClass = `${name}-leave-from`, leaveActiveClass = `${name}-leave-active`, leaveToClass = `${name}-leave-to` } = rawProps; 10190 const durations = normalizeDuration(duration); 10191 const enterDuration = durations && durations[0]; 10192 const leaveDuration = durations && durations[1]; 10193 const { onBeforeEnter, onEnter, onEnterCancelled, onLeave, onLeaveCancelled, onBeforeAppear = onBeforeEnter, onAppear = onEnter, onAppearCancelled = onEnterCancelled } = baseProps; 10194 const finishEnter = (el, isAppear, done) => { 10195 removeTransitionClass(el, isAppear ? appearToClass : enterToClass); 10196 removeTransitionClass(el, isAppear ? appearActiveClass : enterActiveClass); 10197 done && done(); 10198 }; 10199 const finishLeave = (el, done) => { 10200 el._isLeaving = false; 10201 removeTransitionClass(el, leaveFromClass); 10202 removeTransitionClass(el, leaveToClass); 10203 removeTransitionClass(el, leaveActiveClass); 10204 done && done(); 10205 }; 10206 const makeEnterHook = (isAppear) => { 10207 return (el, done) => { 10208 const hook = isAppear ? onAppear : onEnter; 10209 const resolve = () => finishEnter(el, isAppear, done); 10210 callHook$1(hook, [el, resolve]); 10211 nextFrame(() => { 10212 removeTransitionClass(el, isAppear ? appearFromClass : enterFromClass); 10213 addTransitionClass(el, isAppear ? appearToClass : enterToClass); 10214 if (!hasExplicitCallback(hook)) { 10215 whenTransitionEnds(el, type, enterDuration, resolve); 10216 } 10217 }); 10218 }; 10219 }; 10220 return extend(baseProps, { 10221 onBeforeEnter(el) { 10222 callHook$1(onBeforeEnter, [el]); 10223 addTransitionClass(el, enterFromClass); 10224 addTransitionClass(el, enterActiveClass); 10225 }, 10226 onBeforeAppear(el) { 10227 callHook$1(onBeforeAppear, [el]); 10228 addTransitionClass(el, appearFromClass); 10229 addTransitionClass(el, appearActiveClass); 10230 }, 10231 onEnter: makeEnterHook(false), 10232 onAppear: makeEnterHook(true), 10233 onLeave(el, done) { 10234 el._isLeaving = true; 10235 const resolve = () => finishLeave(el, done); 10236 addTransitionClass(el, leaveFromClass); 10237 // force reflow so *-leave-from classes immediately take effect (#2593) 10238 forceReflow(); 10239 addTransitionClass(el, leaveActiveClass); 10240 nextFrame(() => { 10241 if (!el._isLeaving) { 10242 // cancelled 10243 return; 10244 } 10245 removeTransitionClass(el, leaveFromClass); 10246 addTransitionClass(el, leaveToClass); 10247 if (!hasExplicitCallback(onLeave)) { 10248 whenTransitionEnds(el, type, leaveDuration, resolve); 10249 } 10250 }); 10251 callHook$1(onLeave, [el, resolve]); 10252 }, 10253 onEnterCancelled(el) { 10254 finishEnter(el, false); 10255 callHook$1(onEnterCancelled, [el]); 10256 }, 10257 onAppearCancelled(el) { 10258 finishEnter(el, true); 10259 callHook$1(onAppearCancelled, [el]); 10260 }, 10261 onLeaveCancelled(el) { 10262 finishLeave(el); 10263 callHook$1(onLeaveCancelled, [el]); 10264 } 10265 }); 10266 } 10267 function normalizeDuration(duration) { 10268 if (duration == null) { 10269 return null; 10270 } 10271 else if (isObject(duration)) { 10272 return [NumberOf(duration.enter), NumberOf(duration.leave)]; 10273 } 10274 else {
10275 const n = NumberOf(duration); 10276 return [n, n]; 10277 } 10278 } 10279 function NumberOf(val) { 10280 const res = toNumber(val); 10281 validateDuration(res); 10282 return res; 10283 } 10284 function validateDuration(val) { 10285 if (typeof val !== 'number') { 10286 warn$1(`<transition> explicit duration is not a valid number - ` + 10287 `got ${JSON.stringify(val)}.`); 10288 } 10289 else if (isNaN(val)) { 10290 warn$1(`<transition> explicit duration is NaN - ` + 10291 'the duration expression might be incorrect.'); 10292 } 10293 } 10294 function addTransitionClass(el, cls) { 10295 cls.split(/\s+/).forEach(c => c && el.classList.add(c)); 10296 (el._vtc || 10297 (el._vtc = new Set())).add(cls); 10298 } 10299 function removeTransitionClass(el, cls) { 10300 cls.split(/\s+/).forEach(c => c && el.classList.remove(c)); 10301 const { _vtc } = el; 10302 if (_vtc) { 10303 _vtc.delete(cls); 10304 if (!_vtc.size) { 10305 el._vtc = undefined; 10306 } 10307 } 10308 } 10309 function nextFrame(cb) { 10310 requestAnimationFrame(() => { 10311 requestAnimationFrame(cb); 10312 }); 10313 } 10314 let endId = 0; 10315 function whenTransitionEnds(el, expectedType, explicitTimeout, resolve) { 10316 const id = (el._endId = ++endId); 10317 const resolveIfNotStale = () => { 10318 if (id === el._endId) { 10319 resolve(); 10320 } 10321 }; 10322 if (explicitTimeout) { 10323 return setTimeout(resolveIfNotStale, explicitTimeout); 10324 } 10325 const { type, timeout, propCount } = getTransitionInfo(el, expectedType); 10326 if (!type) { 10327 return resolve(); 10328 } 10329 const endEvent = type + 'end'; 10330 let ended = 0; 10331 const end = () => { 10332 el.removeEventListener(endEvent, onEnd); 10333 resolveIfNotStale(); 10334 }; 10335 const onEnd = (e) => { 10336 if (e.target === el && ++ended >= propCount) { 10337 end(); 10338 } 10339 }; 10340 setTimeout(() => { 10341 if (ended < propCount) { 10342 end(); 10343 } 10344 }, timeout + 1); 10345 el.addEventListener(endEvent, onEnd); 10346 } 10347 function getTransitionInfo(el, expectedType) { 10348 const styles = window.getComputedStyle(el); 10349 // JSDOM may return undefined for transition properties 10350 const getStyleProperties = (key) => (styles[key] || '').split(', '); 10351 const transitionDelays = getStyleProperties(`${TRANSITION}Delay`); 10352 const transitionDurations = getStyleProperties(`${TRANSITION}Duration`); 10353 const transitionTimeout = getTimeout(transitionDelays, transitionDurations); 10354 const animationDelays = getStyleProperties(`${ANIMATION}Delay`); 10355 const animationDurations = getStyleProperties(`${ANIMATION}Duration`); 10356 const animationTimeout = getTimeout(animationDelays, animationDurations); 10357 let type = null; 10358 let timeout = 0; 10359 let propCount = 0; 10360 /* istanbul ignore if */ 10361 if (expectedType === TRANSITION) { 10362 if (transitionTimeout > 0) { 10363 type = TRANSITION; 10364 timeout = transitionTimeout; 10365 propCount = transitionDurations.length; 10366 } 10367 } 10368 else if (expectedType === ANIMATION) { 10369 if (animationTimeout > 0) { 10370 type = ANIMATION; 10371 timeout = animationTimeout; 10372 propCount = animationDurations.length; 10373 } 10374 } 10375 else { 10376 timeout = Math.max(transitionTimeout, animationTimeout); 10377 type = 10378 timeout > 0 10379 ? transitionTimeout > animationTimeout 10380 ? TRANSITION 10381 : ANIMATION 10382 : null; 10383 propCount = type 10384 ? type === TRANSITION 10385 ? transitionDurations.length 10386 : animationDurations.length 10387 : 0; 10388 } 10389 const hasTransform = type === TRANSITION && 10390 /\b(transform|all)(,|$)/.test(getStyleProperties(`${TRANSITION}Property`).toString()); 10391 return { 10392 type, 10393 timeout, 10394 propCount, 10395 hasTransform 10396 }; 10397 } 10398 function getTimeout(delays, durations) { 10399 while (delays.length < durations.length) { 10400 delays = delays.concat(delays); 10401 } 10402 return Math.max(...durations.map((d, i) => toMs(d) + toMs(delays[i]))); 10403 } 10404 // Old versions of Chromium (below 61.0.3163.100) formats floating pointer 10405 // numbers in a locale-dependent way, using a comma instead of a dot. 10406 // If comma is not replaced with a dot, the input will be rounded down 10407 // (i.e. acting as a floor function) causing unexpected behaviors 10408 function toMs(s) { 10409 return Number(s.slice(0, -1).replace(',', '.')) * 1000; 10410 } 10411 // synchronously force layout to put elements into a certain state 10412 function forceReflow() { 10413 return document.body.offsetHeight; 10414 } 10415 10416 const positionMap = new WeakMap(); 10417 const newPositionMap = new WeakMap(); 10418 const TransitionGroupImpl = { 10419 name: 'TransitionGroup', 10420 props: /*#__PURE__*/ extend({}, TransitionPropsValidators, { 10421 tag: String, 10422 moveClass: String 10423 }), 10424 setup(props, { slots }) { 10425 const instance = getCurrentInstance(); 10426 const state = useTransitionState(); 10427 let prevChildren; 10428 let children; 10429 onUpdated(() => { 10430 // children is guaranteed to exist after initial render 10431 if (!prevChildren.length) { 10432 return; 10433 } 10434 const moveClass = props.moveClass || `${props.name || 'v'}-move`; 10435 if (!hasCSSTransform(prevChildren[0].el, instance.vnode.el, moveClass)) { 10436 return; 10437 } 10438 // we divide the work into three loops to avoid mixing DOM reads and writes 10439 // in each iteration - which helps prevent layout thrashing.
10440 prevChildren.forEach(callPendingCbs); 10441 prevChildren.forEach(recordPosition); 10442 const movedChildren = prevChildren.filter(applyTranslation); 10443 // force reflow to put everything in position 10444 forceReflow(); 10445 movedChildren.forEach(c => { 10446 const el = c.el; 10447 const style = el.style; 10448 addTransitionClass(el, moveClass); 10449 style.transform = style.webkitTransform = style.transitionDuration = ''; 10450 const cb = (el._moveCb = (e) => { 10451 if (e && e.target !== el) { 10452 return; 10453 } 10454 if (!e || /transform$/.test(e.propertyName)) { 10455 el.removeEventListener('transitionend', cb); 10456 el._moveCb = null; 10457 removeTransitionClass(el, moveClass); 10458 } 10459 }); 10460 el.addEventListener('transitionend', cb); 10461 }); 10462 }); 10463 return () => { 10464 const rawProps = toRaw(props); 10465 const cssTransitionProps = resolveTransitionProps(rawProps); 10466 let tag = rawProps.tag || Fragment; 10467 prevChildren = children; 10468 children = slots.default ? getTransitionRawChildren(slots.default()) : []; 10469 for (let i = 0; i < children.length; i++) { 10470 const child = children[i]; 10471 if (child.key != null) { 10472 setTransitionHooks(child, resolveTransitionHooks(child, cssTransitionProps, state, instance)); 10473 } 10474 else { 10475 warn$1(`<TransitionGroup> children must be keyed.`); 10476 } 10477 } 10478 if (prevChildren) { 10479 for (let i = 0; i < prevChildren.length; i++) { 10480 const child = prevChildren[i]; 10481 setTransitionHooks(child, resolveTransitionHooks(child, cssTransitionProps, state, instance)); 10482 positionMap.set(child, child.el.getBoundingClientRect()); 10483 } 10484 } 10485 return createVNode(tag, null, children); 10486 }; 10487 } 10488 }; 10489 const TransitionGroup = TransitionGroupImpl; 10490 function callPendingCbs(c) { 10491 const el = c.el; 10492 if (el._moveCb) { 10493 el._moveCb(); 10494 } 10495 if (el._enterCb) { 10496 el._enterCb(); 10497 } 10498 } 10499 function recordPosition(c) { 10500 newPositionMap.set(c, c.el.getBoundingClientRect()); 10501 } 10502 function applyTranslation(c) { 10503 const oldPos = positionMap.get(c); 10504 const newPos = newPositionMap.get(c); 10505 const dx = oldPos.left - newPos.left; 10506 const dy = oldPos.top - newPos.top; 10507 if (dx || dy) { 10508 const s = c.el.style; 10509 s.transform = s.webkitTransform = `translate(${dx}px,${dy}px)`; 10510 s.transitionDuration = '0s'; 10511 return c; 10512 } 10513 } 10514 function hasCSSTransform(el, root, moveClass) { 10515 // Detect whether an element with the move class applied has 10516 // CSS transitions. Since the element may be inside an entering 10517 // transition at this very moment, we make a clone of it and remove 10518 // all other transition classes applied to ensure only the move class 10519 // is applied. 10520 const clone = el.cloneNode(); 10521 if (el._vtc) { 10522 el._vtc.forEach(cls => { 10523 cls.split(/\s+/).forEach(c => c && clone.classList.remove(c)); 10524 }); 10525 } 10526 moveClass.split(/\s+/).forEach(c => c && clone.classList.add(c)); 10527 clone.style.display = 'none'; 10528 const container = (root.nodeType === 1 ? root : root.parentNode); 10529 container.appendChild(clone); 10530 const { hasTransform } = getTransitionInfo(clone); 10531 container.removeChild(clone); 10532 return hasTransform; 10533 } 10534 10535 const getModelAssigner = (vnode) => { 10536 const fn = vnode.props['onUpdate:modelValue'] || 10537 (false ); 10538 return isArray(fn) ? value => invokeArrayFns(fn, value) : fn; 10539 }; 10540 function onCompositionStart(e) { 10541 e.target.composing = true; 10542 } 10543 function onCompositionEnd(e) { 10544 const target = e.target; 10545 if (target.composing) { 10546 target.composing = false;
10547 target.dispatchEvent(new Event('input')); 10548 } 10549 } 10550 // We are exporting the v-model runtime directly as vnode hooks so that it can 10551 // be tree-shaken in case v-model is never used. 10552 const vModelText = { 10553 created(el, { modifiers: { lazy, trim, number } }, vnode) { 10554 el._assign = getModelAssigner(vnode); 10555 const castToNumber = number || (vnode.props && vnode.props.type === 'number'); 10556 addEventListener(el, lazy ? 'change' : 'input', e => { 10557 if (e.target.composing) 10558 return; 10559 let domValue = el.value; 10560 if (trim) { 10561 domValue = domValue.trim(); 10562 } 10563 if (castToNumber) { 10564 domValue = toNumber(domValue); 10565 } 10566 el._assign(domValue); 10567 }); 10568 if (trim) { 10569 addEventListener(el, 'change', () => { 10570 el.value = el.value.trim(); 10571 }); 10572 } 10573 if (!lazy) { 10574 addEventListener(el, 'compositionstart', onCompositionStart); 10575 addEventListener(el, 'compositionend', onCompositionEnd); 10576 // Safari < 10.2 & UIWebView doesn't fire compositionend when 10577 // switching focus before confirming composition choice 10578 // this also fixes the issue where some browsers e.g. iOS Chrome 10579 // fires "change" instead of "input" on autocomplete. 10580 addEventListener(el, 'change', onCompositionEnd); 10581 } 10582 }, 10583 // set value on mounted so it's after min/max for type="range" 10584 mounted(el, { value }) { 10585 el.value = value == null ? '' : value; 10586 }, 10587 beforeUpdate(el, { value, modifiers: { lazy, trim, number } }, vnode) { 10588 el._assign = getModelAssigner(vnode); 10589 // avoid clearing unresolved text. #2302 10590 if (el.composing) 10591 return; 10592 if (document.activeElement === el && el.type !== 'range') { 10593 if (lazy) { 10594 return; 10595 } 10596 if (trim && el.value.trim() === value) { 10597 return; 10598 } 10599 if ((number || el.type === 'number') && toNumber(el.value) === value) { 10600 return; 10601 } 10602 } 10603 const newValue = value == null ? '' : value; 10604 if (el.value !== newValue) { 10605 el.value = newValue; 10606 } 10607 } 10608 }; 10609 const vModelCheckbox = { 10610 // #4096 array checkboxes need to be deep traversed 10611 deep: true, 10612 created(el, _, vnode) { 10613 el._assign = getModelAssigner(vnode); 10614 addEventListener(el, 'change', () => { 10615 const modelValue = el._modelValue; 10616 const elementValue = getValue(el); 10617 const checked = el.checked; 10618 const assign = el._assign; 10619 if (isArray(modelValue)) { 10620 const index = looseIndexOf(modelValue, elementValue); 10621 const found = index !== -1; 10622 if (checked && !found) { 10623 assign(modelValue.concat(elementValue)); 10624 } 10625 else if (!checked && found) { 10626 const filtered = [...modelValue]; 10627 filtered.splice(index, 1); 10628 assign(filtered); 10629 } 10630 } 10631 else if (isSet(modelValue)) { 10632 const cloned = new Set(modelValue); 10633 if (checked) { 10634 cloned.add(elementValue); 10635 } 10636 else { 10637 cloned.delete(elementValue); 10638 } 10639 assign(cloned); 10640 } 10641 else { 10642 assign(getCheckboxValue(el, checked)); 10643 } 10644 }); 10645 }, 10646 // set initial checked on mount to wait for true-value/false-value 10647 mounted: setChecked, 10648 beforeUpdate(el, binding, vnode) { 10649 el._assign = getModelAssigner(vnode); 10650 setChecked(el, binding, vnode); 10651 } 10652 }; 10653 function setChecked(el, { value, oldValue }, vnode) { 10654 el._modelValue = value; 10655 if (isArray(value)) { 10656 el.checked = looseIndexOf(value, vnode.props.value) > -1; 10657 } 10658 else if (isSet(value)) { 10659 el.checked = value.has(vnode.props.value); 10660 } 10661 else if (value !== oldValue) { 10662 el.checked = looseEqual(value, getCheckboxValue(el, true)); 10663 } 10664 } 10665 const vModelRadio = { 10666 created(el, { value }, vnode) { 10667 el.checked = looseEqual(value, vnode.props.value); 10668 el._assign = getModelAssigner(vnode); 10669 addEventListener(el, 'change', () => { 10670 el._assign(getValue(el)); 10671 }); 10672 }, 10673 beforeUpdate(el, { value, oldValue }, vnode) { 10674 el._assign = getModelAssigner(vnode); 10675 if (value !== oldValue) { 10676 el.checked = looseEqual(value, vnode.props.value); 10677 } 10678 } 10679 }; 10680 const vModelSelect = { 10681 // <select multiple> value need to be deep traversed 10682 deep: true, 10683 created(el, { value, modifiers: { number } }, vnode) { 10684 const isSetModel = isSet(value); 10685 addEventListener(el, 'change', () => { 10686 const selectedVal = Array.prototype.filter 10687 .call(el.options, (o) => o.selected) 10688 .map((o) => number ? toNumber(getValue(o)) : getValue(o)); 10689 el._assign(el.multiple 10690 ? isSetModel 10691 ? new Set(selectedVal) 10692 : selectedVal 10693 : selectedVal[0]); 10694 }); 10695 el._assign = getModelAssigner(vnode); 10696 }, 10697 // set value in mounted & updated because <select> relies on its children 10698 // <option>s. 10699 mounted(el, { value }) { 10700 setSelected(el, value); 10701 }, 10702 beforeUpdate(el, _binding, vnode) { 10703 el._assign = getModelAssigner(vnode); 10704 }, 10705 updated(el, { value }) { 10706 setSelected(el, value); 10707 } 10708 }; 10709 function setSelected(el, value) { 10710 const isMultiple = el.multiple; 10711 if (isMultiple && !isArray(value) && !isSet(value)) { 10712 warn$1(`<select multiple v-model> expects an Array or Set value for its binding, ` + 10713 `but got ${Object.prototype.toString.call(value).slice(8, -1)}.`); 10714 return; 10715 } 10716 for (let i = 0, l = el.options.length; i < l; i++) { 10717 const option = el.options[i]; 10718 const optionValue = getValue(option); 10719 if (isMultiple) { 10720 if (isArray(value)) { 10721 option.selected = looseIndexOf(value, optionValue) > -1; 10722 } 10723 else { 10724 option.selected = value.has(optionValue); 10725 } 10726 } 10727 else { 10728 if (looseEqual(getValue(option), value)) { 10729 if (el.selectedIndex !== i) 10730 el.selectedIndex = i; 10731 return; 10732 } 10733 } 10734 } 10735 if (!isMultiple && el.selectedIndex !== -1) { 10736 el.selectedIndex = -1; 10737 } 10738 } 10739 // retrieve raw value set via :value bindings 10740 function getValue(el) { 10741 return '_value' in el ? el._value : el.value; 10742 } 10743 // retrieve raw value for true-value and false-value set via :true-value or :false-value bindings 10744 function getCheckboxValue(el, checked) {
10745 const key = checked ? '_trueValue' : '_falseValue'; 10746 return key in el ? el[key] : checked; 10747 } 10748 const vModelDynamic = { 10749 created(el, binding, vnode) { 10750 callModelHook(el, binding, vnode, null, 'created'); 10751 }, 10752 mounted(el, binding, vnode) { 10753 callModelHook(el, binding, vnode, null, 'mounted'); 10754 }, 10755 beforeUpdate(el, binding, vnode, prevVNode) { 10756 callModelHook(el, binding, vnode, prevVNode, 'beforeUpdate'); 10757 }, 10758 updated(el, binding, vnode, prevVNode) { 10759 callModelHook(el, binding, vnode, prevVNode, 'updated'); 10760 } 10761 }; 10762 function resolveDynamicModel(tagName, type) { 10763 switch (tagName) { 10764 case 'SELECT': 10765 return vModelSelect; 10766 case 'TEXTAREA': 10767 return vModelText; 10768 default: 10769 switch (type) { 10770 case 'checkbox': 10771 return vModelCheckbox; 10772 case 'radio': 10773 return vModelRadio; 10774 default: 10775 return vModelText; 10776 } 10777 } 10778 } 10779 function callModelHook(el, binding, vnode, prevVNode, hook) { 10780 const modelToUse = resolveDynamicModel(el.tagName, vnode.props && vnode.props.type); 10781 const fn = modelToUse[hook]; 10782 fn && fn(el, binding, vnode, prevVNode); 10783 } 10784 10785 const systemModifiers = ['ctrl', 'shift', 'alt', 'meta']; 10786 const modifierGuards = { 10787 stop: e => e.stopPropagation(), 10788 prevent: e => e.preventDefault(), 10789 self: e => e.target !== e.currentTarget, 10790 ctrl: e => !e.ctrlKey, 10791 shift: e => !e.shiftKey, 10792 alt: e => !e.altKey, 10793 meta: e => !e.metaKey, 10794 left: e => 'button' in e && e.button !== 0, 10795 middle: e => 'button' in e && e.button !== 1, 10796 right: e => 'button' in e && e.button !== 2, 10797 exact: (e, modifiers) => systemModifiers.some(m => e[`${m}Key`] && !modifiers.includes(m)) 10798 }; 10799 /** 10800 * @private 10801 */ 10802 const withModifiers = (fn, modifiers) => { 10803 return (event, ...args) => { 10804 for (let i = 0; i < modifiers.length; i++) { 10805 const guard = modifierGuards[modifiers[i]]; 10806 if (guard && guard(event, modifiers)) 10807 return; 10808 } 10809 return fn(event, ...args); 10810 }; 10811 }; 10812 // Kept for 2.x compat. 10813 // Note: IE11 compat for `spacebar` and `del` is removed for now. 10814 const keyNames = { 10815 esc: 'escape', 10816 space: ' ', 10817 up: 'arrow-up', 10818 left: 'arrow-left', 10819 right: 'arrow-right', 10820 down: 'arrow-down', 10821 delete: 'backspace' 10822 }; 10823 /** 10824 * @private 10825 */ 10826 const withKeys = (fn, modifiers) => { 10827 return (event) => { 10828 if (!('key' in event)) { 10829 return; 10830 } 10831 const eventKey = hyphenate(event.key); 10832 if (modifiers.some(k => k === eventKey || keyNames[k] === eventKey)) { 10833 return fn(event); 10834 } 10835 }; 10836 }; 10837 10838 const vShow = { 10839 beforeMount(el, { value }, { transition }) { 10840 el._vod = el.style.display === 'none' ? '' : el.style.display; 10841 if (transition && value) { 10842 transition.beforeEnter(el); 10843 } 10844 else { 10845 setDisplay(el, value); 10846 } 10847 }, 10848 mounted(el, { value }, { transition }) { 10849 if (transition && value) { 10850 transition.enter(el); 10851 } 10852 }, 10853 updated(el, { value, oldValue }, { transition }) { 10854 if (!value === !oldValue) 10855 return; 10856 if (transition) { 10857 if (value) { 10858 transition.beforeEnter(el); 10859 setDisplay(el, true); 10860 transition.enter(el); 10861 } 10862 else { 10863 transition.leave(el, () => { 10864 setDisplay(el, false); 10865 }); 10866 } 10867 } 10868 else { 10869 setDisplay(el, value); 10870 } 10871 }, 10872 beforeUnmount(el, { value }) { 10873 setDisplay(el, value); 10874 } 10875 }; 10876 function setDisplay(el, value) { 10877 el.style.display = value ? el._vod : 'none'; 10878 } 10879 10880 const rendererOptions = /*#__PURE__*/ extend({ patchProp }, nodeOps); 10881 // lazy create the renderer - this makes core renderer logic tree-shakable 10882 // in case the user only imports reactivity utilities from Vue. 10883 let renderer; 10884 let enabledHydration = false;
10885 function ensureRenderer() { 10886 return (renderer || 10887 (renderer = createRenderer(rendererOptions))); 10888 } 10889 function ensureHydrationRenderer() { 10890 renderer = enabledHydration 10891 ? renderer 10892 : createHydrationRenderer(rendererOptions); 10893 enabledHydration = true; 10894 return renderer; 10895 } 10896 // use explicit type casts here to avoid import() calls in rolled-up d.ts 10897 const render = ((...args) => { 10898 ensureRenderer().render(...args); 10899 }); 10900 const hydrate = ((...args) => { 10901 ensureHydrationRenderer().hydrate(...args); 10902 }); 10903 const createApp = ((...args) => { 10904 const app = ensureRenderer().createApp(...args); 10905 { 10906 injectNativeTagCheck(app); 10907 injectCompilerOptionsCheck(app); 10908 } 10909 const { mount } = app; 10910 app.mount = (containerOrSelector) => { 10911 const container = normalizeContainer(containerOrSelector); 10912 if (!container) 10913 return; 10914 const component = app._component; 10915 if (!isFunction(component) && !component.render && !component.template) { 10916 // __UNSAFE__ 10917 // Reason: potential execution of JS expressions in in-DOM template. 10918 // The user must make sure the in-DOM template is trusted. If it's 10919 // rendered by the server, the template should not contain any user data. 10920 component.template = container.innerHTML; 10921 } 10922 // clear content before mounting 10923 container.innerHTML = ''; 10924 const proxy = mount(container, false, container instanceof SVGElement); 10925 if (container instanceof Element) { 10926 container.removeAttribute('v-cloak'); 10927 container.setAttribute('data-v-app', ''); 10928 } 10929 return proxy; 10930 }; 10931 return app; 10932 }); 10933 const createSSRApp = ((...args) => { 10934 const app = ensureHydrationRenderer().createApp(...args); 10935 { 10936 injectNativeTagCheck(app); 10937 injectCompilerOptionsCheck(app); 10938 } 10939 const { mount } = app; 10940 app.mount = (containerOrSelector) => { 10941 const container = normalizeContainer(containerOrSelector); 10942 if (container) { 10943 return mount(container, true, container instanceof SVGElement); 10944 } 10945 }; 10946 return app; 10947 }); 10948 function injectNativeTagCheck(app) { 10949 // Inject `isNativeTag` 10950 // this is used for component name validation (dev only) 10951 Object.defineProperty(app.config, 'isNativeTag', { 10952 value: (tag) => isHTMLTag(tag) || isSVGTag(tag), 10953 writable: false 10954 }); 10955 } 10956 // dev only 10957 function injectCompilerOptionsCheck(app) { 10958 if (isRuntimeOnly()) { 10959 const isCustomElement = app.config.isCustomElement; 10960 Object.defineProperty(app.config, 'isCustomElement', { 10961 get() { 10962 return isCustomElement; 10963 }, 10964 set() { 10965 warn$1(`The \`isCustomElement\` config option is deprecated. Use ` + 10966 `\`compilerOptions.isCustomElement\` instead.`); 10967 } 10968 }); 10969 const compilerOptions = app.config.compilerOptions; 10970 const msg = `The \`compilerOptions\` config option is only respected when using ` + 10971 `a build of Vue.js that includes the runtime compiler (aka "full build"). ` + 10972 `Since you are using the runtime-only build, \`compilerOptions\` ` + 10973 `must be passed to \`@vue/compiler-dom\` in the build setup instead.\n` + 10974 `- For vue-loader: pass it via vue-loader's \`compilerOptions\` loader option.\n` + 10975 `- For vue-cli: see https://cli.vuejs.org/guide/webpack.html#modifying-options-of-a-loader\n` + 10976 `- For vite: pass it via @vitejs/plugin-vue options. See https://github.com/vitejs/vite/tree/main/packages/plugin-vue#example-for-passing-options-to-vuecompiler-dom`; 10977 Object.defineProperty(app.config, 'compilerOptions', { 10978 get() { 10979 warn$1(msg); 10980 return compilerOptions; 10981 }, 10982 set() { 10983 warn$1(msg); 10984 } 10985 }); 10986 } 10987 } 10988 function normalizeContainer(container) { 10989 if (isString(container)) { 10990 const res = document.querySelector(container); 10991 if (!res) { 10992 warn$1(`Failed to mount app: mount target selector "${container}" returned null.`); 10993 } 10994 return res; 10995 } 10996 if (window.ShadowRoot && 10997 container instanceof window.ShadowRoot && 10998 container.mode === 'closed') { 10999 warn$1(`mounting on a ShadowRoot with \`{mode: "closed"}\` may lead to unpredictable bugs`); 11000 } 11001 return container; 11002 } 11003 /** 11004 * @internal 11005 */ 11006 const initDirectivesForSSR = NOOP; 11007 11008 function initDev() { 11009 { 11010 { 11011 console.info(`You are running a development build of Vue.\n` + 11012 `Make sure to use the production build (*.prod.js) when deploying for production.`); 11013 } 11014 initCustomFormatter(); 11015 } 11016 } 11017 11018 function defaultOnError(error) { 11019 throw error; 11020 } 11021 function defaultOnWarn(msg) { 11022 console.warn(`[Vue warn] ${msg.message}`); 11023 } 11024 function createCompilerError(code, loc, messages, additionalMe
11024ssage) { 11025 const msg = (messages || errorMessages)[code] + (additionalMessage || ``) 11026 ; 11027 const error = new SyntaxError(String(msg)); 11028 error.code = code; 11029 error.loc = loc; 11030 return error; 11031 } 11032 const errorMessages = { 11033 // parse errors 11034 [0 /* ErrorCodes.ABRUPT_CLOSING_OF_EMPTY_COMMENT */]: 'Illegal comment.', 11035 [1 /* ErrorCodes.CDATA_IN_HTML_CONTENT */]: 'CDATA section is allowed only in XML context.', 11036 [2 /* ErrorCodes.DUPLICATE_ATTRIBUTE */]: 'Duplicate attribute.', 11037 [3 /* ErrorCodes.END_TAG_WITH_ATTRIBUTES */]: 'End tag cannot have attributes.', 11038 [4 /* ErrorCodes.END_TAG_WITH_TRAILING_SOLIDUS */]: "Illegal '/' in tags.", 11039 [5 /* ErrorCodes.EOF_BEFORE_TAG_NAME */]: 'Unexpected EOF in tag.', 11040 [6 /* ErrorCodes.EOF_IN_CDATA */]: 'Unexpected EOF in CDATA section.', 11041 [7 /* ErrorCodes.EOF_IN_COMMENT */]: 'Unexpected EOF in comment.', 11042 [8 /* ErrorCodes.EOF_IN_SCRIPT_HTML_COMMENT_LIKE_TEXT */]: 'Unexpected EOF in script.', 11043 [9 /* ErrorCodes.EOF_IN_TAG */]: 'Unexpected EOF in tag.', 11044 [10 /* ErrorCodes.INCORRECTLY_CLOSED_COMMENT */]: 'Incorrectly closed comment.', 11045 [11 /* ErrorCodes.INCORRECTLY_OPENED_COMMENT */]: 'Incorrectly opened comment.', 11046 [12 /* ErrorCodes.INVALID_FIRST_CHARACTER_OF_TAG_NAME */]: "Illegal tag name. Use '<' to print '<'.", 11047 [13 /* ErrorCodes.MISSING_ATTRIBUTE_VALUE */]: 'Attribute value was expected.', 11048 [14 /* ErrorCodes.MISSING_END_TAG_NAME */]: 'End tag name was expected.', 11049 [15 /* ErrorCodes.MISSING_WHITESPACE_BETWEEN_ATTRIBUTES */]: 'Whitespace was expected.', 11050 [16 /* ErrorCodes.NESTED_COMMENT */]: "Unexpected '<!--' in comment.", 11051 [17 /* ErrorCodes.UNEXPECTED_CHARACTER_IN_ATTRIBUTE_NAME */]: 'Attribute name cannot contain U+0022 ("), U+0027 (\'), and U+003C (<).', 11052 [18 /* ErrorCodes.UNEXPECTED_CHARACTER_IN_UNQUOTED_ATTRIBUTE_VALUE */]: 'Unquoted attribute value cannot contain U+0022 ("), U+0027 (\'), U+003C (<), U+003D (=), and U+0060 (`).', 11053 [19 /* ErrorCodes.UNEXPECTED_EQUALS_SIGN_BEFORE_ATTRIBUTE_NAME */]: "Attribute name cannot start with '='.", 11054 [21 /* ErrorCodes.UNEXPECTED_QUESTION_MARK_INSTEAD_OF_TAG_NAME */]: "'<?' is allowed only in XML context.", 11055 [20 /* ErrorCodes.UNEXPECTED_NULL_CHARACTER */]: `Unexpected null character.`, 11056 [22 /* ErrorCodes.UNEXPECTED_SOLIDUS_IN_TAG */]: "Illegal '/' in tags.", 11057 // Vue-specific parse errors 11058 [23 /* ErrorCodes.X_INVALID_END_TAG */]: 'Invalid end tag.', 11059 [24 /* ErrorCodes.X_MISSING_END_TAG */]: 'Element is missing end tag.', 11060 [25 /* ErrorCodes.X_MISSING_INTERPOLATION_END */]: 'Interpolation end sign was not found.', 11061 [27 /* ErrorCodes.X_MISSING_DYNAMIC_DIRECTIVE_ARGUMENT_END */]: 'End bracket for dynamic directive argument was not found. ' + 11062 'Note that dynamic directive argument cannot contain spaces.', 11063 [26 /* ErrorCodes.X_MISSING_DIRECTIVE_NAME */]: 'Legal directive name was expected.', 11064 // transform errors 11065 [28 /* ErrorCodes.X_V_IF_NO_EXPRESSION */]: `v-if/v-else-if is missing expression.`, 11066 [29 /* ErrorCodes.X_V_IF_SAME_KEY */]: `v-if/else branches must use unique keys.`, 11067 [30 /* ErrorCodes.X_V_ELSE_NO_ADJACENT_IF */]: `v-else/v-else-if has no adjacent v-if or v-else-if.`, 11068 [31 /* ErrorCodes.X_V_FOR_NO_EXPRESSION */]: `v-for is missing expression.`, 11069 [32 /* ErrorCodes.X_V_FOR_MALFORMED_EXPRESSION */]: `v-for has invalid expression.`, 11070 [33 /* ErrorCodes.X_V_FOR_TEMPLATE_KEY_PLACEMENT */]: `<template v-for> key should be placed on the <template> tag.`, 11071 [34 /* ErrorCodes.X_V_BIND_NO_EXPRESSION */]: `v-bind is missing expression.`, 11072 [35 /* ErrorCodes.X_V_ON_NO_EXPRESSION */]: `v-on is missing expression.`, 11073 [36 /* ErrorCodes.X_V_SLOT_UNEXPECTED_DIRECTIVE_ON_SLOT_OUTLET */]: `Unexpected custom directive on <slot> outlet.`, 11074 [37 /* ErrorCodes.X_V_SLOT_MIXED_SLOT_USAGE */]: `Mixed v-slot usage on both the component and nested <template>.` + 11075 `When there are multiple named slots, all slots should use <template> ` + 11076 `syntax to avoid scope ambiguity.`, 11077 [38 /* ErrorCodes.X_V_SLOT_DUPLICATE_SLOT_NAMES */]: `Duplicate slot names found. `, 11078 [39 /* ErrorCodes.X_V_SLOT_EXTRANEOUS_DEFAULT_SLOT_CHILDREN */]: `Extraneous children found when component already has explicitly named ` +
11079 `default slot. These children will be ignored.`, 11080 [40 /* ErrorCodes.X_V_SLOT_MISPLACED */]: `v-slot can only be used on components or <template> tags.`, 11081 [41 /* ErrorCodes.X_V_MODEL_NO_EXPRESSION */]: `v-model is missing expression.`, 11082 [42 /* ErrorCodes.X_V_MODEL_MALFORMED_EXPRESSION */]: `v-model value must be a valid JavaScript member expression.`, 11083 [43 /* ErrorCodes.X_V_MODEL_ON_SCOPE_VARIABLE */]: `v-model cannot be used on v-for or v-slot scope variables because they are not writable.`, 11084 [44 /* ErrorCodes.X_V_MODEL_ON_PROPS */]: `v-model cannot be used on a prop, because local prop bindings are not writable.\nUse a v-bind binding combined with a v-on listener that emits update:x event instead.`, 11085 [45 /* ErrorCodes.X_INVALID_EXPRESSION */]: `Error parsing JavaScript expression: `, 11086 [46 /* ErrorCodes.X_KEEP_ALIVE_INVALID_CHILDREN */]: `<KeepAlive> expects exactly one child component.`, 11087 // generic errors 11088 [47 /* ErrorCodes.X_PREFIX_ID_NOT_SUPPORTED */]: `"prefixIdentifiers" option is not supported in this build of compiler.`, 11089 [48 /* ErrorCodes.X_MODULE_MODE_NOT_SUPPORTED */]: `ES module mode is not supported in this build of compiler.`, 11090 [49 /* ErrorCodes.X_CACHE_HANDLER_NOT_SUPPORTED */]: `"cacheHandlers" option is only supported when the "prefixIdentifiers" option is enabled.`, 11091 [50 /* ErrorCodes.X_SCOPE_ID_NOT_SUPPORTED */]: `"scopeId" option is only supported in module mode.`, 11092 // just to fulfill types 11093 [51 /* ErrorCodes.__EXTEND_POINT__ */]: `` 11094 }; 11095 11096 const FRAGMENT = Symbol(`Fragment` ); 11097 const TELEPORT = Symbol(`Teleport` ); 11098 const SUSPENSE = Symbol(`Suspense` ); 11099 const KEEP_ALIVE = Symbol(`KeepAlive` ); 11100 const BASE_TRANSITION = Symbol(`BaseTransition` ); 11101 const OPEN_BLOCK = Symbol(`openBlock` ); 11102 const CREATE_BLOCK = Symbol(`createBlock` ); 11103 const CREATE_ELEMENT_BLOCK = Symbol(`createElementBlock` ); 11104 const CREATE_VNODE = Symbol(`createVNode` ); 11105 const CREATE_ELEMENT_VNODE = Symbol(`createElementVNode` ); 11106 const CREATE_COMMENT = Symbol(`createCommentVNode` ); 11107 const CREATE_TEXT = Symbol(`createTextVNode` ); 11108 const CREATE_STATIC = Symbol(`createStaticVNode` ); 11109 const RESOLVE_COMPONENT = Symbol(`resolveComponent` ); 11110 const RESOLVE_DYNAMIC_COMPONENT = Symbol(`resolveDynamicComponent` ); 11111 const RESOLVE_DIRECTIVE = Symbol(`resolveDirective` ); 11112 const RESOLVE_FILTER = Symbol(`resolveFilter` ); 11113 const WITH_DIRECTIVES = Symbol(`withDirectives` ); 11114 const RENDER_LIST = Symbol(`renderList` ); 11115 const RENDER_SLOT = Symbol(`renderSlot` ); 11116 const CREATE_SLOTS = Symbol(`createSlots` ); 11117 const TO_DISPLAY_STRING = Symbol(`toDisplayString` ); 11118 const MERGE_PROPS = Symbol(`mergeProps` ); 11119 const NORMALIZE_CLASS = Symbol(`normalizeClass` ); 11120 const NORMALIZE_STYLE = Symbol(`normalizeStyle` ); 11121 const NORMALIZE_PROPS = Symbol(`normalizeProps` ); 11122 const GUARD_REACTIVE_PROPS = Symbol(`guardReactiveProps` ); 11123 const TO_HANDLERS = Symbol(`toHandlers` ); 11124 const CAMELIZE = Symbol(`camelize` ); 11125 const CAPITALIZE = Symbol(`capitalize` ); 11126 const TO_HANDLER_KEY = Symbol(`toHandlerKey` ); 11127 const SET_BLOCK_TRACKING = Symbol(`setBlockTracking` ); 11128 const PUSH_SCOPE_ID = Symbol(`pushScopeId` ); 11129 const POP_SCOPE_ID = Symbol(`popScopeId` ); 11130 const WITH_CTX = Symbol(`withCtx` ); 11131 const UNREF = Symbol(`unref` ); 11132 const IS_REF = Symbol(`isRef` ); 11133 const WITH_MEMO = Symbol(`withMemo` ); 11134 const IS_MEMO_SAME = Symbol(`isMemoSame` ); 11135 // Name mapping for runtime helpers that need to be imported from 'vue' in 11136 // generated code. Make sure these are correctly exported in the runtime! 11137 const helperNameMap = { 11138 [FRAGMENT]: `Fragment`, 11139 [TELEPORT]: `Teleport`, 11140 [SUSPENSE]: `Suspense`, 11141 [KEEP_ALIVE]: `KeepAlive`, 11142 [BASE_TRANSITION]: `BaseTransition`, 11143 [OPEN_BLOCK]: `openBlock`, 11144 [CREATE_BLOCK]: `createBlock`, 11145 [CREATE_ELEMENT_BLOCK]: `createElementBlock`, 11146 [CREATE_VNODE]: `createVNode`, 11147 [CREATE_ELEMENT_VNODE]: `createElementVNode`, 11148 [CREATE_COMMENT]: `createCommentVNode`, 11149 [CREATE_TEXT]: `createTextVNode`, 11150 [CREATE_STATIC]: `createStaticVNode`, 11151 [RESOLVE_COMPONENT]: `resolveComponent`, 11152 [RESOLVE_DYNAMIC_COMPONENT]: `resolveDynamicComponent`, 11153 [RESOLVE_DIRECTIVE]: `resolveDirective`, 11154 [RESOLVE_FILTER]: `resolveFilter`, 11155 [WITH_DIRECTIVES]: `withDirectives`, 11156 [RENDER_LIST]: `renderList`, 11157 [RENDER_SLOT]: `renderSlot`, 11158 [CREATE_SLOTS]: `createSlots`, 11159 [TO_DISPLAY_STRING]: `toDisplayString`, 11160 [MERGE_PROPS]: `mergeProps`, 11161 [NORMALIZE_CLASS]: `normalizeClass`, 11162 [NORMALIZE_STYLE]: `normalizeStyle`, 11163 [NORMALIZE_PROPS]: `normalizeProps`,
11164 [GUARD_REACTIVE_PROPS]: `guardReactiveProps`, 11165 [TO_HANDLERS]: `toHandlers`, 11166 [CAMELIZE]: `camelize`, 11167 [CAPITALIZE]: `capitalize`, 11168 [TO_HANDLER_KEY]: `toHandlerKey`, 11169 [SET_BLOCK_TRACKING]: `setBlockTracking`, 11170 [PUSH_SCOPE_ID]: `pushScopeId`, 11171 [POP_SCOPE_ID]: `popScopeId`, 11172 [WITH_CTX]: `withCtx`, 11173 [UNREF]: `unref`, 11174 [IS_REF]: `isRef`, 11175 [WITH_MEMO]: `withMemo`, 11176 [IS_MEMO_SAME]: `isMemoSame` 11177 }; 11178 function registerRuntimeHelpers(helpers) { 11179 Object.getOwnPropertySymbols(helpers).forEach(s => { 11180 helperNameMap[s] = helpers[s]; 11181 }); 11182 } 11183 11184 // AST Utilities --------------------------------------------------------------- 11185 // Some expressions, e.g. sequence and conditional expressions, are never 11186 // associated with template nodes, so their source locations are just a stub. 11187 // Container types like CompoundExpression also don't need a real location. 11188 const locStub = { 11189 source: '', 11190 start: { line: 1, column: 1, offset: 0 }, 11191 end: { line: 1, column: 1, offset: 0 } 11192 }; 11193 function createRoot(children, loc = locStub) { 11194 return { 11195 type: 0 /* NodeTypes.ROOT */, 11196 children, 11197 helpers: [], 11198 components: [], 11199 directives: [], 11200 hoists: [], 11201 imports: [], 11202 cached: 0, 11203 temps: 0, 11204 codegenNode: undefined, 11205 loc 11206 }; 11207 } 11208 function createVNodeCall(context, tag, props, children, patchFlag, dynamicProps, directives, isBlock = false, disableTracking = false, isComponent = false, loc = locStub) { 11209 if (context) { 11210 if (isBlock) { 11211 context.helper(OPEN_BLOCK); 11212 context.helper(getVNodeBlockHelper(context.inSSR, isComponent)); 11213 } 11214 else { 11215 context.helper(getVNodeHelper(context.inSSR, isComponent)); 11216 } 11217 if (directives) { 11218 context.helper(WITH_DIRECTIVES); 11219 } 11220 } 11221 return { 11222 type: 13 /* NodeTypes.VNODE_CALL */, 11223 tag, 11224 props, 11225 children, 11226 patchFlag, 11227 dynamicProps, 11228 directives, 11229 isBlock, 11230 disableTracking, 11231 isComponent, 11232 loc 11233 }; 11234 } 11235 function createArrayExpression(elements, loc = locStub) { 11236 return { 11237 type: 17 /* NodeTypes.JS_ARRAY_EXPRESSION */, 11238 loc, 11239 elements 11240 }; 11241 } 11242 function createObjectExpression(properties, loc = locStub) { 11243 return { 11244 type: 15 /* NodeTypes.JS_OBJECT_EXPRESSION */, 11245 loc, 11246 properties 11247 }; 11248 } 11249 function createObjectProperty(key, value) { 11250 return { 11251 type: 16 /* NodeTypes.JS_PROPERTY */, 11252 loc: locStub, 11253 key: isString(key) ? createSimpleExpression(key, true) : key, 11254 value 11255 }; 11256 } 11257 function createSimpleExpression(content, isStatic = false, loc = locStub, constType = 0 /* ConstantTypes.NOT_CONSTANT */) { 11258 return { 11259 type: 4 /* NodeTypes.SIMPLE_EXPRESSION */, 11260 loc, 11261 content, 11262 isStatic, 11263 constType: isStatic ? 3 /* ConstantTypes.CAN_STRINGIFY */ : constType 11264 }; 11265 } 11266 function createCompoundExpression(children, loc = locStub) { 11267 return { 11268 type: 8 /* NodeTypes.COMPOUND_EXPRESSION */, 11269 loc, 11270 children 11271 }; 11272 } 11273 function createCallExpression(callee, args = [], loc = locStub) { 11274 return { 11275 type: 14 /* NodeTypes.JS_CALL_EXPRESSION */, 11276 loc, 11277 callee, 11278 arguments: args 11279 }; 11280 } 11281 function createFunctionExpression(params, returns = undefined, newline = false, isSlot = false, loc = locStub) { 11282 return { 11283 type: 18 /* NodeTypes.JS_FUNCTION_EXPRESSION */, 11284 params, 11285 returns, 11286 newline, 11287 isSlot, 11288 loc 11289 }; 11290 } 11291 function createConditionalExpression(test, consequent, alternate, newline = true) { 11292 return { 11293 type: 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */, 11294 test, 11295 consequent, 11296 alternate, 11297 newline, 11298 loc: locStub 11299 }; 11300 } 11301 function createCacheExpression(index, value, isVNode = false) { 11302 return { 11303 type: 20 /* NodeTypes.JS_CACHE_EXPRESSION */, 11304 index, 11305 value, 11306 isVNode, 11307 loc: locStub 11308 }; 11309 }
11310 function createBlockStatement(body) { 11311 return { 11312 type: 21 /* NodeTypes.JS_BLOCK_STATEMENT */, 11313 body, 11314 loc: locStub 11315 }; 11316 } 11317 11318 const isStaticExp = (p) => p.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && p.isStatic; 11319 const isBuiltInType = (tag, expected) => tag === expected || tag === hyphenate(expected); 11320 function isCoreComponent(tag) { 11321 if (isBuiltInType(tag, 'Teleport')) { 11322 return TELEPORT; 11323 } 11324 else if (isBuiltInType(tag, 'Suspense')) { 11325 return SUSPENSE; 11326 } 11327 else if (isBuiltInType(tag, 'KeepAlive')) { 11328 return KEEP_ALIVE; 11329 } 11330 else if (isBuiltInType(tag, 'BaseTransition')) { 11331 return BASE_TRANSITION; 11332 } 11333 } 11334 const nonIdentifierRE = /^\d|[^\$\w]/; 11335 const isSimpleIdentifier = (name) => !nonIdentifierRE.test(name); 11336 const validFirstIdentCharRE = /[A-Za-z_$\xA0-\uFFFF]/; 11337 const validIdentCharRE = /[\.\?\w$\xA0-\uFFFF]/; 11338 const whitespaceRE = /\s+[.[]\s*|\s*[.[]\s+/g; 11339 /** 11340 * Simple lexer to check if an expression is a member expression. This is 11341 * lax and only checks validity at the root level (i.e. does not validate exps 11342 * inside square brackets), but it's ok since these are only used on template 11343 * expressions and false positives are invalid expressions in the first place. 11344 */ 11345 const isMemberExpressionBrowser = (path) => { 11346 // remove whitespaces around . or [ first 11347 path = path.trim().replace(whitespaceRE, s => s.trim()); 11348 let state = 0 /* MemberExpLexState.inMemberExp */; 11349 let stateStack = []; 11350 let currentOpenBracketCount = 0; 11351 let currentOpenParensCount = 0; 11352 let currentStringType = null; 11353 for (let i = 0; i < path.length; i++) { 11354 const char = path.charAt(i); 11355 switch (state) { 11356 case 0 /* MemberExpLexState.inMemberExp */: 11357 if (char === '[') { 11358 stateStack.push(state); 11359 state = 1 /* MemberExpLexState.inBrackets */; 11360 currentOpenBracketCount++; 11361 } 11362 else if (char === '(') { 11363 stateStack.push(state); 11364 state = 2 /* MemberExpLexState.inParens */; 11365 currentOpenParensCount++; 11366 } 11367 else if (!(i === 0 ? validFirstIdentCharRE : validIdentCharRE).test(char)) { 11368 return false; 11369 } 11370 break; 11371 case 1 /* MemberExpLexState.inBrackets */: 11372 if (char === `'` || char === `"` || char === '`') { 11373 stateStack.push(state); 11374 state = 3 /* MemberExpLexState.inString */; 11375 currentStringType = char; 11376 } 11377 else if (char === `[`) { 11378 currentOpenBracketCount++; 11379 } 11380 else if (char === `]`) { 11381 if (!--currentOpenBracketCount) { 11382 state = stateStack.pop(); 11383 } 11384 } 11385 break; 11386 case 2 /* MemberExpLexState.inParens */: 11387 if (char === `'` || char === `"` || char === '`') { 11388 stateStack.push(state); 11389 state = 3 /* MemberExpLexState.inString */; 11390 currentStringType = char; 11391 } 11392 else if (char === `(`) { 11393 currentOpenParensCount++; 11394 } 11395 else if (char === `)`) { 11396 // if the exp ends as a call then it should not be considered valid 11397 if (i === path.length - 1) { 11398 return false; 11399 } 11400 if (!--currentOpenParensCount) { 11401 state = stateStack.pop(); 11402 } 11403 } 11404 break;
vendor: 7,134 bytes, lines 11405-11589
11405 case 3 /* MemberExpLexState.inString */: 11406 if (char === currentStringType) { 11407 state = stateStack.pop(); 11408 currentStringType = null; 11409 } 11410 break; 11411 } 11412 } 11413 return !currentOpenBracketCount && !currentOpenParensCount; 11414 }; 11415 const isMemberExpression = isMemberExpressionBrowser 11416 ; 11417 function getInnerRange(loc, offset, length) { 11418 const source = loc.source.slice(offset, offset + length); 11419 const newLoc = { 11420 source, 11421 start: advancePositionWithClone(loc.start, loc.source, offset), 11422 end: loc.end 11423 }; 11424 if (length != null) { 11425 newLoc.end = advancePositionWithClone(loc.start, loc.source, offset + length); 11426 } 11427 return newLoc; 11428 } 11429 function advancePositionWithClone(pos, source, numberOfCharacters = source.length) { 11430 return advancePositionWithMutation(extend({}, pos), source, numberOfCharacters); 11431 } 11432 // advance by mutation without cloning (for performance reasons), since this 11433 // gets called a lot in the parser 11434 function advancePositionWithMutation(pos, source, numberOfCharacters = source.length) { 11435 let linesCount = 0; 11436 let lastNewLinePos = -1; 11437 for (let i = 0; i < numberOfCharacters; i++) { 11438 if (source.charCodeAt(i) === 10 /* newline char code */) { 11439 linesCount++; 11440 lastNewLinePos = i; 11441 } 11442 } 11443 pos.offset += numberOfCharacters; 11444 pos.line += linesCount; 11445 pos.column = 11446 lastNewLinePos === -1 11447 ? pos.column + numberOfCharacters 11448 : numberOfCharacters - lastNewLinePos; 11449 return pos; 11450 } 11451 function assert(condition, msg) { 11452 /* istanbul ignore if */ 11453 if (!condition) { 11454 throw new Error(msg || `unexpected compiler condition`); 11455 } 11456 } 11457 function findDir(node, name, allowEmpty = false) { 11458 for (let i = 0; i < node.props.length; i++) { 11459 const p = node.props[i]; 11460 if (p.type === 7 /* NodeTypes.DIRECTIVE */ && 11461 (allowEmpty || p.exp) && 11462 (isString(name) ? p.name === name : name.test(p.name))) { 11463 return p; 11464 } 11465 } 11466 } 11467 function findProp(node, name, dynamicOnly = false, allowEmpty = false) { 11468 for (let i = 0; i < node.props.length; i++) { 11469 const p = node.props[i]; 11470 if (p.type === 6 /* NodeTypes.ATTRIBUTE */) { 11471 if (dynamicOnly) 11472 continue; 11473 if (p.name === name && (p.value || allowEmpty)) { 11474 return p; 11475 } 11476 } 11477 else if (p.name === 'bind' && 11478 (p.exp || allowEmpty) && 11479 isStaticArgOf(p.arg, name)) { 11480 return p; 11481 } 11482 } 11483 } 11484 function isStaticArgOf(arg, name) { 11485 return !!(arg && isStaticExp(arg) && arg.content === name); 11486 } 11487 function hasDynamicKeyVBind(node) { 11488 return node.props.some(p => p.type === 7 /* NodeTypes.DIRECTIVE */ && 11489 p.name === 'bind' && 11490 (!p.arg || // v-bind="obj" 11491 p.arg.type !== 4 /* NodeTypes.SIMPLE_EXPRESSION */ || // v-bind:[_ctx.foo] 11492 !p.arg.isStatic) // v-bind:[foo] 11493 ); 11494 } 11495 function isText(node) { 11496 return node.type === 5 /* NodeTypes.INTERPOLATION */ || node.type === 2 /* NodeTypes.TEXT */; 11497 } 11498 function isVSlot(p) { 11499 return p.type === 7 /* NodeTypes.DIRECTIVE */ && p.name === 'slot'; 11500 } 11501 function isTemplateNode(node) { 11502 return (node.type === 1 /* NodeTypes.ELEMENT */ && node.tagType === 3 /* ElementTypes.TEMPLATE */); 11503 } 11504 function isSlotOutlet(node) { 11505 return node.type === 1 /* NodeTypes.ELEMENT */ && node.tagType === 2 /* ElementTypes.SLOT */; 11506 } 11507 function getVNodeHelper(ssr, isComponent) { 11508 return ssr || isComponent ? CREATE_VNODE : CREATE_ELEMENT_VNODE; 11509 } 11510 function getVNodeBlockHelper(ssr, isComponent) { 11511 return ssr || isComponent ? CREATE_BLOCK : CREATE_ELEMENT_BLOCK; 11512 } 11513 const propsHelperSet = new Set([NORMALIZE_PROPS, GUARD_REACTIVE_PROPS]); 11514 function getUnnormalizedProps(props, callPath = []) { 11515 if (props && 11516 !isString(props) && 11517 props.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */) { 11518 const callee = props.callee; 11519 if (!isString(callee) && propsHelperSet.has(callee)) { 11520 return getUnnormalizedProps(props.arguments[0], callPath.concat(props)); 11521 } 11522 } 11523 return [props, callPath]; 11524 } 11525 function injectProp(node, prop, context) { 11526 let propsWithInjection; 11527 /** 11528 * 1. mergeProps(...) 11529 * 2. toHandlers(...) 11530 * 3. normalizeProps(...) 11531 * 4. normalizeProps(guardReactiveProps(...)) 11532 * 11533 * we need to get the real props before normalization 11534 */ 11535 let props = node.type === 13 /* NodeTypes.VNODE_CALL */ ? node.props : node.arguments[2]; 11536 let callPath = []; 11537 let parentCall; 11538 if (props && 11539 !isString(props) && 11540 props.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */) { 11541 const ret = getUnnormalizedProps(props); 11542 props = ret[0]; 11543 callPath = ret[1]; 11544 parentCall = callPath[callPath.length - 1]; 11545 } 11546 if (props == null || isString(props)) { 11547 propsWithInjection = createObjectExpression([prop]); 11548 } 11549 else if (props.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */) { 11550 // merged props... add ours 11551 // only inject key to object literal if it's the first argument so that 11552 // if doesn't override user provided keys 11553 const first = props.arguments[0]; 11554 if (!isString(first) && first.type === 15 /* NodeTypes.JS_OBJECT_EXPRESSION */) { 11555 // #6631 11556 if (!hasProp(prop, first)) { 11557 first.properties.unshift(prop); 11558 } 11559 } 11560 else { 11561 if (props.callee === TO_HANDLERS) { 11562 // #2366 11563 propsWithInjection = createCallExpression(context.helper(MERGE_PROPS), [ 11564 createObjectExpression([prop]), 11565 props 11566 ]); 11567 } 11568 else { 11569 props.arguments.unshift(createObjectExpression([prop])); 11570 } 11571 } 11572 !propsWithInjection && (propsWithInjection = props); 11573 } 11574 else if (props.type === 15 /* NodeTypes.JS_OBJECT_EXPRESSION */) { 11575 if (!hasProp(prop, props)) { 11576 props.properties.unshift(prop); 11577 } 11578 propsWithInjection = props; 11579 } 11580 else { 11581 // single v-bind with expression, return a merged replacement 11582 propsWithInjection = createCallExpression(context.helper(MERGE_PROPS), [ 11583 createObjectExpression([prop]), 11584 props 11585 ]); 11586 // in the case of nested helper call, e.g. `normalizeProps(guardReactiveProps(props))`, 11587 // it will be rewritten as `normalizeProps(mergeProps({ key: 0 }, props))`, 11588 // the `guardReactiveProps` will no longer be needed 11589 if (parentCall && parentCall.callee === GUARD_REACTIVE_PROP
11589S) { 11590 parentCall = callPath[callPath.length - 2]; 11591 } 11592 } 11593 if (node.type === 13 /* NodeTypes.VNODE_CALL */) { 11594 if (parentCall) { 11595 parentCall.arguments[0] = propsWithInjection; 11596 } 11597 else { 11598 node.props = propsWithInjection; 11599 } 11600 } 11601 else { 11602 if (parentCall) { 11603 parentCall.arguments[0] = propsWithInjection; 11604 } 11605 else { 11606 node.arguments[2] = propsWithInjection; 11607 } 11608 } 11609 } 11610 // check existing key to avoid overriding user provided keys 11611 function hasProp(prop, props) { 11612 let result = false; 11613 if (prop.key.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 11614 const propKeyName = prop.key.content; 11615 result = props.properties.some(p => p.key.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && 11616 p.key.content === propKeyName); 11617 } 11618 return result; 11619 } 11620 function toValidAssetId(name, type) { 11621 // see issue#4422, we need adding identifier on validAssetId if variable `name` has specific character 11622 return `_${type}_${name.replace(/[^\w]/g, (searchValue, replaceValue) => { 11623 return searchValue === '-' ? '_' : name.charCodeAt(replaceValue).toString(); 11624 })}`; 11625 } 11626 function getMemoedVNodeCall(node) { 11627 if (node.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */ && node.callee === WITH_MEMO) { 11628 return node.arguments[1].returns; 11629 } 11630 else { 11631 return node; 11632 } 11633 } 11634 function makeBlock(node, { helper, removeHelper, inSSR }) { 11635 if (!node.isBlock) { 11636 node.isBlock = true; 11637 removeHelper(getVNodeHelper(inSSR, node.isComponent)); 11638 helper(OPEN_BLOCK); 11639 helper(getVNodeBlockHelper(inSSR, node.isComponent)); 11640 } 11641 } 11642 11643 const deprecationData = { 11644 ["COMPILER_IS_ON_ELEMENT" /* CompilerDeprecationTypes.COMPILER_IS_ON_ELEMENT */]: { 11645 message: `Platform-native elements with "is" prop will no longer be ` + 11646 `treated as components in Vue 3 unless the "is" value is explicitly ` + 11647 `prefixed with "vue:".`, 11648 link: `https://v3-migration.vuejs.org/breaking-changes/custom-elements-interop.html` 11649 }, 11650 ["COMPILER_V_BIND_SYNC" /* CompilerDeprecationTypes.COMPILER_V_BIND_SYNC */]: { 11651 message: key => `.sync modifier for v-bind has been removed. Use v-model with ` + 11652 `argument instead. \`v-bind:${key}.sync\` should be changed to ` + 11653 `\`v-model:${key}\`.`, 11654 link: `https://v3-migration.vuejs.org/breaking-changes/v
11654-model.html` 11655 }, 11656 ["COMPILER_V_BIND_PROP" /* CompilerDeprecationTypes.COMPILER_V_BIND_PROP */]: { 11657 message: `.prop modifier for v-bind has been removed and no longer necessary. ` + 11658 `Vue 3 will automatically set a binding as DOM property when appropriate.` 11659 }, 11660 ["COMPILER_V_BIND_OBJECT_ORDER" /* CompilerDeprecationTypes.COMPILER_V_BIND_OBJECT_ORDER */]: { 11661 message: `v-bind="obj" usage is now order sensitive and behaves like JavaScript ` + 11662 `object spread: it will now overwrite an existing non-mergeable attribute ` + 11663 `that appears before v-bind in the case of conflict. ` + 11664 `To retain 2.x behavior, move v-bind to make it the first attribute. ` + 11665 `You can also suppress this warning if the usage is intended.`, 11666 link: `https://v3-migration.vuejs.org/breaking-changes/v-bind.html` 11667 }, 11668 ["COMPILER_V_ON_NATIVE" /* CompilerDeprecationTypes.COMPILER_V_ON_NATIVE */]: { 11669 message: `.native modifier for v-on has been removed as is no longer necessary.`, 11670 link: `https://v3-migration.vuejs.org/breaking-changes/v
11670-on-native-modifier-removed.html` 11671 }, 11672 ["COMPILER_V_IF_V_FOR_PRECEDENCE" /* CompilerDeprecationTypes.COMPILER_V_IF_V_FOR_PRECEDENCE */]: { 11673 message: `v-if / v-for precedence when used on the same element has changed ` + 11674 `in Vue 3: v-if now takes higher precedence and will no longer have ` + 11675 `access to v-for scope variables. It is best to avoid the ambiguity ` + 11676 `with <template> tags or use a computed property that filters v-for ` + 11677 `data source.`, 11678 link: `https://v3-migration.vuejs.org/breaking-changes/v-if-v-for.html` 11679 }, 11680 ["COMPILER_NATIVE_TEMPLATE" /* CompilerDeprecationTypes.COMPILER_NATIVE_TEMPLATE */]: { 11681 message: `<template> with no special directives will render as a native template ` + 11682 `element instead of its inner content in Vue 3.` 11683 }, 11684 ["COMPILER_INLINE_TEMPLATE" /* CompilerDeprecationTypes.COMPILER_INLINE_TEMPLATE */]: { 11685 message: `"inline-template" has been removed in Vue 3.`, 11686 link: `https://v3-migration.vuejs.org/breaking-changes/inline-template-attribute.html` 11687 }, 11688 ["COMPILER_FILTER" /* CompilerDeprecationTypes.COMPILER_FILTERS */]: { 11689 message: `filters have been removed in Vue 3. ` + 11690 `The "|" symbol will be treated as native JavaScript bitwise OR operator. ` + 11691 `Use method calls or computed properties instead.`, 11692 link: `https://v3-migration.vuejs.org/breaking-changes/filters.html` 11693 } 11694 }; 11695 function getCompatValue(key, context) { 11696 const config = context.options 11697 ? context.options.compatConfig 11698 : context.compatConfig; 11699 const value = config && config[key]; 11700 if (key === 'MODE') { 11701 return value || 3; // compiler defaults to v3 behavior 11702 } 11703 else { 11704 return value; 11705 } 11706 } 11707 function isCompatEnabled(key, context) { 11708 const mode = getCompatValue('MODE', context); 11709 const value = getCompatValue(key, context); 11710 // in v3 mode, only enable if explicitly set to true 11711 // otherwise enable for any non-false value 11712 return mode === 3 ? value === true : value !== false; 11713 } 11714 function checkCompatEnabled(key, context, loc, ...args) { 11715 const enabled = isCompatEnabled(key, context); 11716 if (enabled) { 11717 warnDeprecation(key, context, loc, ...args); 11718 } 11719 return enabled; 11720 } 11721 function warnDeprecation(key, context, loc, ...args) { 11722 const val = getCompatValue(key, context); 11723 if (val === 'suppress-warning') { 11724 return; 11725 } 11726 const { message, link } = deprecationData[key]; 11727 const msg = `(deprecation ${key}) ${typeof message === 'function' ? message(...args) : message}${link ? `\n Details: ${link}` : ``}`; 11728 const err = new SyntaxError(msg); 11729 err.code = key; 11730 if (loc) 11731 err.loc = loc; 11732 context.onWarn(err); 11733 } 11734 11735 // The default decoder only provides escapes for characters reserved as part of 11736 // the template syntax, and is only used if the custom renderer did not provide 11737 // a platform-specific decoder. 11738 const decodeRE = /&(gt|lt|amp|apos|quot);/g; 11739 const decodeMap = { 11740 gt: '>', 11741 lt: '<', 11742 amp: '&', 11743 apos: "'", 11744 quot: '"' 11745 }; 11746 const defaultParserOptions = { 11747 delimiters: [`{{`, `}}`], 11748 getNamespace: () => 0 /* Namespaces.HTML */, 11749 getTextMode: () => 0 /* TextModes.DATA */, 11750 isVoidTag: NO, 11751 isPreTag: NO, 11752 isCustomElement: NO, 11753 decodeEntities: (rawText) => rawText.replace(decodeRE, (_, p1) => decodeMap[p1]), 11754 onError: defaultOnError, 11755 onWarn: defaultOnWarn, 11756 comments: true 11757 }; 11758 function baseParse(content, options = {}) { 11759 const context = createParserContext(content, options); 11760 const start = getCursor(context); 11761 return createRoot(parseChildren(context, 0 /* TextModes.DATA */, []), getSelection(context, start)); 11762 } 11763 function createParserContext(content, rawOptions) { 11764 const options = extend({}, defaultParserOptions); 11765 let key; 11766 for (key in rawOptions) { 11767 // @ts-ignore 11768 options[key] = 11769 rawOptions[key] === undefined 11770 ? defaultParserOptions[key] 11771 : rawOptions[key]; 11772 } 11773 return { 11774 options, 11775 column: 1, 11776 line: 1, 11777 offset: 0, 11778 originalSource: content, 11779 source: content, 11780 inPre: false, 11781 inVPre: false, 11782 onWarn: options.onWarn 11783 }; 11784 } 11785 function parseChildren(context, mode, ancestors) { 11786 const parent = last(ancestors); 11787 const ns = parent ? parent.ns : 0 /* Namespaces.HTML */; 11788 const nodes = []; 11789 while (!isEnd(context, mode, ancestors)) { 11790 const s = context.source; 11791 let node = undefined; 11792 if (mode === 0 /* TextModes.DATA */ || mode === 1 /* TextModes.RCDATA */) { 11793 if (!context.inVPre && startsWith(s, context.options.delimiters[0])) { 11794 // '{{' 11795 node = parseInterpolation(context, mode); 11796 } 11797 else if (mode === 0 /* TextModes.DATA */ && s[0] === '<') { 11798 // https://html.spec.whatwg.org/multipage/parsing.html#tag-open-state 11799 if (s.length === 1) { 11800 emitError(context, 5 /* ErrorCodes.EOF_BEFORE_TAG_NAME */, 1); 11801 } 11802 else if (s[1] === '!') { 11803 // https://html.spec.whatwg.org/multipage/parsing.html#markup-declaration-open-state 11804 if (startsWith(s, '<!--')) { 11805 node = parseComment(context); 11806 } 11807 else if (startsWith(s, '<!DOCTYPE')) { 11808 // Ignore DOCTYPE by a limitation. 11809 node = parseBogusComment(context); 11810 } 11811 else if (startsWith(s, '<![CDATA[')) { 11812 if (ns !== 0 /* Namespaces.HTML */) { 11813 node = parseCDATA(context, ancestors); 11814 } 11815 else { 11816 emitError(context, 1 /* ErrorCodes.CDATA_IN_HTML_CONTENT */); 11817 node = parseBogusComment(context); 11818 } 11819 } 11820 else { 11821 emitError(context, 11 /* ErrorCodes.INCORRECTLY_OPENED_COMMENT */); 11822 node = parseBogusComment(context); 11823 } 11824 } 11825 else if (s[1] === '/') { 11826 // https://html.spec.whatwg.org/multipage/parsing.html#end-tag-open-state 11827 if (s.length === 2) { 11828 emitError(context, 5 /* ErrorCodes.EOF_BEFORE_TAG_NAME */, 2); 11829 } 11830 else if (s[2] === '>') { 11831 emitError(context, 14 /* ErrorCodes.MISSING_END_TAG_NAME */, 2); 11832 advanceBy(context, 3); 11833 continue; 11834 } 11835 else if (/[a-z]/i.test(s[2])) { 11836 emitError(context, 23 /* ErrorCodes.X_INVALID_END_TAG */); 11837 parseTag(context, 1 /* TagType.End */, parent); 11838 continue; 11839 } 11840 else { 11841 emitError(context, 12 /* ErrorCodes.INVALID_FIRST_CHARACTER_OF_TAG_NAME */, 2); 11842 node = parseBogusComment(context); 11843 } 11844 } 11845 else if (/[a-z]/i.test(s[1])) { 11846 node = parseElement(context, ancestors); 11847 } 11848 else if (s[1] === '?') { 11849 emitError(context, 21 /* ErrorCodes.UNEXPECTED_QUESTION_MARK_INSTEAD_OF_TAG_NAME */, 1); 11850 node = parseBogusComment(context); 11851 } 11852 else { 11853 emitError(context, 12 /* ErrorCodes.INVALID_FIRST_CHARACTER_OF_TAG_NAME */, 1); 11854 } 11855 } 11856 } 11857 if (!node) { 11858 node = parseText(context, mode); 11859 } 11860 if (isArray(node)) { 11861 for (let i = 0; i < node.length; i++) { 11862 pushNode(nodes, node[i]); 11863 } 11864 } 11865 else { 11866 pushNode(nodes, node); 11867 } 11868 } 11869 // Whitespace handling strategy like v2 11870 let removedWhitespace = false;
11871 if (mode !== 2 /* TextModes.RAWTEXT */ && mode !== 1 /* TextModes.RCDATA */) { 11872 const shouldCondense = context.options.whitespace !== 'preserve'; 11873 for (let i = 0; i < nodes.length; i++) { 11874 const node = nodes[i]; 11875 if (node.type === 2 /* NodeTypes.TEXT */) { 11876 if (!context.inPre) { 11877 if (!/[^\t\r\n\f ]/.test(node.content)) { 11878 const prev = nodes[i - 1]; 11879 const next = nodes[i + 1]; 11880 // Remove if: 11881 // - the whitespace is the first or last node, or: 11882 // - (condense mode) the whitespace is between twos comments, or: 11883 // - (condense mode) the whitespace is between comment and element, or: 11884 // - (condense mode) the whitespace is between two elements AND contains newline 11885 if (!prev || 11886 !next || 11887 (shouldCondense && 11888 ((prev.type === 3 /* NodeTypes.COMMENT */ && 11889 next.type === 3 /* NodeTypes.COMMENT */) || 11890 (prev.type === 3 /* NodeTypes.COMMENT */ && 11891 next.type === 1 /* NodeTypes.ELEMENT */) || 11892 (prev.type === 1 /* NodeTypes.ELEMENT */ && 11893 next.type === 3 /* NodeTypes.COMMENT */) || 11894 (prev.type === 1 /* NodeTypes.ELEMENT */ && 11895 next.type === 1 /* NodeTypes.ELEMENT */ && 11896 /[\r\n]/.test(node.content))))) { 11897 removedWhitespace = true; 11898 nodes[i] = null; 11899 } 11900 else { 11901 // Otherwise, the whitespace is condensed into a single space 11902 node.content = ' '; 11903 } 11904 } 11905 else if (shouldCondense) { 11906 // in condense mode, consecutive whitespaces in text are condensed 11907 // down to a single space. 11908 node.content = node.content.replace(/[\t\r\n\f ]+/g, ' '); 11909 } 11910 } 11911 else { 11912 // #6410 normalize windows newlines in <pre>: 11913 // in SSR, browsers normalize server-rendered \r\n into a single \n 11914 // in the DOM 11915 node.content = node.content.replace(/\r\n/g, '\n'); 11916 } 11917 } 11918 // Remove comment nodes if desired by configuration. 11919 else if (node.type === 3 /* NodeTypes.COMMENT */ && !context.options.comments) { 11920 removedWhitespace = true; 11921 nodes[i] = null; 11922 } 11923 } 11924 if (context.inPre && parent && context.options.isPreTag(parent.tag)) { 11925 // remove leading newline per html spec 11926 // https://html.spec.whatwg.org/multipage/grouping-content.html#the-pre-element 11927 const first = nodes[0]; 11928 if (first && first.type === 2 /* NodeTypes.TEXT */) { 11929 first.content = first.content.replace(/^\r?\n/, ''); 11930 } 11931 } 11932 } 11933 return removedWhitespace ? nodes.filter(Boolean) : nodes; 11934 } 11935 function pushNode(nodes, node) { 11936 if (node.type === 2 /* NodeTypes.TEXT */) { 11937 const prev = last(nodes); 11938 // Merge if both this and the previous node are text and those are 11939 // consecutive. This happens for cases like "a < b". 11940 if (prev && 11941 prev.type === 2 /* NodeTypes.TEXT */ && 11942 prev.loc.end.offset === node.loc.start.offset) { 11943 prev.content += node.content; 11944 prev.loc.end = node.loc.end; 11945 prev.loc.source += node.loc.source; 11946 return; 11947 } 11948 } 11949 nodes.push(node); 11950 } 11951 function parseCDATA(context, ancestors) { 11952 advanceBy(context, 9); 11953 const nodes = parseChildren(context, 3 /* TextModes.CDATA */, ancestors); 11954 if (context.source.length === 0) { 11955 emitError(context, 6 /* ErrorCodes.EOF_IN_CDATA */); 11956 } 11957 else { 11958 advanceBy(context, 3); 11959 } 11960 return nodes; 11961 } 11962 function parseComment(context) { 11963 const start = getCursor(context); 11964 let content; 11965 // Regular comment. 11966 const match = /--(\!)?>/.exec(context.source); 11967 if (!match) { 11968 content = context.source.slice(4); 11969 advanceBy(context, context.source.length); 11970 emitError(context, 7 /* ErrorCodes.EOF_IN_COMMENT */); 11971 } 11972 else { 11973 if (match.index <= 3) { 11974 emitError(context, 0 /* ErrorCodes.ABRUPT_CLOSING_OF_EMPTY_COMMENT */); 11975 } 11976 if (match[1]) { 11977 emitError(context, 10 /* ErrorCodes.INCORRECTLY_CLOSED_COMMENT */); 11978 } 11979 content = context.source.slice(4, match.index); 11980 // Advancing with reporting nested comments. 11981 const s = context.source.slice(0, match.index); 11982 let prevIndex = 1, nestedIndex = 0; 11983 while ((nestedIndex = s.indexOf('<!--', prevIndex)) !== -1) { 11984 advanceBy(context, nestedIndex - prevIndex + 1); 11985 if (nestedIndex + 4 < s.length) { 11986 emitError(context, 16 /* ErrorCodes.NESTED_COMMENT */); 11987 } 11988 prevIndex = nestedIndex + 1; 11989 } 11990 advanceBy(context, match.index + match[0].length - prevIndex + 1); 11991 } 11992 return { 11993 type: 3 /* NodeTypes.COMMENT */, 11994 content, 11995 loc: getSelection(context, start) 11996 }; 11997 } 11998 function parseBogusComment(context) { 11999 const start = getCursor(context); 12000 const contentStart = context.source[1] === '?' ? 1 : 2; 12001 let content; 12002 const closeIndex = context.source.indexOf('>'); 12003 if (closeIndex === -1) { 12004 content = context.source.slice(contentStart); 12005 advanceBy(context, context.source.length); 12006 } 12007 else { 12008 content = context.source.slice(contentStart, closeIndex); 12009 advanceBy(context, closeIndex + 1); 12010 } 12011 return { 12012 type: 3 /* NodeTypes.COMMENT */, 12013 content, 12014 loc: getSelection(context, start) 12015 }; 12016 } 12017 function parseElement(context, ancestors) { 12018 // Start tag.
12019 const wasInPre = context.inPre; 12020 const wasInVPre = context.inVPre; 12021 const parent = last(ancestors); 12022 const element = parseTag(context, 0 /* TagType.Start */, parent); 12023 const isPreBoundary = context.inPre && !wasInPre; 12024 const isVPreBoundary = context.inVPre && !wasInVPre; 12025 if (element.isSelfClosing || context.options.isVoidTag(element.tag)) { 12026 // #4030 self-closing <pre> tag 12027 if (isPreBoundary) { 12028 context.inPre = false; 12029 } 12030 if (isVPreBoundary) { 12031 context.inVPre = false; 12032 } 12033 return element; 12034 } 12035 // Children. 12036 ancestors.push(element); 12037 const mode = context.options.getTextMode(element, parent); 12038 const children = parseChildren(context, mode, ancestors); 12039 ancestors.pop(); 12040 element.children = children; 12041 // End tag. 12042 if (startsWithEndTagOpen(context.source, element.tag)) { 12043 parseTag(context, 1 /* TagType.End */, parent); 12044 } 12045 else { 12046 emitError(context, 24 /* ErrorCodes.X_MISSING_END_TAG */, 0, element.loc.start); 12047 if (context.source.length === 0 && element.tag.toLowerCase() === 'script') { 12048 const first = children[0]; 12049 if (first && startsWith(first.loc.source, '<!--')) { 12050 emitError(context, 8 /* ErrorCodes.EOF_IN_SCRIPT_HTML_COMMENT_LIKE_TEXT */); 12051 } 12052 } 12053 } 12054 element.loc = getSelection(context, element.loc.start); 12055 if (isPreBoundary) { 12056 context.inPre = false; 12057 } 12058 if (isVPreBoundary) { 12059 context.inVPre = false; 12060 } 12061 return element; 12062 } 12063 const isSpecialTemplateDirective = /*#__PURE__*/ makeMap(`if,else,else-if,for,slot`); 12064 function parseTag(context, type, parent) { 12065 // Tag open. 12066 const start = getCursor(context); 12067 const match = /^<\/?([a-z][^\t\r\n\f />]*)/i.exec(context.source); 12068 const tag = match[1]; 12069 const ns = context.options.getNamespace(tag, parent); 12070 advanceBy(context, match[0].length); 12071 advanceSpaces(context); 12072 // save current state in case we need to re-parse attributes with v-pre 12073 const cursor = getCursor(context); 12074 const currentSource = context.source; 12075 // check <pre> tag 12076 if (context.options.isPreTag(tag)) { 12077 context.inPre = true; 12078 } 12079 // Attributes. 12080 let props = parseAttributes(context, type); 12081 // check v-pre 12082 if (type === 0 /* TagType.Start */ && 12083 !context.inVPre && 12084 props.some(p => p.type === 7 /* NodeTypes.DIRECTIVE */ && p.name === 'pre')) { 12085 context.inVPre = true; 12086 // reset context 12087 extend(context, cursor); 12088 context.source = currentSource; 12089 // re-parse attrs and filter out v-pre itself 12090 props = parseAttributes(context, type).filter(p => p.name !== 'v-pre'); 12091 } 12092 // Tag close. 12093 let isSelfClosing = false; 12094 if (context.source.length === 0) { 12095 emitError(context, 9 /* ErrorCodes.EOF_IN_TAG */); 12096 } 12097 else { 12098 isSelfClosing = startsWith(context.source, '/>'); 12099 if (type === 1 /* TagType.End */ && isSelfClosing) { 12100 emitError(context, 4 /* ErrorCodes.END_TAG_WITH_TRAILING_SOLIDUS */); 12101 } 12102 advanceBy(context, isSelfClosing ? 2 : 1); 12103 } 12104 if (type === 1 /* TagType.End */) { 12105 return; 12106 } 12107 let tagType = 0 /* ElementTypes.ELEMENT */; 12108 if (!context.inVPre) { 12109 if (tag === 'slot') { 12110 tagType = 2 /* ElementTypes.SLOT */; 12111 } 12112 else if (tag === 'template') { 12113 if (props.some(p => p.type === 7 /* NodeTypes.DIRECTIVE */ && isSpecialTemplateDirective(p.name))) { 12114 tagType = 3 /* ElementTypes.TEMPLATE */; 12115 } 12116 } 12117 else if (isComponent(tag, props, context)) { 12118 tagType = 1 /* ElementTypes.COMPONENT */; 12119 } 12120 } 12121 return { 12122 type: 1 /* NodeTypes.ELEMENT */, 12123 ns, 12124 tag, 12125 tagType, 12126 props, 12127 isSelfClosing, 12128 children: [], 12129 loc: getSelection(context, start), 12130 codegenNode: undefined // to be created during transform phase 12131 }; 12132 } 12133 function isComponent(tag, props, context) { 12134 const options = context.options; 12135 if (options.isCustomElement(tag)) { 12136 return false;
12137 } 12138 if (tag === 'component' || 12139 /^[A-Z]/.test(tag) || 12140 isCoreComponent(tag) || 12141 (options.isBuiltInComponent && options.isBuiltInComponent(tag)) || 12142 (options.isNativeTag && !options.isNativeTag(tag))) { 12143 return true; 12144 } 12145 // at this point the tag should be a native tag, but check for potential "is" 12146 // casting 12147 for (let i = 0; i < props.length; i++) { 12148 const p = props[i]; 12149 if (p.type === 6 /* NodeTypes.ATTRIBUTE */) { 12150 if (p.name === 'is' && p.value) { 12151 if (p.value.content.startsWith('vue:')) { 12152 return true; 12153 } 12154 } 12155 } 12156 else { 12157 // directive 12158 // v-is (TODO Deprecate) 12159 if (p.name === 'is') { 12160 return true; 12161 } 12162 else if ( 12163 // :is on plain element - only treat as component in compat mode 12164 p.name === 'bind' && 12165 isStaticArgOf(p.arg, 'is') && 12166 false && 12167 checkCompatEnabled("COMPILER_IS_ON_ELEMENT" /* CompilerDeprecationTypes.COMPILER_IS_ON_ELEMENT */, context, p.loc)) { 12168 return true; 12169 } 12170 } 12171 } 12172 } 12173 function parseAttributes(context, type) { 12174 const props = []; 12175 const attributeNames = new Set(); 12176 while (context.source.length > 0 && 12177 !startsWith(context.source, '>') && 12178 !startsWith(context.source, '/>')) { 12179 if (startsWith(context.source, '/')) { 12180 emitError(context, 22 /* ErrorCodes.UNEXPECTED_SOLIDUS_IN_TAG */); 12181 advanceBy(context, 1); 12182 advanceSpaces(context); 12183 continue; 12184 } 12185 if (type === 1 /* TagType.End */) { 12186 emitError(context, 3 /* ErrorCodes.END_TAG_WITH_ATTRIBUTES */); 12187 } 12188 const attr = parseAttribute(context, attributeNames); 12189 // Trim whitespace between class 12190 // https://github.com/vuejs/core/issues/4251 12191 if (attr.type === 6 /* NodeTypes.ATTRIBUTE */ && 12192 attr.value && 12193 attr.name === 'class') { 12194 attr.value.content = attr.value.content.replace(/\s+/g, ' ').trim(); 12195 } 12196 if (type === 0 /* TagType.Start */) { 12197 props.push(attr); 12198 } 12199 if (/^[^\t\r\n\f />]/.test(context.source)) { 12200 emitError(context, 15 /* ErrorCodes.MISSING_WHITESPACE_BETWEEN_ATTRIBUTES */); 12201 } 12202 advanceSpaces(context); 12203 } 12204 return props; 12205 } 12206 function parseAttribute(context, nameSet) { 12207 // Name. 12208 const start = getCursor(context); 12209 const match = /^[^\t\r\n\f />][^\t\r\n\f />=]*/.exec(context.source); 12210 const name = match[0]; 12211 if (nameSet.has(name)) { 12212 emitError(context, 2 /* ErrorCodes.DUPLICATE_ATTRIBUTE */); 12213 } 12214 nameSet.add(name); 12215 if (name[0] === '=') { 12216 emitError(context, 19 /* ErrorCodes.UNEXPECTED_EQUALS_SIGN_BEFORE_ATTRIBUTE_NAME */); 12217 } 12218 { 12219 const pattern = /["'<]/g; 12220 let m; 12221 while ((m = pattern.exec(name))) { 12222 emitError(context, 17 /* ErrorCodes.UNEXPECTED_CHARACTER_IN_ATTRIBUTE_NAME */, m.index); 12223 } 12224 } 12225 advanceBy(context, name.length); 12226 // Value 12227 let value = undefined; 12228 if (/^[\t\r\n\f ]*=/.test(context.source)) { 12229 advanceSpaces(context); 12230 advanceBy(context, 1); 12231 advanceSpaces(context); 12232 value = parseAttributeValue(context); 12233 if (!value) { 12234 emitError(context, 13 /* ErrorCodes.MISSING_ATTRIBUTE_VALUE */); 12235 } 12236 } 12237 const loc = getSelection(context, start); 12238 if (!context.inVPre && /^(v-[A-Za-z0-9-]|:|\.|@|#)/.test(name)) { 12239 const match = /(?:^v-([a-z0-9-]+))?(?:(?::|^\.|^@|^#)(\[[^\]]+\]|[^\.]+))?(.+)?$/i.exec(name); 12240 let isPropShorthand = startsWith(name, '.'); 12241 let dirName = match[1] || 12242 (isPropShorthand || startsWith(name, ':') 12243 ? 'bind' 12244 : startsWith(name, '@') 12245 ? 'on' 12246 : 'slot'); 12247 let arg; 12248 if (match[2]) { 12249 const isSlot = dirName === 'slot'; 12250 const startOffset = name.lastIndexOf(match[2]); 12251 const loc = getSelection(context, getNewPosition(context, start, startOffset), getNewPosition(context, start, startOffset + match[2].length + ((isSlot && match[3]) || '').length)); 12252 let content = match[2]; 12253 let isStatic = true; 12254 if (content.startsWith('[')) { 12255 isStatic = false;
12256 if (!content.endsWith(']')) { 12257 emitError(context, 27 /* ErrorCodes.X_MISSING_DYNAMIC_DIRECTIVE_ARGUMENT_END */); 12258 content = content.slice(1); 12259 } 12260 else { 12261 content = content.slice(1, content.length - 1); 12262 } 12263 } 12264 else if (isSlot) { 12265 // #1241 special case for v-slot: vuetify relies extensively on slot 12266 // names containing dots. v-slot doesn't have any modifiers and Vue 2.x 12267 // supports such usage so we are keeping it consistent with 2.x. 12268 content += match[3] || ''; 12269 } 12270 arg = { 12271 type: 4 /* NodeTypes.SIMPLE_EXPRESSION */, 12272 content, 12273 isStatic, 12274 constType: isStatic 12275 ? 3 /* ConstantTypes.CAN_STRINGIFY */ 12276 : 0 /* ConstantTypes.NOT_CONSTANT */, 12277 loc 12278 }; 12279 } 12280 if (value && value.isQuoted) { 12281 const valueLoc = value.loc; 12282 valueLoc.start.offset++; 12283 valueLoc.start.column++; 12284 valueLoc.end = advancePositionWithClone(valueLoc.start, value.content); 12285 valueLoc.source = valueLoc.source.slice(1, -1); 12286 } 12287 const modifiers = match[3] ? match[3].slice(1).split('.') : []; 12288 if (isPropShorthand) 12289 modifiers.push('prop'); 12290 return { 12291 type: 7 /* NodeTypes.DIRECTIVE */, 12292 name: dirName, 12293 exp: value && { 12294 type: 4 /* NodeTypes.SIMPLE_EXPRESSION */, 12295 content: value.content, 12296 isStatic: false, 12297 // Treat as non-constant by default. This can be potentially set to 12298 // other values by `transformExpression` to make it eligible for hoisting. 12299 constType: 0 /* ConstantTypes.NOT_CONSTANT */, 12300 loc: value.loc 12301 }, 12302 arg, 12303 modifiers, 12304 loc 12305 }; 12306 } 12307 // missing directive name or illegal directive name 12308 if (!context.inVPre && startsWith(name, 'v-')) { 12309 emitError(context, 26 /* ErrorCodes.X_MISSING_DIRECTIVE_NAME */); 12310 } 12311 return { 12312 type: 6 /* NodeTypes.ATTRIBUTE */, 12313 name, 12314 value: value && { 12315 type: 2 /* NodeTypes.TEXT */, 12316 content: value.content, 12317 loc: value.loc 12318 }, 12319 loc 12320 }; 12321 } 12322 function parseAttributeValue(context) { 12323 const start = getCursor(context); 12324 let content; 12325 const quote = context.source[0]; 12326 const isQuoted = quote === `"` || quote === `'`; 12327 if (isQuoted) { 12328 // Quoted value. 12329 advanceBy(context, 1); 12330 const endIndex = context.source.indexOf(quote); 12331 if (endIndex === -1) { 12332 content = parseTextData(context, context.source.length, 4 /* TextModes.ATTRIBUTE_VALUE */); 12333 } 12334 else { 12335 content = parseTextData(context, endIndex, 4 /* TextModes.ATTRIBUTE_VALUE */); 12336 advanceBy(context, 1); 12337 } 12338 } 12339 else { 12340 // Unquoted 12341 const match = /^[^\t\r\n\f >]+/.exec(context.source); 12342 if (!match) { 12343 return undefined; 12344 } 12345 const unexpectedChars = /["'<=`]/g; 12346 let m; 12347 while ((m = unexpectedChars.exec(match[0]))) { 12348 emitError(context, 18 /* ErrorCodes.UNEXPECTED_CHARACTER_IN_UNQUOTED_ATTRIBUTE_VALUE */, m.index); 12349 } 12350 content = parseTextData(context, match[0].length, 4 /* TextModes.ATTRIBUTE_VALUE */); 12351 } 12352 return { content, isQuoted, loc: getSelection(context, start) }; 12353 } 12354 function parseInterpolation(context, mode) { 12355 const [open, close] = context.options.delimiters; 12356 const closeIndex = context.source.indexOf(close, open.length); 12357 if (closeIndex === -1) { 12358 emitError(context, 25 /* ErrorCodes.X_MISSING_INTERPOLATION_END */); 12359 return undefined; 12360 } 12361 const start = getCursor(context); 12362 advanceBy(context, open.length); 12363 const innerStart = getCursor(context); 12364 const innerEnd = getCursor(context); 12365 const rawContentLength = closeIndex - open.length; 12366 const rawContent = context.source.slice(0, rawContentLength); 12367 const preTrimContent = parseTextData(context, rawContentLength, mode); 12368 const content = preTrimContent.trim(); 12369 const startOffset = preTrimContent.indexOf(content); 12370 if (startOffset > 0) { 12371 advancePositionWithMutation(innerStart, rawContent, startOffset); 12372 } 12373 const endOffset = rawContentLength - (preTrimContent.length - content.length - startOffset); 12374 advancePositionWithMutation(innerEnd, rawContent, endOffset); 12375 advanceBy(context, close.length); 12376 return { 12377 type: 5 /* NodeTypes.INTERPOLATION */, 12378 content: { 12379 type: 4 /* NodeTypes.SIMPLE_EXPRESSION */, 12380 isStatic: false, 12381 // Set `isConstant` to false by default and will decide in transformExpression 12382 constType: 0 /* ConstantTypes.NOT_CONSTANT */, 12383 content, 12384 loc: getSelection(context, innerStart, innerEnd) 12385 }, 12386 loc: getSelection(context, start) 12387 }; 12388 } 12389 function parseText(context, mode) { 12390 const endTokens = mode === 3 /* TextModes.CDATA */ ? [']]>'] : ['<', context.options.delimiters[0]]; 12391 let endIndex = context.source.length; 12392 for (let i = 0; i < endTokens.length; i++) { 12393 const index = context.source.indexOf(endTokens[i], 1); 12394 if (index !== -1 && endIndex > index) { 12395 endIndex = index; 12396 } 12397 } 12398 const start = getCursor(context); 12399 const content = parseTextData(context, endIndex, mode); 12400 return { 12401 type: 2 /* NodeTypes.TEXT */, 12402 content, 12403 loc: getSelection(context, start) 12404 }; 12405 } 12406 /** 12407 * Get text data with a given length from the current location. 12408 * This translates HTML entities in the text data. 12409 */ 12410 function parseTextData(context, length, mode) { 12411 const rawText = context.source.slice(0, length); 12412 advanceBy(context, length); 12413 if (mode === 2 /* TextModes.RAWTEXT */ || 12414 mode === 3 /* TextModes.CDATA */ || 12415 !rawText.includes('&')) { 12416 return rawText; 12417 } 12418 else { 12419 // DATA or RCDATA containing "&"". Entity decoding required. 12420 return context.options.decodeEntities(rawText, mode === 4 /* TextModes.ATTRIBUTE_VALUE */); 12421 } 12422 } 12423 function getCursor(context) { 12424 const { column, line, offset } = context; 12425 return { column, line, offset }; 12426 } 12427 function getSelection(context, start, end) { 12428 end = end || getCursor(context); 12429 return { 12430 start, 12431 end, 12432 source: context.originalSource.slice(start.offset, end.offset) 12433 }; 12434 } 12435 function last(xs) { 12436 return xs[xs.length - 1]; 12437 } 12438 function startsWith(source, searchString) { 12439 return source.startsWith(searchString); 12440 } 12441 function advanceBy(context, numberOfCharacters) { 12442 const { source }
12442 = context; 12443 advancePositionWithMutation(context, source, numberOfCharacters); 12444 context.source = source.slice(numberOfCharacters); 12445 } 12446 function advanceSpaces(context) { 12447 const match = /^[\t\r\n\f ]+/.exec(context.source); 12448 if (match) { 12449 advanceBy(context, match[0].length); 12450 } 12451 } 12452 function getNewPosition(context, start, numberOfCharacters) { 12453 return advancePositionWithClone(start, context.originalSource.slice(start.offset, numberOfCharacters), numberOfCharacters); 12454 } 12455 function emitError(context, code, offset, loc = getCursor(context)) { 12456 if (offset) { 12457 loc.offset += offset; 12458 loc.column += offset; 12459 } 12460 context.options.onError(createCompilerError(code, { 12461 start: loc, 12462 end: loc, 12463 source: '' 12464 })); 12465 } 12466 function isEnd(context, mode, ancestors) { 12467 const s = context.source; 12468 switch (mode) { 12469 case 0 /* TextModes.DATA */: 12470 if (startsWith(s, '</')) { 12471 // TODO: probably bad performance 12472 for (let i = ancestors.length - 1; i >= 0; --i) { 12473 if (startsWithEndTagOpen(s, ancestors[i].tag)) { 12474 return true; 12475 } 12476 } 12477 } 12478 break; 12479 case 1 /* TextModes.RCDATA */: 12480 case 2 /* TextModes.RAWTEXT */: { 12481 const parent = last(ancestors); 12482 if (parent && startsWithEndTagOpen(s, parent.tag)) { 12483 return true; 12484 } 12485 break; 12486 } 12487 case 3 /* TextModes.CDATA */: 12488 if (startsWith(s, ']]>')) { 12489 return true; 12490 } 12491 break; 12492 } 12493 return !s; 12494 } 12495 function startsWithEndTagOpen(source, tag) { 12496 return (startsWith(source, '</') && 12497 source.slice(2, 2 + tag.length).toLowerCase() === tag.toLowerCase() && 12498 /[\t\r\n\f />]/.test(source[2 + tag.length] || '>')); 12499 } 12500 12501 function hoistStatic(root, context) { 12502 walk(root, context, 12503 // Root node is unfortunately non-hoistable due to potential parent 12504 // fallthrough attributes. 12505 isSingleElementRoot(root, root.children[0])); 12506 } 12507 function isSingleElementRoot(root, child) { 12508 const { children } = root; 12509 return (children.length === 1 && 12510 child.type === 1 /* NodeTypes.ELEMENT */ && 12511 !isSlotOutlet(child)); 12512 } 12513 function walk(node, context, doNotHoistNode = false) { 12514 const { children } = node; 12515 const originalCount = children.length; 12516 let hoistedCount = 0; 12517 for (let i = 0; i < children.length; i++) { 12518 const child = children[i]; 12519 // only plain elements & text calls are eligible for hoisting. 12520 if (child.type === 1 /* NodeTypes.ELEMENT */ && 12521 child.tagType === 0 /* ElementTypes.ELEMENT */) { 12522 const constantType = doNotHoistNode 12523 ? 0 /* ConstantTypes.NOT_CONSTANT */ 12524 : getConstantType(child, context); 12525 if (constantType > 0 /* ConstantTypes.NOT_CONSTANT */) { 12526 if (constantType >= 2 /* ConstantTypes.CAN_HOIST */) { 12527 child.codegenNode.patchFlag = 12528 -1 /* PatchFlags.HOISTED */ + (` /* HOISTED */` ); 12529 child.codegenNode = context.hoist(child.codegenNode); 12530 hoistedCount++; 12531 continue; 12532 } 12533 } 12534 else { 12535 // node may contain dynamic children, but its props may be eligible for 12536 // hoisting. 12537 const codegenNode = child.codegenNode; 12538 if (codegenNode.type === 13 /* NodeTypes.VNODE_CALL */) { 12539 const flag = getPatchFlag(codegenNode); 12540 if ((!flag || 12541 flag === 512 /* PatchFlags.NEED_PATCH */ || 12542 flag === 1 /* PatchFlags.TEXT */) && 12543 getGeneratedPropsConstantType(child, context) >= 12544 2 /* ConstantTypes.CAN_HOIST */) { 12545 const props = getNodeProps(child); 12546 if (props) { 12547 codegenNode.props = context.hoist(props); 12548 } 12549 } 12550 if (codegenNode.dynamicProps) { 12551 codegenNode.dynamicProps = context.hoist(codegenNode.dynamicProps); 12552 } 12553 } 12554 } 12555 } 12556 // walk further 12557 if (child.type === 1 /* NodeTypes.ELEMENT */) { 12558 const isComponent = child.tagType === 1 /* ElementTypes.COMPONENT */; 12559 if (isComponent) { 12560 context.scopes.vSlot++; 12561 }
12562 walk(child, context); 12563 if (isComponent) { 12564 context.scopes.vSlot--; 12565 } 12566 } 12567 else if (child.type === 11 /* NodeTypes.FOR */) { 12568 // Do not hoist v-for single child because it has to be a block 12569 walk(child, context, child.children.length === 1); 12570 } 12571 else if (child.type === 9 /* NodeTypes.IF */) { 12572 for (let i = 0; i < child.branches.length; i++) { 12573 // Do not hoist v-if single child because it has to be a block 12574 walk(child.branches[i], context, child.branches[i].children.length === 1); 12575 } 12576 } 12577 } 12578 if (hoistedCount && context.transformHoist) { 12579 context.transformHoist(children, context, node); 12580 } 12581 // all children were hoisted - the entire children array is hoistable. 12582 if (hoistedCount && 12583 hoistedCount === originalCount && 12584 node.type === 1 /* NodeTypes.ELEMENT */ && 12585 node.tagType === 0 /* ElementTypes.ELEMENT */ && 12586 node.codegenNode && 12587 node.codegenNode.type === 13 /* NodeTypes.VNODE_CALL */ && 12588 isArray(node.codegenNode.children)) { 12589 node.codegenNode.children = context.hoist(createArrayExpression(node.codegenNode.children)); 12590 } 12591 } 12592 function getConstantType(node, context) { 12593 const { constantCache } = context; 12594 switch (node.type) { 12595 case 1 /* NodeTypes.ELEMENT */: 12596 if (node.tagType !== 0 /* ElementTypes.ELEMENT */) { 12597 return 0 /* ConstantTypes.NOT_CONSTANT */; 12598 } 12599 const cached = constantCache.get(node); 12600 if (cached !== undefined) { 12601 return cached; 12602 } 12603 const codegenNode = node.codegenNode; 12604 if (codegenNode.type !== 13 /* NodeTypes.VNODE_CALL */) { 12605 return 0 /* ConstantTypes.NOT_CONSTANT */; 12606 } 12607 if (codegenNode.isBlock && 12608 node.tag !== 'svg' && 12609 node.tag !== 'foreignObject') { 12610 return 0 /* ConstantTypes.NOT_CONSTANT */; 12611 } 12612 const flag = getPatchFlag(codegenNode); 12613 if (!flag) { 12614 let returnType = 3 /* ConstantTypes.CAN_STRINGIFY */; 12615 // Element itself has no patch flag. However we still need to check: 12616 // 1. Even for a node with no patch flag, it is possible for it to contain 12617 // non-hoistable expressions that refers to scope variables, e.g. compiler 12618 // injected keys or cached event handlers. Therefore we need to always 12619 // check the codegenNode's props to be sure. 12620 const generatedPropsType = getGeneratedPropsConstantType(node, context); 12621 if (generatedPropsType === 0 /* ConstantTypes.NOT_CONSTANT */) { 12622 constantCache.set(node, 0 /* ConstantTypes.NOT_CONSTANT */); 12623 return 0 /* ConstantTypes.NOT_CONSTANT */; 12624 } 12625 if (generatedPropsType < returnType) { 12626 returnType = generatedPropsType; 12627 } 12628 // 2. its children. 12629 for (let i = 0; i < node.children.length; i++) { 12630 const childType = getConstantType(node.children[i], context); 12631 if (childType === 0 /* ConstantTypes.NOT_CONSTANT */) { 12632 constantCache.set(node, 0 /* ConstantTypes.NOT_CONSTANT */); 12633 return 0 /* ConstantTypes.NOT_CONSTANT */; 12634 } 12635 if (childType < returnType) { 12636 returnType = childType; 12637 } 12638 } 12639 // 3. if the type is not already CAN_SKIP_PATCH which is the lowest non-0 12640 // type, check if any of the props can cause the type to be lowered 12641 // we can skip can_patch because it's guaranteed by the absence of a 12642 // patchFlag. 12643 if (returnType > 1 /* ConstantTypes.CAN_SKIP_PATCH */) { 12644 for (let i = 0; i < node.props.length; i++) { 12645 const p = node.props[i]; 12646 if (p.type === 7 /* NodeTypes.DIRECTIVE */ && p.name === 'bind' && p.exp) { 12647 const expType = getConstantType(p.exp, context); 12648 if (expType === 0 /* ConstantTypes.NOT_CONSTANT */) {
vendor: 10,650 bytes, lines 12649-12910
12649 constantCache.set(node, 0 /* ConstantTypes.NOT_CONSTANT */); 12650 return 0 /* ConstantTypes.NOT_CONSTANT */; 12651 } 12652 if (expType < returnType) { 12653 returnType = expType; 12654 } 12655 } 12656 } 12657 } 12658 // only svg/foreignObject could be block here, however if they are 12659 // static then they don't need to be blocks since there will be no 12660 // nested updates. 12661 if (codegenNode.isBlock) { 12662 // except set custom directives. 12663 for (let i = 0; i < node.props.length; i++) { 12664 const p = node.props[i]; 12665 if (p.type === 7 /* NodeTypes.DIRECTIVE */) { 12666 constantCache.set(node, 0 /* ConstantTypes.NOT_CONSTANT */); 12667 return 0 /* ConstantTypes.NOT_CONSTANT */; 12668 } 12669 } 12670 context.removeHelper(OPEN_BLOCK); 12671 context.removeHelper(getVNodeBlockHelper(context.inSSR, codegenNode.isComponent)); 12672 codegenNode.isBlock = false; 12673 context.helper(getVNodeHelper(context.inSSR, codegenNode.isComponent)); 12674 } 12675 constantCache.set(node, returnType); 12676 return returnType; 12677 } 12678 else { 12679 constantCache.set(node, 0 /* ConstantTypes.NOT_CONSTANT */); 12680 return 0 /* ConstantTypes.NOT_CONSTANT */; 12681 } 12682 case 2 /* NodeTypes.TEXT */: 12683 case 3 /* NodeTypes.COMMENT */: 12684 return 3 /* ConstantTypes.CAN_STRINGIFY */; 12685 case 9 /* NodeTypes.IF */: 12686 case 11 /* NodeTypes.FOR */: 12687 case 10 /* NodeTypes.IF_BRANCH */: 12688 return 0 /* ConstantTypes.NOT_CONSTANT */; 12689 case 5 /* NodeTypes.INTERPOLATION */: 12690 case 12 /* NodeTypes.TEXT_CALL */: 12691 return getConstantType(node.content, context); 12692 case 4 /* NodeTypes.SIMPLE_EXPRESSION */: 12693 return node.constType; 12694 case 8 /* NodeTypes.COMPOUND_EXPRESSION */: 12695 let returnType = 3 /* ConstantTypes.CAN_STRINGIFY */; 12696 for (let i = 0; i < node.children.length; i++) { 12697 const child = node.children[i]; 12698 if (isString(child) || isSymbol(child)) { 12699 continue; 12700 } 12701 const childType = getConstantType(child, context); 12702 if (childType === 0 /* ConstantTypes.NOT_CONSTANT */) { 12703 return 0 /* ConstantTypes.NOT_CONSTANT */; 12704 } 12705 else if (childType < returnType) { 12706 returnType = childType; 12707 } 12708 } 12709 return returnType; 12710 default: 12711 return 0 /* ConstantTypes.NOT_CONSTANT */; 12712 } 12713 } 12714 const allowHoistedHelperSet = new Set([ 12715 NORMALIZE_CLASS, 12716 NORMALIZE_STYLE, 12717 NORMALIZE_PROPS, 12718 GUARD_REACTIVE_PROPS 12719 ]); 12720 function getConstantTypeOfHelperCall(value, context) { 12721 if (value.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */ && 12722 !isString(value.callee) && 12723 allowHoistedHelperSet.has(value.callee)) { 12724 const arg = value.arguments[0]; 12725 if (arg.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 12726 return getConstantType(arg, context); 12727 } 12728 else if (arg.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */) { 12729 // in the case of nested helper call, e.g. `normalizeProps(guardReactiveProps(exp))` 12730 return getConstantTypeOfHelperCall(arg, context); 12731 } 12732 } 12733 return 0 /* ConstantTypes.NOT_CONSTANT */; 12734 } 12735 function getGeneratedPropsConstantType(node, context) { 12736 let returnType = 3 /* ConstantTypes.CAN_STRINGIFY */; 12737 const props = getNodeProps(node); 12738 if (props && props.type === 15 /* NodeTypes.JS_OBJECT_EXPRESSION */) { 12739 const { properties } = props; 12740 for (let i = 0; i < properties.length; i++) { 12741 const { key, value } = properties[i]; 12742 const keyType = getConstantType(key, context); 12743 if (keyType === 0 /* ConstantTypes.NOT_CONSTANT */) { 12744 return keyType; 12745 } 12746 if (keyType < returnType) { 12747 returnType = keyType; 12748 } 12749 let valueType; 12750 if (value.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 12751 valueType = getConstantType(value, context); 12752 } 12753 else if (value.type === 14 /* NodeTypes.JS_CALL_EXPRESSION */) { 12754 // some helper calls can be hoisted, 12755 // such as the `normalizeProps` generated by the compiler for pre-normalize class, 12756 // in this case we need to respect the ConstantType of the helper's arguments 12757 valueType = getConstantTypeOfHelperCall(value, context); 12758 } 12759 else { 12760 valueType = 0 /* ConstantTypes.NOT_CONSTANT */; 12761 } 12762 if (valueType === 0 /* ConstantTypes.NOT_CONSTANT */) { 12763 return valueType; 12764 } 12765 if (valueType < returnType) { 12766 returnType = valueType; 12767 } 12768 } 12769 } 12770 return returnType; 12771 } 12772 function getNodeProps(node) { 12773 const codegenNode = node.codegenNode; 12774 if (codegenNode.type === 13 /* NodeTypes.VNODE_CALL */) { 12775 return codegenNode.props; 12776 } 12777 } 12778 function getPatchFlag(node) { 12779 const flag = node.patchFlag; 12780 return flag ? parseInt(flag, 10) : undefined; 12781 } 12782 12783 function createTransformContext(root, { filename = '', prefixIdentifiers = false, hoistStatic = false, cacheHandlers = false, nodeTransforms = [], directiveTransforms = {}, transformHoist = null, isBuiltInComponent = NOOP, isCustomElement = NOOP, expressionPlugins = [], scopeId = null, slotted = true, ssr = false, inSSR = false, ssrCssVars = ``, bindingMetadata = EMPTY_OBJ, inline = false, isTS = false, onError = defaultOnError, onWarn = defaultOnWarn, compatConfig }) { 12784 const nameMatch = filename.replace(/\?.*$/, '').match(/([^/\\]+)\.\w+$/); 12785 const context = { 12786 // options 12787 selfName: nameMatch && capitalize(camelize(nameMatch[1])), 12788 prefixIdentifiers, 12789 hoistStatic, 12790 cacheHandlers, 12791 nodeTransforms, 12792 directiveTransforms, 12793 transformHoist, 12794 isBuiltInComponent, 12795 isCustomElement, 12796 expressionPlugins, 12797 scopeId, 12798 slotted, 12799 ssr, 12800 inSSR, 12801 ssrCssVars, 12802 bindingMetadata, 12803 inline, 12804 isTS, 12805 onError, 12806 onWarn, 12807 compatConfig, 12808 // state 12809 root, 12810 helpers: new Map(), 12811 components: new Set(), 12812 directives: new Set(), 12813 hoists: [], 12814 imports: [], 12815 constantCache: new Map(), 12816 temps: 0, 12817 cached: 0, 12818 identifiers: Object.create(null), 12819 scopes: { 12820 vFor: 0, 12821 vSlot: 0, 12822 vPre: 0, 12823 vOnce: 0 12824 }, 12825 parent: null, 12826 currentNode: root, 12827 childIndex: 0, 12828 inVOnce: false, 12829 // methods 12830 helper(name) { 12831 const count = context.helpers.get(name) || 0; 12832 context.helpers.set(name, count + 1); 12833 return name; 12834 }, 12835 removeHelper(name) { 12836 const count = context.helpers.get(name); 12837 if (count) { 12838 const currentCount = count - 1; 12839 if (!currentCount) { 12840 context.helpers.delete(name); 12841 } 12842 else { 12843 context.helpers.set(name, currentCount); 12844 } 12845 } 12846 }, 12847 helperString(name) { 12848 return `_${helperNameMap[context.helper(name)]}`; 12849 }, 12850 replaceNode(node) { 12851 /* istanbul ignore if */ 12852 { 12853 if (!context.currentNode) { 12854 throw new Error(`Node being replaced is already removed.`); 12855 } 12856 if (!context.parent) { 12857 throw new Error(`Cannot replace root node.`); 12858 } 12859 } 12860 context.parent.children[context.childIndex] = context.currentNode = node; 12861 }, 12862 removeNode(node) { 12863 if (!context.parent) { 12864 throw new Error(`Cannot remove root node.`); 12865 } 12866 const list = context.parent.children; 12867 const removalIndex = node 12868 ? list.indexOf(node) 12869 : context.currentNode 12870 ? context.childIndex 12871 : -1; 12872 /* istanbul ignore if */ 12873 if (removalIndex < 0) { 12874 throw new Error(`node being removed is not a child of current parent`); 12875 } 12876 if (!node || node === context.currentNode) { 12877 // current node removed 12878 context.currentNode = null; 12879 context.onNodeRemoved(); 12880 } 12881 else { 12882 // sibling node removed 12883 if (context.childIndex > removalIndex) { 12884 context.childIndex--; 12885 context.onNodeRemoved(); 12886 } 12887 } 12888 context.parent.children.splice(removalIndex, 1); 12889 }, 12890 onNodeRemoved: () => { }, 12891 addIdentifiers(exp) { 12892 }, 12893 removeIdentifiers(exp) { 12894 }, 12895 hoist(exp) { 12896 if (isString(exp)) 12897 exp = createSimpleExpression(exp); 12898 context.hoists.push(exp); 12899 const identifier = createSimpleExpression(`_hoisted_${context.hoists.length}`, false, exp.loc, 2 /* ConstantTypes.CAN_HOIST */); 12900 identifier.hoisted = exp; 12901 return identifier; 12902 }, 12903 cache(exp, isVNode = false) { 12904 return createCacheExpression(context.cached++, exp, isVNode); 12905 } 12906 }; 12907 return context; 12908 } 12909 function transform(root, options) { 12910 const context = createTransformContext(root, options);
12911 traverseNode(root, context); 12912 if (options.hoistStatic) { 12913 hoistStatic(root, context); 12914 } 12915 if (!options.ssr) { 12916 createRootCodegen(root, context); 12917 } 12918 // finalize meta information 12919 root.helpers = [...context.helpers.keys()]; 12920 root.components = [...context.components]; 12921 root.directives = [...context.directives]; 12922 root.imports = context.imports; 12923 root.hoists = context.hoists; 12924 root.temps = context.temps; 12925 root.cached = context.cached; 12926 } 12927 function createRootCodegen(root, context) { 12928 const { helper } = context; 12929 const { children } = root; 12930 if (children.length === 1) { 12931 const child = children[0]; 12932 // if the single child is an element, turn it into a block. 12933 if (isSingleElementRoot(root, child) && child.codegenNode) { 12934 // single element root is never hoisted so codegenNode will never be 12935 // SimpleExpressionNode 12936 const codegenNode = child.codegenNode; 12937 if (codegenNode.type === 13 /* NodeTypes.VNODE_CALL */) { 12938 makeBlock(codegenNode, context); 12939 } 12940 root.codegenNode = codegenNode; 12941 } 12942 else { 12943 // - single <slot/>, IfNode, ForNode: already blocks. 12944 // - single text node: always patched. 12945 // root codegen falls through via genNode() 12946 root.codegenNode = child; 12947 } 12948 } 12949 else if (children.length > 1) { 12950 // root has multiple nodes - return a fragment block. 12951 let patchFlag = 64 /* PatchFlags.STABLE_FRAGMENT */; 12952 let patchFlagText = PatchFlagNames[64 /* PatchFlags.STABLE_FRAGMENT */]; 12953 // check if the fragment actually contains a single valid child with 12954 // the rest being comments 12955 if (children.filter(c => c.type !== 3 /* NodeTypes.COMMENT */).length === 1) { 12956 patchFlag |= 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */; 12957 patchFlagText += `, ${PatchFlagNames[2048 /* PatchFlags.DEV_ROOT_FRAGMENT */]}`; 12958 } 12959 root.codegenNode = createVNodeCall(context, helper(FRAGMENT), undefined, root.children, patchFlag + (` /* ${patchFlagText} */` ), undefined, undefined, true, undefined, false /* isComponent */); 12960 } 12961 else ; 12962 } 12963 function traverseChildren(parent, context) { 12964 let i = 0; 12965 const nodeRemoved = () => { 12966 i--; 12967 }; 12968 for (; i < parent.children.length; i++) { 12969 const child = parent.children[i]; 12970 if (isString(child)) 12971 continue; 12972 context.parent = parent; 12973 context.childIndex = i; 12974 context.onNodeRemoved = nodeRemoved; 12975 traverseNode(child, context); 12976 } 12977 } 12978 function traverseNode(node, context) { 12979 context.currentNode = node; 12980 // apply transform plugins 12981 const { nodeTransforms } = context; 12982 const exitFns = []; 12983 for (let i = 0; i < nodeTransforms.length; i++) { 12984 const onExit = nodeTransforms[i](node, context); 12985 if (onExit) { 12986 if (isArray(onExit)) { 12987 exitFns.push(...onExit); 12988 } 12989 else { 12990 exitFns.push(onExit); 12991 } 12992 } 12993 if (!context.currentNode) { 12994 // node was removed 12995 return; 12996 } 12997 else { 12998 // node may have been replaced 12999 node = context.currentNode; 13000 } 13001 } 13002 switch (node.type) { 13003 case 3 /* NodeTypes.COMMENT */: 13004 if (!context.ssr) { 13005 // inject import for the Comment symbol, which is needed for creating 13006 // comment nodes with `createVNode` 13007 context.helper(CREATE_COMMENT); 13008 } 13009 break; 13010 case 5 /* NodeTypes.INTERPOLATION */: 13011 // no need to traverse, but we need to inject toString helper 13012 if (!context.ssr) { 13013 context.helper(TO_DISPLAY_STRING); 13014 } 13015 break; 13016 // for container types, further traverse downwards 13017 case 9 /* NodeTypes.IF */: 13018 for (let i = 0; i < node.branches.length; i++) {
vendor: 3,818 bytes, lines 13019-13123
13019 traverseNode(node.branches[i], context); 13020 } 13021 break; 13022 case 10 /* NodeTypes.IF_BRANCH */: 13023 case 11 /* NodeTypes.FOR */: 13024 case 1 /* NodeTypes.ELEMENT */: 13025 case 0 /* NodeTypes.ROOT */: 13026 traverseChildren(node, context); 13027 break; 13028 } 13029 // exit transforms 13030 context.currentNode = node; 13031 let i = exitFns.length; 13032 while (i--) { 13033 exitFns[i](); 13034 } 13035 } 13036 function createStructuralDirectiveTransform(name, fn) { 13037 const matches = isString(name) 13038 ? (n) => n === name 13039 : (n) => name.test(n); 13040 return (node, context) => { 13041 if (node.type === 1 /* NodeTypes.ELEMENT */) { 13042 const { props } = node; 13043 // structural directive transforms are not concerned with slots 13044 // as they are handled separately in vSlot.ts 13045 if (node.tagType === 3 /* ElementTypes.TEMPLATE */ && props.some(isVSlot)) { 13046 return; 13047 } 13048 const exitFns = []; 13049 for (let i = 0; i < props.length; i++) { 13050 const prop = props[i]; 13051 if (prop.type === 7 /* NodeTypes.DIRECTIVE */ && matches(prop.name)) { 13052 // structural directives are removed to avoid infinite recursion 13053 // also we remove them *before* applying so that it can further 13054 // traverse itself in case it moves the node around 13055 props.splice(i, 1); 13056 i--; 13057 const onExit = fn(node, prop, context); 13058 if (onExit) 13059 exitFns.push(onExit); 13060 } 13061 } 13062 return exitFns; 13063 } 13064 }; 13065 } 13066 13067 const PURE_ANNOTATION = `/*#__PURE__*/`; 13068 const aliasHelper = (s) => `${helperNameMap[s]}: _${helperNameMap[s]}`; 13069 function createCodegenContext(ast, { mode = 'function', prefixIdentifiers = mode === 'module', sourceMap = false, filename = `template.vue.html`, scopeId = null, optimizeImports = false, runtimeGlobalName = `Vue`, runtimeModuleName = `vue`, ssrRuntimeModuleName = 'vue/server-renderer', ssr = false, isTS = false, inSSR = false }) { 13070 const context = { 13071 mode, 13072 prefixIdentifiers, 13073 sourceMap, 13074 filename, 13075 scopeId, 13076 optimizeImports, 13077 runtimeGlobalName, 13078 runtimeModuleName, 13079 ssrRuntimeModuleName, 13080 ssr, 13081 isTS, 13082 inSSR, 13083 source: ast.loc.source, 13084 code: ``, 13085 column: 1, 13086 line: 1, 13087 offset: 0, 13088 indentLevel: 0, 13089 pure: false, 13090 map: undefined, 13091 helper(key) { 13092 return `_${helperNameMap[key]}`; 13093 }, 13094 push(code, node) { 13095 context.code += code; 13096 }, 13097 indent() { 13098 newline(++context.indentLevel); 13099 }, 13100 deindent(withoutNewLine = false) { 13101 if (withoutNewLine) { 13102 --context.indentLevel; 13103 } 13104 else { 13105 newline(--context.indentLevel); 13106 } 13107 }, 13108 newline() { 13109 newline(context.indentLevel); 13110 } 13111 }; 13112 function newline(n) { 13113 context.push('\n' + ` `.repeat(n)); 13114 } 13115 return context; 13116 } 13117 function generate(ast, options = {}) { 13118 const context = createCodegenContext(ast, options); 13119 if (options.onContextCreated) 13120 options.onContextCreated(context); 13121 const { mode, push, prefixIdentifiers, indent, deindent, newline, scopeId, ssr } = context; 13122 const hasHelpers = ast.helpers.length > 0; 13123 const useWithBlock = !prefixIdentifiers && mode !== 'module';
13124 // preambles 13125 // in setup() inline mode, the preamble is generated in a sub context 13126 // and returned separately. 13127 const preambleContext = context; 13128 { 13129 genFunctionPreamble(ast, preambleContext); 13130 } 13131 // enter render function 13132 const functionName = ssr ? `ssrRender` : `render`; 13133 const args = ssr ? ['_ctx', '_push', '_parent', '_attrs'] : ['_ctx', '_cache']; 13134 const signature = args.join(', '); 13135 { 13136 push(`function ${functionName}(${signature}) {`); 13137 } 13138 indent(); 13139 if (useWithBlock) { 13140 push(`with (_ctx) {`); 13141 indent(); 13142 // function mode const declarations should be inside with block 13143 // also they should be renamed to avoid collision with user properties 13144 if (hasHelpers) { 13145 push(`const { ${ast.helpers.map(aliasHelper).join(', ')} } = _Vue`); 13146 push(`\n`); 13147 newline(); 13148 } 13149 } 13150 // generate asset resolution statements 13151 if (ast.components.length) { 13152 genAssets(ast.components, 'component', context); 13153 if (ast.directives.length || ast.temps > 0) { 13154 newline(); 13155 } 13156 } 13157 if (ast.directives.length) { 13158 genAssets(ast.directives, 'directive', context); 13159 if (ast.temps > 0) { 13160 newline(); 13161 } 13162 } 13163 if (ast.temps > 0) { 13164 push(`let `); 13165 for (let i = 0; i < ast.temps; i++) { 13166 push(`${i > 0 ? `, ` : ``}_temp${i}`); 13167 } 13168 } 13169 if (ast.components.length || ast.directives.length || ast.temps) { 13170 push(`\n`); 13171 newline(); 13172 } 13173 // generate the VNode tree expression 13174 if (!ssr) { 13175 push(`return `); 13176 } 13177 if (ast.codegenNode) { 13178 genNode(ast.codegenNode, context); 13179 } 13180 else { 13181 push(`null`); 13182 } 13183 if (useWithBlock) { 13184 deindent(); 13185 push(`}`); 13186 } 13187 deindent(); 13188 push(`}`); 13189 return { 13190 ast, 13191 code: context.code, 13192 preamble: ``, 13193 // SourceMapGenerator does have toJSON() method but it's not in the types 13194 map: context.map ? context.map.toJSON() : undefined 13195 }; 13196 } 13197 function genFunctionPreamble(ast, context) { 13198 const { ssr, prefixIdentifiers, push, newline, runtimeModuleName, runtimeGlobalName, ssrRuntimeModuleName } = context; 13199 const VueBinding = runtimeGlobalName; 13200 // Generate const declaration for helpers 13201 // In prefix mode, we place the const declaration at top so it's done 13202 // only once; But if we not prefixing, we place the declaration inside the 13203 // with block so it doesn't incur the `in` check cost for every helper access. 13204 if (ast.helpers.length > 0) { 13205 { 13206 // "with" mode. 13207 // save Vue in a separate variable to avoid collision 13208 push(`const _Vue = ${VueBinding}\n`); 13209 // in "with" mode, helpers are declared inside the with block to avoid 13210 // has check cost, but hoists are lifted out of the function - we need 13211 // to provide the helper here. 13212 if (ast.hoists.length) { 13213 const staticHelpers = [ 13214 CREATE_VNODE, 13215 CREATE_ELEMENT_VNODE, 13216 CREATE_COMMENT, 13217 CREATE_TEXT, 13218 CREATE_STATIC 13219 ] 13220 .filter(helper => ast.helpers.includes(helper)) 13221 .map(aliasHelper) 13222 .join(', '); 13223 push(`const { ${staticHelpers} } = _Vue\n`); 13224 } 13225 } 13226 } 13227 genHoists(ast.hoists, context); 13228 newline(); 13229 push(`return `); 13230 } 13231 function genAssets(assets, type, { helper, push, newline, isTS }) { 13232 const resolver = helper(type === 'component' 13233 ? RESOLVE_COMPONENT 13234 : RESOLVE_DIRECTIVE); 13235 for (let i = 0; i < assets.length; i++) { 13236 let id = assets[i]; 13237 // potential component implicit self-reference inferred from SFC filename 13238 const maybeSelfReference = id.endsWith('__self'); 13239 if (maybeSelfReference) { 13240 id = id.slice(0, -6); 13241 } 13242 push(`const ${toValidAssetId(id, type)} = ${resolver}(${JSON.stringify(id)}${maybeSelfReference ? `, true` : ``})${isTS ? `!` : ``}`); 13243 if (i < assets.length - 1) { 13244 newline(); 13245 } 13246 } 13247 } 13248 function genHoists(hoists, context) { 13249 if (!hoists.length) { 13250 return; 13251 } 13252 context.pure = true; 13253 const { push, newline, helper, scopeId, mode } = context; 13254 newline(); 13255 for (let i = 0; i < hoists.length; i++) { 13256 const exp = hoists[i]; 13257 if (exp) { 13258 push(`const _hoisted_${i + 1} = ${``}`); 13259 genNode(exp, context); 13260 newline(); 13261 } 13262 } 13263 context.pure = false;
13264 } 13265 function isText$1(n) { 13266 return (isString(n) || 13267 n.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ || 13268 n.type === 2 /* NodeTypes.TEXT */ || 13269 n.type === 5 /* NodeTypes.INTERPOLATION */ || 13270 n.type === 8 /* NodeTypes.COMPOUND_EXPRESSION */); 13271 } 13272 function genNodeListAsArray(nodes, context) { 13273 const multilines = nodes.length > 3 || 13274 (nodes.some(n => isArray(n) || !isText$1(n))); 13275 context.push(`[`); 13276 multilines && context.indent(); 13277 genNodeList(nodes, context, multilines); 13278 multilines && context.deindent(); 13279 context.push(`]`); 13280 } 13281 function genNodeList(nodes, context, multilines = false, comma = true) { 13282 const { push, newline } = context; 13283 for (let i = 0; i < nodes.length; i++) { 13284 const node = nodes[i]; 13285 if (isString(node)) { 13286 push(node); 13287 } 13288 else if (isArray(node)) { 13289 genNodeListAsArray(node, context); 13290 } 13291 else { 13292 genNode(node, context); 13293 } 13294 if (i < nodes.length - 1) { 13295 if (multilines) { 13296 comma && push(','); 13297 newline(); 13298 } 13299 else { 13300 comma && push(', '); 13301 } 13302 } 13303 } 13304 } 13305 function genNode(node, context) { 13306 if (isString(node)) { 13307 context.push(node); 13308 return; 13309 } 13310 if (isSymbol(node)) { 13311 context.push(context.helper(node)); 13312 return; 13313 } 13314 switch (node.type) { 13315 case 1 /* NodeTypes.ELEMENT */: 13316 case 9 /* NodeTypes.IF */: 13317 case 11 /* NodeTypes.FOR */: 13318 assert(node.codegenNode != null, `Codegen node is missing for element/if/for node. ` + 13319 `Apply appropriate transforms first.`); 13320 genNode(node.codegenNode, context); 13321 break; 13322 case 2 /* NodeTypes.TEXT */: 13323 genText(node, context); 13324 break; 13325 case 4 /* NodeTypes.SIMPLE_EXPRESSION */: 13326 genExpression(node, context); 13327 break; 13328 case 5 /* NodeTypes.INTERPOLATION */: 13329 genInterpolation(node, context); 13330 break; 13331 case 12 /* NodeTypes.TEXT_CALL */: 13332 genNode(node.codegenNode, context); 13333 break; 13334 case 8 /* NodeTypes.COMPOUND_EXPRESSION */: 13335 genCompoundExpression(node, context); 13336 break; 13337 case 3 /* NodeTypes.COMMENT */: 13338 genComment(node, context); 13339 break; 13340 case 13 /* NodeTypes.VNODE_CALL */: 13341 genVNodeCall(node, context); 13342 break; 13343 case 14 /* NodeTypes.JS_CALL_EXPRESSION */: 13344 genCallExpression(node, context); 13345 break; 13346 case 15 /* NodeTypes.JS_OBJECT_EXPRESSION */: 13347 genObjectExpression(node, context); 13348 break; 13349 case 17 /* NodeTypes.JS_ARRAY_EXPRESSION */: 13350 genArrayExpression(node, context); 13351 break; 13352 case 18 /* NodeTypes.JS_FUNCTION_EXPRESSION */: 13353 genFunctionExpression(node, context); 13354 break; 13355 case 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */: 13356 genConditionalExpression(node, context); 13357 break; 13358 case 20 /* NodeTypes.JS_CACHE_EXPRESSION */: 13359 genCacheExpression(node, context); 13360 break; 13361 case 21 /* NodeTypes.JS_BLOCK_STATEMENT */: 13362 genNodeList(node.body, context, true, false); 13363 break; 13364 // SSR only types 13365 case 22 /* NodeTypes.JS_TEMPLATE_LITERAL */: 13366 break; 13367 case 23 /* NodeTypes.JS_IF_STATEMENT */: 13368 break; 13369 case 24 /* NodeTypes.JS_ASSIGNMENT_EXPRESSION */: 13370 break; 13371 case 25 /* NodeTypes.JS_SEQUENCE_EXPRESSION */: 13372 break; 13373 case 26 /* NodeTypes.JS_RETURN_STATEMENT */: 13374 break; 13375 /* istanbul ignore next */ 13376 case 10 /* NodeTypes.IF_BRANCH */: 13377 // noop 13378 break; 13379 default: 13380 { 13381 assert(false, `unhandled codegen node type: ${node.type}`); 13382 // make sure we exhaust all possible types 13383 const exhaustiveCheck = node; 13384 return exhaustiveCheck; 13385 } 13386 } 13387 } 13388 function genText(node, context) { 13389 context.push(JSON.stringify(node.content), node); 13390 } 13391 function genExpression(node, context) { 13392 const { content, isStatic } = node; 13393 context.push(isStatic ? JSON.stringify(content) : content, node); 13394 } 13395 function genInterpolation(node, context) { 13396 const { push, helper, pure } = context; 13397 if (pure) 13398 push(PURE_ANNOTATION); 13399 push(`${helper(TO_DISPLAY_STRING)}(`); 13400 genNode(node.content, context); 13401 push(`)`); 13402 } 13403 function genCompoundExpression(node, context) { 13404 for (let i = 0; i < node.children.length; i++) { 13405 const child = node.children[i]; 13406 if (isString(child)) { 13407 context.push(child); 13408 } 13409 else {
vendor: 4,933 bytes, lines 13410-13570
13410 genNode(child, context); 13411 } 13412 } 13413 } 13414 function genExpressionAsPropertyKey(node, context) { 13415 const { push } = context; 13416 if (node.type === 8 /* NodeTypes.COMPOUND_EXPRESSION */) { 13417 push(`[`); 13418 genCompoundExpression(node, context); 13419 push(`]`); 13420 } 13421 else if (node.isStatic) { 13422 // only quote keys if necessary 13423 const text = isSimpleIdentifier(node.content) 13424 ? node.content 13425 : JSON.stringify(node.content); 13426 push(text, node); 13427 } 13428 else { 13429 push(`[${node.content}]`, node); 13430 } 13431 } 13432 function genComment(node, context) { 13433 const { push, helper, pure } = context; 13434 if (pure) { 13435 push(PURE_ANNOTATION); 13436 } 13437 push(`${helper(CREATE_COMMENT)}(${JSON.stringify(node.content)})`, node); 13438 } 13439 function genVNodeCall(node, context) { 13440 const { push, helper, pure } = context; 13441 const { tag, props, children, patchFlag, dynamicProps, directives, isBlock, disableTracking, isComponent } = node; 13442 if (directives) { 13443 push(helper(WITH_DIRECTIVES) + `(`); 13444 } 13445 if (isBlock) { 13446 push(`(${helper(OPEN_BLOCK)}(${disableTracking ? `true` : ``}), `); 13447 } 13448 if (pure) { 13449 push(PURE_ANNOTATION); 13450 } 13451 const callHelper = isBlock 13452 ? getVNodeBlockHelper(context.inSSR, isComponent) 13453 : getVNodeHelper(context.inSSR, isComponent); 13454 push(helper(callHelper) + `(`, node); 13455 genNodeList(genNullableArgs([tag, props, children, patchFlag, dynamicProps]), context); 13456 push(`)`); 13457 if (isBlock) { 13458 push(`)`); 13459 } 13460 if (directives) { 13461 push(`, `); 13462 genNode(directives, context); 13463 push(`)`); 13464 } 13465 } 13466 function genNullableArgs(args) { 13467 let i = args.length; 13468 while (i--) { 13469 if (args[i] != null) 13470 break; 13471 } 13472 return args.slice(0, i + 1).map(arg => arg || `null`); 13473 } 13474 // JavaScript 13475 function genCallExpression(node, context) { 13476 const { push, helper, pure } = context; 13477 const callee = isString(node.callee) ? node.callee : helper(node.callee); 13478 if (pure) { 13479 push(PURE_ANNOTATION); 13480 } 13481 push(callee + `(`, node); 13482 genNodeList(node.arguments, context); 13483 push(`)`); 13484 } 13485 function genObjectExpression(node, context) { 13486 const { push, indent, deindent, newline } = context; 13487 const { properties } = node; 13488 if (!properties.length) { 13489 push(`{}`, node); 13490 return; 13491 } 13492 const multilines = properties.length > 1 || 13493 (properties.some(p => p.value.type !== 4 /* NodeTypes.SIMPLE_EXPRESSION */)); 13494 push(multilines ? `{` : `{ `); 13495 multilines && indent(); 13496 for (let i = 0; i < properties.length; i++) { 13497 const { key, value } = properties[i]; 13498 // key 13499 genExpressionAsPropertyKey(key, context); 13500 push(`: `); 13501 // value 13502 genNode(value, context); 13503 if (i < properties.length - 1) { 13504 // will only reach this if it's multilines 13505 push(`,`); 13506 newline(); 13507 } 13508 } 13509 multilines && deindent(); 13510 push(multilines ? `}` : ` }`); 13511 } 13512 function genArrayExpression(node, context) { 13513 genNodeListAsArray(node.elements, context); 13514 } 13515 function genFunctionExpression(node, context) { 13516 const { push, indent, deindent } = context; 13517 const { params, returns, body, newline, isSlot } = node; 13518 if (isSlot) { 13519 // wrap slot functions with owner context 13520 push(`_${helperNameMap[WITH_CTX]}(`); 13521 } 13522 push(`(`, node); 13523 if (isArray(params)) { 13524 genNodeList(params, context); 13525 } 13526 else if (params) { 13527 genNode(params, context); 13528 } 13529 push(`) => `); 13530 if (newline || body) { 13531 push(`{`); 13532 indent(); 13533 } 13534 if (returns) { 13535 if (newline) { 13536 push(`return `); 13537 } 13538 if (isArray(returns)) { 13539 genNodeListAsArray(returns, context); 13540 } 13541 else { 13542 genNode(returns, context); 13543 } 13544 } 13545 else if (body) { 13546 genNode(body, context); 13547 } 13548 if (newline || body) { 13549 deindent(); 13550 push(`}`); 13551 } 13552 if (isSlot) { 13553 push(`)`); 13554 } 13555 } 13556 function genConditionalExpression(node, context) { 13557 const { test, consequent, alternate, newline: needNewline } = node; 13558 const { push, indent, deindent, newline } = context; 13559 if (test.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 13560 const needsParens = !isSimpleIdentifier(test.content); 13561 needsParens && push(`(`); 13562 genExpression(test, context); 13563 needsParens && push(`)`); 13564 } 13565 else { 13566 push(`(`); 13567 genNode(test, context); 13568 push(`)`); 13569 } 13570 needNewline && indent();
13571 context.indentLevel++; 13572 needNewline || push(` `); 13573 push(`? `); 13574 genNode(consequent, context); 13575 context.indentLevel--; 13576 needNewline && newline(); 13577 needNewline || push(` `); 13578 push(`: `); 13579 const isNested = alternate.type === 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */; 13580 if (!isNested) { 13581 context.indentLevel++; 13582 } 13583 genNode(alternate, context); 13584 if (!isNested) { 13585 context.indentLevel--; 13586 } 13587 needNewline && deindent(true /* without newline */); 13588 } 13589 function genCacheExpression(node, context) { 13590 const { push, helper, indent, deindent, newline } = context; 13591 push(`_cache[${node.index}] || (`); 13592 if (node.isVNode) { 13593 indent(); 13594 push(`${helper(SET_BLOCK_TRACKING)}(-1),`); 13595 newline(); 13596 } 13597 push(`_cache[${node.index}] = `); 13598 genNode(node.value, context); 13599 if (node.isVNode) { 13600 push(`,`); 13601 newline(); 13602 push(`${helper(SET_BLOCK_TRACKING)}(1),`); 13603 newline(); 13604 push(`_cache[${node.index}]`); 13605 deindent(); 13606 } 13607 push(`)`); 13608 } 13609 13610 // these keywords should not appear inside expressions, but operators like 13611 // typeof, instanceof and in are allowed 13612 const prohibitedKeywordRE = new RegExp('\\b' + 13613 ('do,if,for,let,new,try,var,case,else,with,await,break,catch,class,const,' + 13614 'super,throw,while,yield,delete,export,import,return,switch,default,' + 13615 'extends,finally,continue,debugger,function,arguments,typeof,void') 13616 .split(',') 13617 .join('\\b|\\b') + 13618 '\\b'); 13619 // strip strings in expressions 13620 const stripStringRE = /'(?:[^'\\]|\\.)*'|"(?:[^"\\]|\\.)*"|`(?:[^`\\]|\\.)*\$\{|\}(?:[^`\\]|\\.)*`|`(?:[^`\\]|\\.)*`/g; 13621 /** 13622 * Validate a non-prefixed expression. 13623 * This is only called when using the in-browser runtime compiler since it 13624 * doesn't prefix expressions. 13625 */ 13626 function validateBrowserExpression(node, context, asParams = false, asRawStatements = false) { 13627 const exp = node.content; 13628 // empty expressions are validated per-directive since some directives 13629 // do allow empty expressions. 13630 if (!exp.trim()) { 13631 return; 13632 } 13633 try { 13634 new Function(asRawStatements 13635 ? ` ${exp} ` 13636 : `return ${asParams ? `(${exp}) => {}` : `(${exp})`}`); 13637 } 13638 catch (e) { 13639 let message = e.message; 13640 const keywordMatch = exp 13641 .replace(stripStringRE, '') 13642 .match(prohibitedKeywordRE); 13643 if (keywordMatch) { 13644 message = `avoid using JavaScript keyword as property name: "${keywordMatch[0]}"`; 13645 } 13646 context.onError(createCompilerError(45 /* ErrorCodes.X_INVALID_EXPRESSION */, node.loc, undefined, message)); 13647 } 13648 } 13649 13650 const transformExpression = (node, context) => { 13651 if (node.type === 5 /* NodeTypes.INTERPOLATION */) { 13652 node.content = processExpression(node.content, context); 13653 } 13654 else if (node.type === 1 /* NodeTypes.ELEMENT */) { 13655 // handle directives on element 13656 for (let i = 0; i < node.props.length; i++) { 13657 const dir = node.props[i]; 13658 // do not process for v-on & v-for since they are special handled 13659 if (dir.type === 7 /* NodeTypes.DIRECTIVE */ && dir.name !== 'for') { 13660 const exp = dir.exp; 13661 const arg = dir.arg; 13662 // do not process exp if this is v-on:arg - we need special handling 13663 // for wrapping inline statements. 13664 if (exp && 13665 exp.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && 13666 !(dir.name === 'on' && arg)) { 13667 dir.exp = processExpression(exp, context, 13668 // slot args must be processed as function params 13669 dir.name === 'slot'); 13670 } 13671 if (arg && arg.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && !arg.isStatic) { 13672 dir.arg = processExpression(arg, context); 13673 } 13674 } 13675 } 13676 } 13677 };
vendor: 4,700 bytes, lines 13678-13782
13678 // Important: since this function uses Node.js only dependencies, it should 13679 // always be used with a leading !true check so that it can be 13680 // tree-shaken from the browser build. 13681 function processExpression(node, context, 13682 // some expressions like v-slot props & v-for aliases should be parsed as 13683 // function params 13684 asParams = false, 13685 // v-on handler values may contain multiple statements 13686 asRawStatements = false, localVars = Object.create(context.identifiers)) { 13687 { 13688 { 13689 // simple in-browser validation (same logic in 2.x) 13690 validateBrowserExpression(node, context, asParams, asRawStatements); 13691 } 13692 return node; 13693 } 13694 } 13695 13696 const transformIf = createStructuralDirectiveTransform(/^(if|else|else-if)$/, (node, dir, context) => { 13697 return processIf(node, dir, context, (ifNode, branch, isRoot) => { 13698 // #1587: We need to dynamically increment the key based on the current 13699 // node's sibling nodes, since chained v-if/else branches are 13700 // rendered at the same depth 13701 const siblings = context.parent.children; 13702 let i = siblings.indexOf(ifNode); 13703 let key = 0; 13704 while (i-- >= 0) { 13705 const sibling = siblings[i]; 13706 if (sibling && sibling.type === 9 /* NodeTypes.IF */) { 13707 key += sibling.branches.length; 13708 } 13709 } 13710 // Exit callback. Complete the codegenNode when all children have been 13711 // transformed. 13712 return () => { 13713 if (isRoot) { 13714 ifNode.codegenNode = createCodegenNodeForBranch(branch, key, context); 13715 } 13716 else { 13717 // attach this branch's codegen node to the v-if root. 13718 const parentCondition = getParentCondition(ifNode.codegenNode); 13719 parentCondition.alternate = createCodegenNodeForBranch(branch, key + ifNode.branches.length - 1, context); 13720 } 13721 }; 13722 }); 13723 }); 13724 // target-agnostic transform used for both Client and SSR 13725 function processIf(node, dir, context, processCodegen) { 13726 if (dir.name !== 'else' && 13727 (!dir.exp || !dir.exp.content.trim())) { 13728 const loc = dir.exp ? dir.exp.loc : node.loc; 13729 context.onError(createCompilerError(28 /* ErrorCodes.X_V_IF_NO_EXPRESSION */, dir.loc)); 13730 dir.exp = createSimpleExpression(`true`, false, loc); 13731 } 13732 if (dir.exp) { 13733 validateBrowserExpression(dir.exp, context); 13734 } 13735 if (dir.name === 'if') { 13736 const branch = createIfBranch(node, dir); 13737 const ifNode = { 13738 type: 9 /* NodeTypes.IF */, 13739 loc: node.loc, 13740 branches: [branch] 13741 }; 13742 context.replaceNode(ifNode); 13743 if (processCodegen) { 13744 return processCodegen(ifNode, branch, true); 13745 } 13746 } 13747 else { 13748 // locate the adjacent v-if 13749 const siblings = context.parent.children; 13750 const comments = []; 13751 let i = siblings.indexOf(node); 13752 while (i-- >= -1) { 13753 const sibling = siblings[i]; 13754 if (sibling && sibling.type === 3 /* NodeTypes.COMMENT */) { 13755 context.removeNode(sibling); 13756 comments.unshift(sibling); 13757 continue; 13758 } 13759 if (sibling && 13760 sibling.type === 2 /* NodeTypes.TEXT */ && 13761 !sibling.content.trim().length) { 13762 context.removeNode(sibling); 13763 continue; 13764 } 13765 if (sibling && sibling.type === 9 /* NodeTypes.IF */) { 13766 // Check if v-else was followed by v-else-if 13767 if (dir.name === 'else-if' && 13768 sibling.branches[sibling.branches.length - 1].condition === undefined) { 13769 context.onError(createCompilerError(30 /* ErrorCodes.X_V_ELSE_NO_ADJACENT_IF */, node.loc)); 13770 } 13771 // move the node to the if node's branches 13772 context.removeNode(); 13773 const branch = createIfBranch(node, dir); 13774 if (comments.length && 13775 // #3619 ignore comments if the v-if is direct child of <transition> 13776 !(context.parent && 13777 context.parent.type === 1 /* NodeTypes.ELEMENT */ && 13778 isBuiltInType(context.parent.tag, 'transition'))) { 13779 branch.children = [...comments, ...branch.children]; 13780 } 13781 // check if user is forcing same key on different branches 13782 {
13783 const key = branch.userKey; 13784 if (key) { 13785 sibling.branches.forEach(({ userKey }) => { 13786 if (isSameKey(userKey, key)) { 13787 context.onError(createCompilerError(29 /* ErrorCodes.X_V_IF_SAME_KEY */, branch.userKey.loc)); 13788 } 13789 }); 13790 } 13791 } 13792 sibling.branches.push(branch); 13793 const onExit = processCodegen && processCodegen(sibling, branch, false); 13794 // since the branch was removed, it will not be traversed. 13795 // make sure to traverse here. 13796 traverseNode(branch, context); 13797 // call on exit 13798 if (onExit) 13799 onExit(); 13800 // make sure to reset currentNode after traversal to indicate this 13801 // node has been removed. 13802 context.currentNode = null; 13803 } 13804 else { 13805 context.onError(createCompilerError(30 /* ErrorCodes.X_V_ELSE_NO_ADJACENT_IF */, node.loc)); 13806 } 13807 break; 13808 } 13809 } 13810 } 13811 function createIfBranch(node, dir) { 13812 const isTemplateIf = node.tagType === 3 /* ElementTypes.TEMPLATE */; 13813 return { 13814 type: 10 /* NodeTypes.IF_BRANCH */, 13815 loc: node.loc, 13816 condition: dir.name === 'else' ? undefined : dir.exp, 13817 children: isTemplateIf && !findDir(node, 'for') ? node.children : [node], 13818 userKey: findProp(node, `key`), 13819 isTemplateIf 13820 }; 13821 } 13822 function createCodegenNodeForBranch(branch, keyIndex, context) { 13823 if (branch.condition) { 13824 return createConditionalExpression(branch.condition, createChildrenCodegenNode(branch, keyIndex, context), 13825 // make sure to pass in asBlock: true so that the comment node call 13826 // closes the current block. 13827 createCallExpression(context.helper(CREATE_COMMENT), [ 13828 '"v-if"' , 13829 'true' 13830 ])); 13831 } 13832 else { 13833 return createChildrenCodegenNode(branch, keyIndex, context); 13834 } 13835 } 13836 function createChildrenCodegenNode(branch, keyIndex, context) { 13837 const { helper } = context; 13838 const keyProperty = createObjectProperty(`key`, createSimpleExpression(`${keyIndex}`, false, locStub, 2 /* ConstantTypes.CAN_HOIST */)); 13839 const { children } = branch; 13840 const firstChild = children[0]; 13841 const needFragmentWrapper = children.length !== 1 || firstChild.type !== 1 /* NodeTypes.ELEMENT */; 13842 if (needFragmentWrapper) { 13843 if (children.length === 1 && firstChild.type === 11 /* NodeTypes.FOR */) { 13844 // optimize away nested fragments when child is a ForNode 13845 const vnodeCall = firstChild.codegenNode; 13846 injectProp(vnodeCall, keyProperty, context); 13847 return vnodeCall; 13848 } 13849 else { 13850 let patchFlag = 64 /* PatchFlags.STABLE_FRAGMENT */; 13851 let patchFlagText = PatchFlagNames[64 /* PatchFlags.STABLE_FRAGMENT */]; 13852 // check if the fragment actually contains a single valid child with 13853 // the rest being comments 13854 if (!branch.isTemplateIf && 13855 children.filter(c => c.type !== 3 /* NodeTypes.COMMENT */).length === 1) { 13856 patchFlag |= 2048 /* PatchFlags.DEV_ROOT_FRAGMENT */; 13857 patchFlagText += `, ${PatchFlagNames[2048 /* PatchFlags.DEV_ROOT_FRAGMENT */]}`; 13858 } 13859 return createVNodeCall(context, helper(FRAGMENT), createObjectExpression([keyProperty]), children, patchFlag + (` /* ${patchFlagText} */` ), undefined, undefined, true, false, false /* isComponent */, branch.loc); 13860 } 13861 } 13862 else { 13863 const ret = firstChild.codegenNode; 13864 const vnodeCall = getMemoedVNodeCall(ret); 13865 // Change createVNode to createBlock. 13866 if (vnodeCall.type === 13 /* NodeTypes.VNODE_CALL */) { 13867 makeBlock(vnodeCall, context); 13868 } 13869 // inject branch key
13870 injectProp(vnodeCall, keyProperty, context); 13871 return ret; 13872 } 13873 } 13874 function isSameKey(a, b) { 13875 if (!a || a.type !== b.type) { 13876 return false; 13877 } 13878 if (a.type === 6 /* NodeTypes.ATTRIBUTE */) { 13879 if (a.value.content !== b.value.content) { 13880 return false; 13881 } 13882 } 13883 else { 13884 // directive 13885 const exp = a.exp; 13886 const branchExp = b.exp; 13887 if (exp.type !== branchExp.type) { 13888 return false; 13889 } 13890 if (exp.type !== 4 /* NodeTypes.SIMPLE_EXPRESSION */ || 13891 exp.isStatic !== branchExp.isStatic || 13892 exp.content !== branchExp.content) { 13893 return false; 13894 } 13895 } 13896 return true; 13897 } 13898 function getParentCondition(node) { 13899 while (true) { 13900 if (node.type === 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */) { 13901 if (node.alternate.type === 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */) { 13902 node = node.alternate; 13903 } 13904 else { 13905 return node; 13906 } 13907 } 13908 else if (node.type === 20 /* NodeTypes.JS_CACHE_EXPRESSION */) { 13909 node = node.value; 13910 } 13911 } 13912 } 13913 13914 const transformFor = createStructuralDirectiveTransform('for', (node, dir, context) => { 13915 const { helper, removeHelper } = context; 13916 return processFor(node, dir, context, forNode => { 13917 // create the loop render function expression now, and add the 13918 // iterator on exit after all children have been traversed 13919 const renderExp = createCallExpression(helper(RENDER_LIST), [ 13920 forNode.source 13921 ]); 13922 const isTemplate = isTemplateNode(node); 13923 const memo = findDir(node, 'memo'); 13924 const keyProp = findProp(node, `key`); 13925 const keyExp = keyProp && 13926 (keyProp.type === 6 /* NodeTypes.ATTRIBUTE */ 13927 ? createSimpleExpression(keyProp.value.content, true) 13928 : keyProp.exp); 13929 const keyProperty = keyProp ? createObjectProperty(`key`, keyExp) : null; 13930 const isStableFragment = forNode.source.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && 13931 forNode.source.constType > 0 /* ConstantTypes.NOT_CONSTANT */; 13932 const fragmentFlag = isStableFragment 13933 ? 64 /* PatchFlags.STABLE_FRAGMENT */ 13934 : keyProp 13935 ? 128 /* PatchFlags.KEYED_FRAGMENT */ 13936 : 256 /* PatchFlags.UNKEYED_FRAGMENT */; 13937 forNode.codegenNode = createVNodeCall(context, helper(FRAGMENT), undefined, renderExp, fragmentFlag + 13938 (` /* ${PatchFlagNames[fragmentFlag]} */` ), undefined, undefined, true /* isBlock */, !isStableFragment /* disableTracking */, false /* isComponent */, node.loc); 13939 return () => { 13940 // finish the codegen now that all children have been traversed 13941 let childBlock; 13942 const { children } = forNode; 13943 // check <template v-for> key placement 13944 if (isTemplate) { 13945 node.children.some(c => { 13946 if (c.type === 1 /* NodeTypes.ELEMENT */) { 13947 const key = findProp(c, 'key'); 13948 if (key) { 13949 context.onError(createCompilerError(33 /* ErrorCodes.X_V_FOR_TEMPLATE_KEY_PLACEMENT */, key.loc)); 13950 return true; 13951 } 13952 } 13953 }); 13954 } 13955 const needFragmentWrapper = children.length !== 1 || children[0].type !== 1 /* NodeTypes.ELEMENT */; 13956 const slotOutlet = isSlotOutlet(node) 13957 ? node 13958 : isTemplate && 13959 node.children.length === 1 && 13960 isSlotOutlet(node.children[0]) 13961 ? node.children[0] // api-extractor somehow fails to infer this 13962 : null; 13963 if (slotOutlet) { 13964 // <slot v-for="..."> or <template v-for="..."><slot/></template> 13965 childBlock = slotOutlet.codegenNode; 13966 if (isTemplate && keyProperty) { 13967 // <template v-for="..." :key="..."><slot/></template> 13968 // we need to inject the key to the renderSlot() call. 13969 // the props for renderSlot is passed as the 3rd argument. 13970 injectProp(childBlock, keyProperty, context); 13971 } 13972 } 13973 else if (needFragmentWrapper) { 13974 // <template v-for="..."> with text or multi-elements 13975 // should generate a fragment block for each loop 13976 childBlock = createVNodeCall(context, helper(FRAGMENT), keyProperty ? createObjectExpression([keyProperty]) : undefined, node.children, 64 /* PatchFlags.STABLE_FRAGMENT */ + 13977 (` /* ${PatchFlagNames[64 /* PatchFlags.STABLE_FRAGMENT */]} */` 13978 ), undefined, undefined, true, undefined, false /* isComponent */); 13979 } 13980 else { 13981 // Normal element v-for. Directly use the child's codegenNode 13982 // but mark it as a block. 13983 childBlock = children[0] 13984 .codegenNode; 13985 if (isTemplate && keyProperty) { 13986 injectProp(childBlock, keyProperty, context); 13987 } 13988 if (childBlock.isBlock !== !isStableFragment) { 13989 if (childBlock.isBlock) { 13990 // switch from block to vnode 13991 removeHelper(OPEN_BLOCK); 13992 removeHelper(getVNodeBlockHelper(context.inSSR, childBlock.isComponent)); 13993 } 13994 else { 13995 // switch from vnode to block 13996 removeHelper(getVNodeHelper(context.inSSR, childBlock.isComponent)); 13997 } 13998 } 13999 childBlock.isBlock = !isStableFragment; 14000 if (childBlock.isBlock) { 14001 helper(OPEN_BLOCK); 14002 helper(getVNodeBlockHelper(context.inSSR, childBlock.isComponent)); 14003 } 14004 else { 14005 helper(getVNodeHelper(context.inSSR, childBlock.isComponent)); 14006 } 14007 } 14008 if (memo) { 14009 const loop = createFunctionExpression(createForLoopParams(forNode.parseResult, [ 14010 createSimpleExpression(`_cached`) 14011 ]));
14012 loop.body = createBlockStatement([ 14013 createCompoundExpression([`const _memo = (`, memo.exp, `)`]), 14014 createCompoundExpression([ 14015 `if (_cached`, 14016 ...(keyExp ? [` && _cached.key === `, keyExp] : []), 14017 ` && ${context.helperString(IS_MEMO_SAME)}(_cached, _memo)) return _cached` 14018 ]), 14019 createCompoundExpression([`const _item = `, childBlock]), 14020 createSimpleExpression(`_item.memo = _memo`), 14021 createSimpleExpression(`return _item`) 14022 ]); 14023 renderExp.arguments.push(loop, createSimpleExpression(`_cache`), createSimpleExpression(String(context.cached++))); 14024 } 14025 else { 14026 renderExp.arguments.push(createFunctionExpression(createForLoopParams(forNode.parseResult), childBlock, true /* force newline */)); 14027 } 14028 }; 14029 }); 14030 }); 14031 // target-agnostic transform used for both Client and SSR 14032 function processFor(node, dir, context, processCodegen) { 14033 if (!dir.exp) { 14034 context.onError(createCompilerError(31 /* ErrorCodes.X_V_FOR_NO_EXPRESSION */, dir.loc)); 14035 return; 14036 } 14037 const parseResult = parseForExpression( 14038 // can only be simple expression because vFor transform is applied 14039 // before expression transform. 14040 dir.exp, context); 14041 if (!parseResult) { 14042 context.onError(createCompilerError(32 /* ErrorCodes.X_V_FOR_MALFORMED_EXPRESSION */, dir.loc)); 14043 return; 14044 } 14045 const { addIdentifiers, removeIdentifiers, scopes } = context; 14046 const { source, value, key, index } = parseResult; 14047 const forNode = { 14048 type: 11 /* NodeTypes.FOR */, 14049 loc: dir.loc, 14050 source, 14051 valueAlias: value, 14052 keyAlias: key, 14053 objectIndexAlias: index, 14054 parseResult, 14055 children: isTemplateNode(node) ? node.children : [node] 14056 }; 14057 context.replaceNode(forNode); 14058 // bookkeeping 14059 scopes.vFor++; 14060 const onExit = processCodegen && processCodegen(forNode); 14061 return () => { 14062 scopes.vFor--; 14063 if (onExit) 14064 onExit(); 14065 }; 14066 } 14067 const forAliasRE = /([\s\S]*?)\s+(?:in|of)\s+([\s\S]*)/; 14068 // This regex doesn't cover the case if key or index aliases have destructuring, 14069 // but those do not make sense in the first place, so this works in practice. 14070 const forIteratorRE = /,([^,\}\]]*)(?:,([^,\}\]]*))?$/; 14071 const stripParensRE = /^\(|\)$/g; 14072 function parseForExpression(input, context) { 14073 const loc = input.loc; 14074 const exp = input.content; 14075 const inMatch = exp.match(forAliasRE); 14076 if (!inMatch) 14077 return; 14078 const [, LHS, RHS] = inMatch; 14079 const result = { 14080 source: createAliasExpression(loc, RHS.trim(), exp.indexOf(RHS, LHS.length)), 14081 value: undefined, 14082 key: undefined, 14083 index: undefined 14084 }; 14085 { 14086 validateBrowserExpression(result.source, context); 14087 } 14088 let valueContent = LHS.trim().replace(stripParensRE, '').trim(); 14089 const trimmedOffset = LHS.indexOf(valueContent); 14090 const iteratorMatch = valueContent.match(forIteratorRE); 14091 if (iteratorMatch) { 14092 valueContent = valueContent.replace(forIteratorRE, '').trim(); 14093 const keyContent = iteratorMatch[1].trim(); 14094 let keyOffset; 14095 if (keyContent) { 14096 keyOffset = exp.indexOf(keyContent, trimmedOffset + valueContent.length); 14097 result.key = createAliasExpression(loc, keyContent, keyOffset); 14098 { 14099 validateBrowserExpression(result.key, context, true); 14100 } 14101 } 14102 if (iteratorMatch[2]) { 14103 const indexContent = iteratorMatch[2].trim(); 14104 if (indexContent) { 14105 result.index = createAliasExpression(loc, indexContent, exp.indexOf(indexContent, result.key 14106 ? keyOffset + keyContent.length 14107 : trimmedOffset + valueContent.length)); 14108 { 14109 validateBrowserExpression(result.index, context, true); 14110 } 14111 } 14112 } 14113 }
14114 if (valueContent) { 14115 result.value = createAliasExpression(loc, valueContent, trimmedOffset); 14116 { 14117 validateBrowserExpression(result.value, context, true); 14118 } 14119 } 14120 return result; 14121 } 14122 function createAliasExpression(range, content, offset) { 14123 return createSimpleExpression(content, false, getInnerRange(range, offset, content.length)); 14124 } 14125 function createForLoopParams({ value, key, index }, memoArgs = []) { 14126 return createParamsList([value, key, index, ...memoArgs]); 14127 } 14128 function createParamsList(args) { 14129 let i = args.length; 14130 while (i--) { 14131 if (args[i]) 14132 break; 14133 } 14134 return args 14135 .slice(0, i + 1) 14136 .map((arg, i) => arg || createSimpleExpression(`_`.repeat(i + 1), false)); 14137 } 14138 14139 const defaultFallback = createSimpleExpression(`undefined`, false); 14140 // A NodeTransform that: 14141 // 1. Tracks scope identifiers for scoped slots so that they don't get prefixed 14142 // by transformExpression. This is only applied in non-browser builds with 14143 // { prefixIdentifiers: true }. 14144 // 2. Track v-slot depths so that we know a slot is inside another slot. 14145 // Note the exit callback is executed before buildSlots() on the same node, 14146 // so only nested slots see positive numbers. 14147 const trackSlotScopes = (node, context) => { 14148 if (node.type === 1 /* NodeTypes.ELEMENT */ && 14149 (node.tagType === 1 /* ElementTypes.COMPONENT */ || 14150 node.tagType === 3 /* ElementTypes.TEMPLATE */)) { 14151 // We are only checking non-empty v-slot here 14152 // since we only care about slots that introduce scope variables. 14153 const vSlot = findDir(node, 'slot'); 14154 if (vSlot) { 14155 vSlot.exp; 14156 context.scopes.vSlot++; 14157 return () => { 14158 context.scopes.vSlot--; 14159 }; 14160 } 14161 } 14162 }; 14163 const buildClientSlotFn = (props, children, loc) => createFunctionExpression(props, children, false /* newline */, true /* isSlot */, children.length ? children[0].loc : loc); 14164 // Instead of being a DirectiveTransform, v-slot processing is called during 14165 // transformElement to build the slots object for a component. 14166 function buildSlots(node, context, buildSlotFn = buildClientSlotFn) { 14167 context.helper(WITH_CTX); 14168 const { children, loc } = node; 14169 const slotsProperties = []; 14170 const dynamicSlots = []; 14171 // If the slot is inside a v-for or another v-slot, force it to be dynamic 14172 // since it likely uses a scope variable. 14173 let hasDynamicSlots = context.scopes.vSlot > 0 || context.scopes.vFor > 0; 14174 // 1. Check for slot with slotProps on component itself. 14175 // <Comp v-slot="{ prop }"/> 14176 const onComponentSlot = findDir(node, 'slot', true); 14177 if (onComponentSlot) { 14178 const { arg, exp } = onComponentSlot; 14179 if (arg && !isStaticExp(arg)) { 14180 hasDynamicSlots = true; 14181 } 14182 slotsProperties.push(createObjectProperty(arg || createSimpleExpression('default', true), buildSlotFn(exp, children, loc))); 14183 } 14184 // 2. Iterate through children and check for template slots 14185 // <template v-slot:foo="{ prop }"> 14186 let hasTemplateSlots = false; 14187 let hasNamedDefaultSlot = false; 14188 const implicitDefaultChildren = []; 14189 const seenSlotNames = new Set(); 14190 let conditionalBranchIndex = 0; 14191 for (let i = 0; i < children.length; i++) { 14192 const slotElement = children[i]; 14193 let slotDir; 14194 if (!isTemplateNode(slotElement) || 14195 !(slotDir = findDir(slotElement, 'slot', true))) { 14196 // not a <template v-slot>, skip. 14197 if (slotElement.type !== 3 /* NodeTypes.COMMENT */) { 14198 implicitDefaultChildren.push(slotElement); 14199 } 14200 continue; 14201 } 14202 if (onComponentSlot) { 14203 // already has on-component slot - this is incorrect usage. 14204 context.onError(createCompilerError(37 /* ErrorCodes.X_V_SLOT_MIXED_SLOT_USAGE */, slotDir.loc)); 14205 break; 14206 } 14207 hasTemplateSlots = true; 14208 const { children: slotChildren, loc: slotLoc } = slotElement; 14209 const { arg: slotName = createSimpleExpression(`default`, true), exp: slotProps, loc: dirLoc } = slotDir; 14210 // check if name is dynamic. 14211 let staticSlotName; 14212 if (isStaticExp(slotName)) { 14213 staticSlotName = slotName ? slotName.content : `default`; 14214 } 14215 else { 14216 hasDynamicSlots = true; 14217 } 14218 const slotFunction = buildSlotFn(slotProps, slotChildren, slotLoc); 14219 // check if this slot is conditional (v-if/v-for) 14220 let vIf; 14221 let vElse; 14222 let vFor; 14223 if ((vIf = findDir(slotElement, 'if'))) { 14224 hasDynamicSlots = true; 14225 dynamicSlots.push(createConditionalExpression(vIf.exp, buildDynamicSlot(slotName, slotFunction, conditionalBranchIndex++), defaultFallback)); 14226 } 14227 else if ((vElse = findDir(slotElement, /^else(-if)?$/, true /* allowEmpty */))) { 14228 // find adjacent v-if 14229 let j = i; 14230 let prev; 14231 while (j--) { 14232 prev = children[j]; 14233 if (prev.type !== 3 /* NodeTypes.COMMENT */) { 14234 break; 14235 } 14236 } 14237 if (prev && isTemplateNode(prev) && findDir(prev, 'if')) { 14238 // remove node 14239 children.splice(i, 1); 14240 i--;
vendor: 5,469 bytes, lines 14241-14359
14241 // attach this slot to previous conditional 14242 let conditional = dynamicSlots[dynamicSlots.length - 1]; 14243 while (conditional.alternate.type === 19 /* NodeTypes.JS_CONDITIONAL_EXPRESSION */) { 14244 conditional = conditional.alternate; 14245 } 14246 conditional.alternate = vElse.exp 14247 ? createConditionalExpression(vElse.exp, buildDynamicSlot(slotName, slotFunction, conditionalBranchIndex++), defaultFallback) 14248 : buildDynamicSlot(slotName, slotFunction, conditionalBranchIndex++); 14249 } 14250 else { 14251 context.onError(createCompilerError(30 /* ErrorCodes.X_V_ELSE_NO_ADJACENT_IF */, vElse.loc)); 14252 } 14253 } 14254 else if ((vFor = findDir(slotElement, 'for'))) { 14255 hasDynamicSlots = true; 14256 const parseResult = vFor.parseResult || 14257 parseForExpression(vFor.exp, context); 14258 if (parseResult) { 14259 // Render the dynamic slots as an array and add it to the createSlot() 14260 // args. The runtime knows how to handle it appropriately. 14261 dynamicSlots.push(createCallExpression(context.helper(RENDER_LIST), [ 14262 parseResult.source, 14263 createFunctionExpression(createForLoopParams(parseResult), buildDynamicSlot(slotName, slotFunction), true /* force newline */) 14264 ])); 14265 } 14266 else { 14267 context.onError(createCompilerError(32 /* ErrorCodes.X_V_FOR_MALFORMED_EXPRESSION */, vFor.loc)); 14268 } 14269 } 14270 else { 14271 // check duplicate static names 14272 if (staticSlotName) { 14273 if (seenSlotNames.has(staticSlotName)) { 14274 context.onError(createCompilerError(38 /* ErrorCodes.X_V_SLOT_DUPLICATE_SLOT_NAMES */, dirLoc)); 14275 continue; 14276 } 14277 seenSlotNames.add(staticSlotName); 14278 if (staticSlotName === 'default') { 14279 hasNamedDefaultSlot = true; 14280 } 14281 } 14282 slotsProperties.push(createObjectProperty(slotName, slotFunction)); 14283 } 14284 } 14285 if (!onComponentSlot) { 14286 const buildDefaultSlotProperty = (props, children) => { 14287 const fn = buildSlotFn(props, children, loc); 14288 return createObjectProperty(`default`, fn); 14289 }; 14290 if (!hasTemplateSlots) { 14291 // implicit default slot (on component) 14292 slotsProperties.push(buildDefaultSlotProperty(undefined, children)); 14293 } 14294 else if (implicitDefaultChildren.length && 14295 // #3766 14296 // with whitespace: 'preserve', whitespaces between slots will end up in 14297 // implicitDefaultChildren. Ignore if all implicit children are whitespaces. 14298 implicitDefaultChildren.some(node => isNonWhitespaceContent(node))) { 14299 // implicit default slot (mixed with named slots) 14300 if (hasNamedDefaultSlot) { 14301 context.onError(createCompilerError(39 /* ErrorCodes.X_V_SLOT_EXTRANEOUS_DEFAULT_SLOT_CHILDREN */, implicitDefaultChildren[0].loc)); 14302 } 14303 else { 14304 slotsProperties.push(buildDefaultSlotProperty(undefined, implicitDefaultChildren)); 14305 } 14306 } 14307 } 14308 const slotFlag = hasDynamicSlots 14309 ? 2 /* SlotFlags.DYNAMIC */ 14310 : hasForwardedSlots(node.children) 14311 ? 3 /* SlotFlags.FORWARDED */ 14312 : 1 /* SlotFlags.STABLE */; 14313 let slots = createObjectExpression(slotsProperties.concat(createObjectProperty(`_`, 14314 // 2 = compiled but dynamic = can skip normalization, but must run diff 14315 // 1 = compiled and static = can skip normalization AND diff as optimized 14316 createSimpleExpression(slotFlag + (` /* ${slotFlagsText[slotFlag]} */` ), false))), loc); 14317 if (dynamicSlots.length) { 14318 slots = createCallExpression(context.helper(CREATE_SLOTS), [ 14319 slots, 14320 createArrayExpression(dynamicSlots) 14321 ]); 14322 } 14323 return { 14324 slots, 14325 hasDynamicSlots 14326 }; 14327 } 14328 function buildDynamicSlot(name, fn, index) { 14329 const props = [ 14330 createObjectProperty(`name`, name), 14331 createObjectProperty(`fn`, fn) 14332 ]; 14333 if (index != null) { 14334 props.push(createObjectProperty(`key`, createSimpleExpression(String(index), true))); 14335 } 14336 return createObjectExpression(props); 14337 } 14338 function hasForwardedSlots(children) { 14339 for (let i = 0; i < children.length; i++) { 14340 const child = children[i]; 14341 switch (child.type) { 14342 case 1 /* NodeTypes.ELEMENT */: 14343 if (child.tagType === 2 /* ElementTypes.SLOT */ || 14344 hasForwardedSlots(child.children)) { 14345 return true; 14346 } 14347 break; 14348 case 9 /* NodeTypes.IF */: 14349 if (hasForwardedSlots(child.branches)) 14350 return true; 14351 break; 14352 case 10 /* NodeTypes.IF_BRANCH */: 14353 case 11 /* NodeTypes.FOR */: 14354 if (hasForwardedSlots(child.children)) 14355 return true; 14356 break; 14357 } 14358 } 14359 return false;
14360 } 14361 function isNonWhitespaceContent(node) { 14362 if (node.type !== 2 /* NodeTypes.TEXT */ && node.type !== 12 /* NodeTypes.TEXT_CALL */) 14363 return true; 14364 return node.type === 2 /* NodeTypes.TEXT */ 14365 ? !!node.content.trim() 14366 : isNonWhitespaceContent(node.content); 14367 } 14368 14369 // some directive transforms (e.g. v-model) may return a symbol for runtime 14370 // import, which should be used instead of a resolveDirective call. 14371 const directiveImportMap = new WeakMap(); 14372 // generate a JavaScript AST for this element's codegen 14373 const transformElement = (node, context) => { 14374 // perform the work on exit, after all child expressions have been 14375 // processed and merged. 14376 return function postTransformElement() { 14377 node = context.currentNode; 14378 if (!(node.type === 1 /* NodeTypes.ELEMENT */ && 14379 (node.tagType === 0 /* ElementTypes.ELEMENT */ || 14380 node.tagType === 1 /* ElementTypes.COMPONENT */))) { 14381 return; 14382 } 14383 const { tag, props } = node; 14384 const isComponent = node.tagType === 1 /* ElementTypes.COMPONENT */; 14385 // The goal of the transform is to create a codegenNode implementing the 14386 // VNodeCall interface. 14387 let vnodeTag = isComponent 14388 ? resolveComponentType(node, context) 14389 : `"${tag}"`; 14390 const isDynamicComponent = isObject(vnodeTag) && vnodeTag.callee === RESOLVE_DYNAMIC_COMPONENT; 14391 let vnodeProps; 14392 let vnodeChildren; 14393 let vnodePatchFlag; 14394 let patchFlag = 0; 14395 let vnodeDynamicProps; 14396 let dynamicPropNames; 14397 let vnodeDirectives; 14398 let shouldUseBlock = 14399 // dynamic component may resolve to plain elements 14400 isDynamicComponent || 14401 vnodeTag === TELEPORT || 14402 vnodeTag === SUSPENSE || 14403 (!isComponent && 14404 // <svg> and <foreignObject> must be forced into blocks so that block 14405 // updates inside get proper isSVG flag at runtime. (#639, #643) 14406 // This is technically web-specific, but splitting the logic out of core 14407 // leads to too much unnecessary complexity. 14408 (tag === 'svg' || tag === 'foreignObject')); 14409 // props 14410 if (props.length > 0) { 14411 const propsBuildResult = buildProps(node, context, undefined, isComponent, isDynamicComponent); 14412 vnodeProps = propsBuildResult.props; 14413 patchFlag = propsBuildResult.patchFlag; 14414 dynamicPropNames = propsBuildResult.dynamicPropNames; 14415 const directives = propsBuildResult.directives; 14416 vnodeDirectives = 14417 directives && directives.length 14418 ? createArrayExpression(directives.map(dir => buildDirectiveArgs(dir, context))) 14419 : undefined; 14420 if (propsBuildResult.shouldUseBlock) { 14421 shouldUseBlock = true; 14422 } 14423 } 14424 // children 14425 if (node.children.length > 0) { 14426 if (vnodeTag === KEEP_ALIVE) { 14427 // Although a built-in component, we compile KeepAlive with raw children 14428 // instead of slot functions so that it can be used inside Transition 14429 // or other Transition-wrapping HOCs. 14430 // To ensure correct updates with block optimizations, we need to: 14431 // 1. Force keep-alive into a block. This avoids its children being 14432 // collected by a parent block. 14433 shouldUseBlock = true; 14434 // 2. Force keep-alive to always be updated, since it uses raw children. 14435 patchFlag |= 1024 /* PatchFlags.DYNAMIC_SLOTS */; 14436 if (node.children.length > 1) { 14437 context.onError(createCompilerError(46 /* ErrorCodes.X_KEEP_ALIVE_INVALID_CHILDREN */, { 14438 start: node.children[0].loc.start, 14439 end: node.children[node.children.length - 1].loc.end, 14440 source: '' 14441 })); 14442 } 14443 } 14444 const shouldBuildAsSlots = isComponent && 14445 // Teleport is not a real component and has dedicated runtime handling 14446 vnodeTag !== TELEPORT && 14447 // explained above. 14448 vnodeTag !== KEEP_ALIVE; 14449 if (shouldBuildAsSlots) { 14450 const { slots, hasDynamicSlots } = buildSlots(node, context); 14451 vnodeChildren = slots; 14452 if (hasDynamicSlots) { 14453 patchFlag |= 1024 /* PatchFlags.DYNAMIC_SLOTS */; 14454 } 14455 } 14456 else if (node.children.length === 1 && vnodeTag !== TELEPORT) { 14457 const child = node.children[0]; 14458 const type = child.type; 14459 // check for dynamic text children 14460 const hasDynamicTextChild = type === 5 /* NodeTypes.INTERPOLATION */ || 14461 type === 8 /* NodeTypes.COMPOUND_EXPRESSION */; 14462 if (hasDynamicTextChild &&
14463 getConstantType(child, context) === 0 /* ConstantTypes.NOT_CONSTANT */) { 14464 patchFlag |= 1 /* PatchFlags.TEXT */; 14465 } 14466 // pass directly if the only child is a text node 14467 // (plain / interpolation / expression) 14468 if (hasDynamicTextChild || type === 2 /* NodeTypes.TEXT */) { 14469 vnodeChildren = child; 14470 } 14471 else { 14472 vnodeChildren = node.children; 14473 } 14474 } 14475 else { 14476 vnodeChildren = node.children; 14477 } 14478 } 14479 // patchFlag & dynamicPropNames 14480 if (patchFlag !== 0) { 14481 { 14482 if (patchFlag < 0) { 14483 // special flags (negative and mutually exclusive) 14484 vnodePatchFlag = patchFlag + ` /* ${PatchFlagNames[patchFlag]} */`; 14485 } 14486 else { 14487 // bitwise flags 14488 const flagNames = Object.keys(PatchFlagNames) 14489 .map(Number) 14490 .filter(n => n > 0 && patchFlag & n) 14491 .map(n => PatchFlagNames[n]) 14492 .join(`, `); 14493 vnodePatchFlag = patchFlag + ` /* ${flagNames} */`; 14494 } 14495 } 14496 if (dynamicPropNames && dynamicPropNames.length) { 14497 vnodeDynamicProps = stringifyDynamicPropNames(dynamicPropNames); 14498 } 14499 } 14500 node.codegenNode = createVNodeCall(context, vnodeTag, vnodeProps, vnodeChildren, vnodePatchFlag, vnodeDynamicProps, vnodeDirectives, !!shouldUseBlock, false /* disableTracking */, isComponent, node.loc); 14501 }; 14502 }; 14503 function resolveComponentType(node, context, ssr = false) { 14504 let { tag } = node; 14505 // 1. dynamic component 14506 const isExplicitDynamic = isComponentTag(tag); 14507 const isProp = findProp(node, 'is'); 14508 if (isProp) { 14509 if (isExplicitDynamic || 14510 (false )) { 14511 const exp = isProp.type === 6 /* NodeTypes.ATTRIBUTE */ 14512 ? isProp.value && createSimpleExpression(isProp.value.content, true) 14513 : isProp.exp; 14514 if (exp) { 14515 return createCallExpression(context.helper(RESOLVE_DYNAMIC_COMPONENT), [ 14516 exp 14517 ]); 14518 } 14519 } 14520 else if (isProp.type === 6 /* NodeTypes.ATTRIBUTE */ && 14521 isProp.value.content.startsWith('vue:')) { 14522 // <button is="vue:xxx"> 14523 // if not <component>, only is value that starts with "vue:" will be 14524 // treated as component by the parse phase and reach here, unless it's 14525 // compat mode where all is values are considered components 14526 tag = isProp.value.content.slice(4); 14527 } 14528 } 14529 // 1.5 v-is (TODO: Deprecate) 14530 const isDir = !isExplicitDynamic && findDir(node, 'is'); 14531 if (isDir && isDir.exp) { 14532 return createCallExpression(context.helper(RESOLVE_DYNAMIC_COMPONENT), [ 14533 isDir.exp 14534 ]); 14535 } 14536 // 2. built-in components (Teleport, Transition, KeepAlive, Suspense...) 14537 const builtIn = isCoreComponent(tag) || context.isBuiltInComponent(tag); 14538 if (builtIn) { 14539 // built-ins are simply fallthroughs / have special handling during ssr 14540 // so we don't need to import their runtime equivalents 14541 if (!ssr) 14542 context.helper(builtIn); 14543 return builtIn; 14544 } 14545 // 5. user component (resolve) 14546 context.helper(RESOLVE_COMPONENT); 14547 context.components.add(tag); 14548 return toValidAssetId(tag, `component`); 14549 } 14550 function buildProps(node, context, props = node.props, isComponent, isDynamicComponent, ssr = false) { 14551 const { tag, loc: elementLoc, children } = node; 14552 let properties = []; 14553 const mergeArgs = []; 14554 const runtimeDirectives = []; 14555 const hasChildren = children.length > 0; 14556 let shouldUseBlock = false;
14557 // patchFlag analysis 14558 let patchFlag = 0; 14559 let hasRef = false; 14560 let hasClassBinding = false; 14561 let hasStyleBinding = false; 14562 let hasHydrationEventBinding = false; 14563 let hasDynamicKeys = false; 14564 let hasVnodeHook = false; 14565 const dynamicPropNames = []; 14566 const pushMergeArg = (arg) => { 14567 if (properties.length) { 14568 mergeArgs.push(createObjectExpression(dedupeProperties(properties), elementLoc)); 14569 properties = []; 14570 } 14571 if (arg) 14572 mergeArgs.push(arg); 14573 }; 14574 const analyzePatchFlag = ({ key, value }) => { 14575 if (isStaticExp(key)) { 14576 const name = key.content; 14577 const isEventHandler = isOn(name); 14578 if (isEventHandler && 14579 (!isComponent || isDynamicComponent) && 14580 // omit the flag for click handlers because hydration gives click 14581 // dedicated fast path. 14582 name.toLowerCase() !== 'onclick' && 14583 // omit v-model handlers 14584 name !== 'onUpdate:modelValue' && 14585 // omit onVnodeXXX hooks 14586 !isReservedProp(name)) { 14587 hasHydrationEventBinding = true; 14588 } 14589 if (isEventHandler && isReservedProp(name)) { 14590 hasVnodeHook = true; 14591 } 14592 if (value.type === 20 /* NodeTypes.JS_CACHE_EXPRESSION */ || 14593 ((value.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ || 14594 value.type === 8 /* NodeTypes.COMPOUND_EXPRESSION */) && 14595 getConstantType(value, context) > 0)) { 14596 // skip if the prop is a cached handler or has constant value 14597 return; 14598 } 14599 if (name === 'ref') { 14600 hasRef = true; 14601 } 14602 else if (name === 'class') { 14603 hasClassBinding = true; 14604 } 14605 else if (name === 'style') { 14606 hasStyleBinding = true; 14607 } 14608 else if (name !== 'key' && !dynamicPropNames.includes(name)) { 14609 dynamicPropNames.push(name); 14610 } 14611 // treat the dynamic class and style binding of the component as dynamic props 14612 if (isComponent && 14613 (name === 'class' || name === 'style') && 14614 !dynamicPropNames.includes(name)) { 14615 dynamicPropNames.push(name); 14616 } 14617 } 14618 else { 14619 hasDynamicKeys = true; 14620 } 14621 }; 14622 for (let i = 0; i < props.length; i++) { 14623 // static attribute 14624 const prop = props[i]; 14625 if (prop.type === 6 /* NodeTypes.ATTRIBUTE */) { 14626 const { loc, name, value } = prop; 14627 let isStatic = true; 14628 if (name === 'ref') { 14629 hasRef = true; 14630 if (context.scopes.vFor > 0) { 14631 properties.push(createObjectProperty(createSimpleExpression('ref_for', true), createSimpleExpression('true'))); 14632 } 14633 } 14634 // skip is on <component>, or is="vue:xxx" 14635 if (name === 'is' && 14636 (isComponentTag(tag) || 14637 (value && value.content.startsWith('vue:')) || 14638 (false ))) { 14639 continue; 14640 } 14641 properties.push(createObjectProperty(createSimpleExpression(name, true, getInnerRange(loc, 0, name.length)), createSimpleExpression(value ? value.content : '', isStatic, value ? value.loc : loc))); 14642 } 14643 else { 14644 // directives 14645 const { name, arg, exp, loc } = prop; 14646 const isVBind = name === 'bind'; 14647 const isVOn = name === 'on'; 14648 // skip v-slot - it is handled by its dedicated transform. 14649 if (name === 'slot') { 14650 if (!isComponent) { 14651 context.onError(createCompilerError(40 /* ErrorCodes.X_V_SLOT_MISPLACED */, loc)); 14652 } 14653 continue; 14654 } 14655 // skip v-once/v-memo - they are handled by dedicated transforms. 14656 if (name === 'once' || name === 'memo') { 14657 continue; 14658 } 14659 // skip v-is and :is on <component> 14660 if (name === 'is' || 14661 (isVBind && 14662 isStaticArgOf(arg, 'is') && 14663 (isComponentTag(tag) || 14664 (false )))) { 14665 continue; 14666 } 14667 // skip v-on in SSR compilation 14668 if (isVOn && ssr) { 14669 continue; 14670 } 14671 if ( 14672 // #938: elements with dynamic keys should be forced into blocks 14673 (isVBind && isStaticArgOf(arg, 'key')) || 14674 // inline before-update hooks need to force block so that it is invoked 14675 // before children 14676 (isVOn && hasChildren && isStaticArgOf(arg, 'vue:before-update'))) { 14677 shouldUseBlock = true; 14678 } 14679 if (isVBind && isStaticArgOf(arg, 'ref') && context.scopes.vFor > 0) { 14680 properties.push(createObjectProperty(createSimpleExpression('ref_for', true), createSimpleExpression('true'))); 14681 } 14682 // special case for v-bind and v-on with no argument 14683 if (!arg && (isVBind || isVOn)) { 14684 hasDynamicKeys = true; 14685 if (exp) { 14686 if (isVBind) { 14687 // have to merge early for compat build check 14688 pushMergeArg(); 14689 mergeArgs.push(exp); 14690 } 14691 else { 14692 // v-on="obj" -> toHandlers(obj) 14693 pushMergeArg({ 14694 type: 14 /* NodeTypes.JS_CALL_EXPRESSION */, 14695 loc, 14696 callee: context.helper(TO_HANDLERS),
vendor: 5,482 bytes, lines 14697-14814
14697 arguments: isComponent ? [exp] : [exp, `true`] 14698 }); 14699 } 14700 } 14701 else { 14702 context.onError(createCompilerError(isVBind 14703 ? 34 /* ErrorCodes.X_V_BIND_NO_EXPRESSION */ 14704 : 35 /* ErrorCodes.X_V_ON_NO_EXPRESSION */, loc)); 14705 } 14706 continue; 14707 } 14708 const directiveTransform = context.directiveTransforms[name]; 14709 if (directiveTransform) { 14710 // has built-in directive transform. 14711 const { props, needRuntime } = directiveTransform(prop, node, context); 14712 !ssr && props.forEach(analyzePatchFlag); 14713 if (isVOn && arg && !isStaticExp(arg)) { 14714 pushMergeArg(createObjectExpression(props, elementLoc)); 14715 } 14716 else { 14717 properties.push(...props); 14718 } 14719 if (needRuntime) { 14720 runtimeDirectives.push(prop); 14721 if (isSymbol(needRuntime)) { 14722 directiveImportMap.set(prop, needRuntime); 14723 } 14724 } 14725 } 14726 else if (!isBuiltInDirective(name)) { 14727 // no built-in transform, this is a user custom directive. 14728 runtimeDirectives.push(prop); 14729 // custom dirs may use beforeUpdate so they need to force blocks 14730 // to ensure before-update gets called before children update 14731 if (hasChildren) { 14732 shouldUseBlock = true; 14733 } 14734 } 14735 } 14736 } 14737 let propsExpression = undefined; 14738 // has v-bind="object" or v-on="object", wrap with mergeProps 14739 if (mergeArgs.length) { 14740 // close up any not-yet-merged props 14741 pushMergeArg(); 14742 if (mergeArgs.length > 1) { 14743 propsExpression = createCallExpression(context.helper(MERGE_PROPS), mergeArgs, elementLoc); 14744 } 14745 else { 14746 // single v-bind with nothing else - no need for a mergeProps call 14747 propsExpression = mergeArgs[0]; 14748 } 14749 } 14750 else if (properties.length) { 14751 propsExpression = createObjectExpression(dedupeProperties(properties), elementLoc); 14752 } 14753 // patchFlag analysis 14754 if (hasDynamicKeys) { 14755 patchFlag |= 16 /* PatchFlags.FULL_PROPS */; 14756 } 14757 else { 14758 if (hasClassBinding && !isComponent) { 14759 patchFlag |= 2 /* PatchFlags.CLASS */; 14760 } 14761 if (hasStyleBinding && !isComponent) { 14762 patchFlag |= 4 /* PatchFlags.STYLE */; 14763 } 14764 if (dynamicPropNames.length) { 14765 patchFlag |= 8 /* PatchFlags.PROPS */; 14766 } 14767 if (hasHydrationEventBinding) { 14768 patchFlag |= 32 /* PatchFlags.HYDRATE_EVENTS */; 14769 } 14770 } 14771 if (!shouldUseBlock && 14772 (patchFlag === 0 || patchFlag === 32 /* PatchFlags.HYDRATE_EVENTS */) && 14773 (hasRef || hasVnodeHook || runtimeDirectives.length > 0)) { 14774 patchFlag |= 512 /* PatchFlags.NEED_PATCH */; 14775 } 14776 // pre-normalize props, SSR is skipped for now 14777 if (!context.inSSR && propsExpression) { 14778 switch (propsExpression.type) { 14779 case 15 /* NodeTypes.JS_OBJECT_EXPRESSION */: 14780 // means that there is no v-bind, 14781 // but still need to deal with dynamic key binding 14782 let classKeyIndex = -1; 14783 let styleKeyIndex = -1; 14784 let hasDynamicKey = false; 14785 for (let i = 0; i < propsExpression.properties.length; i++) { 14786 const key = propsExpression.properties[i].key; 14787 if (isStaticExp(key)) { 14788 if (key.content === 'class') { 14789 classKeyIndex = i; 14790 } 14791 else if (key.content === 'style') { 14792 styleKeyIndex = i; 14793 } 14794 } 14795 else if (!key.isHandlerKey) { 14796 hasDynamicKey = true; 14797 } 14798 } 14799 const classProp = propsExpression.properties[classKeyIndex]; 14800 const styleProp = propsExpression.properties[styleKeyIndex]; 14801 // no dynamic key 14802 if (!hasDynamicKey) { 14803 if (classProp && !isStaticExp(classProp.value)) { 14804 classProp.value = createCallExpression(context.helper(NORMALIZE_CLASS), [classProp.value]); 14805 } 14806 if (styleProp && 14807 // the static style is compiled into an object, 14808 // so use `hasStyleBinding` to ensure that it is a dynamic style binding 14809 (hasStyleBinding || 14810 (styleProp.value.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && 14811 styleProp.value.content.trim()[0] === `[`) || 14812 // v-bind:style and style both exist, 14813 // v-bind:style with static literal object 14814 styleProp.value.type === 17 /* NodeTypes.JS_ARRAY_EXPRESSION */)
vendor: 13,049 bytes, lines 14814-15160
14814) { 14815 styleProp.value = createCallExpression(context.helper(NORMALIZE_STYLE), [styleProp.value]); 14816 } 14817 } 14818 else { 14819 // dynamic key binding, wrap with `normalizeProps` 14820 propsExpression = createCallExpression(context.helper(NORMALIZE_PROPS), [propsExpression]); 14821 } 14822 break; 14823 case 14 /* NodeTypes.JS_CALL_EXPRESSION */: 14824 // mergeProps call, do nothing 14825 break; 14826 default: 14827 // single v-bind 14828 propsExpression = createCallExpression(context.helper(NORMALIZE_PROPS), [ 14829 createCallExpression(context.helper(GUARD_REACTIVE_PROPS), [ 14830 propsExpression 14831 ]) 14832 ]); 14833 break; 14834 } 14835 } 14836 return { 14837 props: propsExpression, 14838 directives: runtimeDirectives, 14839 patchFlag, 14840 dynamicPropNames, 14841 shouldUseBlock 14842 }; 14843 } 14844 // Dedupe props in an object literal. 14845 // Literal duplicated attributes would have been warned during the parse phase, 14846 // however, it's possible to encounter duplicated `onXXX` handlers with different 14847 // modifiers. We also need to merge static and dynamic class / style attributes. 14848 // - onXXX handlers / style: merge into array 14849 // - class: merge into single expression with concatenation 14850 function dedupeProperties(properties) { 14851 const knownProps = new Map(); 14852 const deduped = []; 14853 for (let i = 0; i < properties.length; i++) { 14854 const prop = properties[i]; 14855 // dynamic keys are always allowed 14856 if (prop.key.type === 8 /* NodeTypes.COMPOUND_EXPRESSION */ || !prop.key.isStatic) { 14857 deduped.push(prop); 14858 continue; 14859 } 14860 const name = prop.key.content; 14861 const existing = knownProps.get(name); 14862 if (existing) { 14863 if (name === 'style' || name === 'class' || isOn(name)) { 14864 mergeAsArray$1(existing, prop); 14865 } 14866 // unexpected duplicate, should have emitted error during parse 14867 } 14868 else { 14869 knownProps.set(name, prop); 14870 deduped.push(prop); 14871 } 14872 } 14873 return deduped; 14874 } 14875 function mergeAsArray$1(existing, incoming) { 14876 if (existing.value.type === 17 /* NodeTypes.JS_ARRAY_EXPRESSION */) { 14877 existing.value.elements.push(incoming.value); 14878 } 14879 else { 14880 existing.value = createArrayExpression([existing.value, incoming.value], existing.loc); 14881 } 14882 } 14883 function buildDirectiveArgs(dir, context) { 14884 const dirArgs = []; 14885 const runtime = directiveImportMap.get(dir); 14886 if (runtime) { 14887 // built-in directive with runtime 14888 dirArgs.push(context.helperString(runtime)); 14889 } 14890 else { 14891 { 14892 // inject statement for resolving directive 14893 context.helper(RESOLVE_DIRECTIVE); 14894 context.directives.add(dir.name); 14895 dirArgs.push(toValidAssetId(dir.name, `directive`)); 14896 } 14897 } 14898 const { loc } = dir; 14899 if (dir.exp) 14900 dirArgs.push(dir.exp); 14901 if (dir.arg) { 14902 if (!dir.exp) { 14903 dirArgs.push(`void 0`); 14904 } 14905 dirArgs.push(dir.arg); 14906 } 14907 if (Object.keys(dir.modifiers).length) { 14908 if (!dir.arg) { 14909 if (!dir.exp) { 14910 dirArgs.push(`void 0`); 14911 } 14912 dirArgs.push(`void 0`); 14913 } 14914 const trueExpression = createSimpleExpression(`true`, false, loc); 14915 dirArgs.push(createObjectExpression(dir.modifiers.map(modifier => createObjectProperty(modifier, trueExpression)), loc)); 14916 } 14917 return createArrayExpression(dirArgs, dir.loc); 14918 } 14919 function stringifyDynamicPropNames(props) { 14920 let propsNamesString = `[`; 14921 for (let i = 0, l = props.length; i < l; i++) { 14922 propsNamesString += JSON.stringify(props[i]); 14923 if (i < l - 1) 14924 propsNamesString += ', '; 14925 } 14926 return propsNamesString + `]`; 14927 } 14928 function isComponentTag(tag) { 14929 return tag === 'component' || tag === 'Component'; 14930 } 14931 14932 const transformSlotOutlet = (node, context) => { 14933 if (isSlotOutlet(node)) { 14934 const { children, loc } = node; 14935 const { slotName, slotProps } = processSlotOutlet(node, context); 14936 const slotArgs = [ 14937 context.prefixIdentifiers ? `_ctx.$slots` : `$slots`, 14938 slotName, 14939 '{}', 14940 'undefined', 14941 'true' 14942 ]; 14943 let expectedLen = 2; 14944 if (slotProps) { 14945 slotArgs[2] = slotProps; 14946 expectedLen = 3; 14947 } 14948 if (children.length) { 14949 slotArgs[3] = createFunctionExpression([], children, false, false, loc); 14950 expectedLen = 4; 14951 } 14952 if (context.scopeId && !context.slotted) { 14953 expectedLen = 5; 14954 } 14955 slotArgs.splice(expectedLen); // remove unused arguments 14956 node.codegenNode = createCallExpression(context.helper(RENDER_SLOT), slotArgs, loc); 14957 } 14958 }; 14959 function processSlotOutlet(node, context) { 14960 let slotName = `"default"`; 14961 let slotProps = undefined; 14962 const nonNameProps = []; 14963 for (let i = 0; i < node.props.length; i++) { 14964 const p = node.props[i]; 14965 if (p.type === 6 /* NodeTypes.ATTRIBUTE */) { 14966 if (p.value) { 14967 if (p.name === 'name') { 14968 slotName = JSON.stringify(p.value.content); 14969 } 14970 else { 14971 p.name = camelize(p.name); 14972 nonNameProps.push(p); 14973 } 14974 } 14975 } 14976 else { 14977 if (p.name === 'bind' && isStaticArgOf(p.arg, 'name')) { 14978 if (p.exp) 14979 slotName = p.exp; 14980 } 14981 else { 14982 if (p.name === 'bind' && p.arg && isStaticExp(p.arg)) { 14983 p.arg.content = camelize(p.arg.content); 14984 } 14985 nonNameProps.push(p); 14986 } 14987 } 14988 } 14989 if (nonNameProps.length > 0) { 14990 const { props, directives } = buildProps(node, context, nonNameProps, false, false); 14991 slotProps = props; 14992 if (directives.length) { 14993 context.onError(createCompilerError(36 /* ErrorCodes.X_V_SLOT_UNEXPECTED_DIRECTIVE_ON_SLOT_OUTLET */, directives[0].loc)); 14994 } 14995 } 14996 return { 14997 slotName, 14998 slotProps 14999 }; 15000 } 15001 15002 const fnExpRE = /^\s*([\w$_]+|(async\s*)?\([^)]*?\))\s*(:[^=]+)?=>|^\s*(async\s+)?function(?:\s+[\w$]+)?\s*\(/; 15003 const transformOn = (dir, node, context, augmentor) => { 15004 const { loc, modifiers, arg } = dir; 15005 if (!dir.exp && !modifiers.length) { 15006 context.onError(createCompilerError(35 /* ErrorCodes.X_V_ON_NO_EXPRESSION */, loc)); 15007 } 15008 let eventName; 15009 if (arg.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 15010 if (arg.isStatic) { 15011 let rawName = arg.content; 15012 // TODO deprecate @vnodeXXX usage 15013 if (rawName.startsWith('vue:')) { 15014 rawName = `vnode-${rawName.slice(4)}`; 15015 } 15016 const eventString = node.tagType !== 0 /* ElementTypes.ELEMENT */ || 15017 rawName.startsWith('vnode') || 15018 !/[A-Z]/.test(rawName) 15019 ? // for non-element and vnode lifecycle event listeners, auto convert 15020 // it to camelCase. See issue #2249 15021 toHandlerKey(camelize(rawName)) 15022 : // preserve case for plain element listeners that have uppercase 15023 // letters, as these may be custom elements' custom events 15024 `on:${rawName}`; 15025 eventName = createSimpleExpression(eventString, true, arg.loc); 15026 } 15027 else { 15028 // #2388 15029 eventName = createCompoundExpression([ 15030 `${context.helperString(TO_HANDLER_KEY)}(`, 15031 arg, 15032 `)` 15033 ]); 15034 } 15035 } 15036 else { 15037 // already a compound expression. 15038 eventName = arg; 15039 eventName.children.unshift(`${context.helperString(TO_HANDLER_KEY)}(`); 15040 eventName.children.push(`)`); 15041 } 15042 // handler processing 15043 let exp = dir.exp; 15044 if (exp && !exp.content.trim()) { 15045 exp = undefined; 15046 } 15047 let shouldCache = context.cacheHandlers && !exp && !context.inVOnce; 15048 if (exp) { 15049 const isMemberExp = isMemberExpression(exp.content); 15050 const isInlineStatement = !(isMemberExp || fnExpRE.test(exp.content)); 15051 const hasMultipleStatements = exp.content.includes(`;`); 15052 { 15053 validateBrowserExpression(exp, context, false, hasMultipleStatements); 15054 } 15055 if (isInlineStatement || (shouldCache && isMemberExp)) { 15056 // wrap inline statement in a function expression 15057 exp = createCompoundExpression([ 15058 `${isInlineStatement 15059 ? `$event` 15060 : `${``}(...args)`} => ${hasMultipleStatements ? `{` : `(`}`, 15061 exp, 15062 hasMultipleStatements ? `}` : `)` 15063 ]); 15064 } 15065 } 15066 let ret = { 15067 props: [ 15068 createObjectProperty(eventName, exp || createSimpleExpression(`() => {}`, false, loc)) 15069 ] 15070 }; 15071 // apply extended compiler augmentor 15072 if (augmentor) { 15073 ret = augmentor(ret); 15074 } 15075 if (shouldCache) { 15076 // cache handlers so that it's always the same handler being passed down. 15077 // this avoids unnecessary re-renders when users use inline handlers on 15078 // components. 15079 ret.props[0].value = context.cache(ret.props[0].value); 15080 } 15081 // mark the key as handler for props normalization check 15082 ret.props.forEach(p => (p.key.isHandlerKey = true)); 15083 return ret; 15084 }; 15085 15086 // v-bind without arg is handled directly in ./transformElements.ts due to it affecting 15087 // codegen for the entire props object. This transform here is only for v-bind 15088 // *with* args. 15089 const transformBind = (dir, _node, context) => { 15090 const { exp, modifiers, loc } = dir; 15091 const arg = dir.arg; 15092 if (arg.type !== 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 15093 arg.children.unshift(`(`); 15094 arg.children.push(`) || ""`); 15095 } 15096 else if (!arg.isStatic) { 15097 arg.content = `${arg.content} || ""`; 15098 } 15099 // .sync is replaced by v-model:arg 15100 if (modifiers.includes('camel')) { 15101 if (arg.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 15102 if (arg.isStatic) { 15103 arg.content = camelize(arg.content); 15104 } 15105 else { 15106 arg.content = `${context.helperString(CAMELIZE)}(${arg.content})`; 15107 } 15108 } 15109 else { 15110 arg.children.unshift(`${context.helperString(CAMELIZE)}(`); 15111 arg.children.push(`)`); 15112 } 15113 } 15114 if (!context.inSSR) { 15115 if (modifiers.includes('prop')) { 15116 injectPrefix(arg, '.'); 15117 } 15118 if (modifiers.includes('attr')) { 15119 injectPrefix(arg, '^'); 15120 } 15121 } 15122 if (!exp || 15123 (exp.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && !exp.content.trim())) { 15124 context.onError(createCompilerError(34 /* ErrorCodes.X_V_BIND_NO_EXPRESSION */, loc)); 15125 return { 15126 props: [createObjectProperty(arg, createSimpleExpression('', true, loc))] 15127 }; 15128 } 15129 return { 15130 props: [createObjectProperty(arg, exp)] 15131 }; 15132 }; 15133 const injectPrefix = (arg, prefix) => { 15134 if (arg.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */) { 15135 if (arg.isStatic) { 15136 arg.content = prefix + arg.content; 15137 } 15138 else { 15139 arg.content = `\`${prefix}\${${arg.content}}\``; 15140 } 15141 } 15142 else { 15143 arg.children.unshift(`'${prefix}' + (`); 15144 arg.children.push(`)`); 15145 } 15146 }; 15147 15148 // Merge adjacent text nodes and expressions into a single expression 15149 // e.g. <div>abc {{ d }} {{ e }}</div> should have a single expression node as child. 15150 const transformText = (node, context) => { 15151 if (node.type === 0 /* NodeTypes.ROOT */ || 15152 node.type === 1 /* NodeTypes.ELEMENT */ || 15153 node.type === 11 /* NodeTypes.FOR */ || 15154 node.type === 10 /* NodeTypes.IF_BRANCH */) { 15155 // perform the transform on node exit so that all expressions have already 15156 // been processed. 15157 return () => { 15158 const children = node.children; 15159 let currentContainer = undefined; 15160 let hasText = false;
15161 for (let i = 0; i < children.length; i++) { 15162 const child = children[i]; 15163 if (isText(child)) { 15164 hasText = true; 15165 for (let j = i + 1; j < children.length; j++) { 15166 const next = children[j]; 15167 if (isText(next)) { 15168 if (!currentContainer) { 15169 currentContainer = children[i] = createCompoundExpression([child], child.loc); 15170 } 15171 // merge adjacent text node into current 15172 currentContainer.children.push(` + `, next); 15173 children.splice(j, 1); 15174 j--; 15175 } 15176 else { 15177 currentContainer = undefined; 15178 break; 15179 } 15180 } 15181 } 15182 } 15183 if (!hasText || 15184 // if this is a plain element with a single text child, leave it 15185 // as-is since the runtime has dedicated fast path for this by directly 15186 // setting textContent of the element. 15187 // for component root it's always normalized anyway. 15188 (children.length === 1 && 15189 (node.type === 0 /* NodeTypes.ROOT */ || 15190 (node.type === 1 /* NodeTypes.ELEMENT */ && 15191 node.tagType === 0 /* ElementTypes.ELEMENT */ && 15192 // #3756 15193 // custom directives can potentially add DOM elements arbitrarily, 15194 // we need to avoid setting textContent of the element at runtime 15195 // to avoid accidentally overwriting the DOM elements added 15196 // by the user through custom directives. 15197 !node.props.find(p => p.type === 7 /* NodeTypes.DIRECTIVE */ && 15198 !context.directiveTransforms[p.name]) && 15199 // in compat mode, <template> tags with no special directives 15200 // will be rendered as a fragment so its children must be 15201 // converted into vnodes. 15202 !(false ))))) { 15203 return; 15204 } 15205 // pre-convert text nodes into createTextVNode(text) calls to avoid 15206 // runtime normalization. 15207 for (let i = 0; i < children.length; i++) { 15208 const child = children[i]; 15209 if (isText(child) || child.type === 8 /* NodeTypes.COMPOUND_EXPRESSION */) { 15210 const callArgs = []; 15211 // createTextVNode defaults to single whitespace, so if it is a 15212 // single space the code could be an empty call to save bytes. 15213 if (child.type !== 2 /* NodeTypes.TEXT */ || child.content !== ' ') { 15214 callArgs.push(child); 15215 } 15216 // mark dynamic text with flag so it gets patched inside a block 15217 if (!context.ssr && 15218 getConstantType(child, context) === 0 /* ConstantTypes.NOT_CONSTANT */) { 15219 callArgs.push(1 /* PatchFlags.TEXT */ + 15220 (` /* ${PatchFlagNames[1 /* PatchFlags.TEXT */]} */` )); 15221 } 15222 children[i] = { 15223 type: 12 /* NodeTypes.TEXT_CALL */, 15224 content: child, 15225 loc: child.loc, 15226 codegenNode: createCallExpression(context.helper(CREATE_TEXT), callArgs) 15227 }; 15228 } 15229 } 15230 }; 15231 } 15232 }; 15233 15234 const seen = new WeakSet(); 15235 const transformOnce = (node, context) => { 15236 if (node.type === 1 /* NodeTypes.ELEMENT */ && findDir(node, 'once', true)) {
15237 if (seen.has(node) || context.inVOnce) { 15238 return; 15239 } 15240 seen.add(node); 15241 context.inVOnce = true; 15242 context.helper(SET_BLOCK_TRACKING); 15243 return () => { 15244 context.inVOnce = false; 15245 const cur = context.currentNode; 15246 if (cur.codegenNode) { 15247 cur.codegenNode = context.cache(cur.codegenNode, true /* isVNode */); 15248 } 15249 }; 15250 } 15251 }; 15252 15253 const transformModel = (dir, node, context) => { 15254 const { exp, arg } = dir; 15255 if (!exp) { 15256 context.onError(createCompilerError(41 /* ErrorCodes.X_V_MODEL_NO_EXPRESSION */, dir.loc)); 15257 return createTransformProps(); 15258 } 15259 const rawExp = exp.loc.source; 15260 const expString = exp.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ ? exp.content : rawExp; 15261 // im SFC <script setup> inline mode, the exp may have been transformed into 15262 // _unref(exp) 15263 const bindingType = context.bindingMetadata[rawExp]; 15264 // check props 15265 if (bindingType === "props" /* BindingTypes.PROPS */ || 15266 bindingType === "props-aliased" /* BindingTypes.PROPS_ALIASED */) { 15267 context.onError(createCompilerError(44 /* ErrorCodes.X_V_MODEL_ON_PROPS */, exp.loc)); 15268 return createTransformProps(); 15269 } 15270 const maybeRef = !true ; 15271 if (!expString.trim() || 15272 (!isMemberExpression(expString) && !maybeRef)) { 15273 context.onError(createCompilerError(42 /* ErrorCodes.X_V_MODEL_MALFORMED_EXPRESSION */, exp.loc)); 15274 return createTransformProps(); 15275 } 15276 const propName = arg ? arg : createSimpleExpression('modelValue', true); 15277 const eventName = arg 15278 ? isStaticExp(arg) 15279 ? `onUpdate:${arg.content}` 15280 : createCompoundExpression(['"onUpdate:" + ', arg]) 15281 : `onUpdate:modelValue`; 15282 let assignmentExp; 15283 const eventArg = context.isTS ? `($event: any)` : `$event`; 15284 { 15285 assignmentExp = createCompoundExpression([ 15286 `${eventArg} => ((`, 15287 exp, 15288 `) = $event)` 15289 ]); 15290 } 15291 const props = [ 15292 // modelValue: foo 15293 createObjectProperty(propName, dir.exp), 15294 // "onUpdate:modelValue": $event => (foo = $event) 15295 createObjectProperty(eventName, assignmentExp) 15296 ]; 15297 // modelModifiers: { foo: true, "bar-baz": true } 15298 if (dir.modifiers.length && node.tagType === 1 /* ElementTypes.COMPONENT */) { 15299 const modifiers = dir.modifiers 15300 .map(m => (isSimpleIdentifier(m) ? m : JSON.stringify(m)) + `: true`) 15301 .join(`, `); 15302 const modifiersKey = arg 15303 ? isStaticExp(arg) 15304 ? `${arg.content}Modifiers` 15305 : createCompoundExpression([arg, ' + "Modifiers"']) 15306 : `modelModifiers`; 15307 props.push(createObjectProperty(modifiersKey, createSimpleExpression(`{ ${modifiers} }`, false, dir.loc, 2 /* ConstantTypes.CAN_HOIST */))); 15308 } 15309 return createTransformProps(props); 15310 }; 15311 function createTransformProps(props = []) { 15312 return { props }; 15313 } 15314 15315 const seen$1 = new WeakSet(); 15316 const transformMemo = (node, context) => { 15317 if (node.type === 1 /* NodeTypes.ELEMENT */) { 15318 const dir = findDir(node, 'memo'); 15319 if (!dir || seen$1.has(node)) { 15320 return; 15321 } 15322 seen$1.add(node); 15323 return () => { 15324 const codegenNode = node.codegenNode || 15325 context.currentNode.codegenNode; 15326 if (codegenNode && codegenNode.type === 13 /* NodeTypes.VNODE_CALL */) { 15327 // non-component sub tree should be turned into a block 15328 if (node.tagType !== 1 /* ElementTypes.COMPONENT */) { 15329 makeBlock(codegenNode, context); 15330 } 15331 node.codegenNode = createCallExpression(context.helper(WITH_MEMO), [ 15332 dir.exp, 15333 createFunctionExpression(undefined, codegenNode), 15334 `_cache`, 15335 String(context.cached++) 15336 ]); 15337 } 15338 }; 15339 } 15340 }; 15341 15342 function getBaseTransformPreset(prefixIdentifiers) { 15343 return [ 15344 [ 15345 transformOnce, 15346 transformIf, 15347 transformMemo, 15348 transformFor, 15349 ...([]), 15350 ...([transformExpression] 15351 ), 15352 transformSlotOutlet, 15353 transformElement, 15354 trackSlotScopes, 15355 transformText 15356 ], 15357 { 15358 on: transformOn, 15359 bind: transformBind, 15360 model: transformModel 15361 } 15362 ]; 15363 }
vendor: 5,969 bytes, lines 15364-15514
15364 // we name it `baseCompile` so that higher order compilers like 15365 // @vue/compiler-dom can export `compile` while re-exporting everything else. 15366 function baseCompile(template, options = {}) { 15367 const onError = options.onError || defaultOnError; 15368 const isModuleMode = options.mode === 'module'; 15369 /* istanbul ignore if */ 15370 { 15371 if (options.prefixIdentifiers === true) { 15372 onError(createCompilerError(47 /* ErrorCodes.X_PREFIX_ID_NOT_SUPPORTED */)); 15373 } 15374 else if (isModuleMode) { 15375 onError(createCompilerError(48 /* ErrorCodes.X_MODULE_MODE_NOT_SUPPORTED */)); 15376 } 15377 } 15378 const prefixIdentifiers = !true ; 15379 if (options.cacheHandlers) { 15380 onError(createCompilerError(49 /* ErrorCodes.X_CACHE_HANDLER_NOT_SUPPORTED */)); 15381 } 15382 if (options.scopeId && !isModuleMode) { 15383 onError(createCompilerError(50 /* ErrorCodes.X_SCOPE_ID_NOT_SUPPORTED */)); 15384 } 15385 const ast = isString(template) ? baseParse(template, options) : template; 15386 const [nodeTransforms, directiveTransforms] = getBaseTransformPreset(); 15387 transform(ast, extend({}, options, { 15388 prefixIdentifiers, 15389 nodeTransforms: [ 15390 ...nodeTransforms, 15391 ...(options.nodeTransforms || []) // user transforms 15392 ], 15393 directiveTransforms: extend({}, directiveTransforms, options.directiveTransforms || {} // user transforms 15394 ) 15395 })); 15396 return generate(ast, extend({}, options, { 15397 prefixIdentifiers 15398 })); 15399 } 15400 15401 const noopDirectiveTransform = () => ({ props: [] }); 15402 15403 const V_MODEL_RADIO = Symbol(`vModelRadio` ); 15404 const V_MODEL_CHECKBOX = Symbol(`vModelCheckbox` ); 15405 const V_MODEL_TEXT = Symbol(`vModelText` ); 15406 const V_MODEL_SELECT = Symbol(`vModelSelect` ); 15407 const V_MODEL_DYNAMIC = Symbol(`vModelDynamic` ); 15408 const V_ON_WITH_MODIFIERS = Symbol(`vOnModifiersGuard` ); 15409 const V_ON_WITH_KEYS = Symbol(`vOnKeysGuard` ); 15410 const V_SHOW = Symbol(`vShow` ); 15411 const TRANSITION$1 = Symbol(`Transition` ); 15412 const TRANSITION_GROUP = Symbol(`TransitionGroup` ); 15413 registerRuntimeHelpers({ 15414 [V_MODEL_RADIO]: `vModelRadio`, 15415 [V_MODEL_CHECKBOX]: `vModelCheckbox`, 15416 [V_MODEL_TEXT]: `vModelText`, 15417 [V_MODEL_SELECT]: `vModelSelect`, 15418 [V_MODEL_DYNAMIC]: `vModelDynamic`, 15419 [V_ON_WITH_MODIFIERS]: `withModifiers`, 15420 [V_ON_WITH_KEYS]: `withKeys`, 15421 [V_SHOW]: `vShow`, 15422 [TRANSITION$1]: `Transition`, 15423 [TRANSITION_GROUP]: `TransitionGroup` 15424 }); 15425 15426 /* eslint-disable no-restricted-globals */ 15427 let decoder; 15428 function decodeHtmlBrowser(raw, asAttr = false) { 15429 if (!decoder) { 15430 decoder = document.createElement('div'); 15431 } 15432 if (asAttr) { 15433 decoder.innerHTML = `<div foo="${raw.replace(/"/g, '"')}">`; 15434 return decoder.children[0].getAttribute('foo'); 15435 } 15436 else { 15437 decoder.innerHTML = raw; 15438 return decoder.textContent; 15439 } 15440 } 15441 15442 const isRawTextContainer = /*#__PURE__*/ makeMap('style,iframe,script,noscript', true); 15443 const parserOptions = { 15444 isVoidTag, 15445 isNativeTag: tag => isHTMLTag(tag) || isSVGTag(tag), 15446 isPreTag: tag => tag === 'pre', 15447 decodeEntities: decodeHtmlBrowser , 15448 isBuiltInComponent: (tag) => { 15449 if (isBuiltInType(tag, `Transition`)) { 15450 return TRANSITION$1; 15451 } 15452 else if (isBuiltInType(tag, `TransitionGroup`)) { 15453 return TRANSITION_GROUP; 15454 } 15455 }, 15456 // https://html.spec.whatwg.org/multipage/parsing.html#tree-construction-dispatcher 15457 getNamespace(tag, parent) { 15458 let ns = parent ? parent.ns : 0 /* DOMNamespaces.HTML */; 15459 if (parent && ns === 2 /* DOMNamespaces.MATH_ML */) { 15460 if (parent.tag === 'annotation-xml') { 15461 if (tag === 'svg') { 15462 return 1 /* DOMNamespaces.SVG */; 15463 } 15464 if (parent.props.some(a => a.type === 6 /* NodeTypes.ATTRIBUTE */ && 15465 a.name === 'encoding' && 15466 a.value != null && 15467 (a.value.content === 'text/html' || 15468 a.value.content === 'application/xhtml+xml'))) { 15469 ns = 0 /* DOMNamespaces.HTML */; 15470 } 15471 } 15472 else if (/^m(?:[ions]|text)$/.test(parent.tag) && 15473 tag !== 'mglyph' && 15474 tag !== 'malignmark') { 15475 ns = 0 /* DOMNamespaces.HTML */; 15476 } 15477 } 15478 else if (parent && ns === 1 /* DOMNamespaces.SVG */) { 15479 if (parent.tag === 'foreignObject' || 15480 parent.tag === 'desc' || 15481 parent.tag === 'title') { 15482 ns = 0 /* DOMNamespaces.HTML */; 15483 } 15484 } 15485 if (ns === 0 /* DOMNamespaces.HTML */) { 15486 if (tag === 'svg') { 15487 return 1 /* DOMNamespaces.SVG */; 15488 } 15489 if (tag === 'math') { 15490 return 2 /* DOMNamespaces.MATH_ML */; 15491 } 15492 } 15493 return ns; 15494 }, 15495 // https://html.spec.whatwg.org/multipage/parsing.html#parsing-html-fragments 15496 getTextMode({ tag, ns }) { 15497 if (ns === 0 /* DOMNamespaces.HTML */) { 15498 if (tag === 'textarea' || tag === 'title') { 15499 return 1 /* TextModes.RCDATA */; 15500 } 15501 if (isRawTextContainer(tag)) { 15502 return 2 /* TextModes.RAWTEXT */; 15503 } 15504 } 15505 return 0 /* TextModes.DATA */; 15506 } 15507 }; 15508 15509 // Parse inline CSS strings for static style attributes into an object. 15510 // This is a NodeTransform since it works on the static `style` attribute and 15511 // converts it into a dynamic equivalent: 15512 // style="color: red" -> :style='{ "color": "red" }' 15513 // It is then processed by `transformElement` and included in the generated 15514 // props.
vendor: 11,956 bytes, lines 15515-15794
15515 const transformStyle = node => { 15516 if (node.type === 1 /* NodeTypes.ELEMENT */) { 15517 node.props.forEach((p, i) => { 15518 if (p.type === 6 /* NodeTypes.ATTRIBUTE */ && p.name === 'style' && p.value) { 15519 // replace p with an expression node 15520 node.props[i] = { 15521 type: 7 /* NodeTypes.DIRECTIVE */, 15522 name: `bind`, 15523 arg: createSimpleExpression(`style`, true, p.loc), 15524 exp: parseInlineCSS(p.value.content, p.loc), 15525 modifiers: [], 15526 loc: p.loc 15527 }; 15528 } 15529 }); 15530 } 15531 }; 15532 const parseInlineCSS = (cssText, loc) => { 15533 const normalized = parseStringStyle(cssText); 15534 return createSimpleExpression(JSON.stringify(normalized), false, loc, 3 /* ConstantTypes.CAN_STRINGIFY */); 15535 }; 15536 15537 function createDOMCompilerError(code, loc) { 15538 return createCompilerError(code, loc, DOMErrorMessages ); 15539 } 15540 const DOMErrorMessages = { 15541 [51 /* DOMErrorCodes.X_V_HTML_NO_EXPRESSION */]: `v-html is missing expression.`, 15542 [52 /* DOMErrorCodes.X_V_HTML_WITH_CHILDREN */]: `v-html will override element children.`, 15543 [53 /* DOMErrorCodes.X_V_TEXT_NO_EXPRESSION */]: `v-text is missing expression.`, 15544 [54 /* DOMErrorCodes.X_V_TEXT_WITH_CHILDREN */]: `v-text will override element children.`, 15545 [55 /* DOMErrorCodes.X_V_MODEL_ON_INVALID_ELEMENT */]: `v-model can only be used on <input>, <textarea> and <select> elements.`, 15546 [56 /* DOMErrorCodes.X_V_MODEL_ARG_ON_ELEMENT */]: `v-model argument is not supported on plain elements.`, 15547 [57 /* DOMErrorCodes.X_V_MODEL_ON_FILE_INPUT_ELEMENT */]: `v-model cannot be used on file inputs since they are read-only. Use a v-on:change listener instead.`, 15548 [58 /* DOMErrorCodes.X_V_MODEL_UNNECESSARY_VALUE */]: `Unnecessary value binding used alongside v-model. It will interfere with v-model's behavior.`, 15549 [59 /* DOMErrorCodes.X_V_SHOW_NO_EXPRESSION */]: `v-show is missing expression.`, 15550 [60 /* DOMErrorCodes.X_TRANSITION_INVALID_CHILDREN */]: `<Transition> expects exactly one child element or component.`, 15551 [61 /* DOMErrorCodes.X_IGNORED_SIDE_EFFECT_TAG */]: `Tags with side effect (<script> and <style>) are ignored in client component templates.` 15552 }; 15553 15554 const transformVHtml = (dir, node, context) => { 15555 const { exp, loc } = dir; 15556 if (!exp) { 15557 context.onError(createDOMCompilerError(51 /* DOMErrorCodes.X_V_HTML_NO_EXPRESSION */, loc)); 15558 } 15559 if (node.children.length) { 15560 context.onError(createDOMCompilerError(52 /* DOMErrorCodes.X_V_HTML_WITH_CHILDREN */, loc)); 15561 node.children.length = 0; 15562 } 15563 return { 15564 props: [ 15565 createObjectProperty(createSimpleExpression(`innerHTML`, true, loc), exp || createSimpleExpression('', true)) 15566 ] 15567 }; 15568 }; 15569 15570 const transformVText = (dir, node, context) => { 15571 const { exp, loc } = dir; 15572 if (!exp) { 15573 context.onError(createDOMCompilerError(53 /* DOMErrorCodes.X_V_TEXT_NO_EXPRESSION */, loc)); 15574 } 15575 if (node.children.length) { 15576 context.onError(createDOMCompilerError(54 /* DOMErrorCodes.X_V_TEXT_WITH_CHILDREN */, loc)); 15577 node.children.length = 0; 15578 } 15579 return { 15580 props: [ 15581 createObjectProperty(createSimpleExpression(`textContent`, true), exp 15582 ? getConstantType(exp, context) > 0 15583 ? exp 15584 : createCallExpression(context.helperString(TO_DISPLAY_STRING), [exp], loc) 15585 : createSimpleExpression('', true)) 15586 ] 15587 }; 15588 }; 15589 15590 const transformModel$1 = (dir, node, context) => { 15591 const baseResult = transformModel(dir, node, context); 15592 // base transform has errors OR component v-model (only need props) 15593 if (!baseResult.props.length || node.tagType === 1 /* ElementTypes.COMPONENT */) { 15594 return baseResult; 15595 } 15596 if (dir.arg) { 15597 context.onError(createDOMCompilerError(56 /* DOMErrorCodes.X_V_MODEL_ARG_ON_ELEMENT */, dir.arg.loc)); 15598 } 15599 function checkDuplicatedValue() { 15600 const value = findProp(node, 'value'); 15601 if (value) { 15602 context.onError(createDOMCompilerError(58 /* DOMErrorCodes.X_V_MODEL_UNNECESSARY_VALUE */, value.loc)); 15603 } 15604 } 15605 const { tag } = node; 15606 const isCustomElement = context.isCustomElement(tag); 15607 if (tag === 'input' || 15608 tag === 'textarea' || 15609 tag === 'select' || 15610 isCustomElement) { 15611 let directiveToUse = V_MODEL_TEXT; 15612 let isInvalidType = false; 15613 if (tag === 'input' || isCustomElement) { 15614 const type = findProp(node, `type`); 15615 if (type) { 15616 if (type.type === 7 /* NodeTypes.DIRECTIVE */) { 15617 // :type="foo" 15618 directiveToUse = V_MODEL_DYNAMIC; 15619 } 15620 else if (type.value) { 15621 switch (type.value.content) { 15622 case 'radio': 15623 directiveToUse = V_MODEL_RADIO; 15624 break; 15625 case 'checkbox': 15626 directiveToUse = V_MODEL_CHECKBOX; 15627 break; 15628 case 'file': 15629 isInvalidType = true; 15630 context.onError(createDOMCompilerError(57 /* DOMErrorCodes.X_V_MODEL_ON_FILE_INPUT_ELEMENT */, dir.loc)); 15631 break; 15632 default: 15633 // text type 15634 checkDuplicatedValue(); 15635 break; 15636 } 15637 } 15638 } 15639 else if (hasDynamicKeyVBind(node)) { 15640 // element has bindings with dynamic keys, which can possibly contain 15641 // "type". 15642 directiveToUse = V_MODEL_DYNAMIC; 15643 } 15644 else { 15645 // text type 15646 checkDuplicatedValue(); 15647 } 15648 } 15649 else if (tag === 'select') { 15650 directiveToUse = V_MODEL_SELECT; 15651 } 15652 else { 15653 // textarea 15654 checkDuplicatedValue(); 15655 } 15656 // inject runtime directive 15657 // by returning the helper symbol via needRuntime 15658 // the import will replaced a resolveDirective call. 15659 if (!isInvalidType) { 15660 baseResult.needRuntime = context.helper(directiveToUse); 15661 } 15662 } 15663 else { 15664 context.onError(createDOMCompilerError(55 /* DOMErrorCodes.X_V_MODEL_ON_INVALID_ELEMENT */, dir.loc)); 15665 } 15666 // native vmodel doesn't need the `modelValue` props since they are also 15667 // passed to the runtime as `binding.value`. removing it reduces code size. 15668 baseResult.props = baseResult.props.filter(p => !(p.key.type === 4 /* NodeTypes.SIMPLE_EXPRESSION */ && 15669 p.key.content === 'modelValue')); 15670 return baseResult; 15671 }; 15672 15673 const isEventOptionModifier = /*#__PURE__*/ makeMap(`passive,once,capture`); 15674 const isNonKeyModifier = /*#__PURE__*/ makeMap( 15675 // event propagation management 15676`stop,prevent,self,` + 15677 // system modifiers + exact 15678 `ctrl,shift,alt,meta,exact,` + 15679 // mouse 15680 `middle`); 15681 // left & right could be mouse or key modifiers based on event type 15682 const maybeKeyModifier = /*#__PURE__*/ makeMap('left,right'); 15683 const isKeyboardEvent = /*#__PURE__*/ makeMap(`onkeyup,onkeydown,onkeypress`, true); 15684 const resolveModifiers = (key, modifiers, context, loc) => { 15685 const keyModifiers = []; 15686 const nonKeyModifiers = []; 15687 const eventOptionModifiers = []; 15688 for (let i = 0; i < modifiers.length; i++) { 15689 const modifier = modifiers[i]; 15690 if (isEventOptionModifier(modifier)) { 15691 // eventOptionModifiers: modifiers for addEventListener() options, 15692 // e.g. .passive & .capture 15693 eventOptionModifiers.push(modifier); 15694 } 15695 else { 15696 // runtimeModifiers: modifiers that needs runtime guards 15697 if (maybeKeyModifier(modifier)) { 15698 if (isStaticExp(key)) { 15699 if (isKeyboardEvent(key.content)) { 15700 keyModifiers.push(modifier); 15701 } 15702 else { 15703 nonKeyModifiers.push(modifier); 15704 } 15705 } 15706 else { 15707 keyModifiers.push(modifier); 15708 nonKeyModifiers.push(modifier); 15709 } 15710 } 15711 else { 15712 if (isNonKeyModifier(modifier)) { 15713 nonKeyModifiers.push(modifier); 15714 } 15715 else { 15716 keyModifiers.push(modifier); 15717 } 15718 } 15719 } 15720 } 15721 return { 15722 keyModifiers, 15723 nonKeyModifiers, 15724 eventOptionModifiers 15725 }; 15726 }; 15727 const transformClick = (key, event) => { 15728 const isStaticClick = isStaticExp(key) && key.content.toLowerCase() === 'onclick'; 15729 return isStaticClick 15730 ? createSimpleExpression(event, true) 15731 : key.type !== 4 /* NodeTypes.SIMPLE_EXPRESSION */ 15732 ? createCompoundExpression([ 15733 `(`, 15734 key, 15735 `) === "onClick" ? "${event}" : (`, 15736 key, 15737 `)` 15738 ]) 15739 : key; 15740 }; 15741 const transformOn$1 = (dir, node, context) => { 15742 return transformOn(dir, node, context, baseResult => { 15743 const { modifiers } = dir; 15744 if (!modifiers.length) 15745 return baseResult; 15746 let { key, value: handlerExp } = baseResult.props[0]; 15747 const { keyModifiers, nonKeyModifiers, eventOptionModifiers } = resolveModifiers(key, modifiers, context, dir.loc); 15748 // normalize click.right and click.middle since they don't actually fire 15749 if (nonKeyModifiers.includes('right')) { 15750 key = transformClick(key, `onContextmenu`); 15751 } 15752 if (nonKeyModifiers.includes('middle')) { 15753 key = transformClick(key, `onMouseup`); 15754 } 15755 if (nonKeyModifiers.length) { 15756 handlerExp = createCallExpression(context.helper(V_ON_WITH_MODIFIERS), [ 15757 handlerExp, 15758 JSON.stringify(nonKeyModifiers) 15759 ]); 15760 } 15761 if (keyModifiers.length && 15762 // if event name is dynamic, always wrap with keys guard 15763 (!isStaticExp(key) || isKeyboardEvent(key.content))) { 15764 handlerExp = createCallExpression(context.helper(V_ON_WITH_KEYS), [ 15765 handlerExp, 15766 JSON.stringify(keyModifiers) 15767 ]); 15768 } 15769 if (eventOptionModifiers.length) { 15770 const modifierPostfix = eventOptionModifiers.map(capitalize).join(''); 15771 key = isStaticExp(key) 15772 ? createSimpleExpression(`${key.content}${modifierPostfix}`, true) 15773 : createCompoundExpression([`(`, key, `) + "${modifierPostfix}"`]); 15774 } 15775 return { 15776 props: [createObjectProperty(key, handlerExp)] 15777 }; 15778 }); 15779 }; 15780 15781 const transformShow = (dir, node, context) => { 15782 const { exp, loc } = dir; 15783 if (!exp) { 15784 context.onError(createDOMCompilerError(59 /* DOMErrorCodes.X_V_SHOW_NO_EXPRESSION */, loc)); 15785 } 15786 return { 15787 props: [], 15788 needRuntime: context.helper(V_SHOW) 15789 }; 15790 }; 15791 15792 const transformTransition = (node, context) => { 15793 if (node.type === 1 /* NodeTypes.ELEMENT */ && 15794 node.tagType === 1 /* ElementTypes.COMPONENT */) {
15795 const component = context.isBuiltInComponent(node.tag); 15796 if (component === TRANSITION$1) { 15797 return () => { 15798 if (!node.children.length) { 15799 return; 15800 } 15801 // warn multiple transition children 15802 if (hasMultipleChildren(node)) { 15803 context.onError(createDOMCompilerError(60 /* DOMErrorCodes.X_TRANSITION_INVALID_CHILDREN */, { 15804 start: node.children[0].loc.start, 15805 end: node.children[node.children.length - 1].loc.end, 15806 source: '' 15807 })); 15808 } 15809 // check if it's s single child w/ v-show 15810 // if yes, inject "persisted: true" to the transition props 15811 const child = node.children[0]; 15812 if (child.type === 1 /* NodeTypes.ELEMENT */) { 15813 for (const p of child.props) { 15814 if (p.type === 7 /* NodeTypes.DIRECTIVE */ && p.name === 'show') { 15815 node.props.push({ 15816 type: 6 /* NodeTypes.ATTRIBUTE */, 15817 name: 'persisted', 15818 value: undefined, 15819 loc: node.loc 15820 }); 15821 } 15822 } 15823 } 15824 }; 15825 } 15826 } 15827 }; 15828 function hasMultipleChildren(node) { 15829 // #1352 filter out potential comment nodes. 15830 const children = (node.children = node.children.filter(c => c.type !== 3 /* NodeTypes.COMMENT */ && 15831 !(c.type === 2 /* NodeTypes.TEXT */ && !c.content.trim()))); 15832 const child = children[0]; 15833 return (children.length !== 1 || 15834 child.type === 11 /* NodeTypes.FOR */ || 15835 (child.type === 9 /* NodeTypes.IF */ && child.branches.some(hasMultipleChildren))); 15836 } 15837 15838 const ignoreSideEffectTags = (node, context) => { 15839 if (node.type === 1 /* NodeTypes.ELEMENT */ && 15840 node.tagType === 0 /* ElementTypes.ELEMENT */ && 15841 (node.tag === 'script' || node.tag === 'style')) { 15842 context.onError(createDOMCompilerError(61 /* DOMErrorCodes.X_IGNORED_SIDE_EFFECT_TAG */, node.loc)); 15843 context.removeNode(); 15844 } 15845 }; 15846 15847 const DOMNodeTransforms = [ 15848 transformStyle, 15849 ...([transformTransition] ) 15850 ]; 15851 const DOMDirectiveTransforms = { 15852 cloak: noopDirectiveTransform, 15853 html: transformVHtml, 15854 text: transformVText, 15855 model: transformModel$1, 15856 on: transformOn$1, 15857 show: transformShow 15858 }; 15859 function compile$1(template, options = {}) { 15860 return baseCompile(template, extend({}, parserOptions, options, { 15861 nodeTransforms: [ 15862 // ignore <script> and <tag> 15863 // this is not put inside DOMNodeTransforms because that list is used 15864 // by compiler-ssr to generate vnode fallback branches 15865 ignoreSideEffectTags, 15866 ...DOMNodeTransforms, 15867 ...(options.nodeTransforms || []) 15868 ], 15869 directiveTransforms: extend({}, DOMDirectiveTransforms, options.directiveTransforms || {}), 15870 transformHoist: null 15871 })); 15872 } 15873 15874 // This entry is the "full-build" that includes both the runtime 15875 { 15876 initDev(); 15877 } 15878 const compileCache = Object.create(null); 15879 function compileToFunction(template, options) { 15880 if (!isString(template)) { 15881 if (template.nodeType) { 15882 template = template.innerHTML; 15883 } 15884 else { 15885 warn$1(`invalid template option: `, template); 15886 return NOOP; 15887 } 15888 } 15889 const key = template; 15890 const cached = compileCache[key]; 15891 if (cached) { 15892 return cached; 15893 } 15894 if (template[0] === '#') { 15895 const el = document.querySelector(template); 15896 if (!el) { 15897 warn$1(`Template element not found or is empty: ${template}`); 15898 } 15899 // __UNSAFE__ 15900 // Reason: potential execution of JS expressions in in-DOM template. 15901 // The user must make sure the in-DOM template is trusted. If it's rendered 15902 // by the server, the template should not contain any user data. 15903 template = el ? el.innerHTML : ``; 15904 } 15905 const opts = extend({ 15906 hoistStatic: true, 15907 onError: onError , 15908 onWarn: e => onError(e, true) 15909 }, options); 15910 if (!opts.isCustomElement && typeof customElements !== 'undefined') { 15911 opts.isCustomElement = tag => !!customElements.get(tag); 15912 } 15913 const { code } = compile$1(template, opts); 15914 function onError(err, asWarning = false) { 15915 const message = asWarning 15916 ? err.message 15917 : `Template compilation error: ${err.message}`; 15918 const codeFrame = err.loc && 15919 generateCodeFrame(template, err.loc.start.offset, err.loc.end.offset); 15920 warn$1(codeFrame ? `${message}\n${codeFrame}` : message); 15921 } 15922 // The wildcard import results in a huge object with every export 15923 // with keys that cannot be mangled, and can be quite heavy size-wise. 15924 // In the global build we know `Vue` is available globally so we can avoid 15925 // the wildcard object. 15926 const render = (new Function(code)() ); 15927 render._rc = true; 15928 return (compileCache[key] = render); 15929 } 15930 registerRuntimeCompiler(compileToFunction); 15931 15932 exports.BaseTransition = BaseTransition; 15933 exports.Comment = Comment; 15934 exports.EffectScope = EffectScope; 15935 exports.Fragment = Fragment; 15936 exports.KeepAlive = KeepAlive; 15937 exports.ReactiveEffect = ReactiveEffect; 15938 exports.Static = Static; 15939 exports.Suspense = Suspense; 15940 exports.Teleport = Teleport; 15941 exports.Text = Text; 15942 exports.Transition = Transition; 15943 exports.TransitionGroup = TransitionGroup; 15944 exports.VueElement = VueElement; 15945 exports.callWithAsyncErrorHandling = callWithAsyncErrorHandling; 15946 exports.callWithErrorHandling = callWithErrorHandling; 15947 exports.camelize = camelize; 15948 exports.capitalize = capitalize; 15949 exports.cloneVNode = cloneVNode; 15950 exports.compatUtils = compatUtils; 15951 exports.compile = compileToFunction; 15952 exports.computed = computed$1; 15953 exports.createApp = createApp; 15954 exports.createBlock = createBlock; 15955 exports.createCommentVNode = createCommentVNode; 15956 exports.createElementBlock = createElementBlock; 15957 exports.createElementVNode = createBaseVNode; 15958 exports.createHydrationRenderer = createHydrationRenderer; 15959 exports.createPropsRestProxy = createPropsRestProxy; 15960 exports.createRenderer = createRenderer; 15961 exports.createSSRApp = createSSRApp; 15962 exports.createSlots = createSlots; 15963 exports.createStaticVNode = createStaticVNode; 15964 exports.createTextVNode = createTextVNode; 15965 exports.createVNode = createVNode; 15966 exports.customRef = customRef; 15967 exports.defineAsyncComponent = defineAsyncComponent; 15968 exports.defineComponent = defineComponent; 15969 exports.defineCustomElement = defineCustomElement; 15970 exports.defineEmits = defineEmits; 15971 exports.defineExpose = defineExpose; 15972 exports.defineProps = defineProps; 15973 exports.defineSSRCustomElement = defineSSRCustomElement; 15974 exports.effect = effect; 15975 exports.effectScope = effectScope; 15976 exports.getCurrentInstance = getCurrentInstance; 15977 exports.getCurrentScope = getCurrentScope; 15978 exports.getTransitionRawChildren = getTransitionRawChildren; 15979 exports.guardReactiveProps = guardReactiveProps; 15980 exports.h = h; 15981 exports.handleError = handleError; 15982 exports.hydrate = hydrate;
15983 exports.initCustomFormatter = initCustomFormatter; 15984 exports.initDirectivesForSSR = initDirectivesForSSR; 15985 exports.inject = inject; 15986 exports.isMemoSame = isMemoSame; 15987 exports.isProxy = isProxy; 15988 exports.isReactive = isReactive; 15989 exports.isReadonly = isReadonly; 15990 exports.isRef = isRef; 15991 exports.isRuntimeOnly = isRuntimeOnly; 15992 exports.isShallow = isShallow; 15993 exports.isVNode = isVNode; 15994 exports.markRaw = markRaw; 15995 exports.mergeDefaults = mergeDefaults; 15996 exports.mergeProps = mergeProps; 15997 exports.nextTick = nextTick; 15998 exports.normalizeClass = normalizeClass; 15999 exports.normalizeProps = normalizeProps; 16000 exports.normalizeStyle = normalizeStyle; 16001 exports.onActivated = onActivated; 16002 exports.onBeforeMount = onBeforeMount; 16003 exports.onBeforeUnmount = onBeforeUnmount; 16004 exports.onBeforeUpdate = onBeforeUpdate; 16005 exports.onDeactivated = onDeactivated; 16006 exports.onErrorCaptured = onErrorCaptured; 16007 exports.onMounted = onMounted; 16008 exports.onRenderTracked = onRenderTracked; 16009 exports.onRenderTriggered = onRenderTriggered; 16010 exports.onScopeDispose = onScopeDispose; 16011 exports.onServerPrefetch = onServerPrefetch; 16012 exports.onUnmounted = onUnmounted; 16013 exports.onUpdated = onUpdated; 16014 exports.openBlock = openBlock; 16015 exports.popScopeId = popScopeId; 16016 exports.provide = provide; 16017 exports.proxyRefs = proxyRefs; 16018 exports.pushScopeId = pushScopeId; 16019 exports.queuePostFlushCb = queuePostFlushCb; 16020 exports.reactive = reactive; 16021 exports.readonly = readonly; 16022 exports.ref = ref; 16023 exports.registerRuntimeCompiler = registerRuntimeCompiler; 16024 exports.render = render; 16025 exports.renderList = renderList; 16026 exports.renderSlot = renderSlot; 16027 exports.resolveComponent = resolveComponent; 16028 exports.resolveDirective = resolveDirective; 16029 exports.resolveDynamicComponent = resolveDynamicComponent; 16030 exports.resolveFilter = resolveFilter; 16031 exports.resolveTransitionHooks = resolveTransitionHooks; 16032 exports.setBlockTracking = setBlockTracking; 16033 exports.setDevtoolsHook = setDevtoolsHook; 16034 exports.setTransitionHooks = setTransitionHooks; 16035 exports.shallowReactive = shallowReactive; 16036 exports.shallowReadonly = shallowReadonly; 16037 exports.shallowRef = shallowRef; 16038 exports.ssrContextKey = ssrContextKey; 16039 exports.ssrUtils = ssrUtils; 16040 exports.stop = stop; 16041 exports.toDisplayString = toDisplayString; 16042 exports.toHandlerKey = toHandlerKey; 16043 exports.toHandlers = toHandlers; 16044 exports.toRaw = toRaw; 16045 exports.toRef = toRef; 16046 exports.toRefs = toRefs; 16047 exports.transformVNodeArgs = transformVNodeArgs; 16048 exports.triggerRef = triggerRef; 16049 exports.unref = unref; 16050 exports.useAttrs = useAttrs; 16051 exports.useCssModule = useCssModule; 16052 exports.useCssVars = useCssVars; 16053 exports.useSSRContext = useSSRContext; 16054 exports.useSlots = useSlots; 16055 exports.useTransitionState = useTransitionState; 16056 exports.vModelCheckbox = vModelCheckbox; 16057 exports.vModelDynamic = vModelDynamic; 16058 exports.vModelRadio = vModelRadio; 16059 exports.vModelSelect = vModelSelect; 16060 exports.vModelText = vModelText; 16061 exports.vShow = vShow; 16062 exports.version = version; 16063 exports.warn = warn$1; 16064 exports.watch = watch; 16065 exports.watchEffect = watchEffect; 16066 exports.watchPostEffect = watchPostEffect; 16067 exports.watchSyncEffect = watchSyncEffect; 16068 exports.withAsyncContext = withAsyncContext; 16069 exports.withCtx = withCtx; 16070 exports.withDefaults = withDefaults; 16071 exports.withDirectives = withDirectives; 16072 exports.withKeys = withKeys; 16073 exports.withMemo = withMemo; 16074 exports.withModifiers = withModifiers; 16075 exports.withScopeId = withScopeId; 16076 16077 Object.defineProperty(exports, '__esModule', { value: true }); 16078 16079 return exports; 16080 16081}({}));
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.