haori 0.58.0 → 0.59.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.ja.md +1 -1
- package/README.md +1 -1
- package/dist/haori.cjs.js +2 -2
- package/dist/haori.es.js +11 -7
- package/dist/haori.iife.js +2 -2
- package/dist/index.d.ts +1 -1
- package/package.json +1 -1
package/README.ja.md
CHANGED
package/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
Haori.js is a lightweight, HTML-first UI library that enables dynamic user interfaces primarily through HTML attributes. It lets you declare data bindings, conditional rendering, list rendering, form two-way binding, server fetches, and HTML imports without writing much JavaScript.
|
|
4
4
|
|
|
5
|
-
Version: 0.
|
|
5
|
+
Version: 0.59.0
|
|
6
6
|
|
|
7
7
|
---
|
|
8
8
|
|
package/dist/haori.cjs.js
CHANGED
|
@@ -20,7 +20,7 @@ ${L}
|
|
|
20
20
|
`)}catch(Q){m.error("Haori",`Invalid run script: ${Q}`)}}X&&(r.runScript=X)}}const n=p.attrName(t,"fetch"),s=e.hasAttribute(n);if(s){const D=e.getAttributeEvaluation(n);D&&(r.fetchHasUnresolvedReference=D.hasUnresolvedReference,r.fetchUrl=D.hasUnresolvedReference?null:D.value)}const a={},o=t?p.attrName(t,"fetch-method"):p.attrName(null,"method",!0);if(e.hasAttribute(o)){const D=e.getAttributeEvaluation(o);D?.hasUnresolvedReference?r.fetchHasUnresolvedReference=!0:a.method=p.normalizeAttributeText(D?.value)??void 0}const c=t?p.attrName(t,"fetch-headers"):p.attrName(null,"headers",!0),u=p.readFetchHeaders(e,c);u!==null&&(a.headers=u);const d=t?p.attrName(t,"fetch-content-type"):p.attrName(null,"content-type",!0);let g=null;if(e.hasAttribute(d)){const D=e.getAttributeEvaluation(d);D?.hasUnresolvedReference&&(r.fetchHasUnresolvedReference=!0),g=p.normalizeAttributeText(D?.value)}if(g!==null)a.headers=p.withContentType(a.headers,g);else if(a.method&&!p.hasDeclaredContentType(a.headers)){const D=a.method.toUpperCase();a.headers=p.withContentType(a.headers,D==="GET"||D==="HEAD"||D==="OPTIONS"?"application/x-www-form-urlencoded":"application/json")}Object.keys(a).length>0&&(r.fetchOptions=a);const y=t?p.attrName(t,"fetch-download"):p.attrName(null,"download",!0);if(e.hasAttribute(y)&&!s)m.warn("Haori",`${y} は ${n} と併せて指定してください(保存する応答が無いため、この宣言は無視します)。`);else if(e.hasAttribute(y)){r.download=!0;const D=e.getAttributeEvaluation(y);r.downloadFileName=D?.hasUnresolvedReference?null:p.normalizeAttributeText(D?.value)}const A=t?p.attrName(t,"fetch-download-folder"):p.attrName(null,"download-folder",!0);e.hasAttribute(A)&&(r.download?r.downloadFolder=!0:m.warn("Haori",`${A} は ${y} と併せて指定してください(書き出す応答が無いため、この宣言は無視します)。`));const E=t?p.attrName(t,"bind"):p.attrName(null,"bind",!0);if(e.hasAttribute(E)){const D=K.read(e,E);if(D){const L=K.queryAll(D,E);L.length>0?(r.bindFragments=[],L.forEach(X=>{const Q=F.get(X);Q&&r.bindFragments.push(Q)})):m.error("Haori",`Bind element not found: ${D} (${E})`)}}const T=p.attrName(t,"bind-arg"),k=p.attrName(null,"arg",!0),B=p.attrName(null,"bind-arg",!0);t?e.hasAttribute(T)&&(r.bindArg=e.getRawAttribute(T)):e.hasAttribute(k)?r.bindArg=e.getRawAttribute(k):e.hasAttribute(B)&&(r.bindArg=e.getRawAttribute(B));const I=t?p.attrName(t,"bind-params"):p.attrName(null,"bind-params",!0);if(e.hasAttribute(I)){const D=e.getRawAttribute(I);r.bindParams=D.split("&").map(L=>L.trim())}const j=t?p.attrName(t,"bind-append"):p.attrName(null,"bind-append",!0);if(e.hasAttribute(j)){const D=e.getRawAttribute(j);r.bindAppendParams=D.split("&").map(L=>L.trim()).filter(Boolean)}const Z=t?p.attrName(t,"bind-merge"):p.attrName(null,"bind-merge",!0);e.hasAttribute(Z)&&(r.bindMerge=!0);const _=t?p.attrName(t,"bind-transform"):p.attrName(null,"bind-transform",!0);e.hasAttribute(_)&&(r.bindTransform=e.getRawAttribute(_));const P=t?p.attrName(t,"copy-params"):null;if(P&&e.hasAttribute(P)){const D=e.getRawAttribute(P);r.copyParams=D.split("&").map(L=>L.trim()).filter(Boolean)}if(t){if(e.hasAttribute(p.attrName(t,"adjust"))){const W=K.read(e,p.attrName(t,"adjust"));if(W){const G=K.queryAll(W,p.attrName(t,"adjust"));G.length>0?(r.adjustFragments=[],G.forEach(J=>{const Re=F.get(J);Re&&r.adjustFragments.push(Re)})):m.error("Haori",`Adjust element not found: ${W} (${p.attrName(t,"adjust")})`)}if(e.hasAttribute(p.attrName(t,"adjust-value"))){const G=e.getRawAttribute(p.attrName(t,"adjust-value")),J=Number(G);isNaN(J)||(r.adjustValue=J)}}if(e.hasAttribute(p.attrName(t,"row-add"))&&(r.rowAdd=!0),e.hasAttribute(p.attrName(t,"row-remove"))&&(r.rowRemove=!0),e.hasAttribute(p.attrName(t,"row-prev"))&&(r.rowMovePrev=!0),e.hasAttribute(p.attrName(t,"row-next"))&&(r.rowMoveNext=!0),e.hasAttribute(`${l.prefix}${t}-after-run`)){const W=e.getRawAttribute(`${l.prefix}${t}-after-run`);try{r.afterCallback=new Function("response",`
|
|
21
21
|
"use strict";
|
|
22
22
|
${W}
|
|
23
|
-
`)}catch(G){m.error("Haori",`Invalid after script: ${G}`)}}if(e.hasAttribute(p.attrName(t,"dialog"))&&(r.dialogMessage=p.unescapeNewlines(p.readLateAttribute(e,r,"dialog",p.attrName(t,"dialog")))),e.hasAttribute(p.attrName(t,"toast"))&&(r.toastMessage=p.readLateAttribute(e,r,"toast",p.attrName(t,"toast")),r.toastLevel=p.readToastLevel(e,r,"toast-level",p.attrName(t,"toast-level"))),t!=="poll"){const W=p.attrName(t,"error-toast");e.hasAttribute(W)&&(r.errorToastMessage=p.readLateAttribute(e,r,"error-toast",W),r.errorToastLevel=p.readToastLevel(e,r,"error-toast-level",p.attrName(t,"error-toast-level")));const G=p.attrName(t,"error-status");e.hasAttribute(G)&&(r.errorStatuses=p.parseErrorStatuses(e.getRawAttribute(G),G)),r.errorNoMessage=e.hasAttribute(p.attrName(t,"error-no-message")),r.errorBind=e.hasAttribute(p.attrName(t,"error-bind"))}const D=p.attrName(t,"redirect"),L=p.attrName(t,"redirect-replace"),X=e.hasAttribute(D),Q=e.hasAttribute(L);if(X&&(r.redirectUrl=p.readLateAttribute(e,r,"redirect",D)),Q&&(r.redirectReplaceUrl=p.readLateAttribute(e,r,"redirect-replace",L)),X||Q){const W=p.attrName(t,"redirect-return-param");e.hasAttribute(W)&&(r.redirectReturnParam=p.readLateAttribute(e,r,"redirect-return-param",W))}if(e.hasAttribute(p.attrName(t,"scroll-error"))&&(r.scrollOnError=!0),e.hasAttribute(p.attrName(t,"scroll"))&&(r.scrollTarget=p.readLateAttribute(e,r,"scroll",p.attrName(t,"scroll"))),e.hasAttribute(p.attrName(t,"history"))&&(r.historyUrl=p.readLateAttribute(e,r,"history",p.attrName(t,"history"))),e.hasAttribute(p.attrName(t,"history-data"))&&(r.historyDataAttrName=p.attrName(t,"history-data")),e.hasAttribute(p.attrName(t,"history-form"))){const W=K.read(e,p.attrName(t,"history-form"));if(W){const G=K.query(W,p.attrName(t,"history-form"));G!==null?r.historyFormFragment=N.getFormFragment(F.get(G)):m.error("Haori",`Form element not found: ${W} (${p.attrName(t,"history-form")})`)}else r.historyFormFragment=N.getFormFragment(e)}["reset-before","reset","refetch","click","copy","open","close","error-click","error-close"].forEach(W=>{if(W.startsWith("error-")&&t==="poll")return;const G=p.attrName(t,W);if(!e.hasAttribute(G))return;const J=p.resolveSelectorTargets(e,G,W);if(J.length>0)switch(W){case"reset-before":r.resetBeforeFragments=J;break;case"reset":r.resetFragments=J;break;case"refetch":r.refetchFragments=J;break;case"click":r.clickFragments=J,r.clickAwait=e.hasAttribute(`${G}-await`);break;case"copy":r.copyFragments=J;break;case"open":r.openFragments=J;break;case"close":r.closeFragments=J;break;case"error-click":r.errorClickFragments=J,r.errorClickAwait=e.hasAttribute(`${G}-await`);break;case"error-close":r.errorCloseFragments=J;break}}),t!=="poll"&&(r.errorStatusActions=p.readErrorStatusActions(e,r,t));const oe=p.attrName(t,"copy-source");if(e.hasAttribute(oe)){const W=K.read(e,oe);if(W){const G=K.query(W,oe);if(G!==null){const J=F.get(G);J?r.copySourceFragment=J:m.error("Haori",`Element is not managed by Haori: ${W} (${oe})`)}else m.error("Haori",`Element not found: ${W} (${oe})`)}else r.copySourceFragment=e}}if(!t&&(e.hasAttribute(p.attrName(null,"data",!0))&&(r.dataAttrName=p.attrName(null,"data",!0)),e.hasAttribute(p.attrName(null,"form",!0)))){const D=K.read(e,p.attrName(null,"form",!0));if(D){const L=K.query(D,p.attrName(null,"form",!0));L!==null?r.formFragment=N.getFormFragment(F.get(L)):m.error("Haori",`Form element not found: ${D} (${p.attrName(null,"fetch-form",!0)})`)}else r.formFragment=N.getFormFragment(e)}(!t||t==="poll")&&p.readNoMessageDeclarations(e,r,t??"fetch");const se=t?p.attrName(t,"fetch-state"):p.attrName(null,"state",!0);if(e.hasAttribute(se)){const D=K.read(e,se),L=[];D?(K.queryAll(D,se).forEach(Q=>{const fe=F.get(Q);fe&&L.push(fe)}),L.length===0&&m.error("Haori",`Element not found: ${D} (${se})`)):L.push(e),L.length>0&&(r.fetchStateFragments=L)}const Y=t?p.attrName(t,"store-clear"):p.attrName(null,"store-clear",!0);if(e.hasAttribute(Y)){const D=e.getRawAttribute(Y),L=D===null?"":D.trim();if(L==="")m.error("Haori",`ストレージキーが指定されていません (${Y})`);else{r.storeClearKey=L;const X=e.getRawAttribute(`${Y}-type`),Q=X===null?"session":X.trim();Q==="local"||Q==="session"?r.storeClearKind=Q:(m.warn("Haori",`${Y}-type は session または local を指定してください(session として扱います): ${Q}`),r.storeClearKind="session")}}return s&&!r.download&&(!r.bindFragments||r.bindFragments.length===0)&&(r.bindFragments=[e],r.defaultSelfBind=!0),r.download&&r.bindFragments&&r.bindFragments.length>0&&(m.warn("Haori",`${y} と同時にバインド先が指定されています(応答はファイルとして保存し、バインドは行いません)。`),r.bindFragments=null),p.recordRowWriteTargets(r),r}static recordRowWriteTargets(e){const t=new Map,r=[...e.bindFragments??[],...e.copyFragments??[]];for(const i of r){const n=i.getParent();!n||!n.hasAttribute(`${l.prefix}each`)||!n.hasAttribute(`${l.prefix}form-list`)||t.set(i,p.getRowFragments(n).includes(i)?n:null)}t.size>0&&(e.rowWriteTargets=t)}static isNamedInputFragment(e){const t=e.getTarget();return t instanceof HTMLInputElement||t instanceof HTMLSelectElement||t instanceof HTMLTextAreaElement?t.getAttribute("name")!==null||e.hasAttribute(`${l.prefix}form-name`):!1}static isElementFragment(e){if(typeof e!="object"||e===null)return!1;const t=e;return typeof t.getTarget=="function"&&typeof t.getChildElementFragments=="function"}static resolveAutoFetchSignature(e){return new p(e,null).resolveFetchSignature()}run(){return this.runWithResult().then(()=>{})}markReentrantBind(){this.reentrantBind=!0}runWithResult(){return this.execute()}async runWithOutcome(){return await this.execute()?"success":this.skipped?"skipped":"failure"}async execute(){const e=this.acquireExecutionLock();if(e===!1)return!1;try{if(Object.keys(this.options).length===0)return this.skipped=!0,!1;if(this.options.formFragment&&this.validate(this.options.formFragment)===!1)return!1;if(!this.options.formFragment&&this.options.targetFragment&&N.warnUnvalidatedCustomValidity(N.getFormFragment(this.options.targetFragment),`${l.prefix}${this.eventType??"fetch"}-form が解決できません`),!this.evaluateExecutionCondition())return this.skipped=!0,!1;if(this.options.runScript){const g=this.options.targetFragment?.getTarget()??null;try{const y=this.options.runScript.call(g,this.domEvent);y===!1&&this.domEvent&&this.domEvent.preventDefault(),y!=null&&typeof y.then=="function"&&await y}catch(y){m.error("Haori",`Run script execution error: ${y}`)}}if(!await this.confirm()||this.options.downloadFolder&&await this.prepareDownloadFolder()==="cancelled")return!1;this.options.resetBeforeFragments&&this.options.resetBeforeFragments.length>0&&(await Promise.all(this.options.resetBeforeFragments.map(g=>N.reset(g,this.operationSequence))),this.captureHistorySnapshots());const r=this.prepareFetchRequest();this.requestUserEditSequence=S.currentSequence();const i=r.payload;let n=r.url,s=r.options,a=!1,o=!1;if(this.options.beforeCallback){const g=this.options.beforeCallback(n||null,s||null);if(g!=null){if(g===!1||typeof g=="object"&&g.stop)return!1;typeof g=="object"&&(a="fetchUrl"in g,o="fetchOptions"in g,n=a?g.fetchUrl:n,s=o?g.fetchOptions:s)}}const c=Object.keys(i).length>0;if(n){const g=(s?.method||"GET").toUpperCase(),A=!a&&o&&r.transportMode==="query-get"&&Vt(s)&&!He(g)?r.baseUrl??n:n,E=qt(A,s);n=E.url;const T={...E.options},k=E.normalized?E.requestedMethod:r.requestedMethod,B=E.effectiveMethod,I=r.transportMode==="query-get"||E.normalized,j=E.queryString??r.queryString;if(I&&m.info("Haori demo fetch normalization",{runtime:l.runtime,requestedMethod:k,effectiveMethod:B,transportMode:"query-get",url:n,payload:c?i:void 0,queryString:j}),this.options.targetFragment&&n){const Z=performance.now(),_={runtime:l.runtime,requestedMethod:k,effectiveMethod:B,transportMode:I?"query-get":"http",...I?{queryString:j}:{}};return H.fetchStart(this.options.targetFragment.getTarget(),n,T,c?i:void 0,_),await this.injectFetchState("loading"),await p.invokeFetch(n,T).then(P=>this.handleFetchResult(P,n||void 0,Z)).catch(async P=>{throw n&&H.fetchError(this.options.targetFragment.getTarget(),n,P),await this.injectFetchState("error",null,P instanceof Error?P.message:String(P)),await this.runErrorActions(null),P})}return await fetch(n,T).then(Z=>this.handleFetchResult(Z,n||void 0))}if((!this.options.bindFragments||this.options.bindFragments.length===0)&&this.options.formFragment&&c){const g=this.options.formFragment,y=g.getTarget(),A=new Set;e&&e.appliedDisabledAttribute&&this.options.targetFragment&&A.add(this.options.targetFragment);const E=g.getRawBindingData(),T=Ue(i),k=g.getAttribute(`${l.prefix}form-arg`);let B;if(k){B={...E??{}};const I=String(k),j=N.resolveAncestorArgOwner(g,I);B[I]=N.mergeCollectedValues((j?j.value:B[I])??null,T)}else B=N.mergeCollectedValues(E,T,N.ancestorBaseResolver(g));await $.setBindingData(y,B,{skipFragments:A,kind:"nonSupply",sequence:this.operationSequence,editedPaths:N.collectEditedPaths(g,this.operationSequence,k?String(k):"",T)})}this.suppressEmptyReplaceBind=!c&&!this.options.formFragment&&(this.eventType==="change"||this.eventType==="input"),this.twoWayCommitBind=this.eventType==="change"||this.eventType==="input";const u=c?Ue(i):{},d=new Response(JSON.stringify(u),{headers:{"Content-Type":"application/json"}});return await this.handleFetchResult(d)}finally{this.releaseExecutionLock(e)}}acquireExecutionLock(){if(this.eventType!=="click"||!this.options.targetFragment)return null;const e=this.options.targetFragment,t=e.getTarget();if(p.RUNNING_CLICK_TARGETS.has(t)||t.matches(":disabled")||t.hasAttribute("disabled")||t.hasAttribute(Oe))return!1;const r=t.hasAttribute(`${l.prefix}click-no-disabled`);return p.RUNNING_CLICK_TARGETS.add(t),t.setAttribute(Oe,""),r||t.setAttribute("disabled",""),{target:t,fragment:e,appliedDisabledAttribute:!r}}static findDisabledDeclaration(e){const t=`${l.prefix}attr-disabled`,r=e.getRawAttribute(t);if(r!==null)return{name:t,value:r};const i=e.getRawAttribute("disabled");return i!==null&&i.includes("{{")?{name:"disabled",value:i}:null}releaseExecutionLock(e){if(!e)return;const t=e.target;if(p.RUNNING_CLICK_TARGETS.delete(t),t.removeAttribute(Oe),!e.appliedDisabledAttribute)return;const r=p.findDisabledDeclaration(e.fragment);if(r===null){t.removeAttribute("disabled");return}$.setAttribute(t,r.name,r.value).catch(i=>{m.error("Haori",`ロックの解除で ${r.name} を適用し直せませんでした: ${i}`)})}static forgetDownloadFolder(){De=null}async prepareDownloadFolder(){if(De)return this.downloadFolder=De,"ready";const e=globalThis.showDirectoryPicker;if(typeof e!="function")return m.info("Haori","この環境では保存先のフォルダを選ばせられないため、今までどおり保存します。"),"fallback";try{const t=await e.call(globalThis,{mode:"readwrite"});return De=t,this.downloadFolder=t,"ready"}catch(t){return t?.name==="AbortError"?"cancelled":(m.info("Haori",`保存先のフォルダを選ばせられなかったため、今までどおり保存します: ${t}`),"fallback")}}async readResponseBody(e){const t=e.headers.get("Content-Type")??"",r=e.body;if(!r||typeof r.getReader!="function")try{const s=await e.blob();return this.downloadReceivedBytes=s.size,this.dropTotalBytesIfExceeded(),await this.injectFetchState("loading"),s}catch(s){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${s}`),null}const i=[];return await this.pumpResponseBody(r,s=>{i.push(new Blob([s]))})?new Blob(i,t!==""?{type:t}:void 0):null}async pumpResponseBody(e,t){await this.injectFetchState("loading");let r=Date.now();const i=e.getReader();try{for(;;){const{done:n,value:s}=await i.read();if(n)break;await t(s),this.downloadReceivedBytes+=s.byteLength,this.dropTotalBytesIfExceeded();const a=Date.now();a-r>=Lt&&(r=a,await this.injectFetchState("loading"))}}catch(n){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${n}`),!1}return!0}dropTotalBytesIfExceeded(){this.downloadTotalBytes!==null&&this.downloadReceivedBytes>this.downloadTotalBytes&&(this.downloadTotalBytes=null)}static resolveDownloadTotalBytes(e){const t=e.headers.get("Content-Encoding");if(t!==null){const s=t.trim().toLowerCase();if(s!==""&&s!=="identity")return null}const r=e.headers.get("Content-Length");if(r===null)return null;const i=r.trim();if(i==="")return null;const n=Number(i);return!Number.isSafeInteger(n)||n<0?null:n}async saveResponseToFolder(e,t,r){const i=t.body;if(!i||typeof i.getReader!="function")return"fallback";const n=p.resolveDownloadFileName(t,this.options.downloadFileName??null,r??this.options.fetchUrl??null);let s=!0;try{await e.getFileHandle(n)}catch(c){if(c?.name==="NotFoundError")s=!1;else return m.info("Haori",`保存先のフォルダを確かめられなかったため、今までどおり保存します: ${c}`),"fallback"}if(s&&!await he().confirm(`${n} は既にあります。上書きしますか?`))return"cancelled";let a;try{a=await(await e.getFileHandle(n,{create:!0})).createWritable()}catch(c){return m.info("Haori",`保存先のファイルを作れなかったため、今までどおり保存します: ${c}`),"fallback"}if(await this.pumpResponseBody(i,c=>a.write(c)))try{return await a.close(),"saved"}catch(c){m.error("Haori",`ファイルを書き終えられませんでした: ${c}`)}try{await a.abort()}catch(c){m.error("Haori",`書きかけを取り消せませんでした: ${c}`)}if(!s)try{await e.removeEntry(n)}catch(c){m.error("Haori",`作りかけのファイルを取り除けませんでした: ${c}`)}return"failed"}async saveResponseAsFile(e,t){if(this.downloadTotalBytes=p.resolveDownloadTotalBytes(e),this.downloadFolder){const a=await this.saveResponseToFolder(this.downloadFolder,e,t);if(a!=="fallback")return a;this.downloadFolder=null,De=null}const r=await this.readResponseBody(e);if(r===null)return"failed";const i=p.resolveDownloadFileName(e,this.options.downloadFileName??null,t??this.options.fetchUrl??null);if(typeof URL>"u"||typeof URL.createObjectURL!="function")return m.error("Haori","この環境では Blob の URL を生成できないため、ファイルを保存できません。"),"failed";const n=URL.createObjectURL(r),s=document.createElement("a");return s.href=n,s.download=i,document.body.appendChild(s),s.click(),s.remove(),setTimeout(()=>URL.revokeObjectURL(n),0),"saved"}async showDownloadFailure(){const e=this.options.formFragment??(this.options.targetFragment?N.getFormFragment(this.options.targetFragment)||this.options.targetFragment:null),t=e?e.getTarget():document.body,r=he();await r.clearMessages(t),await r.addErrorMessage(t,Je)}static resolveDownloadFileName(e,t,r){const n=[p.readContentDispositionFileName(e.headers.get("Content-Disposition")),t,p.readUrlFileName(r)];for(const s of n){const a=p.sanitizeFileName(s);if(a!==null)return a}return"download"}static readContentDispositionFileName(e){if(!e)return null;const t=/filename\*\s*=\s*([^;]+)/i.exec(e);if(t){const n=t[1].trim(),s=n.split("'"),a=s.length>=3?s.slice(2).join("'"):n;try{return decodeURIComponent(a)}catch(o){m.warn("Haori",`Content-Disposition を解釈できません: ${o}`)}}const r=/filename\s*=\s*"((?:[^"\\]|\\.)*)"/i.exec(e);if(r)return r[1].replace(/\\(.)/g,"$1");const i=/filename\s*=\s*([^;]+)/i.exec(e);return i?i[1].trim():null}static readUrlFileName(e){if(!e)return null;const r=e.split("#")[0].split("?")[0].split("/"),i=r[r.length-1];return i===""?null:i}static sanitizeFileName(e){if(e===null)return null;const t=e.replace(/[\u0000-\u001f\u007f/\\]/g,"").trim();return t===""?null:t}async handleFetchResult(e,t,r){const i=he();if(!e.ok){if(gt(e.status))return!1;this.options.targetFragment&&t&&H.fetchError(this.options.targetFragment.getTarget(),t,new Error(`${e.status} ${e.statusText}`),e.status,r);const A=this.selectErrorActions(e.status),E=A?.bind===!0,T=await this.handleFetchError(E?e.clone():e,A?.noMessage!==!0&&!E);return E&&await this.bindResult(e).catch(k=>{m.error("Haori","Failed to bind the error response:",k)}),await this.injectFetchState("error",e.status,e.statusText||null,T),await this.runErrorActions(e.status),!1}if(this.options.targetFragment&&t&&r&&H.fetchEnd(this.options.targetFragment.getTarget(),t,e.status,r),this.options.afterCallback){const A=this.options.afterCallback(e);if(A!=null){if(A===!1||typeof A=="object"&&A.stop)return!1;typeof A=="object"&&"response"in A&&(e="response"in A?A.response:e)}}if(this.options.download){const A=await this.saveResponseAsFile(e,t);if(A==="cancelled")return await this.injectFetchState("success",e.status,null),!1;if(A==="failed")return await this.showDownloadFailure(),await this.injectFetchState("error",e.status,Je),!1}const n=[];n.push(this.bindResult(e)),n.push(this.adjust()),n.push(this.addRow()),n.push(this.removeRow()),n.push(this.movePrevRow()),n.push(this.moveNextRow()),await Promise.all(n),await this.injectFetchState("success",e.status,null),this.options.resetFragments&&this.options.resetFragments.length>0&&await Promise.all(this.options.resetFragments.map(A=>N.reset(A,this.operationSequence))),await this.copy();const s=[];this.options.refetchFragments&&this.options.refetchFragments.length>0&&this.options.refetchFragments.forEach(A=>{s.push(new p(A,null).run())});const a=await this.clickTargets(this.options.clickFragments,this.options.clickAwait===!0,"click-await");if(!a&&this.options.openFragments&&this.options.openFragments.length>0&&this.options.openFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.openDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),!a&&this.options.closeFragments&&this.options.closeFragments.length>0&&this.options.closeFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.closeDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),await Promise.all(s),a)return!1;const o=p.unescapeNewlines(p.normalizeAttributeText(this.resolveLateAttribute("dialog",this.options.dialogMessage)));o&&await i.dialog(o);const c=p.normalizeAttributeText(this.resolveLateAttribute("toast",this.options.toastMessage));if(c){const A=p.toToastLevel(this.resolveLateAttribute("toast-level",this.options.toastLevel));await i.toast(c,A??"info")}this.clearStore(),this.pushHistory();const u=this.resolveLateAttribute("scroll",this.options.scrollTarget);u&&K.query(u,p.attrName(this.eventType,"scroll"),document)?.scrollIntoView({behavior:"smooth",block:"nearest"});const d=this.resolveLateAttribute("redirect",this.options.redirectUrl),g=this.resolveLateAttribute("redirect-replace",this.options.redirectReplaceUrl);d&&g&&m.warn("Haori",`${p.attrName(this.eventType,"redirect")} と ${p.attrName(this.eventType,"redirect-replace")} の両方が指定されています。履歴を置き換える方を採用します。`);const y=g||d;if(y){let A=y;const E=this.resolveLateAttribute("redirect-return-param",this.options.redirectReturnParam);if(E){const k=new URLSearchParams(window.location.search).get(E);if(k!==null){const B=k.trim();mt.isSafeLocalPath(B)?A=B:m.warn("Haori",`戻り先パスが安全なローカルパスではないため、既定の遷移先へフォールバックします: ${k}`)}}g?window.location.replace(A):window.location.href=A}return!0}clearStore(){const e=this.options.storeClearKey;e&&Fe.clear(e,this.options.storeClearKind??"session")}async clickTargets(e,t,r){if(!e||e.length===0)return!1;for(const i of e){await $.evaluateAll(i);const n=i.getTarget();if(t&&p.takeClickOutcome(n),typeof n.click=="function"?n.click():n.dispatchEvent(new MouseEvent("click",{bubbles:!0,cancelable:!0})),!t)continue;const s=p.takeClickOutcome(n);if(s===null){m.warn("Haori",`${l.prefix}${this.eventType??"fetch"}-${r} はこの対象の完了を待てません(手続きが同期に起動していません)。`);continue}if(await s==="failure")return!0}return!1}async runErrorActions(e){const t=this.selectErrorActions(e);if(!t||await this.clickTargets(t.clickFragments,t.clickAwait,`${t.key}-click-await`))return;const i=he(),n=[];t.closeFragments?.forEach(a=>{const o=a.getTarget();o instanceof HTMLElement?n.push(i.closeDialog(o)):m.error("Haori","Element is not an HTML element: ",o)}),await Promise.all(n);const s=p.normalizeAttributeText(this.resolveLateAttribute(`${t.key}-toast`,t.toastMessage));if(s){const a=p.toToastLevel(this.resolveLateAttribute(`${t.key}-toast-level`,t.toastLevel));await i.toast(s,a??"info")}}selectErrorActions(e){const t=e===null?void 0:this.options.errorStatusActions?.get(e);return t||(this.appliesErrorActions(e)?{key:"error",clickFragments:this.options.errorClickFragments??null,clickAwait:this.options.errorClickAwait===!0,closeFragments:this.options.errorCloseFragments??null,toastMessage:this.options.errorToastMessage??null,toastLevel:this.options.errorToastLevel??null,noMessage:this.options.errorNoMessage===!0,bind:this.options.errorBind===!0}:null)}appliesErrorActions(e){const t=this.options.errorStatuses;return t===void 0||e!==null&&t.includes(e)}resolveLateAttribute(e,t){const r=t??null,i=this.options.lateAttributes?.get(e)??null,n=this.options.targetFragment??null;if(!i||!n||!n.hasAttribute(i.attributeName))return r;const s=n.getAttributeEvaluation(i.attributeName);return s===null?r:s.hasUnresolvedReference&&!i.hasUnresolvedReference?(q.isEnabled()&&m.warn("Haori",`${i.attributeName} の参照が手続きの途中で解決できなくなったため、手続き開始時の値を使います`),r):s.value??null}pushHistory(){const e=this.resolveLateAttribute("history",this.options.historyUrl),t=e!=null,r=this.resolveHistoryDataValues(),i=this.resolveHistoryFormValues(),n=r!=null,s=i!=null;if(!(!t&&!n&&!s))try{const a=t?e:window.location.pathname,o=new URL(a,window.location.href);if(o.origin!==window.location.origin){const u="history.pushState: cross-origin URL is not allowed: "+o.toString();m.error("Haori",u);return}const c=u=>{for(const[d,g]of Object.entries(u))g!=null&&(Array.isArray(g)?(o.searchParams.delete(d),g.forEach(y=>o.searchParams.append(d,String(y)))):typeof g=="object"?o.searchParams.set(d,JSON.stringify(g)):o.searchParams.set(d,String(g)))};n&&c(r),s&&c(i),history.pushState({[Pt]:!0},"",o.toString()),$.refreshUrlParams()}catch(a){m.error("Haori",`history.pushState failed: ${a}`)}}async handleFetchError(e,t){let r=null;this.options.formFragment?r=this.options.formFragment:this.options.targetFragment&&(r=N.getFormFragment(this.options.targetFragment)||this.options.targetFragment);const i=r?r.getTarget():document.body;await he().clearMessages(i);const n=async u=>{const d=r?r.getTarget():document.body;await he().addErrorMessage(d,u)},s=()=>{if(!this.options.scrollOnError)return;const u=r?r.getTarget():document.body;(u.getAttribute("data-message-level")==="error"?u:u.parentElement?.getAttribute("data-message-level")==="error"?u.parentElement:u.querySelector('[data-message-level="error"]'))?.scrollIntoView({behavior:"smooth",block:"nearest"})},a=async u=>{if(t){u.length===0&&await n(`${e.status} ${e.statusText}`);for(const d of u)d.key&&r?await N.addErrorMessage(r,d.key,d.message):await n(d.message);s()}return u.length===0?null:u.map(d=>d.message).join(`
|
|
23
|
+
`)}catch(G){m.error("Haori",`Invalid after script: ${G}`)}}if(e.hasAttribute(p.attrName(t,"dialog"))&&(r.dialogMessage=p.unescapeNewlines(p.readLateAttribute(e,r,"dialog",p.attrName(t,"dialog")))),e.hasAttribute(p.attrName(t,"toast"))&&(r.toastMessage=p.readLateAttribute(e,r,"toast",p.attrName(t,"toast")),r.toastLevel=p.readToastLevel(e,r,"toast-level",p.attrName(t,"toast-level"))),t!=="poll"){const W=p.attrName(t,"error-toast");e.hasAttribute(W)&&(r.errorToastMessage=p.readLateAttribute(e,r,"error-toast",W),r.errorToastLevel=p.readToastLevel(e,r,"error-toast-level",p.attrName(t,"error-toast-level")));const G=p.attrName(t,"error-status");e.hasAttribute(G)&&(r.errorStatuses=p.parseErrorStatuses(e.getRawAttribute(G),G)),r.errorNoMessage=e.hasAttribute(p.attrName(t,"error-no-message")),r.errorBind=e.hasAttribute(p.attrName(t,"error-bind"))}const D=p.attrName(t,"redirect"),L=p.attrName(t,"redirect-replace"),X=e.hasAttribute(D),Q=e.hasAttribute(L);if(X&&(r.redirectUrl=p.readLateAttribute(e,r,"redirect",D)),Q&&(r.redirectReplaceUrl=p.readLateAttribute(e,r,"redirect-replace",L)),X||Q){const W=p.attrName(t,"redirect-return-param");e.hasAttribute(W)&&(r.redirectReturnParam=p.readLateAttribute(e,r,"redirect-return-param",W))}if(e.hasAttribute(p.attrName(t,"scroll-error"))&&(r.scrollOnError=!0),e.hasAttribute(p.attrName(t,"scroll"))&&(r.scrollTarget=p.readLateAttribute(e,r,"scroll",p.attrName(t,"scroll"))),e.hasAttribute(p.attrName(t,"history"))&&(r.historyUrl=p.readLateAttribute(e,r,"history",p.attrName(t,"history"))),e.hasAttribute(p.attrName(t,"history-data"))&&(r.historyDataAttrName=p.attrName(t,"history-data")),e.hasAttribute(p.attrName(t,"history-form"))){const W=K.read(e,p.attrName(t,"history-form"));if(W){const G=K.query(W,p.attrName(t,"history-form"));G!==null?r.historyFormFragment=N.getFormFragment(F.get(G)):m.error("Haori",`Form element not found: ${W} (${p.attrName(t,"history-form")})`)}else r.historyFormFragment=N.getFormFragment(e)}["reset-before","reset","refetch","click","copy","open","close","error-click","error-close"].forEach(W=>{if(W.startsWith("error-")&&t==="poll")return;const G=p.attrName(t,W);if(!e.hasAttribute(G))return;const J=p.resolveSelectorTargets(e,G,W);if(J.length>0)switch(W){case"reset-before":r.resetBeforeFragments=J;break;case"reset":r.resetFragments=J;break;case"refetch":r.refetchFragments=J;break;case"click":r.clickFragments=J,r.clickAwait=e.hasAttribute(`${G}-await`);break;case"copy":r.copyFragments=J;break;case"open":r.openFragments=J;break;case"close":r.closeFragments=J;break;case"error-click":r.errorClickFragments=J,r.errorClickAwait=e.hasAttribute(`${G}-await`);break;case"error-close":r.errorCloseFragments=J;break}}),t!=="poll"&&(r.errorStatusActions=p.readErrorStatusActions(e,r,t));const oe=p.attrName(t,"copy-source");if(e.hasAttribute(oe)){const W=K.read(e,oe);if(W){const G=K.query(W,oe);if(G!==null){const J=F.get(G);J?r.copySourceFragment=J:m.error("Haori",`Element is not managed by Haori: ${W} (${oe})`)}else m.error("Haori",`Element not found: ${W} (${oe})`)}else r.copySourceFragment=e}}if(!t&&(e.hasAttribute(p.attrName(null,"data",!0))&&(r.dataAttrName=p.attrName(null,"data",!0)),e.hasAttribute(p.attrName(null,"form",!0)))){const D=K.read(e,p.attrName(null,"form",!0));if(D){const L=K.query(D,p.attrName(null,"form",!0));L!==null?r.formFragment=N.getFormFragment(F.get(L)):m.error("Haori",`Form element not found: ${D} (${p.attrName(null,"fetch-form",!0)})`)}else r.formFragment=N.getFormFragment(e)}(!t||t==="poll")&&p.readNoMessageDeclarations(e,r,t??"fetch");const se=t?p.attrName(t,"fetch-state"):p.attrName(null,"state",!0);if(e.hasAttribute(se)){const D=K.read(e,se),L=[];D?(K.queryAll(D,se).forEach(Q=>{const fe=F.get(Q);fe&&L.push(fe)}),L.length===0&&m.error("Haori",`Element not found: ${D} (${se})`)):L.push(e),L.length>0&&(r.fetchStateFragments=L)}const Y=t?p.attrName(t,"store-clear"):p.attrName(null,"store-clear",!0);if(e.hasAttribute(Y)){const D=e.getRawAttribute(Y),L=D===null?"":D.trim();if(L==="")m.error("Haori",`ストレージキーが指定されていません (${Y})`);else{r.storeClearKey=L;const X=e.getRawAttribute(`${Y}-type`),Q=X===null?"session":X.trim();Q==="local"||Q==="session"?r.storeClearKind=Q:(m.warn("Haori",`${Y}-type は session または local を指定してください(session として扱います): ${Q}`),r.storeClearKind="session")}}return s&&!r.download&&(!r.bindFragments||r.bindFragments.length===0)&&(r.bindFragments=[e],r.defaultSelfBind=!0),r.download&&r.bindFragments&&r.bindFragments.length>0&&(m.warn("Haori",`${y} と同時にバインド先が指定されています(応答はファイルとして保存し、バインドは行いません)。`),r.bindFragments=null),p.recordRowWriteTargets(r),r}static recordRowWriteTargets(e){const t=new Map,r=[...e.bindFragments??[],...e.copyFragments??[]];for(const i of r){const n=i.getParent();!n||!n.hasAttribute(`${l.prefix}each`)||!n.hasAttribute(`${l.prefix}form-list`)||t.set(i,p.getRowFragments(n).includes(i)?n:null)}t.size>0&&(e.rowWriteTargets=t)}static isNamedInputFragment(e){const t=e.getTarget();return t instanceof HTMLInputElement||t instanceof HTMLSelectElement||t instanceof HTMLTextAreaElement?t.getAttribute("name")!==null||e.hasAttribute(`${l.prefix}form-name`):!1}static isElementFragment(e){if(typeof e!="object"||e===null)return!1;const t=e;return typeof t.getTarget=="function"&&typeof t.getChildElementFragments=="function"}static resolveAutoFetchSignature(e){return new p(e,null).resolveFetchSignature()}run(){return this.runWithResult().then(()=>{})}markReentrantBind(){this.reentrantBind=!0}runWithResult(){return this.execute()}async runWithOutcome(){return await this.execute()?"success":this.skipped?"skipped":"failure"}async execute(){const e=this.acquireExecutionLock();if(e===!1)return!1;try{if(Object.keys(this.options).length===0)return this.skipped=!0,!1;if(this.options.formFragment&&this.validate(this.options.formFragment)===!1)return!1;if(!this.options.formFragment&&this.options.targetFragment&&N.warnUnvalidatedCustomValidity(N.getFormFragment(this.options.targetFragment),`${l.prefix}${this.eventType??"fetch"}-form が解決できません`),!this.evaluateExecutionCondition())return this.skipped=!0,!1;if(this.options.runScript){const g=this.options.targetFragment?.getTarget()??null;try{const y=this.options.runScript.call(g,this.domEvent);y===!1&&this.domEvent&&this.domEvent.preventDefault(),y!=null&&typeof y.then=="function"&&await y}catch(y){m.error("Haori",`Run script execution error: ${y}`)}}if(!await this.confirm()||this.options.downloadFolder&&await this.prepareDownloadFolder()==="cancelled")return!1;this.options.resetBeforeFragments&&this.options.resetBeforeFragments.length>0&&(await Promise.all(this.options.resetBeforeFragments.map(g=>N.reset(g,this.operationSequence))),this.captureHistorySnapshots());const r=this.prepareFetchRequest();this.requestUserEditSequence=S.currentSequence();const i=r.payload;let n=r.url,s=r.options,a=!1,o=!1;if(this.options.beforeCallback){const g=this.options.beforeCallback(n||null,s||null);if(g!=null){if(g===!1||typeof g=="object"&&g.stop)return!1;typeof g=="object"&&(a="fetchUrl"in g,o="fetchOptions"in g,n=a?g.fetchUrl:n,s=o?g.fetchOptions:s)}}const c=Object.keys(i).length>0;if(n){const g=(s?.method||"GET").toUpperCase(),A=!a&&o&&r.transportMode==="query-get"&&Vt(s)&&!He(g)?r.baseUrl??n:n,E=qt(A,s);n=E.url;const T={...E.options},k=E.normalized?E.requestedMethod:r.requestedMethod,B=E.effectiveMethod,I=r.transportMode==="query-get"||E.normalized,j=E.queryString??r.queryString;if(I&&m.info("Haori demo fetch normalization",{runtime:l.runtime,requestedMethod:k,effectiveMethod:B,transportMode:"query-get",url:n,payload:c?i:void 0,queryString:j}),this.options.targetFragment&&n){const Z=performance.now(),_={runtime:l.runtime,requestedMethod:k,effectiveMethod:B,transportMode:I?"query-get":"http",...I?{queryString:j}:{}};return H.fetchStart(this.options.targetFragment.getTarget(),n,T,c?i:void 0,_),await this.injectFetchState("loading"),await p.invokeFetch(n,T).then(P=>this.handleFetchResult(P,n||void 0,Z)).catch(async P=>{throw n&&H.fetchError(this.options.targetFragment.getTarget(),n,P),await this.injectFetchState("error",null,P instanceof Error?P.message:String(P)),await this.runErrorActions(null),P})}return await fetch(n,T).then(Z=>this.handleFetchResult(Z,n||void 0))}if((!this.options.bindFragments||this.options.bindFragments.length===0)&&this.options.formFragment&&c){const g=this.options.formFragment,y=g.getTarget(),A=new Set;e&&e.appliedDisabledAttribute&&this.options.targetFragment&&A.add(this.options.targetFragment);const E=g.getRawBindingData(),T=Ue(i),k=g.getAttribute(`${l.prefix}form-arg`);let B;if(k){B={...E??{}};const I=String(k),j=N.resolveAncestorArgOwner(g,I);B[I]=N.mergeCollectedValues((j?j.value:B[I])??null,T)}else B=N.mergeCollectedValues(E,T,N.ancestorBaseResolver(g));await $.setBindingData(y,B,{skipFragments:A,kind:"nonSupply",sequence:this.operationSequence,editedPaths:N.collectEditedPaths(g,this.operationSequence,k?String(k):"",T)})}this.suppressEmptyReplaceBind=!c&&!this.options.formFragment&&(this.eventType==="change"||this.eventType==="input"),this.twoWayCommitBind=this.eventType==="change"||this.eventType==="input";const u=c?Ue(i):{},d=new Response(JSON.stringify(u),{headers:{"Content-Type":"application/json"}});return await this.handleFetchResult(d)}finally{this.releaseExecutionLock(e)}}acquireExecutionLock(){if(this.eventType!=="click"||!this.options.targetFragment)return null;const e=this.options.targetFragment,t=e.getTarget();if(p.RUNNING_CLICK_TARGETS.has(t)||t.matches(":disabled")||t.hasAttribute("disabled")||t.hasAttribute(Oe))return!1;const r=t.hasAttribute(`${l.prefix}click-no-disabled`);return p.RUNNING_CLICK_TARGETS.add(t),t.setAttribute(Oe,""),r||t.setAttribute("disabled",""),{target:t,fragment:e,appliedDisabledAttribute:!r}}static findDisabledDeclaration(e){const t=`${l.prefix}attr-disabled`,r=e.getRawAttribute(t);if(r!==null)return{name:t,value:r};const i=e.getRawAttribute("disabled");return i!==null&&i.includes("{{")?{name:"disabled",value:i}:null}releaseExecutionLock(e){if(!e)return;const t=e.target;if(p.RUNNING_CLICK_TARGETS.delete(t),t.removeAttribute(Oe),!e.appliedDisabledAttribute)return;const r=p.findDisabledDeclaration(e.fragment);if(r===null){t.removeAttribute("disabled");return}$.setAttribute(t,r.name,r.value).catch(i=>{m.error("Haori",`ロックの解除で ${r.name} を適用し直せませんでした: ${i}`)})}static forgetDownloadFolder(){De=null}async prepareDownloadFolder(){if(De)return this.downloadFolder=De,"ready";const e=globalThis.showDirectoryPicker;if(typeof e!="function")return m.info("Haori","この環境では保存先のフォルダを選ばせられないため、今までどおり保存します。"),"fallback";try{const t=await e.call(globalThis,{mode:"readwrite"});return De=t,this.downloadFolder=t,"ready"}catch(t){return t?.name==="AbortError"?"cancelled":(m.info("Haori",`保存先のフォルダを選ばせられなかったため、今までどおり保存します: ${t}`),"fallback")}}async readResponseBody(e){const t=e.headers.get("Content-Type")??"",r=e.body;if(!r||typeof r.getReader!="function")try{const s=await e.blob();return this.downloadReceivedBytes=s.size,this.dropTotalBytesIfExceeded(),await this.injectFetchState("loading"),s}catch(s){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${s}`),null}const i=[];return await this.pumpResponseBody(r,s=>{i.push(new Blob([s]))})?new Blob(i,t!==""?{type:t}:void 0):null}async pumpResponseBody(e,t){await this.injectFetchState("loading");let r=Date.now();const i=e.getReader();try{for(;;){const{done:n,value:s}=await i.read();if(n)break;await t(s),this.downloadReceivedBytes+=s.byteLength,this.dropTotalBytesIfExceeded();const a=Date.now();a-r>=Lt&&(r=a,await this.injectFetchState("loading"))}}catch(n){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${n}`),!1}return!0}dropTotalBytesIfExceeded(){this.downloadTotalBytes!==null&&this.downloadReceivedBytes>this.downloadTotalBytes&&(this.downloadTotalBytes=null)}static resolveDownloadTotalBytes(e){const t=e.headers.get("Content-Encoding");if(t!==null){const s=t.trim().toLowerCase();if(s!==""&&s!=="identity")return null}const r=e.headers.get("Content-Length");if(r===null)return null;const i=r.trim();if(i==="")return null;const n=Number(i);return!Number.isSafeInteger(n)||n<0?null:n}async saveResponseToFolder(e,t,r){const i=t.body;if(!i||typeof i.getReader!="function")return"fallback";const n=p.resolveDownloadFileName(t,this.options.downloadFileName??null,r??this.options.fetchUrl??null);let s=!0;try{await e.getFileHandle(n)}catch(c){if(c?.name==="NotFoundError")s=!1;else return m.info("Haori",`保存先のフォルダを確かめられなかったため、今までどおり保存します: ${c}`),"fallback"}if(s&&!await he().confirm(`${n} は既にあります。上書きしますか?`))return"cancelled";let a;try{a=await(await e.getFileHandle(n,{create:!0})).createWritable()}catch(c){return m.info("Haori",`保存先のファイルを作れなかったため、今までどおり保存します: ${c}`),"fallback"}if(await this.pumpResponseBody(i,c=>a.write(c)))try{return await a.close(),"saved"}catch(c){m.error("Haori",`ファイルを書き終えられませんでした: ${c}`)}try{await a.abort()}catch(c){m.error("Haori",`書きかけを取り消せませんでした: ${c}`)}if(!s)try{await e.removeEntry(n)}catch(c){m.error("Haori",`作りかけのファイルを取り除けませんでした: ${c}`)}return"failed"}async saveResponseAsFile(e,t){if(this.downloadTotalBytes=p.resolveDownloadTotalBytes(e),this.downloadFolder){const a=await this.saveResponseToFolder(this.downloadFolder,e,t);if(a!=="fallback")return a;this.downloadFolder=null,De=null}const r=await this.readResponseBody(e);if(r===null)return"failed";const i=p.resolveDownloadFileName(e,this.options.downloadFileName??null,t??this.options.fetchUrl??null);if(typeof URL>"u"||typeof URL.createObjectURL!="function")return m.error("Haori","この環境では Blob の URL を生成できないため、ファイルを保存できません。"),"failed";const n=URL.createObjectURL(r),s=document.createElement("a");return s.href=n,s.download=i,document.body.appendChild(s),s.click(),s.remove(),setTimeout(()=>URL.revokeObjectURL(n),0),"saved"}async showDownloadFailure(e){const t=this.options.formFragment??(this.options.targetFragment?N.getFormFragment(this.options.targetFragment)||this.options.targetFragment:null),r=t?t.getTarget():document.body,i=he();await i.clearMessages(r),e&&await i.addErrorMessage(r,Je)}static resolveDownloadFileName(e,t,r){const n=[p.readContentDispositionFileName(e.headers.get("Content-Disposition")),t,p.readUrlFileName(r)];for(const s of n){const a=p.sanitizeFileName(s);if(a!==null)return a}return"download"}static readContentDispositionFileName(e){if(!e)return null;const t=/filename\*\s*=\s*([^;]+)/i.exec(e);if(t){const n=t[1].trim(),s=n.split("'"),a=s.length>=3?s.slice(2).join("'"):n;try{return decodeURIComponent(a)}catch(o){m.warn("Haori",`Content-Disposition を解釈できません: ${o}`)}}const r=/filename\s*=\s*"((?:[^"\\]|\\.)*)"/i.exec(e);if(r)return r[1].replace(/\\(.)/g,"$1");const i=/filename\s*=\s*([^;]+)/i.exec(e);return i?i[1].trim():null}static readUrlFileName(e){if(!e)return null;const r=e.split("#")[0].split("?")[0].split("/"),i=r[r.length-1];return i===""?null:i}static sanitizeFileName(e){if(e===null)return null;const t=e.replace(/[\u0000-\u001f\u007f/\\]/g,"").trim();return t===""?null:t}async handleFetchResult(e,t,r){const i=he();if(!e.ok){if(gt(e.status))return!1;this.options.targetFragment&&t&&H.fetchError(this.options.targetFragment.getTarget(),t,new Error(`${e.status} ${e.statusText}`),e.status,r);const A=this.selectErrorActions(e.status),E=A?.bind===!0,T=await this.handleFetchError(E?e.clone():e,A?.noMessage!==!0&&!E);return E&&await this.bindResult(e).catch(k=>{m.error("Haori","Failed to bind the error response:",k)}),await this.injectFetchState("error",e.status,e.statusText||null,T),await this.runErrorActions(e.status),!1}if(this.options.targetFragment&&t&&r&&H.fetchEnd(this.options.targetFragment.getTarget(),t,e.status,r),this.options.afterCallback){const A=this.options.afterCallback(e);if(A!=null){if(A===!1||typeof A=="object"&&A.stop)return!1;typeof A=="object"&&"response"in A&&(e="response"in A?A.response:e)}}if(this.options.download){const A=await this.saveResponseAsFile(e,t);if(A==="cancelled")return await this.injectFetchState("success",e.status,null),!1;if(A==="failed"){const E=this.selectErrorActions(null);return await this.showDownloadFailure(E?.noMessage!==!0),await this.injectFetchState("error",e.status,Je),await this.runErrorActions(null),!1}}const n=[];n.push(this.bindResult(e)),n.push(this.adjust()),n.push(this.addRow()),n.push(this.removeRow()),n.push(this.movePrevRow()),n.push(this.moveNextRow()),await Promise.all(n),await this.injectFetchState("success",e.status,null),this.options.resetFragments&&this.options.resetFragments.length>0&&await Promise.all(this.options.resetFragments.map(A=>N.reset(A,this.operationSequence))),await this.copy();const s=[];this.options.refetchFragments&&this.options.refetchFragments.length>0&&this.options.refetchFragments.forEach(A=>{s.push(new p(A,null).run())});const a=await this.clickTargets(this.options.clickFragments,this.options.clickAwait===!0,"click-await");if(!a&&this.options.openFragments&&this.options.openFragments.length>0&&this.options.openFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.openDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),!a&&this.options.closeFragments&&this.options.closeFragments.length>0&&this.options.closeFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.closeDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),await Promise.all(s),a)return!1;const o=p.unescapeNewlines(p.normalizeAttributeText(this.resolveLateAttribute("dialog",this.options.dialogMessage)));o&&await i.dialog(o);const c=p.normalizeAttributeText(this.resolveLateAttribute("toast",this.options.toastMessage));if(c){const A=p.toToastLevel(this.resolveLateAttribute("toast-level",this.options.toastLevel));await i.toast(c,A??"info")}this.clearStore(),this.pushHistory();const u=this.resolveLateAttribute("scroll",this.options.scrollTarget);u&&K.query(u,p.attrName(this.eventType,"scroll"),document)?.scrollIntoView({behavior:"smooth",block:"nearest"});const d=this.resolveLateAttribute("redirect",this.options.redirectUrl),g=this.resolveLateAttribute("redirect-replace",this.options.redirectReplaceUrl);d&&g&&m.warn("Haori",`${p.attrName(this.eventType,"redirect")} と ${p.attrName(this.eventType,"redirect-replace")} の両方が指定されています。履歴を置き換える方を採用します。`);const y=g||d;if(y){let A=y;const E=this.resolveLateAttribute("redirect-return-param",this.options.redirectReturnParam);if(E){const k=new URLSearchParams(window.location.search).get(E);if(k!==null){const B=k.trim();mt.isSafeLocalPath(B)?A=B:m.warn("Haori",`戻り先パスが安全なローカルパスではないため、既定の遷移先へフォールバックします: ${k}`)}}g?window.location.replace(A):window.location.href=A}return!0}clearStore(){const e=this.options.storeClearKey;e&&Fe.clear(e,this.options.storeClearKind??"session")}async clickTargets(e,t,r){if(!e||e.length===0)return!1;for(const i of e){await $.evaluateAll(i);const n=i.getTarget();if(t&&p.takeClickOutcome(n),typeof n.click=="function"?n.click():n.dispatchEvent(new MouseEvent("click",{bubbles:!0,cancelable:!0})),!t)continue;const s=p.takeClickOutcome(n);if(s===null){m.warn("Haori",`${l.prefix}${this.eventType??"fetch"}-${r} はこの対象の完了を待てません(手続きが同期に起動していません)。`);continue}if(await s==="failure")return!0}return!1}async runErrorActions(e){const t=this.selectErrorActions(e);if(!t||await this.clickTargets(t.clickFragments,t.clickAwait,`${t.key}-click-await`))return;const i=he(),n=[];t.closeFragments?.forEach(a=>{const o=a.getTarget();o instanceof HTMLElement?n.push(i.closeDialog(o)):m.error("Haori","Element is not an HTML element: ",o)}),await Promise.all(n);const s=p.normalizeAttributeText(this.resolveLateAttribute(`${t.key}-toast`,t.toastMessage));if(s){const a=p.toToastLevel(this.resolveLateAttribute(`${t.key}-toast-level`,t.toastLevel));await i.toast(s,a??"info")}}selectErrorActions(e){const t=e===null?void 0:this.options.errorStatusActions?.get(e);return t||(this.appliesErrorActions(e)?{key:"error",clickFragments:this.options.errorClickFragments??null,clickAwait:this.options.errorClickAwait===!0,closeFragments:this.options.errorCloseFragments??null,toastMessage:this.options.errorToastMessage??null,toastLevel:this.options.errorToastLevel??null,noMessage:this.options.errorNoMessage===!0,bind:this.options.errorBind===!0}:null)}appliesErrorActions(e){const t=this.options.errorStatuses;return t===void 0||e!==null&&t.includes(e)}resolveLateAttribute(e,t){const r=t??null,i=this.options.lateAttributes?.get(e)??null,n=this.options.targetFragment??null;if(!i||!n||!n.hasAttribute(i.attributeName))return r;const s=n.getAttributeEvaluation(i.attributeName);return s===null?r:s.hasUnresolvedReference&&!i.hasUnresolvedReference?(q.isEnabled()&&m.warn("Haori",`${i.attributeName} の参照が手続きの途中で解決できなくなったため、手続き開始時の値を使います`),r):s.value??null}pushHistory(){const e=this.resolveLateAttribute("history",this.options.historyUrl),t=e!=null,r=this.resolveHistoryDataValues(),i=this.resolveHistoryFormValues(),n=r!=null,s=i!=null;if(!(!t&&!n&&!s))try{const a=t?e:window.location.pathname,o=new URL(a,window.location.href);if(o.origin!==window.location.origin){const u="history.pushState: cross-origin URL is not allowed: "+o.toString();m.error("Haori",u);return}const c=u=>{for(const[d,g]of Object.entries(u))g!=null&&(Array.isArray(g)?(o.searchParams.delete(d),g.forEach(y=>o.searchParams.append(d,String(y)))):typeof g=="object"?o.searchParams.set(d,JSON.stringify(g)):o.searchParams.set(d,String(g)))};n&&c(r),s&&c(i),history.pushState({[Pt]:!0},"",o.toString()),$.refreshUrlParams()}catch(a){m.error("Haori",`history.pushState failed: ${a}`)}}async handleFetchError(e,t){let r=null;this.options.formFragment?r=this.options.formFragment:this.options.targetFragment&&(r=N.getFormFragment(this.options.targetFragment)||this.options.targetFragment);const i=r?r.getTarget():document.body;await he().clearMessages(i);const n=async u=>{const d=r?r.getTarget():document.body;await he().addErrorMessage(d,u)},s=()=>{if(!this.options.scrollOnError)return;const u=r?r.getTarget():document.body;(u.getAttribute("data-message-level")==="error"?u:u.parentElement?.getAttribute("data-message-level")==="error"?u.parentElement:u.querySelector('[data-message-level="error"]'))?.scrollIntoView({behavior:"smooth",block:"nearest"})},a=async u=>{if(t){u.length===0&&await n(`${e.status} ${e.statusText}`);for(const d of u)d.key&&r?await N.addErrorMessage(r,d.key,d.message):await n(d.message);s()}return u.length===0?null:u.map(d=>d.message).join(`
|
|
24
24
|
`)};if((e.headers.get("Content-Type")||"").includes("application/json"))try{const u=await e.json(),d=[];if(Array.isArray(u)){const g=new Map,y=[];for(const A of u)if(A&&typeof A=="object"&&!Array.isArray(A)){const E=A.key,T=A.message,k=typeof E=="string"&&E.length>0?E:null,B=typeof T=="string"?T:T!=null?String(T):"";if(B.length===0)continue;if(k!==null){const I=g.get(k)??[];I.push(B),g.set(k,I)}else y.push(B)}else typeof A=="string"&&A.length>0&&y.push(A);for(const[A,E]of g)d.push({key:A,message:E.join(`
|
|
25
25
|
`)});for(const A of y)d.push({message:A})}else if(u&&typeof u=="object"){if(typeof u.message=="string"&&d.push({message:u.message}),Array.isArray(u.messages))for(const g of u.messages)typeof g=="string"&&d.push({message:g});if(u.errors&&typeof u.errors=="object")for(const[g,y]of Object.entries(u.errors))Array.isArray(y)?d.push({key:g,message:y.join(`
|
|
26
26
|
`)}):typeof y=="string"?d.push({key:g,message:y}):y!=null&&d.push({key:g,message:String(y)});if(d.length===0)for(const[g,y]of Object.entries(u))g==="message"||g==="messages"||g==="errors"||(Array.isArray(y)?d.push({key:g,message:y.join(`
|
|
@@ -29,5 +29,5 @@ ${r}
|
|
|
29
29
|
);`)}catch{try{i=new Function(`"use strict";
|
|
30
30
|
${r}
|
|
31
31
|
`)}catch(n){m.error("[Haori]",`Invalid each-rendered-run script: ${n}`)}}if(i)try{i.call(e)}catch(n){m.error("[Haori]",`each-rendered-run execution error: ${n}`)}}static runEachRenderedChange(e){const t=`${l.prefix}each-rendered-change`,r=e.getTarget();if(!r.hasAttribute(t))return;const i=String(r.getAttribute(t)??"").trim().toLowerCase();let n=!1;if(i==="always"?n=!0:i!==""&&i!=="once"&&(f.EACH_RENDERED_CHANGE_WARNED.has(r)||(f.EACH_RENDERED_CHANGE_WARNED.add(r),m.warn("[Haori]",`Invalid ${t} value: "${i}". Use "once" (default) or "always".`))),f.countEachRenderedRows(e)!==0){if(!n){if(f.EACH_RENDERED_CHANGE_FIRED.has(r))return;f.EACH_RENDERED_CHANGE_FIRED.add(r)}try{r.dispatchEvent(new Event("change",{bubbles:!0}))}catch(s){m.error("[Haori]",`each-rendered-change dispatch error: ${s}`)}}}static countEachRenderedRows(e){let t=0;for(const r of e.getChildElementFragments())r.getTarget().hasAttribute(`${l.prefix}row`)&&(t+=1);return t}static performEachUpdate(e){const t=f.resolveEachItems(e);if(t===null)return Promise.reject(new Error("Invalid each attribute."));let r=e.getTemplate();const i=e.getAttribute(`${l.prefix}each-key`),n=f.createBindingSignature({key:i?String(i):null,items:t});if(r===null){let s=!1;if(e.getChildren().forEach(a=>{if(!s&&a instanceof S){if(a.hasAttribute(`${l.prefix}each-before`)||a.hasAttribute(`${l.prefix}each-after`))return;r=a.clone(),f.markFreshInitializationSkippable(r),e.setTemplate(r),s=!0,e.removeChild(a);const o=a.getTarget();o.parentNode&&o.parentNode.removeChild(o),a.setMounted(!1)}}),s&&f.warnExtraEachChildren(e),!s){const a=e.getTarget();Array.from(a.children).filter(c=>!c.hasAttribute(`${l.prefix}each-before`)&&!c.hasAttribute(`${l.prefix}each-after`)).forEach(c=>{if(!s){const d=F.get(c);d instanceof S&&(r=d.clone(),f.markFreshInitializationSkippable(r),e.setTemplate(r),s=!0)}const u=F.get(c);u instanceof S&&e.getChildren().includes(u)&&(e.removeChild(u),u.setMounted(!1)),c.parentNode&&c.parentNode.removeChild(c)})}return this.updateDiff(e,t).then(()=>{e.setEachInputSignature(n)})}return e.getEachInputSignature()===n?f.reevaluateEachRows(e):this.updateDiff(e,t).then(()=>{e.setEachInputSignature(n)})}static reevaluateEachRows(e){if(f.isRowLocalEachTemplate(e))return Promise.resolve();const t=e.getChildElementFragments().filter(r=>!r.hasAttribute(`${l.prefix}each-before`)&&!r.hasAttribute(`${l.prefix}each-after`));return t.length===0?Promise.resolve():Promise.all(t.map(r=>f.evaluateAll(r))).then(()=>{})}static resolveEachItems(e){const t=e.getAttributeEvaluation(`${l.prefix}each`),r=t?.value;return t?.hasUnresolvedReference||r===!1||r===null||r===void 0?[]:Array.isArray(r)?r:(m.error("[Haori]","Invalid each attribute:",r),null)}static canSkipUnchangedNestedEach(e){if(!e.hasAttribute(`${l.prefix}each`)||e.getEachInputSignature()===null)return!1;const t=e.getParent();if(t?.closestByAttribute(`${l.prefix}derive`)||t?.closestByAttribute(`${l.prefix}derive-name`)||t?.closestByAttribute(`${l.prefix}if`)||t?.closestByAttribute(`${l.prefix}fetch`)||t?.closestByAttribute(`${l.prefix}import`)||f.hasNonEachDynamicElementState(e)||!f.isRowLocalEachTemplate(e)||f.hasEachFixedChildren(e))return!1;const r=f.resolveEachItems(e);if(r===null)return!1;const i=e.getAttribute(`${l.prefix}each-key`),n=f.createBindingSignature({key:i?String(i):null,items:r});return e.getEachInputSignature()===n}static isRowLocalEachTemplate(e){const t=e.getRowLocalTemplate();if(t!==null)return t;const r=e.getTemplate(),i=e.getAttribute(`${l.prefix}each-arg`);if(r===null||!i)return e.setRowLocalTemplate(!1),!1;const n=new Set([String(i)]),s=e.getAttribute(`${l.prefix}each-index`);s&&n.add(String(s));const a=f.isRowLocalSubtree(r,n);return e.setRowLocalTemplate(a),a}static isRowLocalSubtree(e,t){for(const i of e.getAttributeNames()){const n=e.getRawAttribute(i),s=typeof n=="string"?n:"";if(s.includes("{{")){if(!f.areExpressionsRowLocal(f.extractInterpolations(s),t))return!1;continue}if(!i.startsWith(l.prefix))continue;const a=i.slice(l.prefix.length);if(f.ROW_LOCAL_EXPRESSION_ATTRIBUTES.has(a)){if(!f.areExpressionsRowLocal([s],t))return!1;continue}if(f.ROW_LOCAL_STATIC_ATTRIBUTES.has(a))continue;const o=a.indexOf("-");if(!(o!==-1&&f.ROW_LOCAL_ROW_OPERATIONS.has(a.slice(o+1))))return!1}let r=t;if(e.hasAttribute(`${l.prefix}each`)){const i=e.getRawAttribute(`${l.prefix}each-arg`);if(typeof i!="string"||i==="")return!1;const n=new Set(t);n.add(i);const s=e.getRawAttribute(`${l.prefix}each-index`);typeof s=="string"&&s!==""&&n.add(s),r=n}for(const i of e.getChildren())if(i instanceof S){if(!f.isRowLocalSubtree(i,r))return!1}else if(i instanceof ne){const n=i.getRawText();if(n.includes("{{")&&!f.areExpressionsRowLocal(f.extractInterpolations(n),t))return!1}return!0}static areExpressionsRowLocal(e,t){for(const r of e){const i=r.trim();if(i==="")continue;const n=ie.getFreeIdentifiers(i);if(n.length===0||n.some(s=>!t.has(s)))return!1}return!0}static extractInterpolations(e){const t=[],r=/\{\{([\s\S]*?)\}\}/g;let i=r.exec(e);for(;i!==null;)t.push(i[1]),i=r.exec(e);return t}static canSkipStableDerivedSubtree(e){return!e.hasAttribute(`${l.prefix}derive`)||e.hasAttribute(`${l.prefix}if`)||e.hasAttribute(`${l.prefix}each`)||e.hasAttribute(`${l.prefix}fetch`)||e.hasAttribute(`${l.prefix}import`)?!1:!f.hasDisallowedDerivedSubtreeDescendant(e)}static hasDisallowedDerivedSubtreeDescendant(e){return e.getChildren().some(t=>t instanceof S?t.hasAttribute(`${l.prefix}derive`)||t.hasAttribute(`${l.prefix}derive-name`)||t.hasAttribute(`${l.prefix}fetch`)||t.hasAttribute(`${l.prefix}import`)?!0:f.hasDisallowedDerivedSubtreeDescendant(t):!1)}static createDescendantBindingSignature(e,t){return f.recordDerivedSubtreeSignatureComputation(e,t),f.createBindingSignature(e.getDescendantBindingData())}static createDeriveInputSignature(e,t,r){const i=typeof r=="string"?r.trim():"";return!t||i===""?null:f.createBindingSignature({expression:t,name:i,scope:e.getBindingData()})}static refreshUrlParams(){const e=`${l.prefix}url-param`,r=Array.from(document.querySelectorAll(`[${e}]`)).map(i=>{const n=F.peek(i);return n instanceof S?f.setAttribute(i,e,n.getRawAttribute(e)??""):Promise.resolve()});return Promise.all(r).then(()=>{}).catch(i=>{m.error("Haori",`${e} を読み直せませんでした: ${i}`)})}static invalidateDerivedSubtreeSignatures(e){for(let r=e.getParent();r!==null;r=r.getParent())r.setDeriveSubtreeSignature(null);const t=r=>{r.setDeriveSubtreeSignature(null),r.getChildren().forEach(i=>{i instanceof S&&t(i)})};t(e)}static refreshDerivedSubtreeSignature(e){if(!f.canSkipStableDerivedSubtree(e)){e.setDeriveSubtreeSignature(null),f.logDerivedSubtreeProfileSnapshot(e,"skip-ineligible");return}e.setDeriveSubtreeSignature(f.createDescendantBindingSignature(e,"refresh")),f.logDerivedSubtreeProfileSnapshot(e,"refresh")}static getOrCreateDerivedSubtreeProfile(e){if(!q.isEnabled()||!e.hasAttribute(`${l.prefix}derive`))return null;const t=f.DERIVE_SUBTREE_PROFILES.get(e);if(t)return t;const r={hostId:f.createDerivedSubtreeHostId(e),signatureComputeTotal:0,signatureComputeFromEvaluateAll:0,signatureComputeFromRefresh:0,skipHitCount:0,skipMissCount:0,skipIneligibleCount:0};return f.DERIVE_SUBTREE_PROFILES.set(e,r),r}static resolveElementId(e){return e.getAttribute("id")??""}static createDerivedSubtreeHostId(e){const t=[];let r=e;for(;r;){const i=r.getTarget();if(!(i instanceof HTMLElement))break;let n=i.tagName.toLowerCase();const s=f.resolveElementId(i).trim();if(s!==""){n+=`#${s}`,t.unshift(n);break}const a=r.getRawAttribute(`${l.prefix}derive-name`);typeof a=="string"&&a.trim()!==""&&(n+=`[${l.prefix}derive-name="${a.trim()}"]`);const o=r.getParent();if(o){const c=o.getChildren().filter(u=>u instanceof S).findIndex(u=>u===r);n+=`:nth-child(${c+1})`}t.unshift(n),r=o}return t.join(" > ")}static recordDerivedSubtreeSignatureComputation(e,t){const r=f.getOrCreateDerivedSubtreeProfile(e);if(r!==null){if(r.signatureComputeTotal+=1,t==="refresh"){r.signatureComputeFromRefresh+=1;return}r.signatureComputeFromEvaluateAll+=1}}static logDerivedSubtreeProfileSnapshot(e,t){const r=f.getOrCreateDerivedSubtreeProfile(e);r!==null&&(t==="skip-hit"?r.skipHitCount+=1:t==="skip-miss"?r.skipMissCount+=1:t==="skip-ineligible"&&(r.skipIneligibleCount+=1),m.info("[Haori][derive-profile]",{reason:t,hostId:r.hostId,signatureComputeTotal:r.signatureComputeTotal,signatureComputeFromEvaluateAll:r.signatureComputeFromEvaluateAll,signatureComputeFromRefresh:r.signatureComputeFromRefresh,skipHitCount:r.skipHitCount,skipMissCount:r.skipMissCount,skipIneligibleCount:r.skipIneligibleCount}))}static hasNonEachDynamicElementState(e){const t=new Set([`${l.prefix}each`,`${l.prefix}each-key`,`${l.prefix}each-arg`,`${l.prefix}each-index`]);return e.getAttributeNames().some(i=>{if(t.has(i))return!1;if(i.startsWith(`${l.prefix}attr-`)||i.startsWith(l.prefix))return!0;const n=e.getRawAttribute(i);return typeof n=="string"&&n.includes("{{")})?!0:e.getChildren().some(i=>i instanceof ne&&i.hasDynamicContent())}static markFreshInitializationSkippable(e){const t=e.getAttributeNames().some(n=>f.isFreshInitializationDynamicAttribute(e,n)),r=e.getChildren().some(n=>n instanceof S?!f.markFreshInitializationSkippable(n):n instanceof ne?n.hasDynamicContent():!1),i=!t&&!r;return e.setFreshInitializationSkippable(i),i}static isFreshInitializationDynamicAttribute(e,t){if(t.startsWith(`${l.prefix}attr-`)||t.startsWith(l.prefix))return!0;const r=e.getRawAttribute(t);return typeof r=="string"&&r.includes("{{")}static updateDiff(e,t){const r=e.getTemplate();if(r===null)return m.error("[Haori]",`Template is not set for ${l.prefix}each="${e.getRawAttribute(`${l.prefix}each`)}". The container needs one element child as the row template.`,e.getTarget()),Promise.resolve();let i=e.getAttribute(`${l.prefix}each-index`);i&&(i=String(i));const n=e.getAttribute(`${l.prefix}each-key`),s=e.getAttribute(`${l.prefix}each-arg`),a=t.map((I,j)=>f.createListKey(I,n?String(n):null,j)),o=new Set(a),c=new Map;a.forEach(I=>{c.set(I,(c.get(I)??0)+1)}),n&&o.size!==a.length&&f.warnDuplicateEachKey(String(n));const u=[];let d=e.getChildren().filter(I=>I instanceof S).filter(I=>!I.hasAttribute(`${l.prefix}each-before`)&&!I.hasAttribute(`${l.prefix}each-after`));const g=d.map(I=>I.getListKey()),y=new Set;d=d.filter((I,j)=>{const Z=String(I.getListKey()),_=c.get(Z)??0;if(_===0){y.add(I);const P=I.getListKey();return P!==null&&H.rowRemove(I.getTarget(),P,j),u.push(I.remove()),!1}return c.set(Z,_-1),!0});const A=d.map(I=>I.getListKey()),E=new Map;d.forEach(I=>{const j=I.getListKey();if(j===null)return;const Z=E.get(j);Z?Z.push(I):E.set(j,[I])});const T=e.getChildElementFragments().filter(I=>!y.has(I)),k=T.filter(I=>I.hasAttribute(`${l.prefix}each-before`)).length;let B=Promise.resolve();return a.forEach((I,j)=>{const Z=t[j],_=j;let P;const se=E.get(I)?.shift();if(se){P=se;const Y=k+j;B=B.then(()=>f.updateRowFragment(P,Z,i,_,s?String(s):null,I).then(D=>f.repositionEachRow(e,P,T,Y).then(L=>{if(L!==null&&H.rowMove(P.getTarget(),I,L-k,j),!(!D&&f.isRowLocalEachTemplate(e)))return f.evaluateAll(P).then(()=>f.applyRowFormValues(e,P,Z))})))}else{P=r.clone();const Y=k+j;B=B.then(()=>f.updateRowFragment(P,Z,i,_,s?String(s):null,I).then(()=>{const D=T[Y]??null;return e.insertBefore(P,D).then(()=>{T.splice(Y,0,P)}).then(()=>f.initializeFreshEachRow(P)).then(()=>f.applyRowFormValues(e,P,Z)).then(()=>{H.rowAdd(P.getTarget(),I,_,Z)})}))}}),Promise.all(u).then(()=>B).then(()=>{const I=a.filter(Y=>Y!==null),j=A.filter(Y=>Y!==null),Z=new Set(j),_=I.filter(Y=>!Z.has(Y)),se=g.filter(Y=>Y!==null).filter(Y=>!o.has(Y));H.eachUpdate(e.getTarget(),_,se,I)})}static warnExtraEachChildren(e){const t=e.getChildren().filter(r=>r instanceof S).filter(r=>!r.hasAttribute(`${l.prefix}each-before`)&&!r.hasAttribute(`${l.prefix}each-after`));t.length!==0&&m.warn("[Haori]",`${l.prefix}each="${e.getRawAttribute(`${l.prefix}each`)}" のコンテナに要素の子が 2 つ以上あります。テンプレートになるのは最初の子だけで、残り ${t.length} 個は行に入りません(${t.map(r=>r.getTarget().tagName.toLowerCase()).join(", ")})。行の中身は 1 つの要素で包んでください。`,e.getTarget())}static warnDuplicateEachKey(e){!q.isEnabled()||f.WARNED_DUPLICATE_EACH_KEYS.has(e)||(f.WARNED_DUPLICATE_EACH_KEYS.add(e),m.warn("[Haori]",`${l.prefix}each-key="${e}" の値が配列の中で重複しています。行は出現順で対応付けますが、キーによる行の識別はできません。`))}static repositionEachRow(e,t,r,i){const n=r.indexOf(t);if(n===-1||n===i)return Promise.resolve(null);r.splice(n,1);const s=r[i]??null;return r.splice(i,0,t),e.insertBefore(t,s).then(()=>n)}static applyRowFormValues(e,t,r){return!e.hasAttribute(`${l.prefix}form-list`)||!N.isCollectedListFromEachSource(e)||typeof r!="object"||r===null||Array.isArray(r)?Promise.resolve():N.syncRowValues(t,r)}static createListKey(e,t,r){let i;if(typeof e=="object"&&e!==null)if(t){const n=e[t];n==null?i=`__index_${r}`:typeof n=="object"?i=JSON.stringify(n):i=String(n)}else i=`__index_${r}`;else i=String(e);return i}static updateRowFragment(e,t,r,i,n,s){let a;if(typeof t=="object"&&t!==null)a=n?{[n]:{...t}}:{...t};else if(n)a={[n]:t};else return m.error("[Haori]",`Primitive value requires '${l.prefix}each-arg' attribute: ${t}`),Promise.resolve(!1);r&&(a[r]=i);const o=a,c=f.createBindingSignature({listKey:s,bindingData:o});return e.getListKey()===s&&e.getRenderSignature()===c?Promise.resolve(!1):(e.setListKey(s),e.setRenderSignature(c),e.setBindingData(o),e.setAttribute(`${l.prefix}row`,s).then(()=>!0))}static needsScheduledEvaluateAll(e){const t=[e];for(;t.length>0;){const r=t.pop();if(r.getChildElementFragments().forEach(i=>{t.push(i)}),r!==e&&!r.isMounted()&&f.hasMountSensitiveAttribute(r))return!0}return!1}static hasMountSensitiveAttribute(e){return["fetch","import"].some(t=>e.hasAttribute(`${l.prefix}${t}`))}static createBindingSignature(e,t=new WeakMap,r={value:0}){if(e===null)return"null";if(e===void 0)return"undefined";if(typeof e=="string")return JSON.stringify(e);if(typeof e=="number"||typeof e=="boolean"||typeof e=="bigint")return String(e);if(typeof e=="function")return`[Function:${e.name||"anonymous"}]`;if(typeof e=="symbol")return e.toString();if(e instanceof Date)return`[Date:${e.toISOString()}]`;if(typeof File<"u"&&e instanceof File)return`[File:${e.name}:${e.size}:${e.lastModified}:${e.type}]`;if(typeof Blob<"u"&&e instanceof Blob)return`[Blob:${e.size}:${e.type}]`;if(Array.isArray(e)){if(t.has(e))return`[Circular:${t.get(e)}]`;const i=`array-${r.value}`;return r.value+=1,t.set(e,i),`[${e.map(n=>f.createBindingSignature(n,t,r)).join(",")}]`}if(typeof e=="object"){if(t.has(e))return`[Circular:${t.get(e)}]`;const i=`object-${r.value}`;r.value+=1,t.set(e,i);const n=e;return`{${Object.keys(n).sort().map(s=>`${JSON.stringify(s)}:${f.createBindingSignature(n[s],t,r)}`).join(",")}}`}return String(e)}static scheduleEvaluateAll(e){setTimeout(()=>{f.evaluateAll(e)},100)}};f.ATTRIBUTE_ALIAS_SUFFIX="attr-",f.PRIORITY_ATTRIBUTE_SUFFIXES=["bind","store","url-param","derive-name","derive","if","each"],f.DEFERRED_ATTRIBUTE_SUFFIXES=["fetch"],f.initialValueRestores=new Set,f.EVALUATE_ALL_EXCLUDED_ATTRIBUTE_SUFFIXES=["bind","derive","derive-name","if","each","fetch","import","url-param","store","validity","validity-message"],f.ATTRIBUTE_PLACEHOLDER_REGEX=/\{\{\{[\s\S]+?\}\}\}|\{\{[\s\S]+?\}\}/,f.ROW_LOCAL_EXPRESSION_ATTRIBUTES=new Set(["each","if","derive"]),f.ROW_LOCAL_STATIC_ATTRIBUTES=new Set(["each-arg","each-key","each-index","each-before","each-after","derive-name","row","form","form-arg","form-list","form-object","form-detach","value-type","store","store-params","store-arg","store-type","enhance","enhance-new"]),f.ROW_LOCAL_ROW_OPERATIONS=new Set(["row-add","row-remove","row-prev","row-next"]),f.REACTIVE_FETCH_STATES=new WeakMap,f.REACTIVE_IMPORT_STATES=new WeakMap,f.DERIVE_SUBTREE_PROFILES=new WeakMap,f.EACH_UPDATE_STATES=new WeakMap,f.EACH_RENDERED_CHANGE_FIRED=new WeakSet,f.EACH_RENDERED_CHANGE_WARNED=new WeakSet,f.WARNED_DUPLICATE_EACH_KEYS=new Set,f.ABSENT_PATH=Symbol("absent");let $=f;const Se=class Se{constructor(e=document){this.customEventHandlers=new Map,this.builtinListenersAdded=!1,this.deferred=!1,this.deferredProcedures=[],this.onClick=t=>this.delegate(t,"click"),this.onReset=t=>{if(t.defaultPrevented||N.isResettingInternally())return;const r=t.target;r instanceof HTMLElement&&setTimeout(()=>te.refreshSubtree(r),0)},this.onChange=t=>this.delegate(t,"change"),this.onInput=t=>this.delegate(t,"input"),this.onLoadCapture=t=>this.delegate(t,"load"),this.onWindowLoad=()=>{if(this.deferred){this.deferredProcedures.push(()=>this.runWindowLoadProcedure());return}this.runWindowLoadProcedure()},this.onPopstate=t=>{const r=t.state;if(!r||r[Se.HISTORY_STATE_KEY]!==!0){$.refreshUrlParams();return}location.reload()},this.root=e}runWindowLoadProcedure(){const e=document.documentElement,t=F.get(e);t&&new ae(t,"load").run()}start(){this.deferred=!1,this.addBuiltinListeners(),this.subscribeDeclaredCustomEvents(),this.observeCustomEventDeclarations()}startDeferred(){this.deferred=!0,this.addBuiltinListeners(),this.subscribeDeclaredCustomEvents()}release(){if(!this.deferred)return;this.deferred=!1,this.subscribeDeclaredCustomEvents(),this.observeCustomEventDeclarations();const e=this.deferredProcedures.splice(0);for(const t of e)try{t()}catch(r){m.error("[Haori]","Deferred event handling error:",r)}}addBuiltinListeners(){this.builtinListenersAdded||(this.builtinListenersAdded=!0,this.root.addEventListener("click",this.onClick),this.root.addEventListener("change",this.onChange),this.root.addEventListener("input",this.onInput),this.root.addEventListener("reset",this.onReset),this.root.addEventListener("load",this.onLoadCapture,!0),window.addEventListener("load",this.onWindowLoad,{once:!0}),window.addEventListener("popstate",this.onPopstate))}stop(){this.root.removeEventListener("click",this.onClick),this.root.removeEventListener("change",this.onChange),this.root.removeEventListener("input",this.onInput),this.root.removeEventListener("reset",this.onReset),this.root.removeEventListener("load",this.onLoadCapture,!0),window.removeEventListener("load",this.onWindowLoad),window.removeEventListener("popstate",this.onPopstate),this.builtinListenersAdded=!1,this.deferred=!1,this.deferredProcedures.length=0;for(const[e,t]of this.customEventHandlers)window.removeEventListener(e,t,!0);this.customEventHandlers.clear(),this.customEventObserver?.disconnect(),this.customEventObserver=void 0}get onAttributeName(){return`${l.prefix}on`}subscribeDeclaredCustomEvents(){this.root.querySelectorAll(`[${this.onAttributeName}]`).forEach(t=>this.subscribeCustomEvent(t.getAttribute(this.onAttributeName)))}subscribeCustomEvent(e){if(e===null||e==="")return;if(Se.BUILTIN_EVENT_NAMES.has(e)){m.warn("[Haori]",`data-on="${e}" は組み込みイベントです。data-${e}-* を使用してください(data-on はカスタムイベント専用)。`);return}if(this.customEventHandlers.has(e))return;const t=r=>this.runCustomEventProcedures(e,r);this.customEventHandlers.set(e,t),window.addEventListener(e,t,!0)}runCustomEventProcedures(e,t){if(this.deferred){this.deferredProcedures.push(()=>this.runCustomEventProcedures(e,t));return}this.root.querySelectorAll(`[${this.onAttributeName}]`).forEach(i=>{if(i.getAttribute(this.onAttributeName)!==e)return;const n=F.get(i);n instanceof S&&this.isFromTarget(n,t)&&new ae(n,"on",t).run().catch(s=>{m.error("[Haori]","Procedure execution error:",s)})})}isFromTarget(e,t){const r=`${this.onAttributeName}-target`;if(!e.hasAttribute(r))return!0;const i=K.read(e,r),n=t.target;return i===null||!(n instanceof Node)?!1:K.queryAll(i,r).some(s=>s.contains(n))}observeCustomEventDeclarations(){if(typeof MutationObserver>"u")return;const e=this.root instanceof Document?this.root:this.root.ownerDocument??document,t=this.root instanceof Document?e.body:this.root;t&&(this.customEventObserver=new MutationObserver(r=>{for(const i of r)i.addedNodes.forEach(n=>{n instanceof HTMLElement&&(n.hasAttribute(this.onAttributeName)&&this.subscribeCustomEvent(n.getAttribute(this.onAttributeName)),n.querySelectorAll(`[${this.onAttributeName}]`).forEach(s=>this.subscribeCustomEvent(s.getAttribute(this.onAttributeName))))})}),this.customEventObserver.observe(t,{childList:!0,subtree:!0}))}delegate(e,t){const r=this.getElementFromTarget(e.target,t);if(r){if(t==="input"){const i=`${l.prefix}input-`;if(!r.getAttributeNames().some(s=>s.startsWith(i))){this.recordUserEdit(r);return}}if(r.hasAttribute(`${l.prefix}${t}-prevent`)&&e.preventDefault(),this.deferred){this.deferredProcedures.push(()=>{r.isConnected&&this.runProcedureFor(r,t,e)});return}this.runProcedureFor(r,t,e)}}runProcedureFor(e,t,r){const i=F.get(e);if(!i)return;(t==="change"||t==="input")&&this.syncUserEdit(e,t==="change");const n=()=>{const s=new ae(i,t,r).runWithOutcome().catch(a=>(m.error("[Haori]","Procedure execution error:",a),"failure"));if(t==="click"){ae.recordClickOutcome(e,s);const a=r.target;a instanceof HTMLElement&&a!==e&&ae.recordClickOutcome(a,s)}};if(t==="click"&&e.hasAttribute(`${l.prefix}click-defer`)){typeof requestAnimationFrame<"u"?requestAnimationFrame(()=>n()):setTimeout(n,0);return}n()}recordUserEdit(e){if(!(!(e instanceof HTMLInputElement)&&!(e instanceof HTMLSelectElement)&&!(e instanceof HTMLTextAreaElement))){if(this.deferred){this.deferredProcedures.push(()=>{e.isConnected&&this.markUserEditOnly(e)});return}this.markUserEditOnly(e)}}markUserEditOnly(e){const t=F.get(e);t instanceof S&&t.markUserEdit()}syncUserEdit(e,t){const r=F.get(e);if(r instanceof S&&(r.syncValue(),t?r.markUserEditOnChange():r.markUserEdit(),e instanceof HTMLInputElement&&e.type==="radio"&&e.name)){const i=document.getElementsByName(e.name);for(const n of Array.from(i)){if(n===e||!(n instanceof HTMLInputElement)||n.type!=="radio"||n.form!==e.form)continue;const s=F.get(n);s instanceof S&&(s.syncValue(),s.markUserEdit())}}}getElementFromTarget(e,t){if(!e)return null;if(e instanceof HTMLElement)return t==="click"?this.findClickableElement(e):e;if(e instanceof Node){const r=e.parentElement;return r?t==="click"?this.findClickableElement(r):r:null}return null}findClickableElement(e){const t=`${l.prefix}click-`,r=`${l.prefix}click-passive`;let i=e;for(;i;){if(i.getAttributeNames().some(s=>s.startsWith(t)&&s!==r))return i;if(i.hasAttribute(r))return null;i=i.parentElement}return null}};Se.HISTORY_STATE_KEY="__haoriHistoryState__",Se.BUILTIN_EVENT_NAMES=new Set(["click","change","input","load"]);let Ve=Se;const V=class V{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(V.isHtmlElement(e)&&V.syncElement(e),e.querySelectorAll("*").forEach(t=>{V.syncElement(t)}))}static syncElement(e){const t=V.registrations.get(e),r=F.get(e);if(!r||!V.shouldObserve(r)){t&&(t.observer.disconnect(),V.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=V.resolveRoot(r),n=V.resolveRootMargin(r),s=V.resolveThreshold(r),a=r.hasAttribute(`${l.prefix}intersect-once`);if(t&&t.root===i&&t.rootMargin===n&&t.threshold===s&&t.once===a){t.fragment=r,V.runPendingIntersect(e,t);return}t&&(t.observer.disconnect(),V.registrations.delete(e));const o=new IntersectionObserver(c=>{const u=V.registrations.get(e);u&&c.forEach(d=>{if(u.intersecting=d.isIntersecting,!!d.isIntersecting){if(u.running||V.isDisabled(u.fragment)){u.pending=!0;return}V.runProcedure(e,u)}})},{root:i,rootMargin:n,threshold:s});o.observe(e),V.registrations.set(e,{fragment:r,observer:o,once:a,running:t?.running??!1,intersecting:!1,pending:!1,root:i,rootMargin:n,threshold:s})}static runProcedure(e,t){t.pending=!1,t.running=!0;let r=!1;new ae(t.fragment,"intersect").runWithResult().then(i=>{r=i}).catch(i=>{m.error("[Haori]","Intersect procedure execution error:",i)}).finally(()=>{const i=V.registrations.get(e);if(i){if(i.running=!1,r&&i.once){i.observer.disconnect(),V.registrations.delete(e);return}V.runPendingIntersect(e,i)}})}static runPendingIntersect(e,t){!t.pending||!t.intersecting||t.running||V.isDisabled(t.fragment)||V.runProcedure(e,t)}static cleanupTree(e){if(V.isHtmlElement(e)){const t=V.registrations.get(e);t&&(t.observer.disconnect(),V.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=V.registrations.get(t);r&&(r.observer.disconnect(),V.registrations.delete(t))})}static disconnectAll(){V.registrations.forEach(e=>{e.observer.disconnect()}),V.registrations.clear()}static shouldObserve(e){return e.getAttributeNames().some(t=>{if(!t.startsWith(`${l.prefix}intersect-`))return!1;const r=t.slice(`${l.prefix}intersect-`.length);return!V.CONFIG_KEYS.has(r)})}static resolveRoot(e){const t=`${l.prefix}intersect-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=K.query(r,t,document);return V.isHtmlElement(i)?i:(m.error("[Haori]",`Intersect root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}intersect-root-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?"0px":String(r)}static resolveThreshold(e){const t=`${l.prefix}intersect-threshold`,r=e.getAttribute(t),i=typeof r=="number"?r:Number.parseFloat(String(r??0));return Number.isNaN(i)?0:Math.min(1,Math.max(0,i))}static isDisabled(e){const t=`${l.prefix}intersect-disabled`,r=e.getAttribute(t);if(r===null||r===!1)return!1;if(typeof r=="boolean")return r;const i=String(r).trim().toLowerCase();return i!==""&&i!=="false"&&i!=="0"}};V.CONFIG_KEYS=new Set(["root","root-margin","threshold","disabled","once"]),V.registrations=new Map;let Ee=V;const v=class v{static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(v.isHtmlElement(e)&&v.syncElement(e),e.querySelectorAll("*").forEach(t=>{v.syncElement(t)}))}static syncElement(e){const t=v.registrations.get(e);if(!t&&!v.hasPollAttribute(e))return;const r=F.get(e);if(!(r instanceof S)||!v.shouldObserve(r)){t&&v.teardown(e,t);return}const i=v.buildConfigKey(r);if(t){if(t.configKey===i){t.fragment=r;return}v.teardown(e,t)}v.startPolling(e,r,i)}static cleanupTree(e){if(v.isHtmlElement(e)){const t=v.registrations.get(e);t&&v.teardown(e,t)}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=v.registrations.get(t);r&&v.teardown(t,r)})}static disconnectAll(){v.registrations.forEach(e=>{v.clearTimers(e)}),v.registrations.clear(),v.visibilityListener&&typeof document<"u"&&document.removeEventListener("visibilitychange",v.visibilityListener),v.visibilityListener=null}static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static hasPollAttribute(e){const t=`${l.prefix}poll-`,r=e.attributes;for(let i=0;i<r.length;i+=1)if(r[i].name.startsWith(t))return!0;return!1}static shouldObserve(e){const t=`${l.prefix}poll-`;return e.getAttributeNames().some(r=>r.startsWith(t)?!v.CONFIG_KEYS.has(r.slice(t.length)):!1)}static buildConfigKey(e){const t=`${l.prefix}poll-`;return e.getAttributeNames().filter(r=>r.startsWith(t)).sort().map(r=>`${r}=${e.getRawAttribute(r)??""}`).join(`
|
|
32
|
-
`)}static startPolling(e,t,r){const i={fragment:t,configKey:r,intervalMs:v.resolveInterval(t),timeoutMs:v.resolveTimeout(t),errorLimit:v.resolveErrorLimit(t),startedAt:performance.now(),intervalTimerId:null,timeoutTimerId:null,fetching:!1,paused:!1,stopped:!1,timedOut:!1,stopReason:null,count:0,consecutiveErrors:0};v.registrations.set(e,i),v.ensureVisibilityListener(),i.timeoutMs!==null&&(i.timeoutTimerId=setTimeout(()=>{v.handleTimeout(e)},i.timeoutMs)),v.injectState(i),v.tick(e)}static async tick(e){const t=v.registrations.get(e);if(!t||t.stopped||t.fetching)return;if(t.intervalTimerId=null,!e.isConnected){await v.stop(e,t,"detached");return}const r=v.isHidden(e)||v.isDisabled(t.fragment);if(r!==t.paused&&(t.paused=r,await v.injectState(t)),r){v.schedule(e,t);return}if(v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}t.fetching=!0,t.count+=1;let i=!1;try{i=await new ae(t.fragment,"poll").runWithResult()}catch(n){m.error("[Haori]","Poll procedure execution error:",n)}finally{t.fetching=!1}if(!(v.registrations.get(e)!==t||t.stopped)){if(i)t.consecutiveErrors=0;else if(t.consecutiveErrors+=1,t.errorLimit!==null&&t.consecutiveErrors>=t.errorLimit){await v.stop(e,t,"error");return}if(i&&v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}v.schedule(e,t)}}static schedule(e,t){t.stopped||t.intervalTimerId!==null||(t.intervalTimerId=setTimeout(()=>{v.tick(e)},t.intervalMs))}static async handleTimeout(e){const t=v.registrations.get(e);!t||t.stopped||(t.timeoutTimerId=null,t.timedOut=!0,e.isConnected&&H.pollTimeout(e,t.count,v.elapsed(t)),await v.stop(e,t,"timeout"))}static async stop(e,t,r){if(!t.stopped){if(t.stopped=!0,t.stopReason=r,t.paused=!1,v.clearTimers(t),r==="detached"){v.registrations.delete(e);return}await v.injectState(t),e.isConnected&&H.pollStop(e,r,t.count,v.elapsed(t))}}static teardown(e,t){v.clearTimers(t),v.registrations.delete(e)}static clearTimers(e){e.intervalTimerId!==null&&(clearTimeout(e.intervalTimerId),e.intervalTimerId=null),e.timeoutTimerId!==null&&(clearTimeout(e.timeoutTimerId),e.timeoutTimerId=null)}static elapsed(e){return Math.round(performance.now()-e.startedAt)}static ensureVisibilityListener(){if(v.visibilityListener||typeof document>"u")return;const e=()=>{document.visibilityState==="visible"&&Array.from(v.registrations.entries()).forEach(([t,r])=>{r.stopped||r.fetching||(r.intervalTimerId!==null&&(clearTimeout(r.intervalTimerId),r.intervalTimerId=null),v.tick(t))})};v.visibilityListener=e,document.addEventListener("visibilitychange",e)}static injectState(e){const t=v.resolveStateFragments(e);if(t.length===0)return Promise.resolve();const r={running:!e.stopped,paused:e.paused,stopped:e.stopped,timedOut:e.timedOut,stopReason:e.stopReason,count:e.count,elapsedMs:v.elapsed(e)};return Promise.all(t.map(i=>{const n=i.getTarget(),s={...i.getRawBindingData()??{},_poll:r};return $.setBindingData(n,s,{reflectToAttribute:!1,kind:"nonSupply",sequence:S.nextSequence()})})).then(()=>{})}static resolveStateFragments(e){const t=`${l.prefix}poll-state`,r=e.fragment;if(!r.hasAttribute(t))return[];const i=r.getAttribute(t);if(typeof i!="string"||i.trim()==="")return r.getTarget().isConnected?[r]:[];const n=K.queryAll(i,t,document);if(n.length===0)return m.error("[Haori]",`Poll state element not found: ${i}`),[];const s=[];return n.forEach(a=>{if(!a.isConnected)return;const o=F.get(a);o instanceof S&&s.push(o)}),s}static resolveInterval(e){const t=`${l.prefix}poll-interval`;if(!e.hasAttribute(t))return v.DEFAULT_INTERVAL_MS;const r=v.toNumber(e.getAttribute(t));return r===null?(m.warn("[Haori]",`${t} は数値で指定してください。既定値 ${v.DEFAULT_INTERVAL_MS}ms を使用します。`),v.DEFAULT_INTERVAL_MS):r<v.MIN_INTERVAL_MS?(m.warn("[Haori]",`${t} の下限は ${v.MIN_INTERVAL_MS}ms です。${r}ms は下限へ切り上げます。`),v.MIN_INTERVAL_MS):r}static resolveTimeout(e){const t=`${l.prefix}poll-timeout`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<=0?(m.warn("[Haori]",`${t} は正の数値で指定してください。無制限として扱います。`),null):r}static resolveErrorLimit(e){const t=`${l.prefix}poll-error-limit`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<1?(m.warn("[Haori]",`${t} は 1 以上の数値で指定してください。無制限として扱います。`),null):Math.floor(r)}static toNumber(e){if(typeof e=="number")return Number.isFinite(e)?e:null;if(typeof e!="string"||e.trim()==="")return null;const t=Number(e.trim());return Number.isFinite(t)?t:null}static isHidden(e){return e.closest(`[${l.prefix}if-false]`)!==null}static isDisabled(e){const t=`${l.prefix}poll-disabled`;return e.hasAttribute(t)?v.isTruthy(e.getAttribute(t)):!1}static isUntilSatisfied(e){const t=`${l.prefix}poll-until`;if(!e.hasAttribute(t))return!1;const r=e.getAttributeEvaluation(t);return r?r.hasUnresolvedReference?(m.warn("[Haori]",`${t} に未解決の参照が含まれています(停止条件は成立扱いにしません):`,e.getRawAttribute(t),e.getTarget()),!1):v.isTruthy(r.value):!1}static isTruthy(e){if(e==null||e===!1)return!1;if(typeof e=="boolean")return e;if(typeof e=="string"){const t=e.trim().toLowerCase();return t!==""&&t!=="false"&&t!=="0"}return!!e}};v.CONFIG_KEYS=new Set(["interval","timeout","until","error-limit","disabled","state"]),v.DEFAULT_INTERVAL_MS=5e3,v.MIN_INTERVAL_MS=100,v.registrations=new Map,v.visibilityListener=null;let ve=v;const At="0.58.0";function Gt(b){typeof requestAnimationFrame=="function"?requestAnimationFrame(()=>b()):Promise.resolve().then(b)}const O=class O{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(O.isHtmlElement(e)&&O.syncElement(e),e.querySelectorAll("*").forEach(t=>{O.syncElement(t)}))}static syncElement(e){const t=O.registrations.get(e),r=F.get(e);if(!(r instanceof S)||!O.shouldObserve(r)){t&&(t.observer.disconnect(),O.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=O.resolveVarName(r);if(i===""){t&&(t.observer.disconnect(),O.registrations.delete(e)),m.warn("[Haori]",'data-each-visible requires a variable name (e.g. data-each-visible="visibleRange").');return}const n=O.resolveRoot(r),s=O.resolveRootMargin(r);if(t&&t.observer.root===n&&t.observer.rootMargin===s&&t.varName===i){t.fragment=r,O.refreshRows(t);return}t&&(t.observer.disconnect(),O.registrations.delete(e));const a=new IntersectionObserver(c=>{const u=O.registrations.get(e);if(!u)return;let d=!1;c.forEach(g=>{const y=g.target;u.observedRows.has(y)&&(g.isIntersecting?u.visibleRows.has(y)||(u.visibleRows.add(y),d=!0):u.visibleRows.delete(y)&&(d=!0))}),d&&O.scheduleCompute(u)},{root:n,rootMargin:s,threshold:O.THRESHOLD}),o={fragment:r,observer:a,varName:i,root:n,rootMargin:s,observedRows:new Set,visibleRows:new Set,scheduled:!1,lastSnapshot:null};O.registrations.set(e,o),O.refreshRows(o)}static cleanupTree(e){if(O.isHtmlElement(e)){const t=O.registrations.get(e);t&&(t.observer.disconnect(),O.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=O.registrations.get(t);r&&(r.observer.disconnect(),O.registrations.delete(t))})}static disconnectAll(){O.registrations.forEach(e=>{e.observer.disconnect()}),O.registrations.clear()}static shouldObserve(e){return e.hasAttribute(`${l.prefix}each`)&&e.hasAttribute(`${l.prefix}each-visible`)}static resolveVarName(e){const t=e.getRawAttribute(`${l.prefix}each-visible`);return typeof t=="string"?t.trim():""}static resolveRoot(e){const t=`${l.prefix}each-visible-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=K.query(r,t,document);return O.isHtmlElement(i)?i:(m.error("[Haori]",`Visible range root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}each-visible-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?O.DEFAULT_ROOT_MARGIN:String(r)}static realRowElements(e){return e.getChildren().filter(t=>t instanceof S&&!t.hasAttribute(`${l.prefix}each-before`)&&!t.hasAttribute(`${l.prefix}each-after`)).map(t=>t.getTarget())}static refreshRows(e){const t=O.realRowElements(e.fragment),r=new Set(t);for(const i of[...e.observedRows])r.has(i)||(e.observer.unobserve(i),e.observedRows.delete(i),e.visibleRows.delete(i));for(const i of t)e.observedRows.has(i)||(e.observer.observe(i),e.observedRows.add(i));O.scheduleCompute(e)}static scheduleCompute(e){e.scheduled||(e.scheduled=!0,Gt(()=>{e.scheduled=!1;const t=e.fragment.getTarget();O.registrations.get(t)===e&&O.computeAndPublish(e)}))}static computeAndPublish(e){const t=O.realRowElements(e.fragment),r=new Map;t.forEach((a,o)=>r.set(a,o));const i=[];for(const a of e.visibleRows){const o=r.get(a);o!==void 0&&i.push(o)}let n;if(i.length===0)n={first:-1,last:-1,firstLabel:0,lastLabel:0,count:0,total:t.length,empty:!0};else{let a=i[0],o=i[0];for(const c of i)c<a&&(a=c),c>o&&(o=c);n={first:a,last:o,firstLabel:a+1,lastLabel:o+1,count:i.length,total:t.length,empty:!1}}const s=JSON.stringify(n);s!==e.lastSnapshot&&(e.lastSnapshot=s,O.publish(e,n))}static publish(e,t){const r=O.resolveBindOwner(e.fragment);if(!r){m.warn("[Haori]","data-each-visible found no ancestor data-bind scope to publish into.");return}const i=r.getTarget(),n={...r.getRawBindingData()??{}};n[e.varName]={...t};const s=e.fragment.getTarget(),a=i===s?new Set:new Set([e.fragment]);$.setBindingData(i,n,{skipFragments:a,reflectToAttribute:!1,kind:"nonSupply",sequence:S.nextSequence()}).catch(o=>{m.error("[Haori]","Failed to publish visible range:",o)})}static resolveBindOwner(e){const t=`${l.prefix}bind`;let r=e.getParent();for(;r;){if(r.hasAttribute(t))return r;r=r.getParent()}return e.hasAttribute(t)?e:null}};O.THRESHOLD=0,O.DEFAULT_ROOT_MARGIN="0px",O.registrations=new Map;let me=O;const U=class U{static disconnectMutationObservers(){U._mutationObservers.forEach(e=>{e.disconnect()}),U._mutationObservers.length=0}static async init(){if(U._initialized)return;U._initialized=!0,U.disconnectMutationObservers(),S.setPendingMutationFlusher(()=>{U.flushPendingMutations()});const e=new Ve;U._dispatcher=e,e.startDeferred(),U._initialIntakes=[];try{const t=await Promise.allSettled([$.scan(document.head),$.scan(document.body)]),[r,i]=t;r.status!=="fulfilled"&&m.error("[Haori]","Failed to build head fragment:",r.reason),i.status!=="fulfilled"&&m.error("[Haori]","Failed to build body fragment:",i.reason),await U.waitInitialIntakes(),await z.wait(),document.body.setAttribute("data-haori-ready",""),U.observe(document.head),U.observe(document.body),Ee.syncTree(document.body),ve.syncTree(document.body),me.syncTree(document.body)}finally{U._initialIntakes=null,e.release()}H.ready(At)}static getDispatcher(){return U._dispatcher}static async waitInitialIntakes(){const e=U._initialIntakes;for(;e!==null&&e.length>0;)await Promise.allSettled(e.splice(0))}static captureMutations(e){if(U._mutationObservers.length>0){e();return}const t=new MutationObserver(()=>{});t.observe(document.documentElement,{childList:!0,subtree:!0,attributes:!0,characterData:!0});try{e()}finally{const r=t.takeRecords().map(i=>U.toCapturedRecord(i));t.disconnect(),U.processMutations(r)}}static toCapturedRecord(e){return e.type!=="childList"?e:{type:e.type,target:e.target,addedNodes:Array.from(e.addedNodes).filter(t=>!U.hasKnownDescendant(t)),removedNodes:[]}}static hasKnownDescendant(e){return e instanceof Element&&Array.from(e.querySelectorAll("*")).some(t=>S.peek(t)!==null)}static isStaleExternalRemoval(e,t){const r=S.peek(t)?.getParent()??null;return r===null||r.getTarget()===e.target?!1:r.getTarget().closest(`[${l.prefix}external]`)!==null}static isExternallyManaged(e){return(e instanceof Element?e:e?.parentElement??null)?.closest(`[${l.prefix}external]`)!=null}static observe(e){const t=new MutationObserver(r=>{U.processMutations(r)});t.observe(e,{childList:!0,subtree:!0,attributes:!0,characterData:!0}),U._mutationObservers.push(t)}static flushPendingMutations(){for(const e of U._mutationObservers){const t=e.takeRecords();if(t.length===0)continue;const r=t.filter(U.isBindAttributeRecord),i=t.filter(n=>!U.isBindAttributeRecord(n));r.length>0&&U.processMutations(r,S.nextSequence()),i.length>0&&Promise.resolve().then(()=>{U.processMutations(i)})}}static isBindAttributeRecord(e){return e.type==="attributes"&&e.attributeName===`${l.prefix}bind`}static processMutations(e,t){for(const r of e)try{if(U.isExternallyManaged(r.target))continue;switch(r.type){case"attributes":{const i=r.target;if(r.attributeName&&i.hasAttribute("data-haori-click-lock")&&(r.attributeName==="disabled"||r.attributeName==="data-haori-click-lock")||r.attributeName&&i.hasAttribute(pe)&&(r.attributeName==="disabled"||r.attributeName===pe))break;if(r.attributeName&&(r.attributeName===`${l.prefix}if-false`||r.attributeName==="style"&&i.hasAttribute(`${l.prefix}if-false`))){r.attributeName==="style"&&S.reassertHiddenDisplay(i);break}if(r.attributeName&&$.isAliasedAttributeReflection(i,r.attributeName))break;const n=$.setAttribute(i,r.attributeName,i.getAttribute(r.attributeName),!0,t);U._initialIntakes?.push(n),Ee.syncElement(i),ve.syncElement(i),me.syncElement(i);break}case"childList":{Array.from(r.removedNodes).forEach(i=>{U.isStaleExternalRemoval(r,i)||(Ee.cleanupTree(i),ve.cleanupTree(i),me.cleanupTree(i),$.removeNode(i))}),Array.from(r.addedNodes).forEach(i=>{if(!(i.parentElement instanceof Element))return;const n=$.addNode(i.parentElement,i);U._initialIntakes?.push(n),Ee.syncTree(i),ve.syncTree(i),me.syncTree(i)}),r.target instanceof Element&&me.syncElement(r.target);break}case"characterData":{r.target instanceof Text||r.target instanceof Comment?$.changeText(r.target,r.target.textContent):m.warn("[Haori]","Unsupported character data type:",r.target);break}default:m.warn("[Haori]","Unknown mutation type:",r.type);continue}}catch(i){m.error("[Haori]","Error processing mutation:",i)}}};U._initialized=!1,U._mutationObservers=[],U._dispatcher=null,U._initialIntakes=null;let Ne=U;te.setMutationCapture(b=>Ne.captureMutations(b));document.readyState==="loading"?document.addEventListener("DOMContentLoaded",Ne.init):Ne.init();const Yt=()=>de.waitForRenders(),Xt=de.enhancers;exports.Core=$;exports.Enhance=te;exports.Env=l;exports.Form=N;exports.Fragment=F;exports.Haori=de;exports.Log=m;exports.Queue=z;exports.default=de;exports.enhancers=Xt;exports.version=At;exports.waitForRenders=Yt;
|
|
32
|
+
`)}static startPolling(e,t,r){const i={fragment:t,configKey:r,intervalMs:v.resolveInterval(t),timeoutMs:v.resolveTimeout(t),errorLimit:v.resolveErrorLimit(t),startedAt:performance.now(),intervalTimerId:null,timeoutTimerId:null,fetching:!1,paused:!1,stopped:!1,timedOut:!1,stopReason:null,count:0,consecutiveErrors:0};v.registrations.set(e,i),v.ensureVisibilityListener(),i.timeoutMs!==null&&(i.timeoutTimerId=setTimeout(()=>{v.handleTimeout(e)},i.timeoutMs)),v.injectState(i),v.tick(e)}static async tick(e){const t=v.registrations.get(e);if(!t||t.stopped||t.fetching)return;if(t.intervalTimerId=null,!e.isConnected){await v.stop(e,t,"detached");return}const r=v.isHidden(e)||v.isDisabled(t.fragment);if(r!==t.paused&&(t.paused=r,await v.injectState(t)),r){v.schedule(e,t);return}if(v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}t.fetching=!0,t.count+=1;let i=!1;try{i=await new ae(t.fragment,"poll").runWithResult()}catch(n){m.error("[Haori]","Poll procedure execution error:",n)}finally{t.fetching=!1}if(!(v.registrations.get(e)!==t||t.stopped)){if(i)t.consecutiveErrors=0;else if(t.consecutiveErrors+=1,t.errorLimit!==null&&t.consecutiveErrors>=t.errorLimit){await v.stop(e,t,"error");return}if(i&&v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}v.schedule(e,t)}}static schedule(e,t){t.stopped||t.intervalTimerId!==null||(t.intervalTimerId=setTimeout(()=>{v.tick(e)},t.intervalMs))}static async handleTimeout(e){const t=v.registrations.get(e);!t||t.stopped||(t.timeoutTimerId=null,t.timedOut=!0,e.isConnected&&H.pollTimeout(e,t.count,v.elapsed(t)),await v.stop(e,t,"timeout"))}static async stop(e,t,r){if(!t.stopped){if(t.stopped=!0,t.stopReason=r,t.paused=!1,v.clearTimers(t),r==="detached"){v.registrations.delete(e);return}await v.injectState(t),e.isConnected&&H.pollStop(e,r,t.count,v.elapsed(t))}}static teardown(e,t){v.clearTimers(t),v.registrations.delete(e)}static clearTimers(e){e.intervalTimerId!==null&&(clearTimeout(e.intervalTimerId),e.intervalTimerId=null),e.timeoutTimerId!==null&&(clearTimeout(e.timeoutTimerId),e.timeoutTimerId=null)}static elapsed(e){return Math.round(performance.now()-e.startedAt)}static ensureVisibilityListener(){if(v.visibilityListener||typeof document>"u")return;const e=()=>{document.visibilityState==="visible"&&Array.from(v.registrations.entries()).forEach(([t,r])=>{r.stopped||r.fetching||(r.intervalTimerId!==null&&(clearTimeout(r.intervalTimerId),r.intervalTimerId=null),v.tick(t))})};v.visibilityListener=e,document.addEventListener("visibilitychange",e)}static injectState(e){const t=v.resolveStateFragments(e);if(t.length===0)return Promise.resolve();const r={running:!e.stopped,paused:e.paused,stopped:e.stopped,timedOut:e.timedOut,stopReason:e.stopReason,count:e.count,elapsedMs:v.elapsed(e)};return Promise.all(t.map(i=>{const n=i.getTarget(),s={...i.getRawBindingData()??{},_poll:r};return $.setBindingData(n,s,{reflectToAttribute:!1,kind:"nonSupply",sequence:S.nextSequence()})})).then(()=>{})}static resolveStateFragments(e){const t=`${l.prefix}poll-state`,r=e.fragment;if(!r.hasAttribute(t))return[];const i=r.getAttribute(t);if(typeof i!="string"||i.trim()==="")return r.getTarget().isConnected?[r]:[];const n=K.queryAll(i,t,document);if(n.length===0)return m.error("[Haori]",`Poll state element not found: ${i}`),[];const s=[];return n.forEach(a=>{if(!a.isConnected)return;const o=F.get(a);o instanceof S&&s.push(o)}),s}static resolveInterval(e){const t=`${l.prefix}poll-interval`;if(!e.hasAttribute(t))return v.DEFAULT_INTERVAL_MS;const r=v.toNumber(e.getAttribute(t));return r===null?(m.warn("[Haori]",`${t} は数値で指定してください。既定値 ${v.DEFAULT_INTERVAL_MS}ms を使用します。`),v.DEFAULT_INTERVAL_MS):r<v.MIN_INTERVAL_MS?(m.warn("[Haori]",`${t} の下限は ${v.MIN_INTERVAL_MS}ms です。${r}ms は下限へ切り上げます。`),v.MIN_INTERVAL_MS):r}static resolveTimeout(e){const t=`${l.prefix}poll-timeout`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<=0?(m.warn("[Haori]",`${t} は正の数値で指定してください。無制限として扱います。`),null):r}static resolveErrorLimit(e){const t=`${l.prefix}poll-error-limit`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<1?(m.warn("[Haori]",`${t} は 1 以上の数値で指定してください。無制限として扱います。`),null):Math.floor(r)}static toNumber(e){if(typeof e=="number")return Number.isFinite(e)?e:null;if(typeof e!="string"||e.trim()==="")return null;const t=Number(e.trim());return Number.isFinite(t)?t:null}static isHidden(e){return e.closest(`[${l.prefix}if-false]`)!==null}static isDisabled(e){const t=`${l.prefix}poll-disabled`;return e.hasAttribute(t)?v.isTruthy(e.getAttribute(t)):!1}static isUntilSatisfied(e){const t=`${l.prefix}poll-until`;if(!e.hasAttribute(t))return!1;const r=e.getAttributeEvaluation(t);return r?r.hasUnresolvedReference?(m.warn("[Haori]",`${t} に未解決の参照が含まれています(停止条件は成立扱いにしません):`,e.getRawAttribute(t),e.getTarget()),!1):v.isTruthy(r.value):!1}static isTruthy(e){if(e==null||e===!1)return!1;if(typeof e=="boolean")return e;if(typeof e=="string"){const t=e.trim().toLowerCase();return t!==""&&t!=="false"&&t!=="0"}return!!e}};v.CONFIG_KEYS=new Set(["interval","timeout","until","error-limit","disabled","state"]),v.DEFAULT_INTERVAL_MS=5e3,v.MIN_INTERVAL_MS=100,v.registrations=new Map,v.visibilityListener=null;let ve=v;const At="0.59.0";function Gt(b){typeof requestAnimationFrame=="function"?requestAnimationFrame(()=>b()):Promise.resolve().then(b)}const O=class O{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(O.isHtmlElement(e)&&O.syncElement(e),e.querySelectorAll("*").forEach(t=>{O.syncElement(t)}))}static syncElement(e){const t=O.registrations.get(e),r=F.get(e);if(!(r instanceof S)||!O.shouldObserve(r)){t&&(t.observer.disconnect(),O.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=O.resolveVarName(r);if(i===""){t&&(t.observer.disconnect(),O.registrations.delete(e)),m.warn("[Haori]",'data-each-visible requires a variable name (e.g. data-each-visible="visibleRange").');return}const n=O.resolveRoot(r),s=O.resolveRootMargin(r);if(t&&t.observer.root===n&&t.observer.rootMargin===s&&t.varName===i){t.fragment=r,O.refreshRows(t);return}t&&(t.observer.disconnect(),O.registrations.delete(e));const a=new IntersectionObserver(c=>{const u=O.registrations.get(e);if(!u)return;let d=!1;c.forEach(g=>{const y=g.target;u.observedRows.has(y)&&(g.isIntersecting?u.visibleRows.has(y)||(u.visibleRows.add(y),d=!0):u.visibleRows.delete(y)&&(d=!0))}),d&&O.scheduleCompute(u)},{root:n,rootMargin:s,threshold:O.THRESHOLD}),o={fragment:r,observer:a,varName:i,root:n,rootMargin:s,observedRows:new Set,visibleRows:new Set,scheduled:!1,lastSnapshot:null};O.registrations.set(e,o),O.refreshRows(o)}static cleanupTree(e){if(O.isHtmlElement(e)){const t=O.registrations.get(e);t&&(t.observer.disconnect(),O.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=O.registrations.get(t);r&&(r.observer.disconnect(),O.registrations.delete(t))})}static disconnectAll(){O.registrations.forEach(e=>{e.observer.disconnect()}),O.registrations.clear()}static shouldObserve(e){return e.hasAttribute(`${l.prefix}each`)&&e.hasAttribute(`${l.prefix}each-visible`)}static resolveVarName(e){const t=e.getRawAttribute(`${l.prefix}each-visible`);return typeof t=="string"?t.trim():""}static resolveRoot(e){const t=`${l.prefix}each-visible-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=K.query(r,t,document);return O.isHtmlElement(i)?i:(m.error("[Haori]",`Visible range root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}each-visible-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?O.DEFAULT_ROOT_MARGIN:String(r)}static realRowElements(e){return e.getChildren().filter(t=>t instanceof S&&!t.hasAttribute(`${l.prefix}each-before`)&&!t.hasAttribute(`${l.prefix}each-after`)).map(t=>t.getTarget())}static refreshRows(e){const t=O.realRowElements(e.fragment),r=new Set(t);for(const i of[...e.observedRows])r.has(i)||(e.observer.unobserve(i),e.observedRows.delete(i),e.visibleRows.delete(i));for(const i of t)e.observedRows.has(i)||(e.observer.observe(i),e.observedRows.add(i));O.scheduleCompute(e)}static scheduleCompute(e){e.scheduled||(e.scheduled=!0,Gt(()=>{e.scheduled=!1;const t=e.fragment.getTarget();O.registrations.get(t)===e&&O.computeAndPublish(e)}))}static computeAndPublish(e){const t=O.realRowElements(e.fragment),r=new Map;t.forEach((a,o)=>r.set(a,o));const i=[];for(const a of e.visibleRows){const o=r.get(a);o!==void 0&&i.push(o)}let n;if(i.length===0)n={first:-1,last:-1,firstLabel:0,lastLabel:0,count:0,total:t.length,empty:!0};else{let a=i[0],o=i[0];for(const c of i)c<a&&(a=c),c>o&&(o=c);n={first:a,last:o,firstLabel:a+1,lastLabel:o+1,count:i.length,total:t.length,empty:!1}}const s=JSON.stringify(n);s!==e.lastSnapshot&&(e.lastSnapshot=s,O.publish(e,n))}static publish(e,t){const r=O.resolveBindOwner(e.fragment);if(!r){m.warn("[Haori]","data-each-visible found no ancestor data-bind scope to publish into.");return}const i=r.getTarget(),n={...r.getRawBindingData()??{}};n[e.varName]={...t};const s=e.fragment.getTarget(),a=i===s?new Set:new Set([e.fragment]);$.setBindingData(i,n,{skipFragments:a,reflectToAttribute:!1,kind:"nonSupply",sequence:S.nextSequence()}).catch(o=>{m.error("[Haori]","Failed to publish visible range:",o)})}static resolveBindOwner(e){const t=`${l.prefix}bind`;let r=e.getParent();for(;r;){if(r.hasAttribute(t))return r;r=r.getParent()}return e.hasAttribute(t)?e:null}};O.THRESHOLD=0,O.DEFAULT_ROOT_MARGIN="0px",O.registrations=new Map;let me=O;const U=class U{static disconnectMutationObservers(){U._mutationObservers.forEach(e=>{e.disconnect()}),U._mutationObservers.length=0}static async init(){if(U._initialized)return;U._initialized=!0,U.disconnectMutationObservers(),S.setPendingMutationFlusher(()=>{U.flushPendingMutations()});const e=new Ve;U._dispatcher=e,e.startDeferred(),U._initialIntakes=[];try{const t=await Promise.allSettled([$.scan(document.head),$.scan(document.body)]),[r,i]=t;r.status!=="fulfilled"&&m.error("[Haori]","Failed to build head fragment:",r.reason),i.status!=="fulfilled"&&m.error("[Haori]","Failed to build body fragment:",i.reason),await U.waitInitialIntakes(),await z.wait(),document.body.setAttribute("data-haori-ready",""),U.observe(document.head),U.observe(document.body),Ee.syncTree(document.body),ve.syncTree(document.body),me.syncTree(document.body)}finally{U._initialIntakes=null,e.release()}H.ready(At)}static getDispatcher(){return U._dispatcher}static async waitInitialIntakes(){const e=U._initialIntakes;for(;e!==null&&e.length>0;)await Promise.allSettled(e.splice(0))}static captureMutations(e){if(U._mutationObservers.length>0){e();return}const t=new MutationObserver(()=>{});t.observe(document.documentElement,{childList:!0,subtree:!0,attributes:!0,characterData:!0});try{e()}finally{const r=t.takeRecords().map(i=>U.toCapturedRecord(i));t.disconnect(),U.processMutations(r)}}static toCapturedRecord(e){return e.type!=="childList"?e:{type:e.type,target:e.target,addedNodes:Array.from(e.addedNodes).filter(t=>!U.hasKnownDescendant(t)),removedNodes:[]}}static hasKnownDescendant(e){return e instanceof Element&&Array.from(e.querySelectorAll("*")).some(t=>S.peek(t)!==null)}static isStaleExternalRemoval(e,t){const r=S.peek(t)?.getParent()??null;return r===null||r.getTarget()===e.target?!1:r.getTarget().closest(`[${l.prefix}external]`)!==null}static isExternallyManaged(e){return(e instanceof Element?e:e?.parentElement??null)?.closest(`[${l.prefix}external]`)!=null}static observe(e){const t=new MutationObserver(r=>{U.processMutations(r)});t.observe(e,{childList:!0,subtree:!0,attributes:!0,characterData:!0}),U._mutationObservers.push(t)}static flushPendingMutations(){for(const e of U._mutationObservers){const t=e.takeRecords();if(t.length===0)continue;const r=t.filter(U.isBindAttributeRecord),i=t.filter(n=>!U.isBindAttributeRecord(n));r.length>0&&U.processMutations(r,S.nextSequence()),i.length>0&&Promise.resolve().then(()=>{U.processMutations(i)})}}static isBindAttributeRecord(e){return e.type==="attributes"&&e.attributeName===`${l.prefix}bind`}static processMutations(e,t){for(const r of e)try{if(U.isExternallyManaged(r.target))continue;switch(r.type){case"attributes":{const i=r.target;if(r.attributeName&&i.hasAttribute("data-haori-click-lock")&&(r.attributeName==="disabled"||r.attributeName==="data-haori-click-lock")||r.attributeName&&i.hasAttribute(pe)&&(r.attributeName==="disabled"||r.attributeName===pe))break;if(r.attributeName&&(r.attributeName===`${l.prefix}if-false`||r.attributeName==="style"&&i.hasAttribute(`${l.prefix}if-false`))){r.attributeName==="style"&&S.reassertHiddenDisplay(i);break}if(r.attributeName&&$.isAliasedAttributeReflection(i,r.attributeName))break;const n=$.setAttribute(i,r.attributeName,i.getAttribute(r.attributeName),!0,t);U._initialIntakes?.push(n),Ee.syncElement(i),ve.syncElement(i),me.syncElement(i);break}case"childList":{Array.from(r.removedNodes).forEach(i=>{U.isStaleExternalRemoval(r,i)||(Ee.cleanupTree(i),ve.cleanupTree(i),me.cleanupTree(i),$.removeNode(i))}),Array.from(r.addedNodes).forEach(i=>{if(!(i.parentElement instanceof Element))return;const n=$.addNode(i.parentElement,i);U._initialIntakes?.push(n),Ee.syncTree(i),ve.syncTree(i),me.syncTree(i)}),r.target instanceof Element&&me.syncElement(r.target);break}case"characterData":{r.target instanceof Text||r.target instanceof Comment?$.changeText(r.target,r.target.textContent):m.warn("[Haori]","Unsupported character data type:",r.target);break}default:m.warn("[Haori]","Unknown mutation type:",r.type);continue}}catch(i){m.error("[Haori]","Error processing mutation:",i)}}};U._initialized=!1,U._mutationObservers=[],U._dispatcher=null,U._initialIntakes=null;let Ne=U;te.setMutationCapture(b=>Ne.captureMutations(b));document.readyState==="loading"?document.addEventListener("DOMContentLoaded",Ne.init):Ne.init();const Yt=()=>de.waitForRenders(),Xt=de.enhancers;exports.Core=$;exports.Enhance=te;exports.Env=l;exports.Form=N;exports.Fragment=F;exports.Haori=de;exports.Log=m;exports.Queue=z;exports.default=de;exports.enhancers=Xt;exports.version=At;exports.waitForRenders=Yt;
|
|
33
33
|
//# sourceMappingURL=haori.cjs.js.map
|
package/dist/haori.es.js
CHANGED
|
@@ -10370,11 +10370,13 @@ ${W}
|
|
|
10370
10370
|
* 表示先は失敗した応答の振り分けと同じ(フォーム、無ければ対象要素、
|
|
10371
10371
|
* それも無ければ `document.body`)です。
|
|
10372
10372
|
*
|
|
10373
|
+
* @param display 表示するか。`-error-no-message` で止めた場合は false で、
|
|
10374
|
+
* 前回の表示を消すだけにする
|
|
10373
10375
|
* @returns 表示の完了 Promise
|
|
10374
10376
|
*/
|
|
10375
|
-
async showDownloadFailure() {
|
|
10376
|
-
const
|
|
10377
|
-
await
|
|
10377
|
+
async showDownloadFailure(e) {
|
|
10378
|
+
const t = this.options.formFragment ?? (this.options.targetFragment ? k.getFormFragment(this.options.targetFragment) || this.options.targetFragment : null), r = t ? t.getTarget() : document.body, i = fe();
|
|
10379
|
+
await i.clearMessages(r), e && await i.addErrorMessage(r, Je);
|
|
10378
10380
|
}
|
|
10379
10381
|
/**
|
|
10380
10382
|
* 保存するファイル名を決めます。
|
|
@@ -10498,12 +10500,14 @@ ${W}
|
|
|
10498
10500
|
const A = await this.saveResponseAsFile(e, t);
|
|
10499
10501
|
if (A === "cancelled")
|
|
10500
10502
|
return await this.injectFetchState("success", e.status, null), !1;
|
|
10501
|
-
if (A === "failed")
|
|
10502
|
-
|
|
10503
|
+
if (A === "failed") {
|
|
10504
|
+
const E = this.selectErrorActions(null);
|
|
10505
|
+
return await this.showDownloadFailure(E?.noMessage !== !0), await this.injectFetchState(
|
|
10503
10506
|
"error",
|
|
10504
10507
|
e.status,
|
|
10505
10508
|
Je
|
|
10506
|
-
), !1;
|
|
10509
|
+
), await this.runErrorActions(null), !1;
|
|
10510
|
+
}
|
|
10507
10511
|
}
|
|
10508
10512
|
const n = [];
|
|
10509
10513
|
n.push(this.bindResult(e)), n.push(this.adjust()), n.push(this.addRow()), n.push(this.removeRow()), n.push(this.movePrevRow()), n.push(this.moveNextRow()), await Promise.all(n), await this.injectFetchState("success", e.status, null), this.options.resetFragments && this.options.resetFragments.length > 0 && await Promise.all(
|
|
@@ -15634,7 +15638,7 @@ v.CONFIG_KEYS = /* @__PURE__ */ new Set([
|
|
|
15634
15638
|
"state"
|
|
15635
15639
|
]), v.DEFAULT_INTERVAL_MS = 5e3, v.MIN_INTERVAL_MS = 100, v.registrations = /* @__PURE__ */ new Map(), v.visibilityListener = null;
|
|
15636
15640
|
let Ee = v;
|
|
15637
|
-
const zt = "0.
|
|
15641
|
+
const zt = "0.59.0";
|
|
15638
15642
|
function Gt(b) {
|
|
15639
15643
|
typeof requestAnimationFrame == "function" ? requestAnimationFrame(() => b()) : Promise.resolve().then(b);
|
|
15640
15644
|
}
|
package/dist/haori.iife.js
CHANGED
|
@@ -20,7 +20,7 @@ ${O}
|
|
|
20
20
|
`)}catch(Q){m.error("Haori",`Invalid run script: ${Q}`)}}X&&(r.runScript=X)}}const n=p.attrName(t,"fetch"),s=e.hasAttribute(n);if(s){const D=e.getAttributeEvaluation(n);D&&(r.fetchHasUnresolvedReference=D.hasUnresolvedReference,r.fetchUrl=D.hasUnresolvedReference?null:D.value)}const a={},o=t?p.attrName(t,"fetch-method"):p.attrName(null,"method",!0);if(e.hasAttribute(o)){const D=e.getAttributeEvaluation(o);D?.hasUnresolvedReference?r.fetchHasUnresolvedReference=!0:a.method=p.normalizeAttributeText(D?.value)??void 0}const c=t?p.attrName(t,"fetch-headers"):p.attrName(null,"headers",!0),u=p.readFetchHeaders(e,c);u!==null&&(a.headers=u);const d=t?p.attrName(t,"fetch-content-type"):p.attrName(null,"content-type",!0);let g=null;if(e.hasAttribute(d)){const D=e.getAttributeEvaluation(d);D?.hasUnresolvedReference&&(r.fetchHasUnresolvedReference=!0),g=p.normalizeAttributeText(D?.value)}if(g!==null)a.headers=p.withContentType(a.headers,g);else if(a.method&&!p.hasDeclaredContentType(a.headers)){const D=a.method.toUpperCase();a.headers=p.withContentType(a.headers,D==="GET"||D==="HEAD"||D==="OPTIONS"?"application/x-www-form-urlencoded":"application/json")}Object.keys(a).length>0&&(r.fetchOptions=a);const y=t?p.attrName(t,"fetch-download"):p.attrName(null,"download",!0);if(e.hasAttribute(y)&&!s)m.warn("Haori",`${y} は ${n} と併せて指定してください(保存する応答が無いため、この宣言は無視します)。`);else if(e.hasAttribute(y)){r.download=!0;const D=e.getAttributeEvaluation(y);r.downloadFileName=D?.hasUnresolvedReference?null:p.normalizeAttributeText(D?.value)}const A=t?p.attrName(t,"fetch-download-folder"):p.attrName(null,"download-folder",!0);e.hasAttribute(A)&&(r.download?r.downloadFolder=!0:m.warn("Haori",`${A} は ${y} と併せて指定してください(書き出す応答が無いため、この宣言は無視します)。`));const E=t?p.attrName(t,"bind"):p.attrName(null,"bind",!0);if(e.hasAttribute(E)){const D=j.read(e,E);if(D){const O=j.queryAll(D,E);O.length>0?(r.bindFragments=[],O.forEach(X=>{const Q=F.get(X);Q&&r.bindFragments.push(Q)})):m.error("Haori",`Bind element not found: ${D} (${E})`)}}const T=p.attrName(t,"bind-arg"),k=p.attrName(null,"arg",!0),H=p.attrName(null,"bind-arg",!0);t?e.hasAttribute(T)&&(r.bindArg=e.getRawAttribute(T)):e.hasAttribute(k)?r.bindArg=e.getRawAttribute(k):e.hasAttribute(H)&&(r.bindArg=e.getRawAttribute(H));const N=t?p.attrName(t,"bind-params"):p.attrName(null,"bind-params",!0);if(e.hasAttribute(N)){const D=e.getRawAttribute(N);r.bindParams=D.split("&").map(O=>O.trim())}const K=t?p.attrName(t,"bind-append"):p.attrName(null,"bind-append",!0);if(e.hasAttribute(K)){const D=e.getRawAttribute(K);r.bindAppendParams=D.split("&").map(O=>O.trim()).filter(Boolean)}const Z=t?p.attrName(t,"bind-merge"):p.attrName(null,"bind-merge",!0);e.hasAttribute(Z)&&(r.bindMerge=!0);const ee=t?p.attrName(t,"bind-transform"):p.attrName(null,"bind-transform",!0);e.hasAttribute(ee)&&(r.bindTransform=e.getRawAttribute(ee));const L=t?p.attrName(t,"copy-params"):null;if(L&&e.hasAttribute(L)){const D=e.getRawAttribute(L);r.copyParams=D.split("&").map(O=>O.trim()).filter(Boolean)}if(t){if(e.hasAttribute(p.attrName(t,"adjust"))){const W=j.read(e,p.attrName(t,"adjust"));if(W){const G=j.queryAll(W,p.attrName(t,"adjust"));G.length>0?(r.adjustFragments=[],G.forEach(J=>{const Ie=F.get(J);Ie&&r.adjustFragments.push(Ie)})):m.error("Haori",`Adjust element not found: ${W} (${p.attrName(t,"adjust")})`)}if(e.hasAttribute(p.attrName(t,"adjust-value"))){const G=e.getRawAttribute(p.attrName(t,"adjust-value")),J=Number(G);isNaN(J)||(r.adjustValue=J)}}if(e.hasAttribute(p.attrName(t,"row-add"))&&(r.rowAdd=!0),e.hasAttribute(p.attrName(t,"row-remove"))&&(r.rowRemove=!0),e.hasAttribute(p.attrName(t,"row-prev"))&&(r.rowMovePrev=!0),e.hasAttribute(p.attrName(t,"row-next"))&&(r.rowMoveNext=!0),e.hasAttribute(`${l.prefix}${t}-after-run`)){const W=e.getRawAttribute(`${l.prefix}${t}-after-run`);try{r.afterCallback=new Function("response",`
|
|
21
21
|
"use strict";
|
|
22
22
|
${W}
|
|
23
|
-
`)}catch(G){m.error("Haori",`Invalid after script: ${G}`)}}if(e.hasAttribute(p.attrName(t,"dialog"))&&(r.dialogMessage=p.unescapeNewlines(p.readLateAttribute(e,r,"dialog",p.attrName(t,"dialog")))),e.hasAttribute(p.attrName(t,"toast"))&&(r.toastMessage=p.readLateAttribute(e,r,"toast",p.attrName(t,"toast")),r.toastLevel=p.readToastLevel(e,r,"toast-level",p.attrName(t,"toast-level"))),t!=="poll"){const W=p.attrName(t,"error-toast");e.hasAttribute(W)&&(r.errorToastMessage=p.readLateAttribute(e,r,"error-toast",W),r.errorToastLevel=p.readToastLevel(e,r,"error-toast-level",p.attrName(t,"error-toast-level")));const G=p.attrName(t,"error-status");e.hasAttribute(G)&&(r.errorStatuses=p.parseErrorStatuses(e.getRawAttribute(G),G)),r.errorNoMessage=e.hasAttribute(p.attrName(t,"error-no-message")),r.errorBind=e.hasAttribute(p.attrName(t,"error-bind"))}const D=p.attrName(t,"redirect"),O=p.attrName(t,"redirect-replace"),X=e.hasAttribute(D),Q=e.hasAttribute(O);if(X&&(r.redirectUrl=p.readLateAttribute(e,r,"redirect",D)),Q&&(r.redirectReplaceUrl=p.readLateAttribute(e,r,"redirect-replace",O)),X||Q){const W=p.attrName(t,"redirect-return-param");e.hasAttribute(W)&&(r.redirectReturnParam=p.readLateAttribute(e,r,"redirect-return-param",W))}if(e.hasAttribute(p.attrName(t,"scroll-error"))&&(r.scrollOnError=!0),e.hasAttribute(p.attrName(t,"scroll"))&&(r.scrollTarget=p.readLateAttribute(e,r,"scroll",p.attrName(t,"scroll"))),e.hasAttribute(p.attrName(t,"history"))&&(r.historyUrl=p.readLateAttribute(e,r,"history",p.attrName(t,"history"))),e.hasAttribute(p.attrName(t,"history-data"))&&(r.historyDataAttrName=p.attrName(t,"history-data")),e.hasAttribute(p.attrName(t,"history-form"))){const W=j.read(e,p.attrName(t,"history-form"));if(W){const G=j.query(W,p.attrName(t,"history-form"));G!==null?r.historyFormFragment=I.getFormFragment(F.get(G)):m.error("Haori",`Form element not found: ${W} (${p.attrName(t,"history-form")})`)}else r.historyFormFragment=I.getFormFragment(e)}["reset-before","reset","refetch","click","copy","open","close","error-click","error-close"].forEach(W=>{if(W.startsWith("error-")&&t==="poll")return;const G=p.attrName(t,W);if(!e.hasAttribute(G))return;const J=p.resolveSelectorTargets(e,G,W);if(J.length>0)switch(W){case"reset-before":r.resetBeforeFragments=J;break;case"reset":r.resetFragments=J;break;case"refetch":r.refetchFragments=J;break;case"click":r.clickFragments=J,r.clickAwait=e.hasAttribute(`${G}-await`);break;case"copy":r.copyFragments=J;break;case"open":r.openFragments=J;break;case"close":r.closeFragments=J;break;case"error-click":r.errorClickFragments=J,r.errorClickAwait=e.hasAttribute(`${G}-await`);break;case"error-close":r.errorCloseFragments=J;break}}),t!=="poll"&&(r.errorStatusActions=p.readErrorStatusActions(e,r,t));const le=p.attrName(t,"copy-source");if(e.hasAttribute(le)){const W=j.read(e,le);if(W){const G=j.query(W,le);if(G!==null){const J=F.get(G);J?r.copySourceFragment=J:m.error("Haori",`Element is not managed by Haori: ${W} (${le})`)}else m.error("Haori",`Element not found: ${W} (${le})`)}else r.copySourceFragment=e}}if(!t&&(e.hasAttribute(p.attrName(null,"data",!0))&&(r.dataAttrName=p.attrName(null,"data",!0)),e.hasAttribute(p.attrName(null,"form",!0)))){const D=j.read(e,p.attrName(null,"form",!0));if(D){const O=j.query(D,p.attrName(null,"form",!0));O!==null?r.formFragment=I.getFormFragment(F.get(O)):m.error("Haori",`Form element not found: ${D} (${p.attrName(null,"fetch-form",!0)})`)}else r.formFragment=I.getFormFragment(e)}(!t||t==="poll")&&p.readNoMessageDeclarations(e,r,t??"fetch");const ae=t?p.attrName(t,"fetch-state"):p.attrName(null,"state",!0);if(e.hasAttribute(ae)){const D=j.read(e,ae),O=[];D?(j.queryAll(D,ae).forEach(Q=>{const ye=F.get(Q);ye&&O.push(ye)}),O.length===0&&m.error("Haori",`Element not found: ${D} (${ae})`)):O.push(e),O.length>0&&(r.fetchStateFragments=O)}const Y=t?p.attrName(t,"store-clear"):p.attrName(null,"store-clear",!0);if(e.hasAttribute(Y)){const D=e.getRawAttribute(Y),O=D===null?"":D.trim();if(O==="")m.error("Haori",`ストレージキーが指定されていません (${Y})`);else{r.storeClearKey=O;const X=e.getRawAttribute(`${Y}-type`),Q=X===null?"session":X.trim();Q==="local"||Q==="session"?r.storeClearKind=Q:(m.warn("Haori",`${Y}-type は session または local を指定してください(session として扱います): ${Q}`),r.storeClearKind="session")}}return s&&!r.download&&(!r.bindFragments||r.bindFragments.length===0)&&(r.bindFragments=[e],r.defaultSelfBind=!0),r.download&&r.bindFragments&&r.bindFragments.length>0&&(m.warn("Haori",`${y} と同時にバインド先が指定されています(応答はファイルとして保存し、バインドは行いません)。`),r.bindFragments=null),p.recordRowWriteTargets(r),r}static recordRowWriteTargets(e){const t=new Map,r=[...e.bindFragments??[],...e.copyFragments??[]];for(const i of r){const n=i.getParent();!n||!n.hasAttribute(`${l.prefix}each`)||!n.hasAttribute(`${l.prefix}form-list`)||t.set(i,p.getRowFragments(n).includes(i)?n:null)}t.size>0&&(e.rowWriteTargets=t)}static isNamedInputFragment(e){const t=e.getTarget();return t instanceof HTMLInputElement||t instanceof HTMLSelectElement||t instanceof HTMLTextAreaElement?t.getAttribute("name")!==null||e.hasAttribute(`${l.prefix}form-name`):!1}static isElementFragment(e){if(typeof e!="object"||e===null)return!1;const t=e;return typeof t.getTarget=="function"&&typeof t.getChildElementFragments=="function"}static resolveAutoFetchSignature(e){return new p(e,null).resolveFetchSignature()}run(){return this.runWithResult().then(()=>{})}markReentrantBind(){this.reentrantBind=!0}runWithResult(){return this.execute()}async runWithOutcome(){return await this.execute()?"success":this.skipped?"skipped":"failure"}async execute(){const e=this.acquireExecutionLock();if(e===!1)return!1;try{if(Object.keys(this.options).length===0)return this.skipped=!0,!1;if(this.options.formFragment&&this.validate(this.options.formFragment)===!1)return!1;if(!this.options.formFragment&&this.options.targetFragment&&I.warnUnvalidatedCustomValidity(I.getFormFragment(this.options.targetFragment),`${l.prefix}${this.eventType??"fetch"}-form が解決できません`),!this.evaluateExecutionCondition())return this.skipped=!0,!1;if(this.options.runScript){const g=this.options.targetFragment?.getTarget()??null;try{const y=this.options.runScript.call(g,this.domEvent);y===!1&&this.domEvent&&this.domEvent.preventDefault(),y!=null&&typeof y.then=="function"&&await y}catch(y){m.error("Haori",`Run script execution error: ${y}`)}}if(!await this.confirm()||this.options.downloadFolder&&await this.prepareDownloadFolder()==="cancelled")return!1;this.options.resetBeforeFragments&&this.options.resetBeforeFragments.length>0&&(await Promise.all(this.options.resetBeforeFragments.map(g=>I.reset(g,this.operationSequence))),this.captureHistorySnapshots());const r=this.prepareFetchRequest();this.requestUserEditSequence=w.currentSequence();const i=r.payload;let n=r.url,s=r.options,a=!1,o=!1;if(this.options.beforeCallback){const g=this.options.beforeCallback(n||null,s||null);if(g!=null){if(g===!1||typeof g=="object"&&g.stop)return!1;typeof g=="object"&&(a="fetchUrl"in g,o="fetchOptions"in g,n=a?g.fetchUrl:n,s=o?g.fetchOptions:s)}}const c=Object.keys(i).length>0;if(n){const g=(s?.method||"GET").toUpperCase(),A=!a&&o&&r.transportMode==="query-get"&&qt(s)&&!Ve(g)?r.baseUrl??n:n,E=Wt(A,s);n=E.url;const T={...E.options},k=E.normalized?E.requestedMethod:r.requestedMethod,H=E.effectiveMethod,N=r.transportMode==="query-get"||E.normalized,K=E.queryString??r.queryString;if(N&&m.info("Haori demo fetch normalization",{runtime:l.runtime,requestedMethod:k,effectiveMethod:H,transportMode:"query-get",url:n,payload:c?i:void 0,queryString:K}),this.options.targetFragment&&n){const Z=performance.now(),ee={runtime:l.runtime,requestedMethod:k,effectiveMethod:H,transportMode:N?"query-get":"http",...N?{queryString:K}:{}};return B.fetchStart(this.options.targetFragment.getTarget(),n,T,c?i:void 0,ee),await this.injectFetchState("loading"),await p.invokeFetch(n,T).then(L=>this.handleFetchResult(L,n||void 0,Z)).catch(async L=>{throw n&&B.fetchError(this.options.targetFragment.getTarget(),n,L),await this.injectFetchState("error",null,L instanceof Error?L.message:String(L)),await this.runErrorActions(null),L})}return await fetch(n,T).then(Z=>this.handleFetchResult(Z,n||void 0))}if((!this.options.bindFragments||this.options.bindFragments.length===0)&&this.options.formFragment&&c){const g=this.options.formFragment,y=g.getTarget(),A=new Set;e&&e.appliedDisabledAttribute&&this.options.targetFragment&&A.add(this.options.targetFragment);const E=g.getRawBindingData(),T=qe(i),k=g.getAttribute(`${l.prefix}form-arg`);let H;if(k){H={...E??{}};const N=String(k),K=I.resolveAncestorArgOwner(g,N);H[N]=I.mergeCollectedValues((K?K.value:H[N])??null,T)}else H=I.mergeCollectedValues(E,T,I.ancestorBaseResolver(g));await $.setBindingData(y,H,{skipFragments:A,kind:"nonSupply",sequence:this.operationSequence,editedPaths:I.collectEditedPaths(g,this.operationSequence,k?String(k):"",T)})}this.suppressEmptyReplaceBind=!c&&!this.options.formFragment&&(this.eventType==="change"||this.eventType==="input"),this.twoWayCommitBind=this.eventType==="change"||this.eventType==="input";const u=c?qe(i):{},d=new Response(JSON.stringify(u),{headers:{"Content-Type":"application/json"}});return await this.handleFetchResult(d)}finally{this.releaseExecutionLock(e)}}acquireExecutionLock(){if(this.eventType!=="click"||!this.options.targetFragment)return null;const e=this.options.targetFragment,t=e.getTarget();if(p.RUNNING_CLICK_TARGETS.has(t)||t.matches(":disabled")||t.hasAttribute("disabled")||t.hasAttribute(Ue))return!1;const r=t.hasAttribute(`${l.prefix}click-no-disabled`);return p.RUNNING_CLICK_TARGETS.add(t),t.setAttribute(Ue,""),r||t.setAttribute("disabled",""),{target:t,fragment:e,appliedDisabledAttribute:!r}}static findDisabledDeclaration(e){const t=`${l.prefix}attr-disabled`,r=e.getRawAttribute(t);if(r!==null)return{name:t,value:r};const i=e.getRawAttribute("disabled");return i!==null&&i.includes("{{")?{name:"disabled",value:i}:null}releaseExecutionLock(e){if(!e)return;const t=e.target;if(p.RUNNING_CLICK_TARGETS.delete(t),t.removeAttribute(Ue),!e.appliedDisabledAttribute)return;const r=p.findDisabledDeclaration(e.fragment);if(r===null){t.removeAttribute("disabled");return}$.setAttribute(t,r.name,r.value).catch(i=>{m.error("Haori",`ロックの解除で ${r.name} を適用し直せませんでした: ${i}`)})}static forgetDownloadFolder(){Te=null}async prepareDownloadFolder(){if(Te)return this.downloadFolder=Te,"ready";const e=globalThis.showDirectoryPicker;if(typeof e!="function")return m.info("Haori","この環境では保存先のフォルダを選ばせられないため、今までどおり保存します。"),"fallback";try{const t=await e.call(globalThis,{mode:"readwrite"});return Te=t,this.downloadFolder=t,"ready"}catch(t){return t?.name==="AbortError"?"cancelled":(m.info("Haori",`保存先のフォルダを選ばせられなかったため、今までどおり保存します: ${t}`),"fallback")}}async readResponseBody(e){const t=e.headers.get("Content-Type")??"",r=e.body;if(!r||typeof r.getReader!="function")try{const s=await e.blob();return this.downloadReceivedBytes=s.size,this.dropTotalBytesIfExceeded(),await this.injectFetchState("loading"),s}catch(s){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${s}`),null}const i=[];return await this.pumpResponseBody(r,s=>{i.push(new Blob([s]))})?new Blob(i,t!==""?{type:t}:void 0):null}async pumpResponseBody(e,t){await this.injectFetchState("loading");let r=Date.now();const i=e.getReader();try{for(;;){const{done:n,value:s}=await i.read();if(n)break;await t(s),this.downloadReceivedBytes+=s.byteLength,this.dropTotalBytesIfExceeded();const a=Date.now();a-r>=Ot&&(r=a,await this.injectFetchState("loading"))}}catch(n){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${n}`),!1}return!0}dropTotalBytesIfExceeded(){this.downloadTotalBytes!==null&&this.downloadReceivedBytes>this.downloadTotalBytes&&(this.downloadTotalBytes=null)}static resolveDownloadTotalBytes(e){const t=e.headers.get("Content-Encoding");if(t!==null){const s=t.trim().toLowerCase();if(s!==""&&s!=="identity")return null}const r=e.headers.get("Content-Length");if(r===null)return null;const i=r.trim();if(i==="")return null;const n=Number(i);return!Number.isSafeInteger(n)||n<0?null:n}async saveResponseToFolder(e,t,r){const i=t.body;if(!i||typeof i.getReader!="function")return"fallback";const n=p.resolveDownloadFileName(t,this.options.downloadFileName??null,r??this.options.fetchUrl??null);let s=!0;try{await e.getFileHandle(n)}catch(c){if(c?.name==="NotFoundError")s=!1;else return m.info("Haori",`保存先のフォルダを確かめられなかったため、今までどおり保存します: ${c}`),"fallback"}if(s&&!await he().confirm(`${n} は既にあります。上書きしますか?`))return"cancelled";let a;try{a=await(await e.getFileHandle(n,{create:!0})).createWritable()}catch(c){return m.info("Haori",`保存先のファイルを作れなかったため、今までどおり保存します: ${c}`),"fallback"}if(await this.pumpResponseBody(i,c=>a.write(c)))try{return await a.close(),"saved"}catch(c){m.error("Haori",`ファイルを書き終えられませんでした: ${c}`)}try{await a.abort()}catch(c){m.error("Haori",`書きかけを取り消せませんでした: ${c}`)}if(!s)try{await e.removeEntry(n)}catch(c){m.error("Haori",`作りかけのファイルを取り除けませんでした: ${c}`)}return"failed"}async saveResponseAsFile(e,t){if(this.downloadTotalBytes=p.resolveDownloadTotalBytes(e),this.downloadFolder){const a=await this.saveResponseToFolder(this.downloadFolder,e,t);if(a!=="fallback")return a;this.downloadFolder=null,Te=null}const r=await this.readResponseBody(e);if(r===null)return"failed";const i=p.resolveDownloadFileName(e,this.options.downloadFileName??null,t??this.options.fetchUrl??null);if(typeof URL>"u"||typeof URL.createObjectURL!="function")return m.error("Haori","この環境では Blob の URL を生成できないため、ファイルを保存できません。"),"failed";const n=URL.createObjectURL(r),s=document.createElement("a");return s.href=n,s.download=i,document.body.appendChild(s),s.click(),s.remove(),setTimeout(()=>URL.revokeObjectURL(n),0),"saved"}async showDownloadFailure(){const e=this.options.formFragment??(this.options.targetFragment?I.getFormFragment(this.options.targetFragment)||this.options.targetFragment:null),t=e?e.getTarget():document.body,r=he();await r.clearMessages(t),await r.addErrorMessage(t,gt)}static resolveDownloadFileName(e,t,r){const n=[p.readContentDispositionFileName(e.headers.get("Content-Disposition")),t,p.readUrlFileName(r)];for(const s of n){const a=p.sanitizeFileName(s);if(a!==null)return a}return"download"}static readContentDispositionFileName(e){if(!e)return null;const t=/filename\*\s*=\s*([^;]+)/i.exec(e);if(t){const n=t[1].trim(),s=n.split("'"),a=s.length>=3?s.slice(2).join("'"):n;try{return decodeURIComponent(a)}catch(o){m.warn("Haori",`Content-Disposition を解釈できません: ${o}`)}}const r=/filename\s*=\s*"((?:[^"\\]|\\.)*)"/i.exec(e);if(r)return r[1].replace(/\\(.)/g,"$1");const i=/filename\s*=\s*([^;]+)/i.exec(e);return i?i[1].trim():null}static readUrlFileName(e){if(!e)return null;const r=e.split("#")[0].split("?")[0].split("/"),i=r[r.length-1];return i===""?null:i}static sanitizeFileName(e){if(e===null)return null;const t=e.replace(/[\u0000-\u001f\u007f/\\]/g,"").trim();return t===""?null:t}async handleFetchResult(e,t,r){const i=he();if(!e.ok){if(ht(e.status))return!1;this.options.targetFragment&&t&&B.fetchError(this.options.targetFragment.getTarget(),t,new Error(`${e.status} ${e.statusText}`),e.status,r);const A=this.selectErrorActions(e.status),E=A?.bind===!0,T=await this.handleFetchError(E?e.clone():e,A?.noMessage!==!0&&!E);return E&&await this.bindResult(e).catch(k=>{m.error("Haori","Failed to bind the error response:",k)}),await this.injectFetchState("error",e.status,e.statusText||null,T),await this.runErrorActions(e.status),!1}if(this.options.targetFragment&&t&&r&&B.fetchEnd(this.options.targetFragment.getTarget(),t,e.status,r),this.options.afterCallback){const A=this.options.afterCallback(e);if(A!=null){if(A===!1||typeof A=="object"&&A.stop)return!1;typeof A=="object"&&"response"in A&&(e="response"in A?A.response:e)}}if(this.options.download){const A=await this.saveResponseAsFile(e,t);if(A==="cancelled")return await this.injectFetchState("success",e.status,null),!1;if(A==="failed")return await this.showDownloadFailure(),await this.injectFetchState("error",e.status,gt),!1}const n=[];n.push(this.bindResult(e)),n.push(this.adjust()),n.push(this.addRow()),n.push(this.removeRow()),n.push(this.movePrevRow()),n.push(this.moveNextRow()),await Promise.all(n),await this.injectFetchState("success",e.status,null),this.options.resetFragments&&this.options.resetFragments.length>0&&await Promise.all(this.options.resetFragments.map(A=>I.reset(A,this.operationSequence))),await this.copy();const s=[];this.options.refetchFragments&&this.options.refetchFragments.length>0&&this.options.refetchFragments.forEach(A=>{s.push(new p(A,null).run())});const a=await this.clickTargets(this.options.clickFragments,this.options.clickAwait===!0,"click-await");if(!a&&this.options.openFragments&&this.options.openFragments.length>0&&this.options.openFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.openDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),!a&&this.options.closeFragments&&this.options.closeFragments.length>0&&this.options.closeFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.closeDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),await Promise.all(s),a)return!1;const o=p.unescapeNewlines(p.normalizeAttributeText(this.resolveLateAttribute("dialog",this.options.dialogMessage)));o&&await i.dialog(o);const c=p.normalizeAttributeText(this.resolveLateAttribute("toast",this.options.toastMessage));if(c){const A=p.toToastLevel(this.resolveLateAttribute("toast-level",this.options.toastLevel));await i.toast(c,A??"info")}this.clearStore(),this.pushHistory();const u=this.resolveLateAttribute("scroll",this.options.scrollTarget);u&&j.query(u,p.attrName(this.eventType,"scroll"),document)?.scrollIntoView({behavior:"smooth",block:"nearest"});const d=this.resolveLateAttribute("redirect",this.options.redirectUrl),g=this.resolveLateAttribute("redirect-replace",this.options.redirectReplaceUrl);d&&g&&m.warn("Haori",`${p.attrName(this.eventType,"redirect")} と ${p.attrName(this.eventType,"redirect-replace")} の両方が指定されています。履歴を置き換える方を採用します。`);const y=g||d;if(y){let A=y;const E=this.resolveLateAttribute("redirect-return-param",this.options.redirectReturnParam);if(E){const k=new URLSearchParams(window.location.search).get(E);if(k!==null){const H=k.trim();pt.isSafeLocalPath(H)?A=H:m.warn("Haori",`戻り先パスが安全なローカルパスではないため、既定の遷移先へフォールバックします: ${k}`)}}g?window.location.replace(A):window.location.href=A}return!0}clearStore(){const e=this.options.storeClearKey;e&&Re.clear(e,this.options.storeClearKind??"session")}async clickTargets(e,t,r){if(!e||e.length===0)return!1;for(const i of e){await $.evaluateAll(i);const n=i.getTarget();if(t&&p.takeClickOutcome(n),typeof n.click=="function"?n.click():n.dispatchEvent(new MouseEvent("click",{bubbles:!0,cancelable:!0})),!t)continue;const s=p.takeClickOutcome(n);if(s===null){m.warn("Haori",`${l.prefix}${this.eventType??"fetch"}-${r} はこの対象の完了を待てません(手続きが同期に起動していません)。`);continue}if(await s==="failure")return!0}return!1}async runErrorActions(e){const t=this.selectErrorActions(e);if(!t||await this.clickTargets(t.clickFragments,t.clickAwait,`${t.key}-click-await`))return;const i=he(),n=[];t.closeFragments?.forEach(a=>{const o=a.getTarget();o instanceof HTMLElement?n.push(i.closeDialog(o)):m.error("Haori","Element is not an HTML element: ",o)}),await Promise.all(n);const s=p.normalizeAttributeText(this.resolveLateAttribute(`${t.key}-toast`,t.toastMessage));if(s){const a=p.toToastLevel(this.resolveLateAttribute(`${t.key}-toast-level`,t.toastLevel));await i.toast(s,a??"info")}}selectErrorActions(e){const t=e===null?void 0:this.options.errorStatusActions?.get(e);return t||(this.appliesErrorActions(e)?{key:"error",clickFragments:this.options.errorClickFragments??null,clickAwait:this.options.errorClickAwait===!0,closeFragments:this.options.errorCloseFragments??null,toastMessage:this.options.errorToastMessage??null,toastLevel:this.options.errorToastLevel??null,noMessage:this.options.errorNoMessage===!0,bind:this.options.errorBind===!0}:null)}appliesErrorActions(e){const t=this.options.errorStatuses;return t===void 0||e!==null&&t.includes(e)}resolveLateAttribute(e,t){const r=t??null,i=this.options.lateAttributes?.get(e)??null,n=this.options.targetFragment??null;if(!i||!n||!n.hasAttribute(i.attributeName))return r;const s=n.getAttributeEvaluation(i.attributeName);return s===null?r:s.hasUnresolvedReference&&!i.hasUnresolvedReference?(q.isEnabled()&&m.warn("Haori",`${i.attributeName} の参照が手続きの途中で解決できなくなったため、手続き開始時の値を使います`),r):s.value??null}pushHistory(){const e=this.resolveLateAttribute("history",this.options.historyUrl),t=e!=null,r=this.resolveHistoryDataValues(),i=this.resolveHistoryFormValues(),n=r!=null,s=i!=null;if(!(!t&&!n&&!s))try{const a=t?e:window.location.pathname,o=new URL(a,window.location.href);if(o.origin!==window.location.origin){const u="history.pushState: cross-origin URL is not allowed: "+o.toString();m.error("Haori",u);return}const c=u=>{for(const[d,g]of Object.entries(u))g!=null&&(Array.isArray(g)?(o.searchParams.delete(d),g.forEach(y=>o.searchParams.append(d,String(y)))):typeof g=="object"?o.searchParams.set(d,JSON.stringify(g)):o.searchParams.set(d,String(g)))};n&&c(r),s&&c(i),history.pushState({[Lt]:!0},"",o.toString()),$.refreshUrlParams()}catch(a){m.error("Haori",`history.pushState failed: ${a}`)}}async handleFetchError(e,t){let r=null;this.options.formFragment?r=this.options.formFragment:this.options.targetFragment&&(r=I.getFormFragment(this.options.targetFragment)||this.options.targetFragment);const i=r?r.getTarget():document.body;await he().clearMessages(i);const n=async u=>{const d=r?r.getTarget():document.body;await he().addErrorMessage(d,u)},s=()=>{if(!this.options.scrollOnError)return;const u=r?r.getTarget():document.body;(u.getAttribute("data-message-level")==="error"?u:u.parentElement?.getAttribute("data-message-level")==="error"?u.parentElement:u.querySelector('[data-message-level="error"]'))?.scrollIntoView({behavior:"smooth",block:"nearest"})},a=async u=>{if(t){u.length===0&&await n(`${e.status} ${e.statusText}`);for(const d of u)d.key&&r?await I.addErrorMessage(r,d.key,d.message):await n(d.message);s()}return u.length===0?null:u.map(d=>d.message).join(`
|
|
23
|
+
`)}catch(G){m.error("Haori",`Invalid after script: ${G}`)}}if(e.hasAttribute(p.attrName(t,"dialog"))&&(r.dialogMessage=p.unescapeNewlines(p.readLateAttribute(e,r,"dialog",p.attrName(t,"dialog")))),e.hasAttribute(p.attrName(t,"toast"))&&(r.toastMessage=p.readLateAttribute(e,r,"toast",p.attrName(t,"toast")),r.toastLevel=p.readToastLevel(e,r,"toast-level",p.attrName(t,"toast-level"))),t!=="poll"){const W=p.attrName(t,"error-toast");e.hasAttribute(W)&&(r.errorToastMessage=p.readLateAttribute(e,r,"error-toast",W),r.errorToastLevel=p.readToastLevel(e,r,"error-toast-level",p.attrName(t,"error-toast-level")));const G=p.attrName(t,"error-status");e.hasAttribute(G)&&(r.errorStatuses=p.parseErrorStatuses(e.getRawAttribute(G),G)),r.errorNoMessage=e.hasAttribute(p.attrName(t,"error-no-message")),r.errorBind=e.hasAttribute(p.attrName(t,"error-bind"))}const D=p.attrName(t,"redirect"),O=p.attrName(t,"redirect-replace"),X=e.hasAttribute(D),Q=e.hasAttribute(O);if(X&&(r.redirectUrl=p.readLateAttribute(e,r,"redirect",D)),Q&&(r.redirectReplaceUrl=p.readLateAttribute(e,r,"redirect-replace",O)),X||Q){const W=p.attrName(t,"redirect-return-param");e.hasAttribute(W)&&(r.redirectReturnParam=p.readLateAttribute(e,r,"redirect-return-param",W))}if(e.hasAttribute(p.attrName(t,"scroll-error"))&&(r.scrollOnError=!0),e.hasAttribute(p.attrName(t,"scroll"))&&(r.scrollTarget=p.readLateAttribute(e,r,"scroll",p.attrName(t,"scroll"))),e.hasAttribute(p.attrName(t,"history"))&&(r.historyUrl=p.readLateAttribute(e,r,"history",p.attrName(t,"history"))),e.hasAttribute(p.attrName(t,"history-data"))&&(r.historyDataAttrName=p.attrName(t,"history-data")),e.hasAttribute(p.attrName(t,"history-form"))){const W=j.read(e,p.attrName(t,"history-form"));if(W){const G=j.query(W,p.attrName(t,"history-form"));G!==null?r.historyFormFragment=I.getFormFragment(F.get(G)):m.error("Haori",`Form element not found: ${W} (${p.attrName(t,"history-form")})`)}else r.historyFormFragment=I.getFormFragment(e)}["reset-before","reset","refetch","click","copy","open","close","error-click","error-close"].forEach(W=>{if(W.startsWith("error-")&&t==="poll")return;const G=p.attrName(t,W);if(!e.hasAttribute(G))return;const J=p.resolveSelectorTargets(e,G,W);if(J.length>0)switch(W){case"reset-before":r.resetBeforeFragments=J;break;case"reset":r.resetFragments=J;break;case"refetch":r.refetchFragments=J;break;case"click":r.clickFragments=J,r.clickAwait=e.hasAttribute(`${G}-await`);break;case"copy":r.copyFragments=J;break;case"open":r.openFragments=J;break;case"close":r.closeFragments=J;break;case"error-click":r.errorClickFragments=J,r.errorClickAwait=e.hasAttribute(`${G}-await`);break;case"error-close":r.errorCloseFragments=J;break}}),t!=="poll"&&(r.errorStatusActions=p.readErrorStatusActions(e,r,t));const le=p.attrName(t,"copy-source");if(e.hasAttribute(le)){const W=j.read(e,le);if(W){const G=j.query(W,le);if(G!==null){const J=F.get(G);J?r.copySourceFragment=J:m.error("Haori",`Element is not managed by Haori: ${W} (${le})`)}else m.error("Haori",`Element not found: ${W} (${le})`)}else r.copySourceFragment=e}}if(!t&&(e.hasAttribute(p.attrName(null,"data",!0))&&(r.dataAttrName=p.attrName(null,"data",!0)),e.hasAttribute(p.attrName(null,"form",!0)))){const D=j.read(e,p.attrName(null,"form",!0));if(D){const O=j.query(D,p.attrName(null,"form",!0));O!==null?r.formFragment=I.getFormFragment(F.get(O)):m.error("Haori",`Form element not found: ${D} (${p.attrName(null,"fetch-form",!0)})`)}else r.formFragment=I.getFormFragment(e)}(!t||t==="poll")&&p.readNoMessageDeclarations(e,r,t??"fetch");const ae=t?p.attrName(t,"fetch-state"):p.attrName(null,"state",!0);if(e.hasAttribute(ae)){const D=j.read(e,ae),O=[];D?(j.queryAll(D,ae).forEach(Q=>{const ye=F.get(Q);ye&&O.push(ye)}),O.length===0&&m.error("Haori",`Element not found: ${D} (${ae})`)):O.push(e),O.length>0&&(r.fetchStateFragments=O)}const Y=t?p.attrName(t,"store-clear"):p.attrName(null,"store-clear",!0);if(e.hasAttribute(Y)){const D=e.getRawAttribute(Y),O=D===null?"":D.trim();if(O==="")m.error("Haori",`ストレージキーが指定されていません (${Y})`);else{r.storeClearKey=O;const X=e.getRawAttribute(`${Y}-type`),Q=X===null?"session":X.trim();Q==="local"||Q==="session"?r.storeClearKind=Q:(m.warn("Haori",`${Y}-type は session または local を指定してください(session として扱います): ${Q}`),r.storeClearKind="session")}}return s&&!r.download&&(!r.bindFragments||r.bindFragments.length===0)&&(r.bindFragments=[e],r.defaultSelfBind=!0),r.download&&r.bindFragments&&r.bindFragments.length>0&&(m.warn("Haori",`${y} と同時にバインド先が指定されています(応答はファイルとして保存し、バインドは行いません)。`),r.bindFragments=null),p.recordRowWriteTargets(r),r}static recordRowWriteTargets(e){const t=new Map,r=[...e.bindFragments??[],...e.copyFragments??[]];for(const i of r){const n=i.getParent();!n||!n.hasAttribute(`${l.prefix}each`)||!n.hasAttribute(`${l.prefix}form-list`)||t.set(i,p.getRowFragments(n).includes(i)?n:null)}t.size>0&&(e.rowWriteTargets=t)}static isNamedInputFragment(e){const t=e.getTarget();return t instanceof HTMLInputElement||t instanceof HTMLSelectElement||t instanceof HTMLTextAreaElement?t.getAttribute("name")!==null||e.hasAttribute(`${l.prefix}form-name`):!1}static isElementFragment(e){if(typeof e!="object"||e===null)return!1;const t=e;return typeof t.getTarget=="function"&&typeof t.getChildElementFragments=="function"}static resolveAutoFetchSignature(e){return new p(e,null).resolveFetchSignature()}run(){return this.runWithResult().then(()=>{})}markReentrantBind(){this.reentrantBind=!0}runWithResult(){return this.execute()}async runWithOutcome(){return await this.execute()?"success":this.skipped?"skipped":"failure"}async execute(){const e=this.acquireExecutionLock();if(e===!1)return!1;try{if(Object.keys(this.options).length===0)return this.skipped=!0,!1;if(this.options.formFragment&&this.validate(this.options.formFragment)===!1)return!1;if(!this.options.formFragment&&this.options.targetFragment&&I.warnUnvalidatedCustomValidity(I.getFormFragment(this.options.targetFragment),`${l.prefix}${this.eventType??"fetch"}-form が解決できません`),!this.evaluateExecutionCondition())return this.skipped=!0,!1;if(this.options.runScript){const g=this.options.targetFragment?.getTarget()??null;try{const y=this.options.runScript.call(g,this.domEvent);y===!1&&this.domEvent&&this.domEvent.preventDefault(),y!=null&&typeof y.then=="function"&&await y}catch(y){m.error("Haori",`Run script execution error: ${y}`)}}if(!await this.confirm()||this.options.downloadFolder&&await this.prepareDownloadFolder()==="cancelled")return!1;this.options.resetBeforeFragments&&this.options.resetBeforeFragments.length>0&&(await Promise.all(this.options.resetBeforeFragments.map(g=>I.reset(g,this.operationSequence))),this.captureHistorySnapshots());const r=this.prepareFetchRequest();this.requestUserEditSequence=w.currentSequence();const i=r.payload;let n=r.url,s=r.options,a=!1,o=!1;if(this.options.beforeCallback){const g=this.options.beforeCallback(n||null,s||null);if(g!=null){if(g===!1||typeof g=="object"&&g.stop)return!1;typeof g=="object"&&(a="fetchUrl"in g,o="fetchOptions"in g,n=a?g.fetchUrl:n,s=o?g.fetchOptions:s)}}const c=Object.keys(i).length>0;if(n){const g=(s?.method||"GET").toUpperCase(),A=!a&&o&&r.transportMode==="query-get"&&qt(s)&&!Ve(g)?r.baseUrl??n:n,E=Wt(A,s);n=E.url;const T={...E.options},k=E.normalized?E.requestedMethod:r.requestedMethod,H=E.effectiveMethod,N=r.transportMode==="query-get"||E.normalized,K=E.queryString??r.queryString;if(N&&m.info("Haori demo fetch normalization",{runtime:l.runtime,requestedMethod:k,effectiveMethod:H,transportMode:"query-get",url:n,payload:c?i:void 0,queryString:K}),this.options.targetFragment&&n){const Z=performance.now(),ee={runtime:l.runtime,requestedMethod:k,effectiveMethod:H,transportMode:N?"query-get":"http",...N?{queryString:K}:{}};return B.fetchStart(this.options.targetFragment.getTarget(),n,T,c?i:void 0,ee),await this.injectFetchState("loading"),await p.invokeFetch(n,T).then(L=>this.handleFetchResult(L,n||void 0,Z)).catch(async L=>{throw n&&B.fetchError(this.options.targetFragment.getTarget(),n,L),await this.injectFetchState("error",null,L instanceof Error?L.message:String(L)),await this.runErrorActions(null),L})}return await fetch(n,T).then(Z=>this.handleFetchResult(Z,n||void 0))}if((!this.options.bindFragments||this.options.bindFragments.length===0)&&this.options.formFragment&&c){const g=this.options.formFragment,y=g.getTarget(),A=new Set;e&&e.appliedDisabledAttribute&&this.options.targetFragment&&A.add(this.options.targetFragment);const E=g.getRawBindingData(),T=qe(i),k=g.getAttribute(`${l.prefix}form-arg`);let H;if(k){H={...E??{}};const N=String(k),K=I.resolveAncestorArgOwner(g,N);H[N]=I.mergeCollectedValues((K?K.value:H[N])??null,T)}else H=I.mergeCollectedValues(E,T,I.ancestorBaseResolver(g));await $.setBindingData(y,H,{skipFragments:A,kind:"nonSupply",sequence:this.operationSequence,editedPaths:I.collectEditedPaths(g,this.operationSequence,k?String(k):"",T)})}this.suppressEmptyReplaceBind=!c&&!this.options.formFragment&&(this.eventType==="change"||this.eventType==="input"),this.twoWayCommitBind=this.eventType==="change"||this.eventType==="input";const u=c?qe(i):{},d=new Response(JSON.stringify(u),{headers:{"Content-Type":"application/json"}});return await this.handleFetchResult(d)}finally{this.releaseExecutionLock(e)}}acquireExecutionLock(){if(this.eventType!=="click"||!this.options.targetFragment)return null;const e=this.options.targetFragment,t=e.getTarget();if(p.RUNNING_CLICK_TARGETS.has(t)||t.matches(":disabled")||t.hasAttribute("disabled")||t.hasAttribute(Ue))return!1;const r=t.hasAttribute(`${l.prefix}click-no-disabled`);return p.RUNNING_CLICK_TARGETS.add(t),t.setAttribute(Ue,""),r||t.setAttribute("disabled",""),{target:t,fragment:e,appliedDisabledAttribute:!r}}static findDisabledDeclaration(e){const t=`${l.prefix}attr-disabled`,r=e.getRawAttribute(t);if(r!==null)return{name:t,value:r};const i=e.getRawAttribute("disabled");return i!==null&&i.includes("{{")?{name:"disabled",value:i}:null}releaseExecutionLock(e){if(!e)return;const t=e.target;if(p.RUNNING_CLICK_TARGETS.delete(t),t.removeAttribute(Ue),!e.appliedDisabledAttribute)return;const r=p.findDisabledDeclaration(e.fragment);if(r===null){t.removeAttribute("disabled");return}$.setAttribute(t,r.name,r.value).catch(i=>{m.error("Haori",`ロックの解除で ${r.name} を適用し直せませんでした: ${i}`)})}static forgetDownloadFolder(){Te=null}async prepareDownloadFolder(){if(Te)return this.downloadFolder=Te,"ready";const e=globalThis.showDirectoryPicker;if(typeof e!="function")return m.info("Haori","この環境では保存先のフォルダを選ばせられないため、今までどおり保存します。"),"fallback";try{const t=await e.call(globalThis,{mode:"readwrite"});return Te=t,this.downloadFolder=t,"ready"}catch(t){return t?.name==="AbortError"?"cancelled":(m.info("Haori",`保存先のフォルダを選ばせられなかったため、今までどおり保存します: ${t}`),"fallback")}}async readResponseBody(e){const t=e.headers.get("Content-Type")??"",r=e.body;if(!r||typeof r.getReader!="function")try{const s=await e.blob();return this.downloadReceivedBytes=s.size,this.dropTotalBytesIfExceeded(),await this.injectFetchState("loading"),s}catch(s){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${s}`),null}const i=[];return await this.pumpResponseBody(r,s=>{i.push(new Blob([s]))})?new Blob(i,t!==""?{type:t}:void 0):null}async pumpResponseBody(e,t){await this.injectFetchState("loading");let r=Date.now();const i=e.getReader();try{for(;;){const{done:n,value:s}=await i.read();if(n)break;await t(s),this.downloadReceivedBytes+=s.byteLength,this.dropTotalBytesIfExceeded();const a=Date.now();a-r>=Ot&&(r=a,await this.injectFetchState("loading"))}}catch(n){return m.error("Haori",`応答をファイルとして読み取れませんでした: ${n}`),!1}return!0}dropTotalBytesIfExceeded(){this.downloadTotalBytes!==null&&this.downloadReceivedBytes>this.downloadTotalBytes&&(this.downloadTotalBytes=null)}static resolveDownloadTotalBytes(e){const t=e.headers.get("Content-Encoding");if(t!==null){const s=t.trim().toLowerCase();if(s!==""&&s!=="identity")return null}const r=e.headers.get("Content-Length");if(r===null)return null;const i=r.trim();if(i==="")return null;const n=Number(i);return!Number.isSafeInteger(n)||n<0?null:n}async saveResponseToFolder(e,t,r){const i=t.body;if(!i||typeof i.getReader!="function")return"fallback";const n=p.resolveDownloadFileName(t,this.options.downloadFileName??null,r??this.options.fetchUrl??null);let s=!0;try{await e.getFileHandle(n)}catch(c){if(c?.name==="NotFoundError")s=!1;else return m.info("Haori",`保存先のフォルダを確かめられなかったため、今までどおり保存します: ${c}`),"fallback"}if(s&&!await he().confirm(`${n} は既にあります。上書きしますか?`))return"cancelled";let a;try{a=await(await e.getFileHandle(n,{create:!0})).createWritable()}catch(c){return m.info("Haori",`保存先のファイルを作れなかったため、今までどおり保存します: ${c}`),"fallback"}if(await this.pumpResponseBody(i,c=>a.write(c)))try{return await a.close(),"saved"}catch(c){m.error("Haori",`ファイルを書き終えられませんでした: ${c}`)}try{await a.abort()}catch(c){m.error("Haori",`書きかけを取り消せませんでした: ${c}`)}if(!s)try{await e.removeEntry(n)}catch(c){m.error("Haori",`作りかけのファイルを取り除けませんでした: ${c}`)}return"failed"}async saveResponseAsFile(e,t){if(this.downloadTotalBytes=p.resolveDownloadTotalBytes(e),this.downloadFolder){const a=await this.saveResponseToFolder(this.downloadFolder,e,t);if(a!=="fallback")return a;this.downloadFolder=null,Te=null}const r=await this.readResponseBody(e);if(r===null)return"failed";const i=p.resolveDownloadFileName(e,this.options.downloadFileName??null,t??this.options.fetchUrl??null);if(typeof URL>"u"||typeof URL.createObjectURL!="function")return m.error("Haori","この環境では Blob の URL を生成できないため、ファイルを保存できません。"),"failed";const n=URL.createObjectURL(r),s=document.createElement("a");return s.href=n,s.download=i,document.body.appendChild(s),s.click(),s.remove(),setTimeout(()=>URL.revokeObjectURL(n),0),"saved"}async showDownloadFailure(e){const t=this.options.formFragment??(this.options.targetFragment?I.getFormFragment(this.options.targetFragment)||this.options.targetFragment:null),r=t?t.getTarget():document.body,i=he();await i.clearMessages(r),e&&await i.addErrorMessage(r,gt)}static resolveDownloadFileName(e,t,r){const n=[p.readContentDispositionFileName(e.headers.get("Content-Disposition")),t,p.readUrlFileName(r)];for(const s of n){const a=p.sanitizeFileName(s);if(a!==null)return a}return"download"}static readContentDispositionFileName(e){if(!e)return null;const t=/filename\*\s*=\s*([^;]+)/i.exec(e);if(t){const n=t[1].trim(),s=n.split("'"),a=s.length>=3?s.slice(2).join("'"):n;try{return decodeURIComponent(a)}catch(o){m.warn("Haori",`Content-Disposition を解釈できません: ${o}`)}}const r=/filename\s*=\s*"((?:[^"\\]|\\.)*)"/i.exec(e);if(r)return r[1].replace(/\\(.)/g,"$1");const i=/filename\s*=\s*([^;]+)/i.exec(e);return i?i[1].trim():null}static readUrlFileName(e){if(!e)return null;const r=e.split("#")[0].split("?")[0].split("/"),i=r[r.length-1];return i===""?null:i}static sanitizeFileName(e){if(e===null)return null;const t=e.replace(/[\u0000-\u001f\u007f/\\]/g,"").trim();return t===""?null:t}async handleFetchResult(e,t,r){const i=he();if(!e.ok){if(ht(e.status))return!1;this.options.targetFragment&&t&&B.fetchError(this.options.targetFragment.getTarget(),t,new Error(`${e.status} ${e.statusText}`),e.status,r);const A=this.selectErrorActions(e.status),E=A?.bind===!0,T=await this.handleFetchError(E?e.clone():e,A?.noMessage!==!0&&!E);return E&&await this.bindResult(e).catch(k=>{m.error("Haori","Failed to bind the error response:",k)}),await this.injectFetchState("error",e.status,e.statusText||null,T),await this.runErrorActions(e.status),!1}if(this.options.targetFragment&&t&&r&&B.fetchEnd(this.options.targetFragment.getTarget(),t,e.status,r),this.options.afterCallback){const A=this.options.afterCallback(e);if(A!=null){if(A===!1||typeof A=="object"&&A.stop)return!1;typeof A=="object"&&"response"in A&&(e="response"in A?A.response:e)}}if(this.options.download){const A=await this.saveResponseAsFile(e,t);if(A==="cancelled")return await this.injectFetchState("success",e.status,null),!1;if(A==="failed"){const E=this.selectErrorActions(null);return await this.showDownloadFailure(E?.noMessage!==!0),await this.injectFetchState("error",e.status,gt),await this.runErrorActions(null),!1}}const n=[];n.push(this.bindResult(e)),n.push(this.adjust()),n.push(this.addRow()),n.push(this.removeRow()),n.push(this.movePrevRow()),n.push(this.moveNextRow()),await Promise.all(n),await this.injectFetchState("success",e.status,null),this.options.resetFragments&&this.options.resetFragments.length>0&&await Promise.all(this.options.resetFragments.map(A=>I.reset(A,this.operationSequence))),await this.copy();const s=[];this.options.refetchFragments&&this.options.refetchFragments.length>0&&this.options.refetchFragments.forEach(A=>{s.push(new p(A,null).run())});const a=await this.clickTargets(this.options.clickFragments,this.options.clickAwait===!0,"click-await");if(!a&&this.options.openFragments&&this.options.openFragments.length>0&&this.options.openFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.openDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),!a&&this.options.closeFragments&&this.options.closeFragments.length>0&&this.options.closeFragments.forEach(A=>{const E=A.getTarget();E instanceof HTMLElement?s.push(i.closeDialog(E)):m.error("Haori","Element is not an HTML element: ",E)}),await Promise.all(s),a)return!1;const o=p.unescapeNewlines(p.normalizeAttributeText(this.resolveLateAttribute("dialog",this.options.dialogMessage)));o&&await i.dialog(o);const c=p.normalizeAttributeText(this.resolveLateAttribute("toast",this.options.toastMessage));if(c){const A=p.toToastLevel(this.resolveLateAttribute("toast-level",this.options.toastLevel));await i.toast(c,A??"info")}this.clearStore(),this.pushHistory();const u=this.resolveLateAttribute("scroll",this.options.scrollTarget);u&&j.query(u,p.attrName(this.eventType,"scroll"),document)?.scrollIntoView({behavior:"smooth",block:"nearest"});const d=this.resolveLateAttribute("redirect",this.options.redirectUrl),g=this.resolveLateAttribute("redirect-replace",this.options.redirectReplaceUrl);d&&g&&m.warn("Haori",`${p.attrName(this.eventType,"redirect")} と ${p.attrName(this.eventType,"redirect-replace")} の両方が指定されています。履歴を置き換える方を採用します。`);const y=g||d;if(y){let A=y;const E=this.resolveLateAttribute("redirect-return-param",this.options.redirectReturnParam);if(E){const k=new URLSearchParams(window.location.search).get(E);if(k!==null){const H=k.trim();pt.isSafeLocalPath(H)?A=H:m.warn("Haori",`戻り先パスが安全なローカルパスではないため、既定の遷移先へフォールバックします: ${k}`)}}g?window.location.replace(A):window.location.href=A}return!0}clearStore(){const e=this.options.storeClearKey;e&&Re.clear(e,this.options.storeClearKind??"session")}async clickTargets(e,t,r){if(!e||e.length===0)return!1;for(const i of e){await $.evaluateAll(i);const n=i.getTarget();if(t&&p.takeClickOutcome(n),typeof n.click=="function"?n.click():n.dispatchEvent(new MouseEvent("click",{bubbles:!0,cancelable:!0})),!t)continue;const s=p.takeClickOutcome(n);if(s===null){m.warn("Haori",`${l.prefix}${this.eventType??"fetch"}-${r} はこの対象の完了を待てません(手続きが同期に起動していません)。`);continue}if(await s==="failure")return!0}return!1}async runErrorActions(e){const t=this.selectErrorActions(e);if(!t||await this.clickTargets(t.clickFragments,t.clickAwait,`${t.key}-click-await`))return;const i=he(),n=[];t.closeFragments?.forEach(a=>{const o=a.getTarget();o instanceof HTMLElement?n.push(i.closeDialog(o)):m.error("Haori","Element is not an HTML element: ",o)}),await Promise.all(n);const s=p.normalizeAttributeText(this.resolveLateAttribute(`${t.key}-toast`,t.toastMessage));if(s){const a=p.toToastLevel(this.resolveLateAttribute(`${t.key}-toast-level`,t.toastLevel));await i.toast(s,a??"info")}}selectErrorActions(e){const t=e===null?void 0:this.options.errorStatusActions?.get(e);return t||(this.appliesErrorActions(e)?{key:"error",clickFragments:this.options.errorClickFragments??null,clickAwait:this.options.errorClickAwait===!0,closeFragments:this.options.errorCloseFragments??null,toastMessage:this.options.errorToastMessage??null,toastLevel:this.options.errorToastLevel??null,noMessage:this.options.errorNoMessage===!0,bind:this.options.errorBind===!0}:null)}appliesErrorActions(e){const t=this.options.errorStatuses;return t===void 0||e!==null&&t.includes(e)}resolveLateAttribute(e,t){const r=t??null,i=this.options.lateAttributes?.get(e)??null,n=this.options.targetFragment??null;if(!i||!n||!n.hasAttribute(i.attributeName))return r;const s=n.getAttributeEvaluation(i.attributeName);return s===null?r:s.hasUnresolvedReference&&!i.hasUnresolvedReference?(q.isEnabled()&&m.warn("Haori",`${i.attributeName} の参照が手続きの途中で解決できなくなったため、手続き開始時の値を使います`),r):s.value??null}pushHistory(){const e=this.resolveLateAttribute("history",this.options.historyUrl),t=e!=null,r=this.resolveHistoryDataValues(),i=this.resolveHistoryFormValues(),n=r!=null,s=i!=null;if(!(!t&&!n&&!s))try{const a=t?e:window.location.pathname,o=new URL(a,window.location.href);if(o.origin!==window.location.origin){const u="history.pushState: cross-origin URL is not allowed: "+o.toString();m.error("Haori",u);return}const c=u=>{for(const[d,g]of Object.entries(u))g!=null&&(Array.isArray(g)?(o.searchParams.delete(d),g.forEach(y=>o.searchParams.append(d,String(y)))):typeof g=="object"?o.searchParams.set(d,JSON.stringify(g)):o.searchParams.set(d,String(g)))};n&&c(r),s&&c(i),history.pushState({[Lt]:!0},"",o.toString()),$.refreshUrlParams()}catch(a){m.error("Haori",`history.pushState failed: ${a}`)}}async handleFetchError(e,t){let r=null;this.options.formFragment?r=this.options.formFragment:this.options.targetFragment&&(r=I.getFormFragment(this.options.targetFragment)||this.options.targetFragment);const i=r?r.getTarget():document.body;await he().clearMessages(i);const n=async u=>{const d=r?r.getTarget():document.body;await he().addErrorMessage(d,u)},s=()=>{if(!this.options.scrollOnError)return;const u=r?r.getTarget():document.body;(u.getAttribute("data-message-level")==="error"?u:u.parentElement?.getAttribute("data-message-level")==="error"?u.parentElement:u.querySelector('[data-message-level="error"]'))?.scrollIntoView({behavior:"smooth",block:"nearest"})},a=async u=>{if(t){u.length===0&&await n(`${e.status} ${e.statusText}`);for(const d of u)d.key&&r?await I.addErrorMessage(r,d.key,d.message):await n(d.message);s()}return u.length===0?null:u.map(d=>d.message).join(`
|
|
24
24
|
`)};if((e.headers.get("Content-Type")||"").includes("application/json"))try{const u=await e.json(),d=[];if(Array.isArray(u)){const g=new Map,y=[];for(const A of u)if(A&&typeof A=="object"&&!Array.isArray(A)){const E=A.key,T=A.message,k=typeof E=="string"&&E.length>0?E:null,H=typeof T=="string"?T:T!=null?String(T):"";if(H.length===0)continue;if(k!==null){const N=g.get(k)??[];N.push(H),g.set(k,N)}else y.push(H)}else typeof A=="string"&&A.length>0&&y.push(A);for(const[A,E]of g)d.push({key:A,message:E.join(`
|
|
25
25
|
`)});for(const A of y)d.push({message:A})}else if(u&&typeof u=="object"){if(typeof u.message=="string"&&d.push({message:u.message}),Array.isArray(u.messages))for(const g of u.messages)typeof g=="string"&&d.push({message:g});if(u.errors&&typeof u.errors=="object")for(const[g,y]of Object.entries(u.errors))Array.isArray(y)?d.push({key:g,message:y.join(`
|
|
26
26
|
`)}):typeof y=="string"?d.push({key:g,message:y}):y!=null&&d.push({key:g,message:String(y)});if(d.length===0)for(const[g,y]of Object.entries(u))g==="message"||g==="messages"||g==="errors"||(Array.isArray(y)?d.push({key:g,message:y.join(`
|
|
@@ -29,5 +29,5 @@ ${r}
|
|
|
29
29
|
);`)}catch{try{i=new Function(`"use strict";
|
|
30
30
|
${r}
|
|
31
31
|
`)}catch(n){m.error("[Haori]",`Invalid each-rendered-run script: ${n}`)}}if(i)try{i.call(e)}catch(n){m.error("[Haori]",`each-rendered-run execution error: ${n}`)}}static runEachRenderedChange(e){const t=`${l.prefix}each-rendered-change`,r=e.getTarget();if(!r.hasAttribute(t))return;const i=String(r.getAttribute(t)??"").trim().toLowerCase();let n=!1;if(i==="always"?n=!0:i!==""&&i!=="once"&&(f.EACH_RENDERED_CHANGE_WARNED.has(r)||(f.EACH_RENDERED_CHANGE_WARNED.add(r),m.warn("[Haori]",`Invalid ${t} value: "${i}". Use "once" (default) or "always".`))),f.countEachRenderedRows(e)!==0){if(!n){if(f.EACH_RENDERED_CHANGE_FIRED.has(r))return;f.EACH_RENDERED_CHANGE_FIRED.add(r)}try{r.dispatchEvent(new Event("change",{bubbles:!0}))}catch(s){m.error("[Haori]",`each-rendered-change dispatch error: ${s}`)}}}static countEachRenderedRows(e){let t=0;for(const r of e.getChildElementFragments())r.getTarget().hasAttribute(`${l.prefix}row`)&&(t+=1);return t}static performEachUpdate(e){const t=f.resolveEachItems(e);if(t===null)return Promise.reject(new Error("Invalid each attribute."));let r=e.getTemplate();const i=e.getAttribute(`${l.prefix}each-key`),n=f.createBindingSignature({key:i?String(i):null,items:t});if(r===null){let s=!1;if(e.getChildren().forEach(a=>{if(!s&&a instanceof w){if(a.hasAttribute(`${l.prefix}each-before`)||a.hasAttribute(`${l.prefix}each-after`))return;r=a.clone(),f.markFreshInitializationSkippable(r),e.setTemplate(r),s=!0,e.removeChild(a);const o=a.getTarget();o.parentNode&&o.parentNode.removeChild(o),a.setMounted(!1)}}),s&&f.warnExtraEachChildren(e),!s){const a=e.getTarget();Array.from(a.children).filter(c=>!c.hasAttribute(`${l.prefix}each-before`)&&!c.hasAttribute(`${l.prefix}each-after`)).forEach(c=>{if(!s){const d=F.get(c);d instanceof w&&(r=d.clone(),f.markFreshInitializationSkippable(r),e.setTemplate(r),s=!0)}const u=F.get(c);u instanceof w&&e.getChildren().includes(u)&&(e.removeChild(u),u.setMounted(!1)),c.parentNode&&c.parentNode.removeChild(c)})}return this.updateDiff(e,t).then(()=>{e.setEachInputSignature(n)})}return e.getEachInputSignature()===n?f.reevaluateEachRows(e):this.updateDiff(e,t).then(()=>{e.setEachInputSignature(n)})}static reevaluateEachRows(e){if(f.isRowLocalEachTemplate(e))return Promise.resolve();const t=e.getChildElementFragments().filter(r=>!r.hasAttribute(`${l.prefix}each-before`)&&!r.hasAttribute(`${l.prefix}each-after`));return t.length===0?Promise.resolve():Promise.all(t.map(r=>f.evaluateAll(r))).then(()=>{})}static resolveEachItems(e){const t=e.getAttributeEvaluation(`${l.prefix}each`),r=t?.value;return t?.hasUnresolvedReference||r===!1||r===null||r===void 0?[]:Array.isArray(r)?r:(m.error("[Haori]","Invalid each attribute:",r),null)}static canSkipUnchangedNestedEach(e){if(!e.hasAttribute(`${l.prefix}each`)||e.getEachInputSignature()===null)return!1;const t=e.getParent();if(t?.closestByAttribute(`${l.prefix}derive`)||t?.closestByAttribute(`${l.prefix}derive-name`)||t?.closestByAttribute(`${l.prefix}if`)||t?.closestByAttribute(`${l.prefix}fetch`)||t?.closestByAttribute(`${l.prefix}import`)||f.hasNonEachDynamicElementState(e)||!f.isRowLocalEachTemplate(e)||f.hasEachFixedChildren(e))return!1;const r=f.resolveEachItems(e);if(r===null)return!1;const i=e.getAttribute(`${l.prefix}each-key`),n=f.createBindingSignature({key:i?String(i):null,items:r});return e.getEachInputSignature()===n}static isRowLocalEachTemplate(e){const t=e.getRowLocalTemplate();if(t!==null)return t;const r=e.getTemplate(),i=e.getAttribute(`${l.prefix}each-arg`);if(r===null||!i)return e.setRowLocalTemplate(!1),!1;const n=new Set([String(i)]),s=e.getAttribute(`${l.prefix}each-index`);s&&n.add(String(s));const a=f.isRowLocalSubtree(r,n);return e.setRowLocalTemplate(a),a}static isRowLocalSubtree(e,t){for(const i of e.getAttributeNames()){const n=e.getRawAttribute(i),s=typeof n=="string"?n:"";if(s.includes("{{")){if(!f.areExpressionsRowLocal(f.extractInterpolations(s),t))return!1;continue}if(!i.startsWith(l.prefix))continue;const a=i.slice(l.prefix.length);if(f.ROW_LOCAL_EXPRESSION_ATTRIBUTES.has(a)){if(!f.areExpressionsRowLocal([s],t))return!1;continue}if(f.ROW_LOCAL_STATIC_ATTRIBUTES.has(a))continue;const o=a.indexOf("-");if(!(o!==-1&&f.ROW_LOCAL_ROW_OPERATIONS.has(a.slice(o+1))))return!1}let r=t;if(e.hasAttribute(`${l.prefix}each`)){const i=e.getRawAttribute(`${l.prefix}each-arg`);if(typeof i!="string"||i==="")return!1;const n=new Set(t);n.add(i);const s=e.getRawAttribute(`${l.prefix}each-index`);typeof s=="string"&&s!==""&&n.add(s),r=n}for(const i of e.getChildren())if(i instanceof w){if(!f.isRowLocalSubtree(i,r))return!1}else if(i instanceof ne){const n=i.getRawText();if(n.includes("{{")&&!f.areExpressionsRowLocal(f.extractInterpolations(n),t))return!1}return!0}static areExpressionsRowLocal(e,t){for(const r of e){const i=r.trim();if(i==="")continue;const n=re.getFreeIdentifiers(i);if(n.length===0||n.some(s=>!t.has(s)))return!1}return!0}static extractInterpolations(e){const t=[],r=/\{\{([\s\S]*?)\}\}/g;let i=r.exec(e);for(;i!==null;)t.push(i[1]),i=r.exec(e);return t}static canSkipStableDerivedSubtree(e){return!e.hasAttribute(`${l.prefix}derive`)||e.hasAttribute(`${l.prefix}if`)||e.hasAttribute(`${l.prefix}each`)||e.hasAttribute(`${l.prefix}fetch`)||e.hasAttribute(`${l.prefix}import`)?!1:!f.hasDisallowedDerivedSubtreeDescendant(e)}static hasDisallowedDerivedSubtreeDescendant(e){return e.getChildren().some(t=>t instanceof w?t.hasAttribute(`${l.prefix}derive`)||t.hasAttribute(`${l.prefix}derive-name`)||t.hasAttribute(`${l.prefix}fetch`)||t.hasAttribute(`${l.prefix}import`)?!0:f.hasDisallowedDerivedSubtreeDescendant(t):!1)}static createDescendantBindingSignature(e,t){return f.recordDerivedSubtreeSignatureComputation(e,t),f.createBindingSignature(e.getDescendantBindingData())}static createDeriveInputSignature(e,t,r){const i=typeof r=="string"?r.trim():"";return!t||i===""?null:f.createBindingSignature({expression:t,name:i,scope:e.getBindingData()})}static refreshUrlParams(){const e=`${l.prefix}url-param`,r=Array.from(document.querySelectorAll(`[${e}]`)).map(i=>{const n=F.peek(i);return n instanceof w?f.setAttribute(i,e,n.getRawAttribute(e)??""):Promise.resolve()});return Promise.all(r).then(()=>{}).catch(i=>{m.error("Haori",`${e} を読み直せませんでした: ${i}`)})}static invalidateDerivedSubtreeSignatures(e){for(let r=e.getParent();r!==null;r=r.getParent())r.setDeriveSubtreeSignature(null);const t=r=>{r.setDeriveSubtreeSignature(null),r.getChildren().forEach(i=>{i instanceof w&&t(i)})};t(e)}static refreshDerivedSubtreeSignature(e){if(!f.canSkipStableDerivedSubtree(e)){e.setDeriveSubtreeSignature(null),f.logDerivedSubtreeProfileSnapshot(e,"skip-ineligible");return}e.setDeriveSubtreeSignature(f.createDescendantBindingSignature(e,"refresh")),f.logDerivedSubtreeProfileSnapshot(e,"refresh")}static getOrCreateDerivedSubtreeProfile(e){if(!q.isEnabled()||!e.hasAttribute(`${l.prefix}derive`))return null;const t=f.DERIVE_SUBTREE_PROFILES.get(e);if(t)return t;const r={hostId:f.createDerivedSubtreeHostId(e),signatureComputeTotal:0,signatureComputeFromEvaluateAll:0,signatureComputeFromRefresh:0,skipHitCount:0,skipMissCount:0,skipIneligibleCount:0};return f.DERIVE_SUBTREE_PROFILES.set(e,r),r}static resolveElementId(e){return e.getAttribute("id")??""}static createDerivedSubtreeHostId(e){const t=[];let r=e;for(;r;){const i=r.getTarget();if(!(i instanceof HTMLElement))break;let n=i.tagName.toLowerCase();const s=f.resolveElementId(i).trim();if(s!==""){n+=`#${s}`,t.unshift(n);break}const a=r.getRawAttribute(`${l.prefix}derive-name`);typeof a=="string"&&a.trim()!==""&&(n+=`[${l.prefix}derive-name="${a.trim()}"]`);const o=r.getParent();if(o){const c=o.getChildren().filter(u=>u instanceof w).findIndex(u=>u===r);n+=`:nth-child(${c+1})`}t.unshift(n),r=o}return t.join(" > ")}static recordDerivedSubtreeSignatureComputation(e,t){const r=f.getOrCreateDerivedSubtreeProfile(e);if(r!==null){if(r.signatureComputeTotal+=1,t==="refresh"){r.signatureComputeFromRefresh+=1;return}r.signatureComputeFromEvaluateAll+=1}}static logDerivedSubtreeProfileSnapshot(e,t){const r=f.getOrCreateDerivedSubtreeProfile(e);r!==null&&(t==="skip-hit"?r.skipHitCount+=1:t==="skip-miss"?r.skipMissCount+=1:t==="skip-ineligible"&&(r.skipIneligibleCount+=1),m.info("[Haori][derive-profile]",{reason:t,hostId:r.hostId,signatureComputeTotal:r.signatureComputeTotal,signatureComputeFromEvaluateAll:r.signatureComputeFromEvaluateAll,signatureComputeFromRefresh:r.signatureComputeFromRefresh,skipHitCount:r.skipHitCount,skipMissCount:r.skipMissCount,skipIneligibleCount:r.skipIneligibleCount}))}static hasNonEachDynamicElementState(e){const t=new Set([`${l.prefix}each`,`${l.prefix}each-key`,`${l.prefix}each-arg`,`${l.prefix}each-index`]);return e.getAttributeNames().some(i=>{if(t.has(i))return!1;if(i.startsWith(`${l.prefix}attr-`)||i.startsWith(l.prefix))return!0;const n=e.getRawAttribute(i);return typeof n=="string"&&n.includes("{{")})?!0:e.getChildren().some(i=>i instanceof ne&&i.hasDynamicContent())}static markFreshInitializationSkippable(e){const t=e.getAttributeNames().some(n=>f.isFreshInitializationDynamicAttribute(e,n)),r=e.getChildren().some(n=>n instanceof w?!f.markFreshInitializationSkippable(n):n instanceof ne?n.hasDynamicContent():!1),i=!t&&!r;return e.setFreshInitializationSkippable(i),i}static isFreshInitializationDynamicAttribute(e,t){if(t.startsWith(`${l.prefix}attr-`)||t.startsWith(l.prefix))return!0;const r=e.getRawAttribute(t);return typeof r=="string"&&r.includes("{{")}static updateDiff(e,t){const r=e.getTemplate();if(r===null)return m.error("[Haori]",`Template is not set for ${l.prefix}each="${e.getRawAttribute(`${l.prefix}each`)}". The container needs one element child as the row template.`,e.getTarget()),Promise.resolve();let i=e.getAttribute(`${l.prefix}each-index`);i&&(i=String(i));const n=e.getAttribute(`${l.prefix}each-key`),s=e.getAttribute(`${l.prefix}each-arg`),a=t.map((N,K)=>f.createListKey(N,n?String(n):null,K)),o=new Set(a),c=new Map;a.forEach(N=>{c.set(N,(c.get(N)??0)+1)}),n&&o.size!==a.length&&f.warnDuplicateEachKey(String(n));const u=[];let d=e.getChildren().filter(N=>N instanceof w).filter(N=>!N.hasAttribute(`${l.prefix}each-before`)&&!N.hasAttribute(`${l.prefix}each-after`));const g=d.map(N=>N.getListKey()),y=new Set;d=d.filter((N,K)=>{const Z=String(N.getListKey()),ee=c.get(Z)??0;if(ee===0){y.add(N);const L=N.getListKey();return L!==null&&B.rowRemove(N.getTarget(),L,K),u.push(N.remove()),!1}return c.set(Z,ee-1),!0});const A=d.map(N=>N.getListKey()),E=new Map;d.forEach(N=>{const K=N.getListKey();if(K===null)return;const Z=E.get(K);Z?Z.push(N):E.set(K,[N])});const T=e.getChildElementFragments().filter(N=>!y.has(N)),k=T.filter(N=>N.hasAttribute(`${l.prefix}each-before`)).length;let H=Promise.resolve();return a.forEach((N,K)=>{const Z=t[K],ee=K;let L;const ae=E.get(N)?.shift();if(ae){L=ae;const Y=k+K;H=H.then(()=>f.updateRowFragment(L,Z,i,ee,s?String(s):null,N).then(D=>f.repositionEachRow(e,L,T,Y).then(O=>{if(O!==null&&B.rowMove(L.getTarget(),N,O-k,K),!(!D&&f.isRowLocalEachTemplate(e)))return f.evaluateAll(L).then(()=>f.applyRowFormValues(e,L,Z))})))}else{L=r.clone();const Y=k+K;H=H.then(()=>f.updateRowFragment(L,Z,i,ee,s?String(s):null,N).then(()=>{const D=T[Y]??null;return e.insertBefore(L,D).then(()=>{T.splice(Y,0,L)}).then(()=>f.initializeFreshEachRow(L)).then(()=>f.applyRowFormValues(e,L,Z)).then(()=>{B.rowAdd(L.getTarget(),N,ee,Z)})}))}}),Promise.all(u).then(()=>H).then(()=>{const N=a.filter(Y=>Y!==null),K=A.filter(Y=>Y!==null),Z=new Set(K),ee=N.filter(Y=>!Z.has(Y)),ae=g.filter(Y=>Y!==null).filter(Y=>!o.has(Y));B.eachUpdate(e.getTarget(),ee,ae,N)})}static warnExtraEachChildren(e){const t=e.getChildren().filter(r=>r instanceof w).filter(r=>!r.hasAttribute(`${l.prefix}each-before`)&&!r.hasAttribute(`${l.prefix}each-after`));t.length!==0&&m.warn("[Haori]",`${l.prefix}each="${e.getRawAttribute(`${l.prefix}each`)}" のコンテナに要素の子が 2 つ以上あります。テンプレートになるのは最初の子だけで、残り ${t.length} 個は行に入りません(${t.map(r=>r.getTarget().tagName.toLowerCase()).join(", ")})。行の中身は 1 つの要素で包んでください。`,e.getTarget())}static warnDuplicateEachKey(e){!q.isEnabled()||f.WARNED_DUPLICATE_EACH_KEYS.has(e)||(f.WARNED_DUPLICATE_EACH_KEYS.add(e),m.warn("[Haori]",`${l.prefix}each-key="${e}" の値が配列の中で重複しています。行は出現順で対応付けますが、キーによる行の識別はできません。`))}static repositionEachRow(e,t,r,i){const n=r.indexOf(t);if(n===-1||n===i)return Promise.resolve(null);r.splice(n,1);const s=r[i]??null;return r.splice(i,0,t),e.insertBefore(t,s).then(()=>n)}static applyRowFormValues(e,t,r){return!e.hasAttribute(`${l.prefix}form-list`)||!I.isCollectedListFromEachSource(e)||typeof r!="object"||r===null||Array.isArray(r)?Promise.resolve():I.syncRowValues(t,r)}static createListKey(e,t,r){let i;if(typeof e=="object"&&e!==null)if(t){const n=e[t];n==null?i=`__index_${r}`:typeof n=="object"?i=JSON.stringify(n):i=String(n)}else i=`__index_${r}`;else i=String(e);return i}static updateRowFragment(e,t,r,i,n,s){let a;if(typeof t=="object"&&t!==null)a=n?{[n]:{...t}}:{...t};else if(n)a={[n]:t};else return m.error("[Haori]",`Primitive value requires '${l.prefix}each-arg' attribute: ${t}`),Promise.resolve(!1);r&&(a[r]=i);const o=a,c=f.createBindingSignature({listKey:s,bindingData:o});return e.getListKey()===s&&e.getRenderSignature()===c?Promise.resolve(!1):(e.setListKey(s),e.setRenderSignature(c),e.setBindingData(o),e.setAttribute(`${l.prefix}row`,s).then(()=>!0))}static needsScheduledEvaluateAll(e){const t=[e];for(;t.length>0;){const r=t.pop();if(r.getChildElementFragments().forEach(i=>{t.push(i)}),r!==e&&!r.isMounted()&&f.hasMountSensitiveAttribute(r))return!0}return!1}static hasMountSensitiveAttribute(e){return["fetch","import"].some(t=>e.hasAttribute(`${l.prefix}${t}`))}static createBindingSignature(e,t=new WeakMap,r={value:0}){if(e===null)return"null";if(e===void 0)return"undefined";if(typeof e=="string")return JSON.stringify(e);if(typeof e=="number"||typeof e=="boolean"||typeof e=="bigint")return String(e);if(typeof e=="function")return`[Function:${e.name||"anonymous"}]`;if(typeof e=="symbol")return e.toString();if(e instanceof Date)return`[Date:${e.toISOString()}]`;if(typeof File<"u"&&e instanceof File)return`[File:${e.name}:${e.size}:${e.lastModified}:${e.type}]`;if(typeof Blob<"u"&&e instanceof Blob)return`[Blob:${e.size}:${e.type}]`;if(Array.isArray(e)){if(t.has(e))return`[Circular:${t.get(e)}]`;const i=`array-${r.value}`;return r.value+=1,t.set(e,i),`[${e.map(n=>f.createBindingSignature(n,t,r)).join(",")}]`}if(typeof e=="object"){if(t.has(e))return`[Circular:${t.get(e)}]`;const i=`object-${r.value}`;r.value+=1,t.set(e,i);const n=e;return`{${Object.keys(n).sort().map(s=>`${JSON.stringify(s)}:${f.createBindingSignature(n[s],t,r)}`).join(",")}}`}return String(e)}static scheduleEvaluateAll(e){setTimeout(()=>{f.evaluateAll(e)},100)}};f.ATTRIBUTE_ALIAS_SUFFIX="attr-",f.PRIORITY_ATTRIBUTE_SUFFIXES=["bind","store","url-param","derive-name","derive","if","each"],f.DEFERRED_ATTRIBUTE_SUFFIXES=["fetch"],f.initialValueRestores=new Set,f.EVALUATE_ALL_EXCLUDED_ATTRIBUTE_SUFFIXES=["bind","derive","derive-name","if","each","fetch","import","url-param","store","validity","validity-message"],f.ATTRIBUTE_PLACEHOLDER_REGEX=/\{\{\{[\s\S]+?\}\}\}|\{\{[\s\S]+?\}\}/,f.ROW_LOCAL_EXPRESSION_ATTRIBUTES=new Set(["each","if","derive"]),f.ROW_LOCAL_STATIC_ATTRIBUTES=new Set(["each-arg","each-key","each-index","each-before","each-after","derive-name","row","form","form-arg","form-list","form-object","form-detach","value-type","store","store-params","store-arg","store-type","enhance","enhance-new"]),f.ROW_LOCAL_ROW_OPERATIONS=new Set(["row-add","row-remove","row-prev","row-next"]),f.REACTIVE_FETCH_STATES=new WeakMap,f.REACTIVE_IMPORT_STATES=new WeakMap,f.DERIVE_SUBTREE_PROFILES=new WeakMap,f.EACH_UPDATE_STATES=new WeakMap,f.EACH_RENDERED_CHANGE_FIRED=new WeakSet,f.EACH_RENDERED_CHANGE_WARNED=new WeakSet,f.WARNED_DUPLICATE_EACH_KEYS=new Set,f.ABSENT_PATH=Symbol("absent");let $=f;const we=class we{constructor(e=document){this.customEventHandlers=new Map,this.builtinListenersAdded=!1,this.deferred=!1,this.deferredProcedures=[],this.onClick=t=>this.delegate(t,"click"),this.onReset=t=>{if(t.defaultPrevented||I.isResettingInternally())return;const r=t.target;r instanceof HTMLElement&&setTimeout(()=>te.refreshSubtree(r),0)},this.onChange=t=>this.delegate(t,"change"),this.onInput=t=>this.delegate(t,"input"),this.onLoadCapture=t=>this.delegate(t,"load"),this.onWindowLoad=()=>{if(this.deferred){this.deferredProcedures.push(()=>this.runWindowLoadProcedure());return}this.runWindowLoadProcedure()},this.onPopstate=t=>{const r=t.state;if(!r||r[we.HISTORY_STATE_KEY]!==!0){$.refreshUrlParams();return}location.reload()},this.root=e}runWindowLoadProcedure(){const e=document.documentElement,t=F.get(e);t&&new se(t,"load").run()}start(){this.deferred=!1,this.addBuiltinListeners(),this.subscribeDeclaredCustomEvents(),this.observeCustomEventDeclarations()}startDeferred(){this.deferred=!0,this.addBuiltinListeners(),this.subscribeDeclaredCustomEvents()}release(){if(!this.deferred)return;this.deferred=!1,this.subscribeDeclaredCustomEvents(),this.observeCustomEventDeclarations();const e=this.deferredProcedures.splice(0);for(const t of e)try{t()}catch(r){m.error("[Haori]","Deferred event handling error:",r)}}addBuiltinListeners(){this.builtinListenersAdded||(this.builtinListenersAdded=!0,this.root.addEventListener("click",this.onClick),this.root.addEventListener("change",this.onChange),this.root.addEventListener("input",this.onInput),this.root.addEventListener("reset",this.onReset),this.root.addEventListener("load",this.onLoadCapture,!0),window.addEventListener("load",this.onWindowLoad,{once:!0}),window.addEventListener("popstate",this.onPopstate))}stop(){this.root.removeEventListener("click",this.onClick),this.root.removeEventListener("change",this.onChange),this.root.removeEventListener("input",this.onInput),this.root.removeEventListener("reset",this.onReset),this.root.removeEventListener("load",this.onLoadCapture,!0),window.removeEventListener("load",this.onWindowLoad),window.removeEventListener("popstate",this.onPopstate),this.builtinListenersAdded=!1,this.deferred=!1,this.deferredProcedures.length=0;for(const[e,t]of this.customEventHandlers)window.removeEventListener(e,t,!0);this.customEventHandlers.clear(),this.customEventObserver?.disconnect(),this.customEventObserver=void 0}get onAttributeName(){return`${l.prefix}on`}subscribeDeclaredCustomEvents(){this.root.querySelectorAll(`[${this.onAttributeName}]`).forEach(t=>this.subscribeCustomEvent(t.getAttribute(this.onAttributeName)))}subscribeCustomEvent(e){if(e===null||e==="")return;if(we.BUILTIN_EVENT_NAMES.has(e)){m.warn("[Haori]",`data-on="${e}" は組み込みイベントです。data-${e}-* を使用してください(data-on はカスタムイベント専用)。`);return}if(this.customEventHandlers.has(e))return;const t=r=>this.runCustomEventProcedures(e,r);this.customEventHandlers.set(e,t),window.addEventListener(e,t,!0)}runCustomEventProcedures(e,t){if(this.deferred){this.deferredProcedures.push(()=>this.runCustomEventProcedures(e,t));return}this.root.querySelectorAll(`[${this.onAttributeName}]`).forEach(i=>{if(i.getAttribute(this.onAttributeName)!==e)return;const n=F.get(i);n instanceof w&&this.isFromTarget(n,t)&&new se(n,"on",t).run().catch(s=>{m.error("[Haori]","Procedure execution error:",s)})})}isFromTarget(e,t){const r=`${this.onAttributeName}-target`;if(!e.hasAttribute(r))return!0;const i=j.read(e,r),n=t.target;return i===null||!(n instanceof Node)?!1:j.queryAll(i,r).some(s=>s.contains(n))}observeCustomEventDeclarations(){if(typeof MutationObserver>"u")return;const e=this.root instanceof Document?this.root:this.root.ownerDocument??document,t=this.root instanceof Document?e.body:this.root;t&&(this.customEventObserver=new MutationObserver(r=>{for(const i of r)i.addedNodes.forEach(n=>{n instanceof HTMLElement&&(n.hasAttribute(this.onAttributeName)&&this.subscribeCustomEvent(n.getAttribute(this.onAttributeName)),n.querySelectorAll(`[${this.onAttributeName}]`).forEach(s=>this.subscribeCustomEvent(s.getAttribute(this.onAttributeName))))})}),this.customEventObserver.observe(t,{childList:!0,subtree:!0}))}delegate(e,t){const r=this.getElementFromTarget(e.target,t);if(r){if(t==="input"){const i=`${l.prefix}input-`;if(!r.getAttributeNames().some(s=>s.startsWith(i))){this.recordUserEdit(r);return}}if(r.hasAttribute(`${l.prefix}${t}-prevent`)&&e.preventDefault(),this.deferred){this.deferredProcedures.push(()=>{r.isConnected&&this.runProcedureFor(r,t,e)});return}this.runProcedureFor(r,t,e)}}runProcedureFor(e,t,r){const i=F.get(e);if(!i)return;(t==="change"||t==="input")&&this.syncUserEdit(e,t==="change");const n=()=>{const s=new se(i,t,r).runWithOutcome().catch(a=>(m.error("[Haori]","Procedure execution error:",a),"failure"));if(t==="click"){se.recordClickOutcome(e,s);const a=r.target;a instanceof HTMLElement&&a!==e&&se.recordClickOutcome(a,s)}};if(t==="click"&&e.hasAttribute(`${l.prefix}click-defer`)){typeof requestAnimationFrame<"u"?requestAnimationFrame(()=>n()):setTimeout(n,0);return}n()}recordUserEdit(e){if(!(!(e instanceof HTMLInputElement)&&!(e instanceof HTMLSelectElement)&&!(e instanceof HTMLTextAreaElement))){if(this.deferred){this.deferredProcedures.push(()=>{e.isConnected&&this.markUserEditOnly(e)});return}this.markUserEditOnly(e)}}markUserEditOnly(e){const t=F.get(e);t instanceof w&&t.markUserEdit()}syncUserEdit(e,t){const r=F.get(e);if(r instanceof w&&(r.syncValue(),t?r.markUserEditOnChange():r.markUserEdit(),e instanceof HTMLInputElement&&e.type==="radio"&&e.name)){const i=document.getElementsByName(e.name);for(const n of Array.from(i)){if(n===e||!(n instanceof HTMLInputElement)||n.type!=="radio"||n.form!==e.form)continue;const s=F.get(n);s instanceof w&&(s.syncValue(),s.markUserEdit())}}}getElementFromTarget(e,t){if(!e)return null;if(e instanceof HTMLElement)return t==="click"?this.findClickableElement(e):e;if(e instanceof Node){const r=e.parentElement;return r?t==="click"?this.findClickableElement(r):r:null}return null}findClickableElement(e){const t=`${l.prefix}click-`,r=`${l.prefix}click-passive`;let i=e;for(;i;){if(i.getAttributeNames().some(s=>s.startsWith(t)&&s!==r))return i;if(i.hasAttribute(r))return null;i=i.parentElement}return null}};we.HISTORY_STATE_KEY="__haoriHistoryState__",we.BUILTIN_EVENT_NAMES=new Set(["click","change","input","load"]);let We=we;const V=class V{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(V.isHtmlElement(e)&&V.syncElement(e),e.querySelectorAll("*").forEach(t=>{V.syncElement(t)}))}static syncElement(e){const t=V.registrations.get(e),r=F.get(e);if(!r||!V.shouldObserve(r)){t&&(t.observer.disconnect(),V.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=V.resolveRoot(r),n=V.resolveRootMargin(r),s=V.resolveThreshold(r),a=r.hasAttribute(`${l.prefix}intersect-once`);if(t&&t.root===i&&t.rootMargin===n&&t.threshold===s&&t.once===a){t.fragment=r,V.runPendingIntersect(e,t);return}t&&(t.observer.disconnect(),V.registrations.delete(e));const o=new IntersectionObserver(c=>{const u=V.registrations.get(e);u&&c.forEach(d=>{if(u.intersecting=d.isIntersecting,!!d.isIntersecting){if(u.running||V.isDisabled(u.fragment)){u.pending=!0;return}V.runProcedure(e,u)}})},{root:i,rootMargin:n,threshold:s});o.observe(e),V.registrations.set(e,{fragment:r,observer:o,once:a,running:t?.running??!1,intersecting:!1,pending:!1,root:i,rootMargin:n,threshold:s})}static runProcedure(e,t){t.pending=!1,t.running=!0;let r=!1;new se(t.fragment,"intersect").runWithResult().then(i=>{r=i}).catch(i=>{m.error("[Haori]","Intersect procedure execution error:",i)}).finally(()=>{const i=V.registrations.get(e);if(i){if(i.running=!1,r&&i.once){i.observer.disconnect(),V.registrations.delete(e);return}V.runPendingIntersect(e,i)}})}static runPendingIntersect(e,t){!t.pending||!t.intersecting||t.running||V.isDisabled(t.fragment)||V.runProcedure(e,t)}static cleanupTree(e){if(V.isHtmlElement(e)){const t=V.registrations.get(e);t&&(t.observer.disconnect(),V.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=V.registrations.get(t);r&&(r.observer.disconnect(),V.registrations.delete(t))})}static disconnectAll(){V.registrations.forEach(e=>{e.observer.disconnect()}),V.registrations.clear()}static shouldObserve(e){return e.getAttributeNames().some(t=>{if(!t.startsWith(`${l.prefix}intersect-`))return!1;const r=t.slice(`${l.prefix}intersect-`.length);return!V.CONFIG_KEYS.has(r)})}static resolveRoot(e){const t=`${l.prefix}intersect-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=j.query(r,t,document);return V.isHtmlElement(i)?i:(m.error("[Haori]",`Intersect root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}intersect-root-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?"0px":String(r)}static resolveThreshold(e){const t=`${l.prefix}intersect-threshold`,r=e.getAttribute(t),i=typeof r=="number"?r:Number.parseFloat(String(r??0));return Number.isNaN(i)?0:Math.min(1,Math.max(0,i))}static isDisabled(e){const t=`${l.prefix}intersect-disabled`,r=e.getAttribute(t);if(r===null||r===!1)return!1;if(typeof r=="boolean")return r;const i=String(r).trim().toLowerCase();return i!==""&&i!=="false"&&i!=="0"}};V.CONFIG_KEYS=new Set(["root","root-margin","threshold","disabled","once"]),V.registrations=new Map;let Ae=V;const v=class v{static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(v.isHtmlElement(e)&&v.syncElement(e),e.querySelectorAll("*").forEach(t=>{v.syncElement(t)}))}static syncElement(e){const t=v.registrations.get(e);if(!t&&!v.hasPollAttribute(e))return;const r=F.get(e);if(!(r instanceof w)||!v.shouldObserve(r)){t&&v.teardown(e,t);return}const i=v.buildConfigKey(r);if(t){if(t.configKey===i){t.fragment=r;return}v.teardown(e,t)}v.startPolling(e,r,i)}static cleanupTree(e){if(v.isHtmlElement(e)){const t=v.registrations.get(e);t&&v.teardown(e,t)}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=v.registrations.get(t);r&&v.teardown(t,r)})}static disconnectAll(){v.registrations.forEach(e=>{v.clearTimers(e)}),v.registrations.clear(),v.visibilityListener&&typeof document<"u"&&document.removeEventListener("visibilitychange",v.visibilityListener),v.visibilityListener=null}static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static hasPollAttribute(e){const t=`${l.prefix}poll-`,r=e.attributes;for(let i=0;i<r.length;i+=1)if(r[i].name.startsWith(t))return!0;return!1}static shouldObserve(e){const t=`${l.prefix}poll-`;return e.getAttributeNames().some(r=>r.startsWith(t)?!v.CONFIG_KEYS.has(r.slice(t.length)):!1)}static buildConfigKey(e){const t=`${l.prefix}poll-`;return e.getAttributeNames().filter(r=>r.startsWith(t)).sort().map(r=>`${r}=${e.getRawAttribute(r)??""}`).join(`
|
|
32
|
-
`)}static startPolling(e,t,r){const i={fragment:t,configKey:r,intervalMs:v.resolveInterval(t),timeoutMs:v.resolveTimeout(t),errorLimit:v.resolveErrorLimit(t),startedAt:performance.now(),intervalTimerId:null,timeoutTimerId:null,fetching:!1,paused:!1,stopped:!1,timedOut:!1,stopReason:null,count:0,consecutiveErrors:0};v.registrations.set(e,i),v.ensureVisibilityListener(),i.timeoutMs!==null&&(i.timeoutTimerId=setTimeout(()=>{v.handleTimeout(e)},i.timeoutMs)),v.injectState(i),v.tick(e)}static async tick(e){const t=v.registrations.get(e);if(!t||t.stopped||t.fetching)return;if(t.intervalTimerId=null,!e.isConnected){await v.stop(e,t,"detached");return}const r=v.isHidden(e)||v.isDisabled(t.fragment);if(r!==t.paused&&(t.paused=r,await v.injectState(t)),r){v.schedule(e,t);return}if(v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}t.fetching=!0,t.count+=1;let i=!1;try{i=await new se(t.fragment,"poll").runWithResult()}catch(n){m.error("[Haori]","Poll procedure execution error:",n)}finally{t.fetching=!1}if(!(v.registrations.get(e)!==t||t.stopped)){if(i)t.consecutiveErrors=0;else if(t.consecutiveErrors+=1,t.errorLimit!==null&&t.consecutiveErrors>=t.errorLimit){await v.stop(e,t,"error");return}if(i&&v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}v.schedule(e,t)}}static schedule(e,t){t.stopped||t.intervalTimerId!==null||(t.intervalTimerId=setTimeout(()=>{v.tick(e)},t.intervalMs))}static async handleTimeout(e){const t=v.registrations.get(e);!t||t.stopped||(t.timeoutTimerId=null,t.timedOut=!0,e.isConnected&&B.pollTimeout(e,t.count,v.elapsed(t)),await v.stop(e,t,"timeout"))}static async stop(e,t,r){if(!t.stopped){if(t.stopped=!0,t.stopReason=r,t.paused=!1,v.clearTimers(t),r==="detached"){v.registrations.delete(e);return}await v.injectState(t),e.isConnected&&B.pollStop(e,r,t.count,v.elapsed(t))}}static teardown(e,t){v.clearTimers(t),v.registrations.delete(e)}static clearTimers(e){e.intervalTimerId!==null&&(clearTimeout(e.intervalTimerId),e.intervalTimerId=null),e.timeoutTimerId!==null&&(clearTimeout(e.timeoutTimerId),e.timeoutTimerId=null)}static elapsed(e){return Math.round(performance.now()-e.startedAt)}static ensureVisibilityListener(){if(v.visibilityListener||typeof document>"u")return;const e=()=>{document.visibilityState==="visible"&&Array.from(v.registrations.entries()).forEach(([t,r])=>{r.stopped||r.fetching||(r.intervalTimerId!==null&&(clearTimeout(r.intervalTimerId),r.intervalTimerId=null),v.tick(t))})};v.visibilityListener=e,document.addEventListener("visibilitychange",e)}static injectState(e){const t=v.resolveStateFragments(e);if(t.length===0)return Promise.resolve();const r={running:!e.stopped,paused:e.paused,stopped:e.stopped,timedOut:e.timedOut,stopReason:e.stopReason,count:e.count,elapsedMs:v.elapsed(e)};return Promise.all(t.map(i=>{const n=i.getTarget(),s={...i.getRawBindingData()??{},_poll:r};return $.setBindingData(n,s,{reflectToAttribute:!1,kind:"nonSupply",sequence:w.nextSequence()})})).then(()=>{})}static resolveStateFragments(e){const t=`${l.prefix}poll-state`,r=e.fragment;if(!r.hasAttribute(t))return[];const i=r.getAttribute(t);if(typeof i!="string"||i.trim()==="")return r.getTarget().isConnected?[r]:[];const n=j.queryAll(i,t,document);if(n.length===0)return m.error("[Haori]",`Poll state element not found: ${i}`),[];const s=[];return n.forEach(a=>{if(!a.isConnected)return;const o=F.get(a);o instanceof w&&s.push(o)}),s}static resolveInterval(e){const t=`${l.prefix}poll-interval`;if(!e.hasAttribute(t))return v.DEFAULT_INTERVAL_MS;const r=v.toNumber(e.getAttribute(t));return r===null?(m.warn("[Haori]",`${t} は数値で指定してください。既定値 ${v.DEFAULT_INTERVAL_MS}ms を使用します。`),v.DEFAULT_INTERVAL_MS):r<v.MIN_INTERVAL_MS?(m.warn("[Haori]",`${t} の下限は ${v.MIN_INTERVAL_MS}ms です。${r}ms は下限へ切り上げます。`),v.MIN_INTERVAL_MS):r}static resolveTimeout(e){const t=`${l.prefix}poll-timeout`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<=0?(m.warn("[Haori]",`${t} は正の数値で指定してください。無制限として扱います。`),null):r}static resolveErrorLimit(e){const t=`${l.prefix}poll-error-limit`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<1?(m.warn("[Haori]",`${t} は 1 以上の数値で指定してください。無制限として扱います。`),null):Math.floor(r)}static toNumber(e){if(typeof e=="number")return Number.isFinite(e)?e:null;if(typeof e!="string"||e.trim()==="")return null;const t=Number(e.trim());return Number.isFinite(t)?t:null}static isHidden(e){return e.closest(`[${l.prefix}if-false]`)!==null}static isDisabled(e){const t=`${l.prefix}poll-disabled`;return e.hasAttribute(t)?v.isTruthy(e.getAttribute(t)):!1}static isUntilSatisfied(e){const t=`${l.prefix}poll-until`;if(!e.hasAttribute(t))return!1;const r=e.getAttributeEvaluation(t);return r?r.hasUnresolvedReference?(m.warn("[Haori]",`${t} に未解決の参照が含まれています(停止条件は成立扱いにしません):`,e.getRawAttribute(t),e.getTarget()),!1):v.isTruthy(r.value):!1}static isTruthy(e){if(e==null||e===!1)return!1;if(typeof e=="boolean")return e;if(typeof e=="string"){const t=e.trim().toLowerCase();return t!==""&&t!=="false"&&t!=="0"}return!!e}};v.CONFIG_KEYS=new Set(["interval","timeout","until","error-limit","disabled","state"]),v.DEFAULT_INTERVAL_MS=5e3,v.MIN_INTERVAL_MS=100,v.registrations=new Map,v.visibilityListener=null;let Ee=v;const Et="0.58.0";function Yt(b){typeof requestAnimationFrame=="function"?requestAnimationFrame(()=>b()):Promise.resolve().then(b)}const P=class P{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(P.isHtmlElement(e)&&P.syncElement(e),e.querySelectorAll("*").forEach(t=>{P.syncElement(t)}))}static syncElement(e){const t=P.registrations.get(e),r=F.get(e);if(!(r instanceof w)||!P.shouldObserve(r)){t&&(t.observer.disconnect(),P.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=P.resolveVarName(r);if(i===""){t&&(t.observer.disconnect(),P.registrations.delete(e)),m.warn("[Haori]",'data-each-visible requires a variable name (e.g. data-each-visible="visibleRange").');return}const n=P.resolveRoot(r),s=P.resolveRootMargin(r);if(t&&t.observer.root===n&&t.observer.rootMargin===s&&t.varName===i){t.fragment=r,P.refreshRows(t);return}t&&(t.observer.disconnect(),P.registrations.delete(e));const a=new IntersectionObserver(c=>{const u=P.registrations.get(e);if(!u)return;let d=!1;c.forEach(g=>{const y=g.target;u.observedRows.has(y)&&(g.isIntersecting?u.visibleRows.has(y)||(u.visibleRows.add(y),d=!0):u.visibleRows.delete(y)&&(d=!0))}),d&&P.scheduleCompute(u)},{root:n,rootMargin:s,threshold:P.THRESHOLD}),o={fragment:r,observer:a,varName:i,root:n,rootMargin:s,observedRows:new Set,visibleRows:new Set,scheduled:!1,lastSnapshot:null};P.registrations.set(e,o),P.refreshRows(o)}static cleanupTree(e){if(P.isHtmlElement(e)){const t=P.registrations.get(e);t&&(t.observer.disconnect(),P.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=P.registrations.get(t);r&&(r.observer.disconnect(),P.registrations.delete(t))})}static disconnectAll(){P.registrations.forEach(e=>{e.observer.disconnect()}),P.registrations.clear()}static shouldObserve(e){return e.hasAttribute(`${l.prefix}each`)&&e.hasAttribute(`${l.prefix}each-visible`)}static resolveVarName(e){const t=e.getRawAttribute(`${l.prefix}each-visible`);return typeof t=="string"?t.trim():""}static resolveRoot(e){const t=`${l.prefix}each-visible-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=j.query(r,t,document);return P.isHtmlElement(i)?i:(m.error("[Haori]",`Visible range root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}each-visible-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?P.DEFAULT_ROOT_MARGIN:String(r)}static realRowElements(e){return e.getChildren().filter(t=>t instanceof w&&!t.hasAttribute(`${l.prefix}each-before`)&&!t.hasAttribute(`${l.prefix}each-after`)).map(t=>t.getTarget())}static refreshRows(e){const t=P.realRowElements(e.fragment),r=new Set(t);for(const i of[...e.observedRows])r.has(i)||(e.observer.unobserve(i),e.observedRows.delete(i),e.visibleRows.delete(i));for(const i of t)e.observedRows.has(i)||(e.observer.observe(i),e.observedRows.add(i));P.scheduleCompute(e)}static scheduleCompute(e){e.scheduled||(e.scheduled=!0,Yt(()=>{e.scheduled=!1;const t=e.fragment.getTarget();P.registrations.get(t)===e&&P.computeAndPublish(e)}))}static computeAndPublish(e){const t=P.realRowElements(e.fragment),r=new Map;t.forEach((a,o)=>r.set(a,o));const i=[];for(const a of e.visibleRows){const o=r.get(a);o!==void 0&&i.push(o)}let n;if(i.length===0)n={first:-1,last:-1,firstLabel:0,lastLabel:0,count:0,total:t.length,empty:!0};else{let a=i[0],o=i[0];for(const c of i)c<a&&(a=c),c>o&&(o=c);n={first:a,last:o,firstLabel:a+1,lastLabel:o+1,count:i.length,total:t.length,empty:!1}}const s=JSON.stringify(n);s!==e.lastSnapshot&&(e.lastSnapshot=s,P.publish(e,n))}static publish(e,t){const r=P.resolveBindOwner(e.fragment);if(!r){m.warn("[Haori]","data-each-visible found no ancestor data-bind scope to publish into.");return}const i=r.getTarget(),n={...r.getRawBindingData()??{}};n[e.varName]={...t};const s=e.fragment.getTarget(),a=i===s?new Set:new Set([e.fragment]);$.setBindingData(i,n,{skipFragments:a,reflectToAttribute:!1,kind:"nonSupply",sequence:w.nextSequence()}).catch(o=>{m.error("[Haori]","Failed to publish visible range:",o)})}static resolveBindOwner(e){const t=`${l.prefix}bind`;let r=e.getParent();for(;r;){if(r.hasAttribute(t))return r;r=r.getParent()}return e.hasAttribute(t)?e:null}};P.THRESHOLD=0,P.DEFAULT_ROOT_MARGIN="0px",P.registrations=new Map;let ge=P;const U=class U{static disconnectMutationObservers(){U._mutationObservers.forEach(e=>{e.disconnect()}),U._mutationObservers.length=0}static async init(){if(U._initialized)return;U._initialized=!0,U.disconnectMutationObservers(),w.setPendingMutationFlusher(()=>{U.flushPendingMutations()});const e=new We;U._dispatcher=e,e.startDeferred(),U._initialIntakes=[];try{const t=await Promise.allSettled([$.scan(document.head),$.scan(document.body)]),[r,i]=t;r.status!=="fulfilled"&&m.error("[Haori]","Failed to build head fragment:",r.reason),i.status!=="fulfilled"&&m.error("[Haori]","Failed to build body fragment:",i.reason),await U.waitInitialIntakes(),await z.wait(),document.body.setAttribute("data-haori-ready",""),U.observe(document.head),U.observe(document.body),Ae.syncTree(document.body),Ee.syncTree(document.body),ge.syncTree(document.body)}finally{U._initialIntakes=null,e.release()}B.ready(Et)}static getDispatcher(){return U._dispatcher}static async waitInitialIntakes(){const e=U._initialIntakes;for(;e!==null&&e.length>0;)await Promise.allSettled(e.splice(0))}static captureMutations(e){if(U._mutationObservers.length>0){e();return}const t=new MutationObserver(()=>{});t.observe(document.documentElement,{childList:!0,subtree:!0,attributes:!0,characterData:!0});try{e()}finally{const r=t.takeRecords().map(i=>U.toCapturedRecord(i));t.disconnect(),U.processMutations(r)}}static toCapturedRecord(e){return e.type!=="childList"?e:{type:e.type,target:e.target,addedNodes:Array.from(e.addedNodes).filter(t=>!U.hasKnownDescendant(t)),removedNodes:[]}}static hasKnownDescendant(e){return e instanceof Element&&Array.from(e.querySelectorAll("*")).some(t=>w.peek(t)!==null)}static isStaleExternalRemoval(e,t){const r=w.peek(t)?.getParent()??null;return r===null||r.getTarget()===e.target?!1:r.getTarget().closest(`[${l.prefix}external]`)!==null}static isExternallyManaged(e){return(e instanceof Element?e:e?.parentElement??null)?.closest(`[${l.prefix}external]`)!=null}static observe(e){const t=new MutationObserver(r=>{U.processMutations(r)});t.observe(e,{childList:!0,subtree:!0,attributes:!0,characterData:!0}),U._mutationObservers.push(t)}static flushPendingMutations(){for(const e of U._mutationObservers){const t=e.takeRecords();if(t.length===0)continue;const r=t.filter(U.isBindAttributeRecord),i=t.filter(n=>!U.isBindAttributeRecord(n));r.length>0&&U.processMutations(r,w.nextSequence()),i.length>0&&Promise.resolve().then(()=>{U.processMutations(i)})}}static isBindAttributeRecord(e){return e.type==="attributes"&&e.attributeName===`${l.prefix}bind`}static processMutations(e,t){for(const r of e)try{if(U.isExternallyManaged(r.target))continue;switch(r.type){case"attributes":{const i=r.target;if(r.attributeName&&i.hasAttribute("data-haori-click-lock")&&(r.attributeName==="disabled"||r.attributeName==="data-haori-click-lock")||r.attributeName&&i.hasAttribute(fe)&&(r.attributeName==="disabled"||r.attributeName===fe))break;if(r.attributeName&&(r.attributeName===`${l.prefix}if-false`||r.attributeName==="style"&&i.hasAttribute(`${l.prefix}if-false`))){r.attributeName==="style"&&w.reassertHiddenDisplay(i);break}if(r.attributeName&&$.isAliasedAttributeReflection(i,r.attributeName))break;const n=$.setAttribute(i,r.attributeName,i.getAttribute(r.attributeName),!0,t);U._initialIntakes?.push(n),Ae.syncElement(i),Ee.syncElement(i),ge.syncElement(i);break}case"childList":{Array.from(r.removedNodes).forEach(i=>{U.isStaleExternalRemoval(r,i)||(Ae.cleanupTree(i),Ee.cleanupTree(i),ge.cleanupTree(i),$.removeNode(i))}),Array.from(r.addedNodes).forEach(i=>{if(!(i.parentElement instanceof Element))return;const n=$.addNode(i.parentElement,i);U._initialIntakes?.push(n),Ae.syncTree(i),Ee.syncTree(i),ge.syncTree(i)}),r.target instanceof Element&&ge.syncElement(r.target);break}case"characterData":{r.target instanceof Text||r.target instanceof Comment?$.changeText(r.target,r.target.textContent):m.warn("[Haori]","Unsupported character data type:",r.target);break}default:m.warn("[Haori]","Unknown mutation type:",r.type);continue}}catch(i){m.error("[Haori]","Error processing mutation:",i)}}};U._initialized=!1,U._mutationObservers=[],U._dispatcher=null,U._initialIntakes=null;let Fe=U;te.setMutationCapture(b=>Fe.captureMutations(b)),document.readyState==="loading"?document.addEventListener("DOMContentLoaded",Fe.init):Fe.init();const Xt=()=>oe.waitForRenders(),Jt=oe.enhancers,Zt=Object.freeze(Object.defineProperty({__proto__:null,Core:$,Enhance:te,Env:l,Form:I,Fragment:F,Haori:oe,Log:m,Queue:z,default:oe,enhancers:Jt,version:Et,waitForRenders:Xt},Symbol.toStringTag,{value:"Module"})),je=oe;for(const[b,e]of Object.entries(Zt))b in je||Object.defineProperty(je,b,{value:e,writable:!0,enumerable:!0,configurable:!0});return je}();
|
|
32
|
+
`)}static startPolling(e,t,r){const i={fragment:t,configKey:r,intervalMs:v.resolveInterval(t),timeoutMs:v.resolveTimeout(t),errorLimit:v.resolveErrorLimit(t),startedAt:performance.now(),intervalTimerId:null,timeoutTimerId:null,fetching:!1,paused:!1,stopped:!1,timedOut:!1,stopReason:null,count:0,consecutiveErrors:0};v.registrations.set(e,i),v.ensureVisibilityListener(),i.timeoutMs!==null&&(i.timeoutTimerId=setTimeout(()=>{v.handleTimeout(e)},i.timeoutMs)),v.injectState(i),v.tick(e)}static async tick(e){const t=v.registrations.get(e);if(!t||t.stopped||t.fetching)return;if(t.intervalTimerId=null,!e.isConnected){await v.stop(e,t,"detached");return}const r=v.isHidden(e)||v.isDisabled(t.fragment);if(r!==t.paused&&(t.paused=r,await v.injectState(t)),r){v.schedule(e,t);return}if(v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}t.fetching=!0,t.count+=1;let i=!1;try{i=await new se(t.fragment,"poll").runWithResult()}catch(n){m.error("[Haori]","Poll procedure execution error:",n)}finally{t.fetching=!1}if(!(v.registrations.get(e)!==t||t.stopped)){if(i)t.consecutiveErrors=0;else if(t.consecutiveErrors+=1,t.errorLimit!==null&&t.consecutiveErrors>=t.errorLimit){await v.stop(e,t,"error");return}if(i&&v.isUntilSatisfied(t.fragment)){await v.stop(e,t,"until");return}v.schedule(e,t)}}static schedule(e,t){t.stopped||t.intervalTimerId!==null||(t.intervalTimerId=setTimeout(()=>{v.tick(e)},t.intervalMs))}static async handleTimeout(e){const t=v.registrations.get(e);!t||t.stopped||(t.timeoutTimerId=null,t.timedOut=!0,e.isConnected&&B.pollTimeout(e,t.count,v.elapsed(t)),await v.stop(e,t,"timeout"))}static async stop(e,t,r){if(!t.stopped){if(t.stopped=!0,t.stopReason=r,t.paused=!1,v.clearTimers(t),r==="detached"){v.registrations.delete(e);return}await v.injectState(t),e.isConnected&&B.pollStop(e,r,t.count,v.elapsed(t))}}static teardown(e,t){v.clearTimers(t),v.registrations.delete(e)}static clearTimers(e){e.intervalTimerId!==null&&(clearTimeout(e.intervalTimerId),e.intervalTimerId=null),e.timeoutTimerId!==null&&(clearTimeout(e.timeoutTimerId),e.timeoutTimerId=null)}static elapsed(e){return Math.round(performance.now()-e.startedAt)}static ensureVisibilityListener(){if(v.visibilityListener||typeof document>"u")return;const e=()=>{document.visibilityState==="visible"&&Array.from(v.registrations.entries()).forEach(([t,r])=>{r.stopped||r.fetching||(r.intervalTimerId!==null&&(clearTimeout(r.intervalTimerId),r.intervalTimerId=null),v.tick(t))})};v.visibilityListener=e,document.addEventListener("visibilitychange",e)}static injectState(e){const t=v.resolveStateFragments(e);if(t.length===0)return Promise.resolve();const r={running:!e.stopped,paused:e.paused,stopped:e.stopped,timedOut:e.timedOut,stopReason:e.stopReason,count:e.count,elapsedMs:v.elapsed(e)};return Promise.all(t.map(i=>{const n=i.getTarget(),s={...i.getRawBindingData()??{},_poll:r};return $.setBindingData(n,s,{reflectToAttribute:!1,kind:"nonSupply",sequence:w.nextSequence()})})).then(()=>{})}static resolveStateFragments(e){const t=`${l.prefix}poll-state`,r=e.fragment;if(!r.hasAttribute(t))return[];const i=r.getAttribute(t);if(typeof i!="string"||i.trim()==="")return r.getTarget().isConnected?[r]:[];const n=j.queryAll(i,t,document);if(n.length===0)return m.error("[Haori]",`Poll state element not found: ${i}`),[];const s=[];return n.forEach(a=>{if(!a.isConnected)return;const o=F.get(a);o instanceof w&&s.push(o)}),s}static resolveInterval(e){const t=`${l.prefix}poll-interval`;if(!e.hasAttribute(t))return v.DEFAULT_INTERVAL_MS;const r=v.toNumber(e.getAttribute(t));return r===null?(m.warn("[Haori]",`${t} は数値で指定してください。既定値 ${v.DEFAULT_INTERVAL_MS}ms を使用します。`),v.DEFAULT_INTERVAL_MS):r<v.MIN_INTERVAL_MS?(m.warn("[Haori]",`${t} の下限は ${v.MIN_INTERVAL_MS}ms です。${r}ms は下限へ切り上げます。`),v.MIN_INTERVAL_MS):r}static resolveTimeout(e){const t=`${l.prefix}poll-timeout`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<=0?(m.warn("[Haori]",`${t} は正の数値で指定してください。無制限として扱います。`),null):r}static resolveErrorLimit(e){const t=`${l.prefix}poll-error-limit`;if(!e.hasAttribute(t))return null;const r=v.toNumber(e.getAttribute(t));return r===null||r<1?(m.warn("[Haori]",`${t} は 1 以上の数値で指定してください。無制限として扱います。`),null):Math.floor(r)}static toNumber(e){if(typeof e=="number")return Number.isFinite(e)?e:null;if(typeof e!="string"||e.trim()==="")return null;const t=Number(e.trim());return Number.isFinite(t)?t:null}static isHidden(e){return e.closest(`[${l.prefix}if-false]`)!==null}static isDisabled(e){const t=`${l.prefix}poll-disabled`;return e.hasAttribute(t)?v.isTruthy(e.getAttribute(t)):!1}static isUntilSatisfied(e){const t=`${l.prefix}poll-until`;if(!e.hasAttribute(t))return!1;const r=e.getAttributeEvaluation(t);return r?r.hasUnresolvedReference?(m.warn("[Haori]",`${t} に未解決の参照が含まれています(停止条件は成立扱いにしません):`,e.getRawAttribute(t),e.getTarget()),!1):v.isTruthy(r.value):!1}static isTruthy(e){if(e==null||e===!1)return!1;if(typeof e=="boolean")return e;if(typeof e=="string"){const t=e.trim().toLowerCase();return t!==""&&t!=="false"&&t!=="0"}return!!e}};v.CONFIG_KEYS=new Set(["interval","timeout","until","error-limit","disabled","state"]),v.DEFAULT_INTERVAL_MS=5e3,v.MIN_INTERVAL_MS=100,v.registrations=new Map,v.visibilityListener=null;let Ee=v;const Et="0.59.0";function Yt(b){typeof requestAnimationFrame=="function"?requestAnimationFrame(()=>b()):Promise.resolve().then(b)}const P=class P{static isHtmlElement(e){if(!(e instanceof Element))return!1;const t=e.ownerDocument?.defaultView?.HTMLElement;return typeof t<"u"&&e instanceof t}static syncTree(e){(e instanceof Element||e instanceof DocumentFragment)&&(P.isHtmlElement(e)&&P.syncElement(e),e.querySelectorAll("*").forEach(t=>{P.syncElement(t)}))}static syncElement(e){const t=P.registrations.get(e),r=F.get(e);if(!(r instanceof w)||!P.shouldObserve(r)){t&&(t.observer.disconnect(),P.registrations.delete(e));return}if(typeof IntersectionObserver>"u")return;const i=P.resolveVarName(r);if(i===""){t&&(t.observer.disconnect(),P.registrations.delete(e)),m.warn("[Haori]",'data-each-visible requires a variable name (e.g. data-each-visible="visibleRange").');return}const n=P.resolveRoot(r),s=P.resolveRootMargin(r);if(t&&t.observer.root===n&&t.observer.rootMargin===s&&t.varName===i){t.fragment=r,P.refreshRows(t);return}t&&(t.observer.disconnect(),P.registrations.delete(e));const a=new IntersectionObserver(c=>{const u=P.registrations.get(e);if(!u)return;let d=!1;c.forEach(g=>{const y=g.target;u.observedRows.has(y)&&(g.isIntersecting?u.visibleRows.has(y)||(u.visibleRows.add(y),d=!0):u.visibleRows.delete(y)&&(d=!0))}),d&&P.scheduleCompute(u)},{root:n,rootMargin:s,threshold:P.THRESHOLD}),o={fragment:r,observer:a,varName:i,root:n,rootMargin:s,observedRows:new Set,visibleRows:new Set,scheduled:!1,lastSnapshot:null};P.registrations.set(e,o),P.refreshRows(o)}static cleanupTree(e){if(P.isHtmlElement(e)){const t=P.registrations.get(e);t&&(t.observer.disconnect(),P.registrations.delete(e))}(e instanceof Element||e instanceof DocumentFragment)&&e.querySelectorAll("*").forEach(t=>{const r=P.registrations.get(t);r&&(r.observer.disconnect(),P.registrations.delete(t))})}static disconnectAll(){P.registrations.forEach(e=>{e.observer.disconnect()}),P.registrations.clear()}static shouldObserve(e){return e.hasAttribute(`${l.prefix}each`)&&e.hasAttribute(`${l.prefix}each-visible`)}static resolveVarName(e){const t=e.getRawAttribute(`${l.prefix}each-visible`);return typeof t=="string"?t.trim():""}static resolveRoot(e){const t=`${l.prefix}each-visible-root`;if(!e.hasAttribute(t))return null;const r=e.getAttribute(t);if(typeof r!="string"||r.trim()==="")return null;const i=j.query(r,t,document);return P.isHtmlElement(i)?i:(m.error("[Haori]",`Visible range root element not found: ${r}`),null)}static resolveRootMargin(e){const t=`${l.prefix}each-visible-margin`,r=e.getAttribute(t);return r===null||r===!1||r===""?P.DEFAULT_ROOT_MARGIN:String(r)}static realRowElements(e){return e.getChildren().filter(t=>t instanceof w&&!t.hasAttribute(`${l.prefix}each-before`)&&!t.hasAttribute(`${l.prefix}each-after`)).map(t=>t.getTarget())}static refreshRows(e){const t=P.realRowElements(e.fragment),r=new Set(t);for(const i of[...e.observedRows])r.has(i)||(e.observer.unobserve(i),e.observedRows.delete(i),e.visibleRows.delete(i));for(const i of t)e.observedRows.has(i)||(e.observer.observe(i),e.observedRows.add(i));P.scheduleCompute(e)}static scheduleCompute(e){e.scheduled||(e.scheduled=!0,Yt(()=>{e.scheduled=!1;const t=e.fragment.getTarget();P.registrations.get(t)===e&&P.computeAndPublish(e)}))}static computeAndPublish(e){const t=P.realRowElements(e.fragment),r=new Map;t.forEach((a,o)=>r.set(a,o));const i=[];for(const a of e.visibleRows){const o=r.get(a);o!==void 0&&i.push(o)}let n;if(i.length===0)n={first:-1,last:-1,firstLabel:0,lastLabel:0,count:0,total:t.length,empty:!0};else{let a=i[0],o=i[0];for(const c of i)c<a&&(a=c),c>o&&(o=c);n={first:a,last:o,firstLabel:a+1,lastLabel:o+1,count:i.length,total:t.length,empty:!1}}const s=JSON.stringify(n);s!==e.lastSnapshot&&(e.lastSnapshot=s,P.publish(e,n))}static publish(e,t){const r=P.resolveBindOwner(e.fragment);if(!r){m.warn("[Haori]","data-each-visible found no ancestor data-bind scope to publish into.");return}const i=r.getTarget(),n={...r.getRawBindingData()??{}};n[e.varName]={...t};const s=e.fragment.getTarget(),a=i===s?new Set:new Set([e.fragment]);$.setBindingData(i,n,{skipFragments:a,reflectToAttribute:!1,kind:"nonSupply",sequence:w.nextSequence()}).catch(o=>{m.error("[Haori]","Failed to publish visible range:",o)})}static resolveBindOwner(e){const t=`${l.prefix}bind`;let r=e.getParent();for(;r;){if(r.hasAttribute(t))return r;r=r.getParent()}return e.hasAttribute(t)?e:null}};P.THRESHOLD=0,P.DEFAULT_ROOT_MARGIN="0px",P.registrations=new Map;let ge=P;const U=class U{static disconnectMutationObservers(){U._mutationObservers.forEach(e=>{e.disconnect()}),U._mutationObservers.length=0}static async init(){if(U._initialized)return;U._initialized=!0,U.disconnectMutationObservers(),w.setPendingMutationFlusher(()=>{U.flushPendingMutations()});const e=new We;U._dispatcher=e,e.startDeferred(),U._initialIntakes=[];try{const t=await Promise.allSettled([$.scan(document.head),$.scan(document.body)]),[r,i]=t;r.status!=="fulfilled"&&m.error("[Haori]","Failed to build head fragment:",r.reason),i.status!=="fulfilled"&&m.error("[Haori]","Failed to build body fragment:",i.reason),await U.waitInitialIntakes(),await z.wait(),document.body.setAttribute("data-haori-ready",""),U.observe(document.head),U.observe(document.body),Ae.syncTree(document.body),Ee.syncTree(document.body),ge.syncTree(document.body)}finally{U._initialIntakes=null,e.release()}B.ready(Et)}static getDispatcher(){return U._dispatcher}static async waitInitialIntakes(){const e=U._initialIntakes;for(;e!==null&&e.length>0;)await Promise.allSettled(e.splice(0))}static captureMutations(e){if(U._mutationObservers.length>0){e();return}const t=new MutationObserver(()=>{});t.observe(document.documentElement,{childList:!0,subtree:!0,attributes:!0,characterData:!0});try{e()}finally{const r=t.takeRecords().map(i=>U.toCapturedRecord(i));t.disconnect(),U.processMutations(r)}}static toCapturedRecord(e){return e.type!=="childList"?e:{type:e.type,target:e.target,addedNodes:Array.from(e.addedNodes).filter(t=>!U.hasKnownDescendant(t)),removedNodes:[]}}static hasKnownDescendant(e){return e instanceof Element&&Array.from(e.querySelectorAll("*")).some(t=>w.peek(t)!==null)}static isStaleExternalRemoval(e,t){const r=w.peek(t)?.getParent()??null;return r===null||r.getTarget()===e.target?!1:r.getTarget().closest(`[${l.prefix}external]`)!==null}static isExternallyManaged(e){return(e instanceof Element?e:e?.parentElement??null)?.closest(`[${l.prefix}external]`)!=null}static observe(e){const t=new MutationObserver(r=>{U.processMutations(r)});t.observe(e,{childList:!0,subtree:!0,attributes:!0,characterData:!0}),U._mutationObservers.push(t)}static flushPendingMutations(){for(const e of U._mutationObservers){const t=e.takeRecords();if(t.length===0)continue;const r=t.filter(U.isBindAttributeRecord),i=t.filter(n=>!U.isBindAttributeRecord(n));r.length>0&&U.processMutations(r,w.nextSequence()),i.length>0&&Promise.resolve().then(()=>{U.processMutations(i)})}}static isBindAttributeRecord(e){return e.type==="attributes"&&e.attributeName===`${l.prefix}bind`}static processMutations(e,t){for(const r of e)try{if(U.isExternallyManaged(r.target))continue;switch(r.type){case"attributes":{const i=r.target;if(r.attributeName&&i.hasAttribute("data-haori-click-lock")&&(r.attributeName==="disabled"||r.attributeName==="data-haori-click-lock")||r.attributeName&&i.hasAttribute(fe)&&(r.attributeName==="disabled"||r.attributeName===fe))break;if(r.attributeName&&(r.attributeName===`${l.prefix}if-false`||r.attributeName==="style"&&i.hasAttribute(`${l.prefix}if-false`))){r.attributeName==="style"&&w.reassertHiddenDisplay(i);break}if(r.attributeName&&$.isAliasedAttributeReflection(i,r.attributeName))break;const n=$.setAttribute(i,r.attributeName,i.getAttribute(r.attributeName),!0,t);U._initialIntakes?.push(n),Ae.syncElement(i),Ee.syncElement(i),ge.syncElement(i);break}case"childList":{Array.from(r.removedNodes).forEach(i=>{U.isStaleExternalRemoval(r,i)||(Ae.cleanupTree(i),Ee.cleanupTree(i),ge.cleanupTree(i),$.removeNode(i))}),Array.from(r.addedNodes).forEach(i=>{if(!(i.parentElement instanceof Element))return;const n=$.addNode(i.parentElement,i);U._initialIntakes?.push(n),Ae.syncTree(i),Ee.syncTree(i),ge.syncTree(i)}),r.target instanceof Element&&ge.syncElement(r.target);break}case"characterData":{r.target instanceof Text||r.target instanceof Comment?$.changeText(r.target,r.target.textContent):m.warn("[Haori]","Unsupported character data type:",r.target);break}default:m.warn("[Haori]","Unknown mutation type:",r.type);continue}}catch(i){m.error("[Haori]","Error processing mutation:",i)}}};U._initialized=!1,U._mutationObservers=[],U._dispatcher=null,U._initialIntakes=null;let Fe=U;te.setMutationCapture(b=>Fe.captureMutations(b)),document.readyState==="loading"?document.addEventListener("DOMContentLoaded",Fe.init):Fe.init();const Xt=()=>oe.waitForRenders(),Jt=oe.enhancers,Zt=Object.freeze(Object.defineProperty({__proto__:null,Core:$,Enhance:te,Env:l,Form:I,Fragment:F,Haori:oe,Log:m,Queue:z,default:oe,enhancers:Jt,version:Et,waitForRenders:Xt},Symbol.toStringTag,{value:"Module"})),je=oe;for(const[b,e]of Object.entries(Zt))b in je||Object.defineProperty(je,b,{value:e,writable:!0,enumerable:!0,configurable:!0});return je}();
|
|
33
33
|
//# sourceMappingURL=haori.iife.js.map
|
package/dist/index.d.ts
CHANGED
|
@@ -4804,7 +4804,7 @@ declare interface ValueChangeOrigin {
|
|
|
4804
4804
|
* リリース時に `package.json` と揃えて更新します(`tests/version.test.ts` が
|
|
4805
4805
|
* 一致を検査します)。
|
|
4806
4806
|
*/
|
|
4807
|
-
export declare const version = "0.
|
|
4807
|
+
export declare const version = "0.59.0";
|
|
4808
4808
|
|
|
4809
4809
|
/**
|
|
4810
4810
|
* すべてのレンダリングタスク(追従投入分を含む)の完了を待ちます。
|