@weppy/roblox-mcp 2.11.2 → 2.11.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +8 -0
- package/dashboard/dist/assets/{AssetsPage-O4fuVc8N.js → AssetsPage-4k54hYuC.js} +1 -1
- package/dashboard/dist/assets/{ChangelogDetailPage-rC1KFRqD.js → ChangelogDetailPage-D0DwxSBF.js} +1 -1
- package/dashboard/dist/assets/{ChangelogPage-CjVIKM_I.js → ChangelogPage-qjNm-uZG.js} +1 -1
- package/dashboard/dist/assets/{ConfirmModal-DzzePbJa.js → ConfirmModal-DgQvChuz.js} +1 -1
- package/dashboard/dist/assets/{ConnectionPage-DkAYL5lD.js → ConnectionPage-iZPBNX_5.js} +1 -1
- package/dashboard/dist/assets/{ControlsPage-iUVigyLq.js → ControlsPage-yMTnqqI2.js} +1 -1
- package/dashboard/dist/assets/{CurrentPlaceScope-ILgcdBgL.js → CurrentPlaceScope-DGj3VpQ6.js} +1 -1
- package/dashboard/dist/assets/{GameChangeDetail-D5DL-c5w.js → GameChangeDetail-C9DWOQnm.js} +1 -1
- package/dashboard/dist/assets/{InfoLabel-DANjLZ88.js → InfoLabel-D5NGX4sX.js} +1 -1
- package/dashboard/dist/assets/{OverviewPage-DHFQ-W9q.js → OverviewPage-CxaJcmjT.js} +1 -1
- package/dashboard/dist/assets/{PageHeader-CIEYGd1d.js → PageHeader-BSIg4cK5.js} +1 -1
- package/dashboard/dist/assets/{PlaytestPage-kN109lxu.js → PlaytestPage-DoRsSmrA.js} +1 -1
- package/dashboard/dist/assets/SettingsPage-BR71s-WH.css +1 -0
- package/dashboard/dist/assets/SettingsPage-D1UhOgbU.js +1 -0
- package/dashboard/dist/assets/{StatusBadge-It13fqQV.js → StatusBadge-CehOE1eN.js} +1 -1
- package/dashboard/dist/assets/{SyncPage-BLb2y3a-.js → SyncPage-DbWbpAmP.js} +1 -1
- package/dashboard/dist/assets/{Tabs-B_vNTq0e.js → Tabs-DSCGye2g.js} +1 -1
- package/dashboard/dist/assets/{ToolsPage-CyrmKGlr.js → ToolsPage-C6Zj2TeT.js} +1 -1
- package/dashboard/dist/assets/{TooltipText-WYIcU5Ix.js → TooltipText-Chm9jfjd.js} +1 -1
- package/dashboard/dist/assets/{UiPrimitive-CoOY1M8-.js → UiPrimitive-BDJJzEcy.js} +1 -1
- package/dashboard/dist/assets/{UiStudioPage-BMIAX-ik.js → UiStudioPage-Cz57lI6I.js} +1 -1
- package/dashboard/dist/assets/{WhatsNewPage-CGo7UGNR.js → WhatsNewPage-CuoRGZ1-.js} +1 -1
- package/dashboard/dist/assets/{copy-DD_Ti5vm.js → copy-BYpXG6-W.js} +1 -1
- package/dashboard/dist/assets/index-ChbQL9S4.js +682 -0
- package/dashboard/dist/assets/{sample-requests-BxROai7H.js → sample-requests-DmIksoW2.js} +1 -1
- package/dashboard/dist/assets/{useLiveUptime-C-QraLBj.js → useLiveUptime-a-NbFX-N.js} +1 -1
- package/dashboard/dist/assets/useSettings-BFBjELsK.js +1 -0
- package/dashboard/dist/assets/useSettings-CpzQAFQq.css +1 -0
- package/dashboard/dist/index.html +1 -1
- package/dist/index.js +1 -1
- package/package.json +1 -1
- package/roblox-plugin/WeppyRobloxMCP.rbxm +0 -0
- package/dashboard/dist/assets/SettingsPage-BKk40N3D.js +0 -1
- package/dashboard/dist/assets/SettingsPage-ByHSUA7b.css +0 -1
- package/dashboard/dist/assets/index-DRw0NuYR.js +0 -682
- package/dashboard/dist/assets/useSettings-C7K0TrFY.js +0 -1
- package/dashboard/dist/assets/useSettings-uLUwCzcr.css +0 -1
package/dist/index.js
CHANGED
|
@@ -526,7 +526,7 @@ Used by: toggle_ui_preview (optional).
|
|
|
526
526
|
${FB}
|
|
527
527
|
`:`${FB}
|
|
528
528
|
`}async function Whe(t,e){let n=`${t}.${process.pid}.${Date.now()}.tmp`;await Wf.mkdir(qB.dirname(t),{recursive:!0});try{await Wf.writeFile(n,e,"utf8"),await Wf.rename(n,t)}finally{await Wf.rm(n,{force:!0})}}function UB(t){return t.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}Ui();Tf();import{createHash as Ghe}from"crypto";import Rt from"path";import{promises as Mr}from"fs";bs();var Khe={readFile:t=>Mr.readFile(t),writeFileAtomic:async(t,e)=>{await fn(t,typeof e=="string"?e:e.toString("utf8"))},copyFile:async(t,e)=>{await Mr.mkdir(Rt.dirname(e),{recursive:!0}),await Mr.copyFile(t,e)},unlink:async t=>{await Mr.unlink(t)},mkdir:async t=>{await Mr.mkdir(t,{recursive:!0})}},Ki=class extends Error{constructor(n,r,i=r){super(i);this.statusCode=n;this.code=r;this.name="SyncMigrationError"}},x_=class{constructor(e,n=Khe){this.ctx=e;this.fileOps=n}async preview(e){let{operations:n,...r}=await this.buildPlan(e);return{...r,generatedAt:new Date().toISOString()}}async apply(e){let n=await this.buildPlan(e.placeId);if(n.previewFingerprint!==e.previewFingerprint)throw new Ki(409,"preview_stale");if(n.status==="blocked")throw new Ki(409,"migration_blocked");if(n.status==="not_required")return this.preview(e.placeId);let r=this.ctx.places.get(e.placeId);if(!r)throw new Ki(404,"place_not_found");let i=this.ctx.config.getSyncRoot(),a=Rt.dirname(r.index.getExplorerRoot()),o=Rt.join(a,".sync-index.json"),s=Rt.join(a,".sync-meta.json"),c=Rt.join(a,".sync-migration-backups",`v2-to-v3-${n.previewFingerprint}`),l=await this.captureOriginals(i,n.changes,o,s),u={studioHashes:r.index.getAllHashes(),fileHashes:r.index.getAllFileHashes()},d=await WB(r.index.getExplorerRoot());await this.writeBackup(i,c,l),r.fileWatcher?.beginFullSyncReplacement();try{await this.applyOperations(i,r,n,l),await this.assertUserSourcesUnchanged(r.index.getExplorerRoot(),d);let p={version:1,syncFormatVersion:Pt,placeId:r.placeId,placeName:r.placeName,lastFullSync:r.lastFullSync??null,lastIncrementalSync:r.lastIncrementalSync??null,instanceCount:r.instanceCount??0,scriptCount:r.scriptCount??0,syncMode:"mirror"};await this.fileOps.writeFileAtomic(s,JSON.stringify(p,null,2)+`
|
|
529
|
-
`),r.index.setFormatVersion(Pt);let f=ys(r.index.toSyncIndexData());return await this.fileOps.writeFileAtomic(o,f),r.formatVersion=Pt,r.writer.setFormatVersion(Pt),await r.fileWatcher?.endFullSyncReplacement(),this.preview(e.placeId)}catch(p){throw await this.rollback(l,c,r,u),p}}async buildPlan(e){let n=this.ctx.places.get(e);if(!n)throw new Ki(404,"place_not_found");let r=this.ctx.config.getSyncRoot(),i=Rt.dirname(n.index.getExplorerRoot()),a=n.index.getExplorerRoot();if(n.formatVersion!==ut){let x=ZB(ys({blockers:[],changes:[],fromVersion:ut,placeId:e,toVersion:Pt}));return{placeId:e,fromVersion:ut,toVersion:Pt,status:"not_required",previewFingerprint:x,userSourceModified:0,summary:{add:0,modify:0,delete:0,blocked:0},changes:[],blockers:[],operations:new Map}}let s=await Jhe(r,a),c=new Set(s.map(x=>x.absolutePath)),l=[],u=new Map;for(let x of s){let _=await Yhe(x,c);_&&(l.push(_.change),u.set(_.change.path,_.after))}let d=await this.planManagedIgnore(r);d&&(l.push(d.change),u.set(d.change.path,d.after)),l.sort(eye);let p=await this.collectBlockers(r,n);p.sort(tye);let f=Rt.join(i,".sync-index.json"),m=await this.readFileOrNull(f),g=[...n.index.getAllFileHashes().keys()].map(x=>{let _=b_(r,x);if(Ps(_)!=="canonical_mirror")return null;let w=n.index.getHashPair(x);return{path:_,fileHash:w.fileHash??null,studioHash:w.studioHash??null}}).filter(x=>x!==null).sort((x,_)=>x.path.localeCompare(_.path)),h=ZB(ys({blockers:p,changes:l,fromVersion:ut,indexHash:m?Os(m):null,indexState:g,placeId:e,toVersion:Pt})),v={add:l.filter(x=>x.operation==="add").length,modify:l.filter(x=>x.operation==="modify").length,delete:l.filter(x=>x.operation==="delete").length,blocked:p.length};return{placeId:e,fromVersion:ut,toVersion:Pt,status:p.length>0?"blocked":"ready",previewFingerprint:h,userSourceModified:0,summary:v,changes:l,blockers:p,operations:u}}async planManagedIgnore(e){let n=Rt.join(e,".gitignore"),r=await this.readFileOrNull(n),i=r?.toString("utf8")??"",a=Buffer.from(VT(i),"utf8");return r?.equals(a)?null:{change:{path:".gitignore",ownership:"generated",operation:r===null?"add":"modify",reason:"runtime_ignore_policy",...r!==null?{beforeHash:Os(r)}:{},afterHash:Os(a)},after:a}}async readFileOrNull(e){return this.fileOps.readFile(e).catch(n=>{if(n.code==="ENOENT")return null;throw n})}async captureOriginals(e,n,r,i){let a=[];for(let o of n){let s=Rt.resolve(e,o.path);a.push({absolutePath:s,content:await this.readFileOrNull(s)})}return a.push({absolutePath:r,content:await this.readFileOrNull(r)}),a.push({absolutePath:i,content:await this.readFileOrNull(i)}),a}async writeBackup(e,n,r){await this.fileOps.mkdir(n);for(let i of r){if(i.content===null)continue;let a=b_(e,i.absolutePath);await this.fileOps.copyFile(i.absolutePath,Rt.join(n,"files",a))}}async applyOperations(e,n,r,i){let a=new Map(i.map(o=>[o.absolutePath,o.content]));for(let o of r.changes){let s=Rt.resolve(e,o.path),c=r.operations.get(o.path);if(c===void 0)throw new Error(`Missing migration operation content: ${o.path}`);if(n.fileWatcher?.suppressPath(s,c===null?"missing":n.index.computeHash(c.toString("utf8"))),c===null?await this.fileOps.unlink(s):await this.fileOps.writeFileAtomic(s,c),o.ownership!=="canonical_mirror")continue;if(c===null){n.index.removeHash(s);continue}let l=a.get(s);(l?n.index.getFileStatus(s,n.index.computeHash(l.toString("utf8"))):"synced")==="studio-modified"?n.index.updateFileHash(s,c.toString("utf8")):n.index.updateBothHashes(s,c.toString("utf8"))}}async assertUserSourcesUnchanged(e,n){let r=await WB(e);if(!rye(n,r))throw new Ki(409,"source_mutation_detected")}async rollback(e,n,r,i){let a;for(let o of[...e].reverse())try{o.content===null?await this.fileOps.unlink(o.absolutePath).catch(s=>{if(s.code!=="ENOENT")throw s}):await this.fileOps.writeFileAtomic(o.absolutePath,o.content)}catch(s){a??=s}r.index.clearAllHashes();for(let[o,s]of i.studioHashes)r.index.updateHashByValue(o,s);for(let[o,s]of i.fileHashes)r.index.updateFileHashByValue(o,s);if(r.index.setFormatVersion(ut),r.formatVersion=ut,r.writer.setFormatVersion(ut),await Mr.rm(n,{recursive:!0,force:!0}),await r.fileWatcher?.endFullSyncReplacement(),a)throw a}async collectBlockers(e,n){let r=[];(n.fileWatcher?.getPendingCount()??0)>0&&r.push({reason:"reverse_pending"});for(let i of n.index.getAllFileHashes().keys()){let a=b_(e,i);if(Ps(a)!=="canonical_mirror")continue;let o=await Qhe(i);if(o===null){r.push({path:a,reason:"local_canonical_change"});continue}let s=n.index.getFileStatus(i,n.index.computeHash(o.toString("utf8")));s==="conflict"?r.push({path:a,reason:"conflict"}):s==="file-modified"&&r.push({path:a,reason:"local_canonical_change"})}return nye(r)}};async function Jhe(t,e){let n=[];async function r(i){let a=await Mr.readdir(i,{withFileTypes:!0}).catch(o=>{if(o.code==="ENOENT")return[];throw o});for(let o of a){let s=Rt.join(i,o.name);if(o.isDirectory()){await r(s);continue}Xhe(o.name)&&n.push({absolutePath:s,relativePath:b_(t,s),content:await Mr.readFile(s)})}}return await r(e),n.sort((i,a)=>i.relativePath.localeCompare(a.relativePath))}async function Yhe(t,e){let n=JSON.parse(t.content.toString("utf8")),r=Os(t.content);if(t.absolutePath.endsWith(".props.json")){let o=n,s=t.absolutePath.replace(/\.props\.json$/,".value.json");if(LT(o,e.has(s)))return{change:{path:t.relativePath,ownership:"canonical_mirror",operation:"delete",reason:"redundant_empty_metadata",beforeHash:r},after:null}}let i="serializer_regeneration";Rt.basename(t.absolutePath)==="_tree.json"&&n!==null&&typeof n=="object"&&!Array.isArray(n)&&Object.prototype.hasOwnProperty.call(n,"syncedAt")&&(delete n.syncedAt,i="volatile_metadata_removal");let a=Buffer.from(ys(n),"utf8");return t.content.equals(a)?null:{change:{path:t.relativePath,ownership:"canonical_mirror",operation:"modify",reason:i,beforeHash:r,afterHash:Os(a)},after:a}}function Xhe(t){return t==="_tree.json"||t.endsWith(".props.json")||t.endsWith(".value.json")}function b_(t,e){return Rt.relative(t,e).replaceAll(Rt.sep,"/")}function Os(t){return Ghe("sha256").update(t).digest("hex")}function ZB(t){return Os(Buffer.from(t,"utf8"))}function Qhe(t){return Mr.readFile(t).catch(e=>{if(e.code==="ENOENT")return null;throw e})}function eye(t,e){return t.path.localeCompare(e.path)||t.operation.localeCompare(e.operation)||t.reason.localeCompare(e.reason)}function tye(t,e){return(t.path??"").localeCompare(e.path??"")||t.reason.localeCompare(e.reason)}function nye(t){let e=new Set;return t.filter(n=>{let r=`${n.path??""}\0${n.reason}`;return e.has(r)?!1:(e.add(r),!0)})}async function WB(t){let e=new Map;async function n(r){let i=await Mr.readdir(r,{withFileTypes:!0}).catch(a=>{if(a.code==="ENOENT")return[];throw a});for(let a of i){let o=Rt.join(r,a.name);a.isDirectory()?await n(o):(a.name.endsWith(".server.luau")||a.name.endsWith(".client.luau")||a.name.endsWith(".module.luau"))&&e.set(Rt.relative(t,o).replaceAll(Rt.sep,"/"),Os(await Mr.readFile(o)))}}return await n(t),e}function rye(t,e){if(t.size!==e.size)return!1;for(let[n,r]of t)if(e.get(n)!==r)return!1;return!0}Ui();ae();var iye=5;function GB(t){if(!t||typeof t!="object")return;let e=t;if(Array.isArray(e.instances))for(let n of e.instances)Array.isArray(n.properties)&&n.properties.length===0&&(n.properties={}),Array.isArray(n.attributes)&&n.attributes.length===0&&(n.attributes={});if(Array.isArray(e.changes))for(let n of e.changes)Array.isArray(n.properties)&&n.properties.length===0&&(n.properties={}),Array.isArray(n.attributes)&&n.attributes.length===0&&(n.attributes={})}function aye(t){return t.type==="instanceAdded"||t.type==="instanceRemoved"||t.type==="instanceRenamed"||t.type==="instanceMoved"||t.type==="scriptSourceChanged"}var pi=class{config;places;apiHandler;changeProcessor;initHandler;reverseHandler;migrationService;reverseDetectorFactory;placeDisposals=new Map;activeFullSyncPlaceId=null;activeRuntimeSyncPlaceId=null;currentConnectedPlaceId=null;currentConnectedPlaceName=null;constructor(e,n={}){this.config=new wx(e,n),this.reverseDetectorFactory=n.reverseDetectorFactory??(r=>new l_(r.explorerRoot,r.syncIndex,{placeId:r.placeId})),this.apiHandler=new g_(this),this.changeProcessor=new f_(this),this.initHandler=new h_(this),this.reverseHandler=new v_(this),this.places=new o_({max:iye,dispose:(r,i)=>{this.trackPlaceDisposal(r,i)}}),this.migrationService=new x_(this)}getSyncRoot(){return this.config.getSyncRoot()}async getOrCreatePlaceContext(e,n){let r=this.places.get(e);if(r&&n){let i=this.config.getPlaceRoot(e),a=await this.config.resolvePlaceRoot(e,n);a!==i&&(y.info("Place root migrated, recreating context",{placeId:e,from:i,to:a}),this.places.delete(e),r=void 0)}if(!r){await this.waitForPlaceDisposal(e);let i=await this.config.resolvePlaceRoot(e,n),a=HT.join(i,"explorer"),o=await r8(i),s=o.formatVersion;o.recovery&&y.warn("Recovered corrupt sync index",{indexPath:o.recovery.indexPath,quarantinePath:o.recovery.quarantinePath,formatVersion:o.recovery.formatVersion,reason:o.recovery.reason}),await ZT.mkdir(i,{recursive:!0}),await ZT.mkdir(a,{recursive:!0});let c=new eu(i,a,s);await c.loadFromDisk();let l=new tu(this.config,c,e,s),u=new c_(this.config,c,i);if(l.startChangeLogFlusher(),r={placeId:e,placeName:"",formatVersion:s,pendingIndexRecovery:o.recovery??null,index:c,writer:l,reader:u,fileWatcher:null,state:"idle",activeClientId:null,activeFullSyncSessionId:null,instanceCount:0,scriptCount:0,lastFullSync:null,lastIncrementalSync:null,tmpIndex:null,tmpWriter:null,incompleteSyncTimer:null,syncInitRequestsInFlight:0,changesSinceLastSave:0,directions:{...gs},applyModes:{...hs},autoApplyDeletes:!1,forwardRestoreQueue:[],syncProgress:null,collisionDirMap:null,activeSyncIdentityScope:null},this.places.set(e,r),r.pendingIndexRecovery){let d=r.pendingIndexRecovery;l.appendHistory({timestamp:new Date().toISOString(),type:"indexRecovery",direction:"forward",source:"studio",path:d.indexPath,details:JSON.stringify({quarantinePath:d.quarantinePath,formatVersion:d.formatVersion,reason:d.reason})}),await l.flushHistory(),r.pendingIndexRecovery=null}y.info("Created new place context",{placeId:e,placeRoot:i})}return r}async handleSyncInit(e,n){try{GB(e.body);let r=LB(e.body);if(!r.success){n.status(400).json({error:"Validation error",message:r.error});return}let i=r.data,a=i.phase==="start"?i.placeId??null:i.phase==="chunk"||i.phase==="complete"?this.activeFullSyncPlaceId:null;if(a==null){n.status(400).json({error:"Missing placeId",message:"placeId is required in start phase or must be set by previous start"});return}switch(i.phase){case"start":this.setCurrentConnectedPlace(a,i.placeName),await this.initHandler.handleInitStart(a,i,n);break;case"chunk":await this.initHandler.handleInitChunk(a,i,n);break;case"complete":await this.initHandler.handleInitComplete(a,i,n);break}}catch(r){this.sendError(n,r,"handleSyncInit")}}async handleSyncUpdate(e,n){try{GB(e.body);let r=zB(e.body);if(!r.success){n.status(400).json({error:"Validation error",message:r.error});return}let i=r.data,a=i.placeId??this.getDefaultRuntimePlaceId();if(a==null){n.status(400).json({error:"Missing placeId",message:"placeId is required in body or must have an active sync session"});return}let o=await this.getOrCreatePlaceContext(a);if(this.setCurrentConnectedPlace(a,o.placeName||this.currentConnectedPlaceName),o.activeFullSyncSessionId!==null||o.state==="initializing"){n.status(409).json({error:"Conflict",message:`Full sync in progress for place ${a}`});return}o.activeClientId=i.clientId,this.touchRuntimePlace(a);let s=NB(o,i.changes);y.info("Sync update received",{placeId:a,clientId:i.clientId,changeCount:s.length,receivedCount:i.changes.length,types:s.map(m=>m.type)});let c=[],l=[],u=0,d=!1,p=new Map;for(let m of s)try{let g=await this.changeProcessor.processChangeForPlace(o,m,p);g?l.push(g):(u++,aye(m)&&(d=!0))}catch(g){let h="path"in m?m.path:"oldPath"in m?m.oldPath:"unknown";c.push({path:h,error:g instanceof Error?g.message:String(g)})}for(let m of p.values())try{await u_(o,m)}catch(g){c.push({path:m.instancePath,error:g instanceof Error?g.message:String(g)})}if(d)try{let m=this.config.getSyncRoot(),g=this.config.getPlaceRoot(a);await Tx(m,g,o.formatVersion,o.writer),await zl(m,o.writer)}catch(m){y.warn("Failed to refresh sourcemaps after incremental sync update",{placeId:a,error:m instanceof Error?m.message:String(m)})}o.changesSinceLastSave+=u,o.changesSinceLastSave>=MB&&(await o.index.saveToDisk(),o.changesSinceLastSave=0),o.lastIncrementalSync=new Date().toISOString();let f={processed:u,failed:c.length,errors:c,syncedAt:o.lastIncrementalSync};l.length>0&&(f.conflicts=l),n.status(200).json(f)}catch(r){this.sendError(n,r,"handleSyncUpdate")}}getDefaultRuntimePlaceId(){return this.currentConnectedPlaceId}getDefaultRuntimePlaceName(){if(this.currentConnectedPlaceName)return this.currentConnectedPlaceName;if(this.currentConnectedPlaceId!==null&&this.currentConnectedPlaceId!==void 0){let e=this.places.get(this.currentConnectedPlaceId);if(e?.placeName)return e.placeName}return null}setCurrentConnectedPlace(e,n){if(this.currentConnectedPlaceId=e,e==null){this.currentConnectedPlaceName=null;return}if(typeof n=="string"&&n.length>0){this.currentConnectedPlaceName=n;let i=this.places.get(e);i&&(i.placeName=n);return}let r=this.places.get(e);r?.placeName&&(this.currentConnectedPlaceName=r.placeName)}clearCurrentConnectedPlaceIfMatch(e){this.currentConnectedPlaceId===e&&(this.currentConnectedPlaceId=null,this.currentConnectedPlaceName=null)}touchRuntimePlace(e){this.activeRuntimeSyncPlaceId=e}clearRuntimePlaceIfMatch(e){this.activeRuntimeSyncPlaceId===e&&(this.activeRuntimeSyncPlaceId=null)}resolveQueryPlaceId(e,n="runtime"){let r=e.query.placeId;if(r){let i=parseInt(r,10);if(!isNaN(i))return i}return n==="full"?this.activeFullSyncPlaceId:this.getDefaultRuntimePlaceId()}async handleSyncStatus(e,n){try{let r=u=>({state:"idle",instanceCount:0,scriptCount:0,lastFullSync:null,lastIncrementalSync:null,syncRoot:u,activeClientId:null,reverseSyncAvailable:!1,modifiedFileCount:0,autoApplyDeletes:!1,reverseDetectorActive:!1,reverseDetectorMode:gt,fileWatcherActive:!1}),i=this.resolveQueryPlaceId(e);if(i==null){let u=r(this.config.getSyncRoot());n.status(200).json(u);return}let a=this.places.get(i);if(!a){let u=r(this.config.getPlaceRoot(i));n.status(200).json(u);return}let o=a.fileWatcher?.getPendingCount()??0,s=a.fileWatcher?.isActivelyScanning()??!1,c=a.fileWatcher!==null;this.touchRuntimePlace(i);let l={state:a.state,instanceCount:a.instanceCount,scriptCount:a.scriptCount,lastFullSync:a.lastFullSync,lastIncrementalSync:a.lastIncrementalSync,syncRoot:this.config.getPlaceRoot(i),activeClientId:a.activeClientId,reverseSyncAvailable:o>0,modifiedFileCount:o,applyModes:a.applyModes,autoApplyDeletes:a.autoApplyDeletes,directions:a.directions,reverseDetectorActive:s,reverseDetectorMode:gt,fileWatcherActive:c,forwardOnlyClasses:[...Ll]};n.status(200).json(l)}catch(r){this.sendError(n,r,"handleSyncStatus")}}async handleSyncStop(e,n){try{let r=e.body,i=r.placeId??this.getDefaultRuntimePlaceId(),a=Zf(r);if(y.info("handleSyncStop requested",{placeId:i,clientId:r.clientId??null,identityScope:a,reason:r.reason??"requested"}),i==null){n.status(200).json({status:"idle",state:"idle",placeId:null,message:"No active sync place"});return}let o=this.places.get(i);if(!o){y.info("handleSyncStop no place context",{placeId:i,clientId:r.clientId??null}),n.status(200).json({status:"idle",state:"idle",placeId:i,message:`No sync context for place ${i}`});return}let s=!!(r.clientId&&o.activeClientId&&r.clientId!==o.activeClientId),c=o.activeFullSyncSessionId!==null||o.state==="syncing"||o.state==="initializing",l=!!(a&&o.activeSyncIdentityScope&&a===o.activeSyncIdentityScope);if(s&&c&&!l){y.warn("handleSyncStop rejected due to active client mismatch",{placeId:i,requestedClientId:r.clientId,activeClientId:o.activeClientId,requestedIdentityScope:a,activeIdentityScope:o.activeSyncIdentityScope,state:o.state,activeFullSyncSessionId:o.activeFullSyncSessionId}),n.status(409).json({error:"Conflict",message:`This sync session belongs to client ${o.activeClientId}`});return}s&&l&&y.info("handleSyncStop accepted stale client cleanup by identity scope",{placeId:i,requestedClientId:r.clientId,activeClientId:o.activeClientId,identityScope:a,state:o.state});let u=o.activeFullSyncSessionId,d=o.state,p=o.fileWatcher!==null;if(u&&(this.initHandler.clearPreserveLocalFiles(u),this.initHandler.clearPendingServiceTrees(u)),o.fileWatcher&&(y.info("handleSyncStop suspending reverse detector",{placeId:i,state:o.state,activeClientId:o.activeClientId,mode:gt}),o.fileWatcher.beginFullSyncReplacement()),o.incompleteSyncTimer&&(clearTimeout(o.incompleteSyncTimer),o.incompleteSyncTimer=null),u){let f=this.config.getPlaceRoot(i),m=HT.join(f,`explorer_tmp_${u}`);await ZT.rm(m,{recursive:!0,force:!0}).catch(()=>{})}o.tmpWriter&&(o.tmpWriter.stopChangeLogFlusher(),o.tmpWriter=null),o.tmpIndex=null,o.collisionDirMap=null,o.activeSyncIdentityScope=null,o.syncInitRequestsInFlight=0,o.activeFullSyncSessionId=null,o.syncProgress=null,o.state="idle",o.activeClientId=null,o.instanceCount=0,o.scriptCount=0,o.forwardRestoreQueue=[],this.activeFullSyncPlaceId===i&&(this.activeFullSyncPlaceId=null),this.clearRuntimePlaceIfMatch(i),y.info("handleSyncStop responding idle",{placeId:i,previousState:d,activeFullSyncSessionId:u,hadWatcher:p}),y.info("Sync stopped",{placeId:i,reason:r.reason??"requested"}),n.status(200).json({status:"stopped",state:"idle",placeId:i})}catch(r){this.sendError(n,r,"handleSyncStop")}}async initialize(){try{await this.config.loadFromMeta(),await HB(this.config.getSyncRoot()),await this.initHandler.cleanupStaleTempDirs(),y.info("SyncController initialized")}catch(e){y.error("SyncController initialization failed",e instanceof Error?e:new Error(String(e)))}}async previewMigration(e){return this.migrationService.preview(e)}async applyMigration(e){return this.migrationService.apply(e)}async shutdown(){try{y.info("SyncController shutdown: clearing place contexts",{placeCount:this.places.size}),this.places.clear(),await Promise.all(this.placeDisposals.values()),y.info("SyncController shut down")}catch(e){y.error("SyncController shutdown error",e instanceof Error?e:new Error(String(e)))}}trackPlaceDisposal(e,n){let r=this.disposePlaceContext(e,n).catch(i=>{y.error("Place context dispose failed",i instanceof Error?i:new Error(String(i)))});this.placeDisposals.set(n,r),r.then(()=>{this.placeDisposals.get(n)===r&&this.placeDisposals.delete(n)})}async waitForPlaceDisposal(e){await this.placeDisposals.get(e)}async disposePlaceContext(e,n){y.info("Disposing place context (LRU eviction)",{placeId:n}),this.activeFullSyncPlaceId===n&&(this.activeFullSyncPlaceId=null);let r=e.index.toSyncIndexData(),i=e.fileWatcher,a=e.tmpWriter;e.fileWatcher=null,e.tmpWriter=null,e.incompleteSyncTimer&&(clearTimeout(e.incompleteSyncTimer),e.incompleteSyncTimer=null),e.activeFullSyncSessionId&&this.initHandler.clearPendingServiceTrees(e.activeFullSyncSessionId),e.tmpIndex=null,e.collisionDirMap=null,e.activeSyncIdentityScope=null,e.syncInitRequestsInFlight=0;let o=[e.index.savePersistenceStateToDisk(r).catch(s=>{y.error("Error saving index during dispose",s)}),e.writer.stopChangeLogFlusher().catch(s=>{y.error("LRU dispose \uC911 changelog flush \uC2E4\uD328",s)})];i&&(y.info("Disposing place context: stopping reverse detector",{placeId:n,reason:"lru-dispose",mode:gt}),o.push(i.stop("lru-dispose").catch(s=>{y.error("Error stopping reverse detector during dispose",s)}))),a&&o.push(a.stopChangeLogFlusher().catch(s=>{y.error("LRU dispose \uC911 \uC784\uC2DC changelog flush \uC2E4\uD328",s)})),await Promise.all(o),e.index.clearAllMaps()}async atomicWriteFile(e,n){await fn(e,n)}async handlePreCheck(e,n){try{await this.apiHandler.handlePreCheck(e,n)}catch(r){this.sendError(n,r,"handlePreCheck")}}async handleSyncDirections(e,n){try{await this.apiHandler.handleSyncDirections(e,n)}catch(r){this.sendError(n,r,"handleSyncDirections")}}async handleForwardRestoreList(e,n){try{await this.apiHandler.handleForwardRestoreList(e,n)}catch(r){this.sendError(n,r,"handleForwardRestoreList")}}async handleReversePending(e,n){try{await this.reverseHandler.handleReversePending(e,n)}catch(r){this.sendError(n,r,"handleReversePending")}}async handleReverseSyncChanges(e,n){try{await this.reverseHandler.handleReverseSyncChanges(e,n)}catch(r){this.sendError(n,r,"handleReverseSyncChanges")}}async handleReverseSyncResult(e,n){try{await this.reverseHandler.handleReverseSyncResult(e,n)}catch(r){this.sendError(n,r,"handleReverseSyncResult")}}async handleResolveConflict(e,n){try{await this.reverseHandler.handleResolveConflict(e,n)}catch(r){this.sendError(n,r,"handleResolveConflict")}}async handleReverseRescan(e,n){try{await this.reverseHandler.handleReverseRescan(e,n)}catch(r){this.sendError(n,r,"handleReverseRescan")}}async handleSyncHistory(e,n){try{await this.apiHandler.handleSyncHistory(e,n)}catch(r){this.sendError(n,r,"handleSyncHistory")}}async startFileWatcherForPlace(e){if(e.state!=="syncing"){y.debug("Skipping reverse detector start - place not syncing",{placeId:e.placeId,state:e.state});return}if(e.fileWatcher){if(e.fileWatcher.isActivelyScanning()){y.info("startFileWatcherForPlace: reusing active reverse detector",{placeId:e.placeId,mode:gt});return}y.info("startFileWatcherForPlace: resuming paused reverse detector",{placeId:e.placeId,mode:gt}),e.fileWatcher.endFullSyncReplacement();return}let n=this.createReverseChangeDetector(e);this.configureReverseChangeDetector(e,n),e.fileWatcher=n,n.start().then(()=>{e.fileWatcher===n&&y.info("Reverse detector started for reverse sync",{placeId:e.placeId,mode:gt})}).catch(r=>{y.warn("Failed to start reverse detector",{placeId:e.placeId,mode:gt,error:r instanceof Error?r.message:String(r)}),e.fileWatcher===n&&(e.fileWatcher=null)})}createReverseChangeDetector(e){return this.reverseDetectorFactory({explorerRoot:HT.join(this.config.getPlaceRoot(e.placeId),"explorer"),syncIndex:e.index,placeId:e.placeId})}configureReverseChangeDetector(e,n){e.writer.setOnWriteCallback((r,i,a)=>{n.suppressPath(r,i,a)}),n.setDirectionChecker(r=>{let i=t8(r);return e.directions[i]}),n.setOnForwardViolation(r=>{e.forwardRestoreQueue.includes(r)||(e.forwardRestoreQueue.push(r),y.info("Forward violation queued for restore",{placeId:e.placeId,relativePath:r,queueSize:e.forwardRestoreQueue.length}))})}getStatusSummary(){return this.apiHandler.getStatusSummary()}getDirectionForCategory(e){return this.apiHandler.getDirectionForCategory(e)}getStatusDirect(e){return this.apiHandler.getStatusDirect(e)}async getHistoryDirect(e,n){return this.apiHandler.getHistoryDirect(e,n)}getDirectionsDirect(e){return this.apiHandler.getDirectionsDirect(e)}getProgressDirect(e){return this.apiHandler.getProgressDirect(e)}async readSyncedFile(e,n){return this.apiHandler.readSyncedFile(e,n)}async writeSyncedFile(e,n,r){await this.apiHandler.writeSyncedFile(e,n,r)}async executeViaDisk(e,n){return this.apiHandler.executeViaDisk(e,n)}sendError(e,n,r){let i=n instanceof Error?n.message:String(n);if(i.includes("Path traversal detected")){e.status(403).json({error:"Forbidden",message:i});return}let a=n.code;if(a==="ENOSPC"||a==="EPERM"||a==="EACCES"){y.warn(`SyncController.${r} disk error`,{code:a,message:i}),e.status(500).json({error:"Disk error",message:i,code:a,operation:r});return}y.error(`SyncController.${r} failed`,n instanceof Error?n:new Error(i)),e.status(500).json({error:"Internal error",message:`${r}: ${i}`})}};import{randomUUID as oye}from"crypto";function KB(t,e){let n=oye(),r=n.replace(/-/g,"").substring(0,8).toUpperCase(),i=`${r.substring(0,4)}-${r.substring(4,8)}`;return{config:t,app:e,instanceId:n,sessionId:i,startTime:Date.now(),baseUrl:`http://${t.httpHost}:${t.httpPort}`,commandQueue:new Map,pendingCommands:new Map,globalPendingCommands:[],totalCommandsProcessed:0,pluginClients:new Map,pluginCommandSessionsByClientId:new Map,pluginCommandClientIdsByProcessToken:new Map,mcpInstances:new Map,cachedSelectionMap:new Map,studioRoutingMode:"recentPriority",pinnedTargetClientId:null,isClientMode:!1,clientModeHealthTimer:null,clientModeConsecutiveHealthFailures:0,clientModeUpstreamReachable:!0,clientModeUpstreamContextCaptureEnabled:!0,clientModeLastHealthSuccessAt:null,clientModeLastHealthFailureAt:null,clientModeLastHealthError:null,shuttingDown:!1,onUpstreamPermanentlyDown:null,clientModeIdleTimeoutMs:t.clientModeIdleTimeoutMs??36e5,clientModeIdleWatchdogTimer:null,shutdownFn:null,historyManager:null,analyticsManager:null,executionContextManager:null,licenseState:null,syncController:null,internalCommandExecutor:null,dashboardFolderPicker:null,assetLibraryOpenCloudServiceFactory:null,projectChangesCleanupScheduler:null,activeSyncOwnerInstanceId:null,activeProjectRoot:null,pendingDashboardSyncRootPin:null,playtestControlCommand:null,dashboardSyncRootSwitchInFlight:!1,uiStudioRecorders:new Map,aiClientName:"",pluginVersion:"",syncedSessionToken:null,serverLastCommandAt:null}}var JB=Dt(Ya(),1);ae();function YB(t){let e=JB.default.json({limit:"5mb"});t.app.use((n,r,i)=>{if(n.path.startsWith("/sync/")){i();return}e(n,r,i)}),t.app.use((n,r,i)=>{r.setHeader("Access-Control-Allow-Origin","http://localhost:3002"),r.setHeader("Access-Control-Allow-Methods","GET, POST, OPTIONS"),r.setHeader("Access-Control-Allow-Headers","Content-Type"),i()}),t.app.use((n,r,i)=>{y.debug(`${n.method} ${n.path}`,{ip:n.ip}),i()})}Ua();import{randomUUID as X_}from"crypto";Ua();ae();function sye(){let t=process.env.WEPPY_ROBLOX_MCP_VERSION?.trim();return t||null}var nt=sye()??"2.11.2";Fi();Vn();Yf();no();ql();Ua();no();var r5="studio-",lye=/^studio-[1-9]\d*$/;function I_(t){return lye.test(t)}function i5(t,e){let n=new Set;for(let r of t)e!==void 0&&r.clientId===e||r.targetAlias&&I_(r.targetAlias)&&n.add(r.targetAlias);return n}function uye(t,e){let n=i5(t,e),r=1;for(;n.has(`${r5}${r}`);)r+=1;return`${r5}${r}`}function C_(t,e){let n=i5(t,e.clientId);return e.targetAlias&&I_(e.targetAlias)&&!n.has(e.targetAlias)||(e.targetAlias=uye(t,e.clientId)),e.targetAlias}ql();function P_(t){for(let e of t)C_(t,e)}function k_(t){let e={clientId:t.clientId,targetAlias:t.targetAlias??t.clientId.slice(0,8),lastSeen:t.lastSeen,connectedAt:t.connectedAt,transport:"websocket",connectionState:t.commandSessionState??He.CONNECTED};return t.placeId!==void 0&&(e.placeId=t.placeId),t.placeName!==void 0&&(e.placeName=t.placeName),t.pluginVersion!==void 0&&(e.pluginVersion=t.pluginVersion),t.studioVersion!==void 0&&(e.studioVersion=t.studioVersion),t.lastRoutedAt!==void 0&&(e.lastRoutedAt=t.lastRoutedAt),t.processToken!==void 0&&(e.processToken=t.processToken),t.inFlightRequestId!==void 0&&(e.inFlightRequestId=t.inFlightRequestId),t.studioState!==void 0&&(e.studioState=t.studioState),t.studioStateSource!==void 0&&(e.studioStateSource=t.studioStateSource),t.studioStateUpdatedAt!==void 0&&(e.studioStateUpdatedAt=t.studioStateUpdatedAt),t.playtestMode!==void 0&&(e.playtestMode=t.playtestMode),e}function QT(t){let e=$n(t);return P_(e),jf(e.map(k_),null)}function E_(t){let e=new Set;t.aiClientName&&e.add(t.aiClientName);for(let n of t.mcpInstances.values())n.aiClientName&&e.add(n.aiClientName);return Array.from(e)}function a5(t){let n=Date.now();for(let[r,i]of t.mcpInstances)i.lastSeen&&n-i.lastSeen>15e3&&(t.mcpInstances.delete(r),i.sessionId&&t.executionContextManager?.endSession(i.sessionId),y.debug("Removed stale MCP instance",{instanceId:r,lastSeen:i.lastSeen}))}function o5(t,e,n){let r=e.query.clientId;if(r&&t.pluginClients.has(r)){let i=t.pluginClients.get(r);i.lastSeen=Date.now()}try{let i=e.body;if(!i||!Array.isArray(i.selection)||typeof i.count!="number"){y.warn("Invalid selection update request",{body:i}),n.status(400).json({error:"Invalid request body"});return}let a=r||"unknown",o=Date.now();t.cachedSelectionMap.set(a,{selection:i.selection,count:i.count,timestamp:o,clientId:a}),y.debug("Selection cache updated",{count:i.count,clientId:a,timestamp:o}),n.json({status:"ok",timestamp:o})}catch(i){y.error("Error handling selection update",i),n.status(500).json({error:"Internal server error"})}}function s5(t,e,n){let r=parseInt(e.query.maxAge)||3e4,i=Xf(t,r);i?n.json({cached:!0,...i}):n.json({cached:!1,message:"No cached selection available"})}function Xf(t,e=3e4,n){if(t.cachedSelectionMap.size===0)return null;let r;if(n)r=t.cachedSelectionMap.get(n);else for(let a of t.cachedSelectionMap.values())(!r||a.timestamp>r.timestamp)&&(r=a);if(!r)return null;let i=Date.now()-r.timestamp;return e===0||i<=e?r:null}function eA(t,e){let n=t.pluginClients.get(e.clientId),r=Date.now(),i=[...t.pluginClients.values()].filter(c=>c.clientId===e.clientId||c.commandSessionState!==He.DISCONNECTED),a=n??{clientId:e.clientId,connectedAt:r,lastSeen:r,commandsProcessed:0,connectionType:"polling"},o=C_(i,a),s={clientId:e.clientId,targetAlias:o,projectName:e.projectName??n?.projectName,placeName:e.placeName??n?.placeName,placeId:e.placeId??n?.placeId,pluginVersion:e.pluginVersion??n?.pluginVersion,studioVersion:e.studioVersion??n?.studioVersion,connectedAt:n?.connectedAt||r,lastSeen:r,commandsProcessed:n?.commandsProcessed||0,connectionType:n?.connectionType||"polling",inFlightRequestId:n?.inFlightRequestId,studioState:n?.studioState,studioStateSource:n?.studioStateSource,studioStateUpdatedAt:n?.studioStateUpdatedAt,playtestMode:n?.playtestMode,...n?.commandSessionState?{commandSessionState:n.commandSessionState}:{},...n?.processToken?{processToken:n.processToken}:{}};return t.pluginClients.set(e.clientId,s),t.syncController&&typeof t.syncController.setCurrentConnectedPlace=="function"&&typeof e.placeId=="number"&&Number.isFinite(e.placeId)&&t.syncController.setCurrentConnectedPlace(e.placeId,e.placeName??null),t.pendingCommands.has(e.clientId)||t.pendingCommands.set(e.clientId,[]),e.pluginVersion&&(t.pluginVersion=e.pluginVersion),typeof s.placeId=="number"&&Number.isFinite(s.placeId)&&Yx(t,s.placeId,s.placeName??null),t.analyticsManager&&(e.pluginVersion&&t.analyticsManager.setPluginVersion(e.pluginVersion),t.analyticsManager.trackPluginConnected()),y.info("Plugin client registered",{clientId:e.clientId,targetAlias:o,projectName:e.projectName,placeName:e.placeName,isReconnect:!!n}),{clientInfo:s,sessionId:t.sessionId,mcpVersion:nt,mcpInstanceCount:t.mcpInstances.size+1,aiClientNames:E_(t)}}function tA(t,e){let n=t.pluginClients.get(e),r=t.pluginClients.has(e),i=n?.commandSessionState===He.CONNECTED;if(t.pluginClients.delete(e),t.pendingCommands.delete(e),r&&Ul(t,e),r&&t.syncController&&typeof t.syncController.clearCurrentConnectedPlaceIfMatch=="function"&&typeof n?.placeId=="number"&&Number.isFinite(n.placeId)){let a=[...t.pluginClients.values()].filter(o=>typeof o.placeId=="number"&&Number.isFinite(o.placeId)).sort((o,s)=>s.lastSeen-o.lastSeen)[0];a?t.syncController.setCurrentConnectedPlace?.(a.placeId??null,a.placeName??null):t.syncController.clearCurrentConnectedPlaceIfMatch(n.placeId)}return i&&Mf(t,e,"disconnected",n),y.info("Plugin client unregistered",{clientId:e,existed:r}),r}function R_(t,e,n){try{let r=e.body;if(!r.clientId){n.status(400).json({error:"Missing clientId"});return}let i=eA(t,{clientId:r.clientId,projectName:r.projectName,placeName:r.placeName,placeId:r.placeId,pluginVersion:r.pluginVersion,studioVersion:r.studioVersion});n.json({status:"ok",clientId:r.clientId,targetAlias:i.clientInfo.targetAlias,serverInstanceId:t.instanceId,sessionId:i.sessionId,mcpVersion:i.mcpVersion,connectedAt:i.clientInfo.connectedAt,aiClientNames:i.aiClientNames,serverStartTime:t.startTime,mcpInstanceCount:i.mcpInstanceCount})}catch(r){y.error("Error registering plugin client",r),n.status(500).json({error:"Internal server error"})}}function T_(t,e,n){let r=e.body?.clientId;if(!r){n.status(400).json({error:"Missing clientId"});return}let i=tA(t,r);n.json({status:"ok",existed:i})}function c5(t,e,n){try{let r=e.body;if(!r.instanceId){n.status(400).json({error:"Missing instanceId"});return}let i=Date.now(),a={instanceId:r.instanceId,...typeof r.sessionId=="string"?{sessionId:r.sessionId}:{},pid:r.pid,connectedAt:i,isServer:!1,lastSeen:i};r.aiClientName&&(a.aiClientName=r.aiClientName),r.cwd&&(a.cwd=r.cwd),"projectRoot"in r&&(a.projectRoot=r.projectRoot),t.mcpInstances.set(r.instanceId,a),ot(t,"mcp_status",{aiClientName:a.aiClientName??"Unknown",instanceId:r.instanceId,status:"registered"}),Zl(t,{timestamp:new Date().toISOString(),type:"mcp",status:"registered",instanceId:r.instanceId,message:`MCP registered \u2014 ${a.aiClientName??r.instanceId}`,...a.aiClientName?{aiClientName:a.aiClientName}:{}}),y.info("MCP instance registered (client mode)",{instanceId:r.instanceId,pid:r.pid,cwd:r.cwd}),n.json({status:"ok",instanceId:r.instanceId,serverInstanceId:t.instanceId,sessionId:t.sessionId,mcpVersion:nt,mcpInstanceCount:t.mcpInstances.size+1})}catch(r){y.error("Error registering MCP instance",r),n.status(500).json({error:"Internal server error"})}}function l5(t,e,n){let r=e.body?.instanceId;if(!r){n.status(400).json({error:"Missing instanceId"});return}let i=t.mcpInstances.get(r),a=!!i;t.mcpInstances.delete(r),i?.sessionId&&t.executionContextManager?.endSession(i.sessionId),a&&(ot(t,"mcp_status",{aiClientName:i?.aiClientName??"Unknown",instanceId:r,status:"unregistered"}),Zl(t,{timestamp:new Date().toISOString(),type:"mcp",status:"unregistered",instanceId:r,message:`MCP unregistered \u2014 ${i?.aiClientName??r}`,...i?.aiClientName?{aiClientName:i.aiClientName}:{}})),y.info("MCP instance unregistered",{instanceId:r,existed:a}),n.json({status:"ok",existed:a})}function u5(t,e,n){let{instanceId:r,aiClientName:i}=e.body;if(r&&i){let a=t.mcpInstances.get(r);a&&(a.aiClientName=i)}n.json({status:"ok"})}function d5(t){let e=3e4,n=Date.now(),r=Tr({appDataDir:t.config.appDataDir});for(let[a,o]of t.pluginClients)n-o.lastSeen>e&&(t.pluginClients.delete(a),t.pendingCommands.delete(a),Ul(t,a));a5(t);let i=$n(t);return P_(i),{serverInstanceId:t.instanceId,sessionId:t.sessionId,mcpVersion:nt,uptime:n-t.startTime,serverStartTime:t.startTime,serverExecutable:process.execPath,serverHost:t.config.httpHost,serverPort:t.config.httpPort,serverPid:process.pid,pluginClients:i.map(k_),studioRoutingMode:t.studioRoutingMode,pinnedTargetClientId:t.pinnedTargetClientId,mcpInstances:[{instanceId:t.instanceId,pid:process.pid,connectedAt:t.startTime,isServer:!0,cwd:process.cwd(),projectRoot:r,lastSeen:n,...t.aiClientName?{aiClientName:t.aiClientName}:{}},...Array.from(t.mcpInstances.values())],mcpInstanceCount:t.mcpInstances.size+1}}function A_(t,e){e.json(d5(t))}function O_(t,e,n){let r=e.query.instanceId;r&&t.mcpInstances.has(r)&&(t.mcpInstances.get(r).lastSeen=Date.now()),a5(t);let i=$n(t);P_(i);let s={...{status:"online",connectedClients:i.length,queuedCommands:B8(t),uptime:Date.now()-t.startTime,version:nt,enableContextCapture:t.executionContextManager?.isEnabled()??t.config.enableContextCapture??!0,isClientMode:t.isClientMode,shuttingDown:t.shuttingDown,pid:process.pid,sessionId:t.sessionId,nodeVersion:process.version,studioRoutingMode:t.studioRoutingMode,pinnedTargetClientId:t.pinnedTargetClientId},instanceId:t.instanceId,mcpInstanceCount:t.mcpInstances.size+1,aiClientNames:E_(t),pluginVersion:t.pluginVersion||void 0,dashboardSseClients:t.dashboardSseClients?.size??0,websocketClients:i.length,pluginClients:i.map(k_),...t.isClientMode?{upstream:{reachable:t.clientModeUpstreamReachable,consecutiveFailures:t.clientModeConsecutiveHealthFailures,lastSuccessAt:t.clientModeLastHealthSuccessAt,lastFailureAt:t.clientModeLastHealthFailureAt,lastError:t.clientModeLastHealthError,baseUrl:t.baseUrl}}:{}};n.json(s)}function p5(t,e,n,r){let i=e.ip||e.socket.remoteAddress||"";if(!(i==="127.0.0.1"||i==="::1"||i==="::ffff:127.0.0.1"||i==="localhost")){y.warn("Shutdown request rejected from non-localhost",{ip:i}),n.status(403).json({error:"Forbidden: localhost only"});return}y.info("Shutdown request received, initiating graceful shutdown",{requestedBy:i,uptime:Date.now()-t.startTime}),n.json({status:"shutting_down",message:"Server will shutdown gracefully",pid:process.pid}),setTimeout(async()=>{try{await r(),y.info("Graceful shutdown completed"),process.exit(0)}catch(o){y.error("Error during graceful shutdown",o),process.exit(1)}},100)}async function $_(t){if(t.isClientMode)try{let e=await fetch(`${t.baseUrl}/connection-info`);if(e.ok)return await e.json()}catch(e){y.warn("Failed to fetch connection info from server",{error:e})}return d5(t)}no();var ht={bridgeRunTest:"manage_studio_run_test_bridge",placeInfo:"system_info_place_info",clearLogs:"manage_logs_clear",createScript:"manage_scripts_create",getLogs:"manage_logs_get",deleteScript:"manage_scripts_delete",canonical:{playStart:"manage_studio_play_start",playStop:"manage_studio_play_stop",playPause:"manage_studio_play_pause",playResume:"manage_studio_play_resume",playStatus:"manage_studio_play_status",runTest:"manage_studio_run_test"}},pye=new Set([ht.canonical.runTest]),fye=new Set([ht.canonical.playStop]),D2e=new Set([ht.canonical.playStart,ht.canonical.playStop,ht.canonical.playPause,ht.canonical.playResume,ht.canonical.playStatus]);function fi(t){return pye.has(t)}function Qf(t){return fye.has(t)}var L2e=ht.canonical.playStop,f5=[5e3,15e3];ql();var mye=new Set(["manage_assets_export_selection_rbxm","manage_assets_export_path_rbxm","manage_assets_review_model","manage_assets_generate_model","manage_assets_import_rbxm","manage_assets_generate_thumbnail"]),gn=class t extends Error{code;routing;constructor(e,n,r){super(n),this.name="CommandTargetSelectionError",this.code=e,this.routing=r,Object.setPrototypeOf(this,t.prototype)}};function gye(t={},e){let n={},r=t.clientId,i=t.targetAlias,a=t.placeId;if(r!==void 0){if(typeof r!="string"||r.trim().length===0)throw new gn("invalid_target_selector","clientId target selector must be a non-empty string",{selectionMode:"clientId",...typeof r=="string"?{requestedClientId:r.trim()}:{}});n.requestedClientId=r.trim()}if(i!==void 0){if(typeof i!="string"||i.trim().length===0)throw new gn("invalid_target_selector","targetAlias target selector must be a non-empty string",{selectionMode:"targetAlias",...typeof i=="string"?{requestedTargetAlias:i.trim()}:{}});n.requestedTargetAlias=i.trim()}if(a!==void 0&&hye(e,t)){if(typeof a!="number"||!Number.isFinite(a))throw new gn("invalid_target_selector","placeId target selector must be a finite number",{selectionMode:"placeId"});n.requestedPlaceId=a}return n}function D_(t,e,n={},r){let i=gye(n,r),a=v8(e,t.studioRoutingMode==="pinned"?t.pinnedTargetClientId:null);if(i.requestedClientId!==void 0)return yye(a,i);if(i.requestedTargetAlias!==void 0)return vye(a,i);if(i.requestedPlaceId!==void 0)return bye(a,i);if(t.studioRoutingMode==="pinned"&&t.pinnedTargetClientId!==null){let s=a.find(c=>c.clientId===t.pinnedTargetClientId);if(s)return{targetClientId:s.clientId,routing:Lr("pinnedTarget",i,s)}}let o=a[0];return o?{targetClientId:o.clientId,routing:Lr("recentPriority",i,o)}:{routing:{selectionMode:"globalQueue"}}}function hye(t,e){return!t||!mye.has(t)?!0:e.scope==="shared"}function yye(t,e){let n=t.find(r=>r.clientId===e.requestedClientId);if(!n)throw new gn("target_client_not_found",`Target client not found: ${e.requestedClientId}`,Lr("clientId",e));if(e.requestedTargetAlias!==void 0&&n.targetAlias!==e.requestedTargetAlias)throw new gn("target_selector_mismatch",`Target client ${n.clientId} does not match targetAlias ${e.requestedTargetAlias}`,Lr("clientId",e,n));return m5("clientId",e,n),{targetClientId:n.clientId,routing:Lr("clientId",e,n)}}function vye(t,e){let n=t.find(r=>r.targetAlias!==void 0&&I_(r.targetAlias)&&r.targetAlias===e.requestedTargetAlias);if(!n)throw new gn("target_alias_not_found",`Target alias not found: ${e.requestedTargetAlias}`,Lr("targetAlias",e));return m5("targetAlias",e,n),{targetClientId:n.clientId,routing:Lr("targetAlias",e,n)}}function bye(t,e){let n=t.filter(i=>i.placeId===e.requestedPlaceId);if(n.length===0)throw new gn("target_place_not_found",`Target place not found: ${e.requestedPlaceId}`,Lr("placeId",e));if(n.length>1)throw new gn("target_place_ambiguous",`Target place is ambiguous: ${e.requestedPlaceId}`,Lr("placeId",e));let r=n[0];return{targetClientId:r.clientId,routing:Lr("placeId",e,r)}}function m5(t,e,n){if(e.requestedPlaceId!==void 0&&n.placeId!==e.requestedPlaceId)throw new gn("target_selector_mismatch",`Target client ${n.clientId} is not connected to placeId ${e.requestedPlaceId}`,Lr(t,e,n))}function Lr(t,e,n){let r={selectionMode:t};return e.requestedClientId!==void 0&&(r.requestedClientId=e.requestedClientId),e.requestedTargetAlias!==void 0&&(r.requestedTargetAlias=e.requestedTargetAlias),e.requestedPlaceId!==void 0&&(r.requestedPlaceId=e.requestedPlaceId),n!==void 0&&(r.actualClientId=n.clientId,n.targetAlias!==void 0&&(r.actualTargetAlias=n.targetAlias),n.placeId!==void 0&&(r.actualPlaceId=n.placeId),n.placeName!==void 0&&(r.actualPlaceName=n.placeName)),r}aT();ae();Gf();var $s={query_instances:{discriminator:"action",validActions:new Set(["get","children","find_child","find_descendant","wait_for_child","class_info","search_name","search_class","search_property","search_tag","file_tree","project_structure","descendants","ancestors"]),allowedParams:{query_instances_get:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"]),query_instances_children:new Set(["path","sessionDebugId","siblingIndex","recursive","maxDepth","placeId","clientId","targetAlias"]),query_instances_find_child:new Set(["path","childName","placeId","clientId","targetAlias"]),query_instances_find_descendant:new Set(["path","descendantName","placeId","clientId","targetAlias"]),query_instances_wait_for_child:new Set(["path","childName","timeout","placeId","clientId","targetAlias"]),query_instances_class_info:new Set(["className","placeId","clientId","targetAlias"]),query_instances_search_name:new Set(["root","query","caseSensitive","maxResults","placeId","clientId","targetAlias"]),query_instances_search_class:new Set(["className","root","includeSubclasses","maxResults","placeId","clientId","targetAlias"]),query_instances_search_property:new Set(["root","propertyName","propertyValue","maxResults","placeId","clientId","targetAlias"]),query_instances_search_tag:new Set(["root","tag","maxResults","placeId","clientId","targetAlias"]),query_instances_file_tree:new Set(["maxDepth","root","includeServices","placeId","clientId","targetAlias"]),query_instances_project_structure:new Set(["root","depth","placeId","clientId","targetAlias"]),query_instances_descendants:new Set(["path","sessionDebugId","siblingIndex","maxResults","placeId","clientId","targetAlias"]),query_instances_ancestors:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"])},paramAliases:{query_instances_search_name:{query:"pattern"},query_instances_search_property:{root:"rootPath"},query_instances_search_tag:{root:"rootPath"},query_instances_project_structure:{root:"rootPath"}}},mutate_instances:{discriminator:"action",validActions:new Set(["create","create_with_props","delete","clone","move","rename","pivot","create_tree","mass_create","mass_delete","mass_duplicate","smart_duplicate","scatter"]),allowedParams:{mutate_instances_create:new Set(["className","parent","name","properties","placeId","clientId","targetAlias"]),mutate_instances_create_with_props:new Set(["className","parent","name","properties","placeId","clientId","targetAlias"]),mutate_instances_delete:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"]),mutate_instances_clone:new Set(["path","sourcePath","sessionDebugId","siblingIndex","targetParent","newName","placeId","clientId","targetAlias"]),mutate_instances_move:new Set(["path","sessionDebugId","siblingIndex","newParent","placeId","clientId","targetAlias"]),mutate_instances_rename:new Set(["path","sessionDebugId","siblingIndex","newName","placeId","clientId","targetAlias"]),mutate_instances_pivot:new Set(["path","sessionDebugId","siblingIndex","position","cframe","offset","placeId","clientId","targetAlias"]),mutate_instances_create_tree:new Set(["parent","tree","placeId","clientId","targetAlias"]),mutate_instances_mass_create:new Set(["instances","placeId","clientId","targetAlias"]),mutate_instances_mass_delete:new Set(["paths","placeId","clientId","targetAlias"]),mutate_instances_mass_duplicate:new Set(["targetParent","paths","placeId","clientId","targetAlias"]),mutate_instances_smart_duplicate:new Set(["path","sessionDebugId","siblingIndex","targetParent","offset","count","placeId","clientId","targetAlias"]),mutate_instances_scatter:new Set(["templatePaths","region","count","seed","maxSlope","avoidWater","alignToNormal","scaleJitter","minSpacing","parentName","placeId","clientId","targetAlias"])},paramAliases:{mutate_instances_clone:{path:"sourcePath"},mutate_instances_smart_duplicate:{spacing:"offset"}}},manage_properties:{discriminator:"action",validActions:new Set(["get","set","get_all","set_multiple","get_attr","set_attr","get_all_attrs","delete_attr","add_tag","remove_tag","check_tag","get_tags","get_tagged","set_calculated","set_relative","mass_set","mass_get","modify_children"]),allowedParams:{manage_properties_get:new Set(["path","property","placeId","clientId","targetAlias"]),manage_properties_set:new Set(["path","property","value","placeId","clientId","targetAlias"]),manage_properties_get_all:new Set(["path","includeReadOnly","placeId","clientId","targetAlias"]),manage_properties_set_multiple:new Set(["path","properties","placeId","clientId","targetAlias"]),manage_properties_get_attr:new Set(["path","attribute","placeId","clientId","targetAlias"]),manage_properties_set_attr:new Set(["path","value","attribute","placeId","clientId","targetAlias"]),manage_properties_get_all_attrs:new Set(["path","placeId","clientId","targetAlias"]),manage_properties_delete_attr:new Set(["path","attribute","placeId","clientId","targetAlias"]),manage_properties_add_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_remove_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_check_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_get_tags:new Set(["path","placeId","clientId","targetAlias"]),manage_properties_get_tagged:new Set(["tagName","root","maxResults","placeId","clientId","targetAlias"]),manage_properties_set_calculated:new Set(["path","expression","variables","propertyName","placeId","clientId","targetAlias"]),manage_properties_set_relative:new Set(["path","value","operation","amount","propertyName","placeId","clientId","targetAlias"]),manage_properties_mass_set:new Set(["paths","propertyName","propertyValue","placeId","clientId","targetAlias"]),manage_properties_mass_get:new Set(["paths","propertyName","placeId","clientId","targetAlias"]),manage_properties_modify_children:new Set(["parentPath","modifications","propertyName","propertyValue","filter","recursive","placeId","clientId","targetAlias"])},paramAliases:{manage_properties_get_tagged:{tagName:"tag",root:"rootPath"},manage_properties_set_relative:{amount:"value"}}},manage_scripts:{discriminator:"action",validActions:new Set(["get_source","set_source","create","delete","edit_replace","edit_insert","edit_delete","search","replace","get_dependencies"]),allowedParams:{manage_scripts_get_source:new Set(["path","startLine","endLine","placeId","clientId","targetAlias"]),manage_scripts_set_source:new Set(["path","source","placeId","clientId","targetAlias"]),manage_scripts_create:new Set(["source","scriptType","parent","name","placeId","clientId","targetAlias"]),manage_scripts_delete:new Set(["path","placeId","clientId","targetAlias"]),manage_scripts_edit_replace:new Set(["path","startLine","endLine","newLines","placeId","clientId","targetAlias"]),manage_scripts_edit_insert:new Set(["path","lines","afterLine","content","placeId","clientId","targetAlias"]),manage_scripts_edit_delete:new Set(["path","startLine","endLine","placeId","clientId","targetAlias"]),manage_scripts_search:new Set(["path","pattern","caseSensitive","wholeWord","usePattern","maxResults","placeId","clientId","targetAlias"]),manage_scripts_replace:new Set(["path","pattern","replacement","usePattern","dryRun","placeId","clientId","targetAlias"]),manage_scripts_get_dependencies:new Set(["path","placeId","clientId","targetAlias"])},paramAliases:{manage_scripts_edit_replace:{newLines:"newContent"},manage_scripts_edit_insert:{lines:"content"},manage_scripts_replace:{pattern:"searchPattern"}}},manage_ui:{discriminator:"action",validActions:new Set(["design_brief","create_tree","update","delete","preview","check"]),allowedParams:{manage_ui_design_brief:new Set(["brief","placeId","clientId","targetAlias"]),manage_ui_create_tree:new Set(["briefId","tree","placeId","clientId","targetAlias"]),manage_ui_update:new Set(["targetPath","changes","briefId","placeId","clientId","targetAlias"]),manage_ui_delete:new Set(["targetPath","placeId","clientId","targetAlias"]),manage_ui_preview:new Set(["targetPath","briefId","placeId","clientId","targetAlias"]),manage_ui_check:new Set(["targetPath","briefId","includeVisualAnalysis","snapshotId","placeId","clientId","targetAlias"])}},manage_lighting:{discriminator:"action",validActions:new Set(["lighting","atmosphere","sky","terrain_props","time","mood"]),allowedParams:{manage_lighting_lighting:new Set(["properties","placeId","clientId","targetAlias"]),manage_lighting_atmosphere:new Set(["properties","createIfMissing","placeId","clientId","targetAlias"]),manage_lighting_sky:new Set(["properties","createIfMissing","placeId","clientId","targetAlias"]),manage_lighting_terrain_props:new Set(["properties","placeId","clientId","targetAlias"]),manage_lighting_time:new Set(["time","clockTime","placeId","clientId","targetAlias"]),manage_lighting_mood:new Set(["preset","overrides","placeId","clientId","targetAlias"])}},manage_selection:{discriminator:"action",validActions:new Set(["get","set","clear","cached","context","details","add","remove","watch"]),allowedParams:{manage_selection_get:new Set(["placeId","clientId","targetAlias"]),manage_selection_set:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_clear:new Set(["placeId","clientId","targetAlias"]),manage_selection_cached:new Set(["maxAge"]),manage_selection_context:new Set(["includeSource","includeProperties","includeChildren","placeId","clientId","targetAlias"]),manage_selection_details:new Set(["maxDepth","includeAncestors","placeId","clientId","targetAlias"]),manage_selection_add:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_remove:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_watch:new Set(["placeId","clientId","targetAlias"])}},manage_camera:{discriminator:"action",validActions:new Set(["info","focus_path","focus_position","suggest","screenshot"]),allowedParams:{manage_camera_info:new Set(["placeId","clientId","targetAlias"]),manage_camera_focus_path:new Set(["path","distance","duration","offset","respectAutoFocusSetting","placeId","clientId","targetAlias"]),manage_camera_focus_position:new Set(["position","distance","duration","offset","lookAt","respectAutoFocusSetting","placeId","clientId","targetAlias"]),manage_camera_suggest:new Set(["path","placeId","clientId","targetAlias"]),manage_camera_screenshot:new Set(["placeId","clientId","targetAlias"])},paramAliases:{manage_camera_suggest:{path:"targetPath"}}},manage_tween:{discriminator:"action",validActions:new Set(["create","play","pause","cancel"]),allowedParams:{manage_tween_create:new Set(["path","tweenInfo","properties","placeId","clientId","targetAlias"]),manage_tween_play:new Set(["tweenId","placeId","clientId","targetAlias"]),manage_tween_pause:new Set(["tweenId","placeId","clientId","targetAlias"]),manage_tween_cancel:new Set(["tweenId","placeId","clientId","targetAlias"])}},manage_audio:{discriminator:"action",validActions:new Set(["play","stop","pause","resume","set_listener"]),allowedParams:{manage_audio_play:new Set(["path","soundId","volume","looped","playbackSpeed","placeId","clientId","targetAlias"]),manage_audio_stop:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_pause:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_resume:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_set_listener:new Set(["listenerType","listenerPath","placeId","clientId","targetAlias"])}},manage_animation:{discriminator:"action",validActions:new Set(["load","play","stop","get_tracks"]),allowedParams:{manage_animation_load:new Set(["path","animationId","placeId","clientId","targetAlias"]),manage_animation_play:new Set(["path","trackId","speed","fadeTime","weight","priority","placeId","clientId","targetAlias"]),manage_animation_stop:new Set(["path","trackId","fadeTime","placeId","clientId","targetAlias"]),manage_animation_get_tracks:new Set(["path","placeId","clientId","targetAlias"])}},manage_physics:{discriminator:"action",validActions:new Set(["register_group","set_collidable","get_groups"]),allowedParams:{manage_physics_register_group:new Set(["groupName","placeId","clientId","targetAlias"]),manage_physics_set_collidable:new Set(["group1","group2","collidable","placeId","clientId","targetAlias"]),manage_physics_get_groups:new Set(["placeId","clientId","targetAlias"])}},manage_effects:{discriminator:"action",validActions:new Set(["emit","clear","toggle"]),allowedParams:{manage_effects_emit:new Set(["path","count","placeId","clientId","targetAlias"]),manage_effects_clear:new Set(["path","placeId","clientId","targetAlias"]),manage_effects_toggle:new Set(["path","enabled","placeId","clientId","targetAlias"])}},manage_terrain:{discriminator:"action",validActions:new Set(["fill_block","fill_ball","fill_cylinder","fill_wedge","clear_region","clear_bounds","replace_material","colors_get","colors_set","read_voxel","read_voxels","write_voxels","generate","smooth"]),allowedParams:{manage_terrain_fill_block:new Set(["cframe","size","placeId","clientId","targetAlias"]),manage_terrain_fill_ball:new Set(["center","radius","placeId","clientId","targetAlias"]),manage_terrain_fill_cylinder:new Set(["cframe","radius","height","placeId","clientId","targetAlias"]),manage_terrain_fill_wedge:new Set(["cframe","size","placeId","clientId","targetAlias"]),manage_terrain_clear_region:new Set(["region","placeId","clientId","targetAlias"]),manage_terrain_clear_bounds:new Set(["min","max","placeId","clientId","targetAlias"]),manage_terrain_replace_material:new Set(["material","region","sourceMaterial","targetMaterial","placeId","clientId","targetAlias"]),manage_terrain_colors_get:new Set(["material","placeId","clientId","targetAlias"]),manage_terrain_colors_set:new Set(["material","color","placeId","clientId","targetAlias"]),manage_terrain_read_voxel:new Set(["position","placeId","clientId","targetAlias"]),manage_terrain_read_voxels:new Set(["region","resolution","placeId","clientId","targetAlias"]),manage_terrain_write_voxels:new Set(["region","resolution","materials","occupancy","placeId","clientId","targetAlias"]),manage_terrain_generate:new Set(["region","preset","seed","baseHeight","amplitude","frequency","octaves","persistence","waterLevel","edgeBlend","materialPalette","layers","placeId","clientId","targetAlias"]),manage_terrain_smooth:new Set(["region","intensity","placeId","clientId","targetAlias"])}},spatial_query:{discriminator:"action",validActions:new Set(["raycast","find_ground","check_placement","multi_raycast","scan_area","find_flat","find_spawn","analyze_walkable","spatial_map","find_space","bounds","snap_grid","collision"]),allowedParams:{spatial_query_raycast:new Set(["origin","direction","filterType","filterList","filterInstances","ignoreWater","placeId","clientId","targetAlias"]),spatial_query_find_ground:new Set(["maxDistance","position","filterList","filterInstances","offset","placeId","clientId","targetAlias"]),spatial_query_check_placement:new Set(["position","size","filterList","filterInstances","rotation","checkGround","placeId","clientId","targetAlias"]),spatial_query_multi_raycast:new Set(["filterType","filterList","filterInstances","ignoreWater","rays","placeId","clientId","targetAlias"]),spatial_query_scan_area:new Set(["size","filterList","filterInstances","center","resolution","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_flat:new Set(["searchArea","minSize","maxSlope","tolerance","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_spawn:new Set(["searchArea","spawnSize","minSpacing","preferOutdoor","count","placeId","clientId","targetAlias"]),spatial_query_analyze_walkable:new Set(["area","maxSlope","resolution","characterHeight","maxStepHeight","placeId","clientId","targetAlias"]),spatial_query_spatial_map:new Set(["path","rootPath","includeModels","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_space:new Set(["size","searchArea","gridSize","gridSnap","padding","placeId","clientId","targetAlias"]),spatial_query_bounds:new Set(["path","paths","placeId","clientId","targetAlias"]),spatial_query_snap_grid:new Set(["gridSize","path","gridSnap","axes","placeId","clientId","targetAlias"]),spatial_query_collision:new Set(["position","path","ignorePaths","placeId","clientId","targetAlias"])},paramAliases:{spatial_query_spatial_map:{path:"rootPath"}}},manage_assets:{discriminator:"action",validActions:new Set(["insert","info","search","search_insert","insert_free","insert_package","export_selection_json","export_selection_rbxm","export_path_rbxm","review_model","generate_model","upload_asset","import_rbxm","generate_thumbnail"]),allowedParams:{manage_assets_insert:new Set(["assetId","parent","name","position","placeId","clientId","targetAlias"]),manage_assets_info:new Set(["assetId","placeId","clientId","targetAlias"]),manage_assets_search:new Set(["query","maxResults","category","sortType","placeId","clientId","targetAlias"]),manage_assets_search_insert:new Set(["parent","name","query","placeId","clientId","targetAlias"]),manage_assets_insert_free:new Set(["assetId","parent","name","position","placeId","clientId","targetAlias"]),manage_assets_insert_package:new Set(["assetId","parent","name","placeId","clientId","targetAlias"]),manage_assets_export_selection_json:new Set(["format","includeProperties","includeChildren","maxDepth","placeId","clientId","targetAlias"]),manage_assets_export_selection_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","clientId","targetAlias"]),manage_assets_export_path_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","sourcePath","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","clientId","targetAlias"]),manage_assets_review_model:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","sourcePath","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","exportToLibrary","expectedUse","expectedGroups","maxDescendants","maxDepth","readiness","clientId","targetAlias"]),manage_assets_generate_model:new Set(["contextId","contextSummary","replayMetadata","placeId","category","prompt","schemaMode","predefinedSchema","schemaGroups","size","maxTriangles","generateTextures","review","targetParent","name","displayName","expectedUse","expectedGroups","maxDescendants","maxDepth","readiness","anchorMode","clientId","targetAlias"]),manage_assets_upload_asset:new Set(["contextId","contextSummary","replayMetadata","placeId","category","assetType","sourcePath","displayName","description","creatorType","creatorId","clientId","targetAlias"]),manage_assets_import_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","assetLibraryAssetId","targetParent","name","clientId","targetAlias"]),manage_assets_generate_thumbnail:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","assetLibraryAssetId","clientId","targetAlias"])},paramAliases:{manage_assets_search:{maxResults:"limit"}}},manage_open_cloud_assets:{discriminator:"action",validActions:new Set(["preflight","credential_status","capabilities","upload","update","info","operation_status"]),allowedParams:{manage_open_cloud_assets_preflight:new Set(["filePath","category","creatorType","creatorId"]),manage_open_cloud_assets_credential_status:new Set([]),manage_open_cloud_assets_capabilities:new Set([]),manage_open_cloud_assets_upload:new Set(["contextId","contextSummary","replayMetadata","filePath","category","displayName","description","creatorType","creatorId","expectedPrice","waitForOperation","operationPollTimeoutMs","operationPollIntervalMs"]),manage_open_cloud_assets_update:new Set(["contextId","contextSummary","replayMetadata","assetId","filePath","category","displayName","description","creatorType","creatorId","expectedPrice","updateMask","waitForOperation","operationPollTimeoutMs","operationPollIntervalMs"]),manage_open_cloud_assets_info:new Set(["assetId","readMask"]),manage_open_cloud_assets_operation_status:new Set(["operationId"])}},manage_sync:{discriminator:"action",validActions:new Set(["status_current_place","history","directions","read_file","write_file","progress"]),allowedParams:{manage_sync_status_current_place:new Set([]),manage_sync_history:new Set(["placeId","query"]),manage_sync_directions:new Set(["placeId"]),manage_sync_read_file:new Set(["placeId","instancePath"]),manage_sync_write_file:new Set(["placeId","instancePath","content"]),manage_sync_progress:new Set([])}},workspace_state:{discriminator:"action",validActions:new Set(["sync","snapshot","changes","viewport","clear_history","metadata","scripts","selection_info","clear_cache"]),allowedParams:{workspace_state_sync:new Set(["includeMetadata","placeId","clientId","targetAlias"]),workspace_state_snapshot:new Set(["placeId","clientId","targetAlias"]),workspace_state_changes:new Set(["limit","placeId","clientId","targetAlias"]),workspace_state_viewport:new Set(["includeCameraInfo","includeSelectionBounds","placeId","clientId","targetAlias"]),workspace_state_clear_history:new Set(["placeId","clientId","targetAlias"]),workspace_state_metadata:new Set(["placeId","clientId","targetAlias"]),workspace_state_scripts:new Set(["placeId","clientId","targetAlias"]),workspace_state_selection_info:new Set(["placeId","clientId","targetAlias"]),workspace_state_clear_cache:new Set(["placeId","clientId","targetAlias"])}},manage_logs:{discriminator:"action",validActions:new Set(["get","clear","errors"]),allowedParams:{manage_logs_get:new Set(["level","limit","pattern","since","sinceSeq","placeId","clientId","targetAlias"]),manage_logs_clear:new Set(["placeId","clientId","targetAlias"]),manage_logs_errors:new Set(["limit","placeId","clientId","targetAlias"])},paramAliases:{manage_logs_get:{level:"type"}}},system_info:{discriminator:"action",validActions:new Set(["ping","connection","usage","place_info","services","preflight"]),allowedParams:{system_info_ping:new Set(["message","placeId","clientId","targetAlias"]),system_info_connection:new Set([]),system_info_usage:new Set(["placeId","clientId","targetAlias"]),system_info_place_info:new Set(["placeId","clientId","targetAlias"]),system_info_services:new Set(["placeId","clientId","targetAlias"]),system_info_preflight:new Set(["placeId","clientId","targetAlias"])}},manage_studio:{discriminator:"action",validActions:new Set(["toggle_ui_preview","play_start","play_stop","play_pause","play_resume","play_status","run_test"]),allowedParams:{manage_studio_toggle_ui_preview:new Set(["enabled","placeId","clientId","targetAlias"]),manage_studio_play_start:new Set(["mode","placeId","clientId","targetAlias"]),manage_studio_play_stop:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_pause:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_resume:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_status:new Set(["placeId","clientId","targetAlias"]),manage_studio_run_test:new Set(["mode","script","test_name","timeout","placeId","clientId","targetAlias","contextId","contextSummary","replayMetadata"])}}};var xye={manage_selection_cached:"internal",manage_open_cloud_assets_preflight:"internal",manage_open_cloud_assets_credential_status:"internal",manage_open_cloud_assets_capabilities:"internal",manage_open_cloud_assets_upload:"internal",manage_open_cloud_assets_update:"internal",manage_open_cloud_assets_info:"internal",manage_open_cloud_assets_operation_status:"internal",manage_sync_status_current_place:"internal",manage_sync_history:"internal",manage_sync_directions:"internal",manage_sync_read_file:"internal",manage_sync_write_file:"internal",manage_sync_progress:"internal",system_info_connection:"internal",system_info_preflight:"internal",manage_studio_run_test:"internal"};function N_(t){return xye[t]||"plugin"}var g5=new Set(["batch_execute","execute_luau","extended_call_method","extended_call_methods","extended_get_properties","extended_get_property","extended_set_properties","extended_set_property","manage_animation_get_tracks","manage_animation_load","manage_animation_play","manage_animation_stop","manage_assets_export_path_rbxm","manage_assets_export_selection_json","manage_assets_export_selection_rbxm","manage_assets_generate_model","manage_assets_generate_thumbnail","manage_assets_import_rbxm","manage_assets_info","manage_assets_insert","manage_assets_insert_free","manage_assets_insert_package","manage_assets_review_model","manage_assets_search","manage_assets_search_insert","manage_assets_upload_asset","manage_audio_pause","manage_audio_play","manage_audio_resume","manage_audio_set_listener","manage_audio_stop","manage_camera_screenshot","manage_effects_clear","manage_effects_emit","manage_effects_toggle","manage_lighting_atmosphere","manage_lighting_lighting","manage_lighting_mood","manage_lighting_sky","manage_lighting_terrain_props","manage_lighting_time","manage_open_cloud_assets_capabilities","manage_open_cloud_assets_credential_status","manage_open_cloud_assets_info","manage_open_cloud_assets_operation_status","manage_open_cloud_assets_preflight","manage_open_cloud_assets_update","manage_open_cloud_assets_upload","manage_physics_get_groups","manage_physics_register_group","manage_physics_set_collidable","manage_properties_mass_get","manage_properties_mass_set","manage_properties_modify_children","manage_properties_set_calculated","manage_properties_set_relative","manage_scripts_replace","manage_selection_add","manage_selection_context","manage_selection_details","manage_selection_remove","manage_selection_watch","manage_studio_play_pause","manage_studio_play_resume","manage_studio_play_start","manage_studio_play_status","manage_studio_play_stop","manage_studio_run_test","manage_studio_toggle_ui_preview","manage_sync_directions","manage_sync_history","manage_sync_progress","manage_sync_read_file","manage_sync_status_current_place","manage_sync_write_file","manage_terrain_clear_bounds","manage_terrain_clear_region","manage_terrain_colors_get","manage_terrain_colors_set","manage_terrain_fill_ball","manage_terrain_fill_block","manage_terrain_fill_cylinder","manage_terrain_fill_wedge","manage_terrain_generate","manage_terrain_read_voxel","manage_terrain_read_voxels","manage_terrain_replace_material","manage_terrain_smooth","manage_terrain_write_voxels","manage_tween_cancel","manage_tween_create","manage_tween_pause","manage_tween_play","manage_ui_check","manage_ui_create_tree","manage_ui_delete","manage_ui_design_brief","manage_ui_preview","manage_ui_update","mutate_instances_create_tree","mutate_instances_mass_create","mutate_instances_mass_delete","mutate_instances_mass_duplicate","mutate_instances_scatter","mutate_instances_smart_duplicate","query_instances_ancestors","query_instances_descendants","query_instances_file_tree","query_instances_project_structure","query_instances_search_property","query_instances_search_tag","spatial_query_analyze_walkable","spatial_query_bounds","spatial_query_check_placement","spatial_query_collision","spatial_query_find_flat","spatial_query_find_ground","spatial_query_find_space","spatial_query_find_spawn","spatial_query_multi_raycast","spatial_query_raycast","spatial_query_scan_area","spatial_query_snap_grid","spatial_query_spatial_map","system_info_place_info","system_info_services","workspace_state_changes","workspace_state_clear_cache","workspace_state_clear_history","workspace_state_metadata","workspace_state_scripts","workspace_state_selection_info","workspace_state_snapshot","workspace_state_sync","workspace_state_viewport"]),nA=new Set(["system_info_connection","system_info_ping","system_info_preflight","system_info_usage"]);function Gn(t){return g5.has(t)?"pro":"basic"}ui();j_();import{readFile as Fye}from"node:fs/promises";import Uye from"node:path";import{createHash as Nye,randomUUID as oA}from"node:crypto";import{mkdir as am,readFile as I5,readdir as C5,rename as P5,rm as jye,stat as Mye,writeFile as B_}from"node:fs/promises";import Ht from"node:path";import{extname as Iye}from"node:path";import{constants as Cye}from"node:fs";import{access as Pye,stat as kye}from"node:fs/promises";var tm=20*1024*1024,z_=[{category:"image",assetType:"Image",folder:"images",extensions:[".png",".jpeg",".jpg",".bmp",".tga"],supportsContentUpdate:!1,contentTypes:{".png":"image/png",".jpeg":"image/jpeg",".jpg":"image/jpeg",".bmp":"image/bmp",".tga":"image/tga"}},{category:"decal",assetType:"Decal",folder:"decals",extensions:[".png",".jpeg",".jpg",".bmp",".tga"],supportsContentUpdate:!1,contentTypes:{".png":"image/png",".jpeg":"image/jpeg",".jpg":"image/jpeg",".bmp":"image/bmp",".tga":"image/tga"}},{category:"audio",assetType:"Audio",folder:"audio",extensions:[".mp3",".ogg",".wav",".flac"],supportsContentUpdate:!1,contentTypes:{".mp3":"audio/mpeg",".ogg":"audio/ogg",".wav":"audio/wav",".flac":"audio/flac"}},{category:"mesh",assetType:"Mesh",folder:"meshes",extensions:[".mesh"],supportsContentUpdate:!1,contentTypes:{".mesh":"application/octet-stream"}},{category:"model",assetType:"Model",folder:"models",extensions:[".fbx",".gltf",".glb",".rbxm",".rbxmx"],supportsContentUpdate:!0,contentTypes:{".fbx":"model/fbx",".gltf":"model/gltf+json",".glb":"model/gltf-binary",".rbxm":"model/x-rbxm",".rbxmx":"model/x-rbxm"}},{category:"video",assetType:"Video",folder:"videos",extensions:[".mp4",".mov"],supportsContentUpdate:!1,contentTypes:{".mp4":"video/mp4",".mov":"video/quicktime"}},{category:"animation",assetType:"Animation",folder:"animations",extensions:[".rbxm",".rbxmx"],supportsContentUpdate:!0,contentTypes:{".rbxm":"model/x-rbxm",".rbxmx":"model/x-rbxm"}}],Eye=new Map(z_.map(t=>[t.category,t]));function v5(t){if(!t)throw new Error("Open Cloud asset upload is disabled in WEPPY Dashboard settings.")}function M_(t,e){return t.split(e.apiKey).join("[redacted]")}function L_(t){let e=Eye.get(t);if(!e)throw new Error(`Unsupported asset category: ${t}`);return e}function F_(t){return L_(t)}async function iA(t,e,n=tm){let r=L_(t),i=Iye(e).toLowerCase(),a=r.contentTypes[i]??null,o=await kye(e),s=!0;try{await Pye(e,Cye.R_OK)}catch{s=!1}return{category:t,extension:i,contentType:a,formatValid:a!==null,sizeBytes:o.size,sizeValid:o.size<=n,maxFileSizeBytes:n,regularFile:o.isFile(),readable:s}}function b5(t,e){let n=t.creatorType??e.creatorType,r=t.creatorId??e.creatorId;if(!n||!r)throw new Error("creatorType and creatorId are required for Roblox Open Cloud asset upload/update.");return{...t,creatorType:n,creatorId:r}}async function x5(t,e,n){let r=await iA(t.category,e,n);if(!r.formatValid||!r.contentType)throw new Error(`Unsupported file extension ${r.extension||"(none)"} for ${t.category}.`);if(!r.regularFile)throw new Error("Asset path must reference a regular file.");if(!r.readable)throw new Error("Asset file is not readable.");if(!r.sizeValid)throw new Error(`Asset file is too large. Maximum size is ${n} bytes.`);return r.contentType}function _5(t){return typeof t.path=="string"&&t.path.startsWith("operations/")?t.path:null}function S5(t,e,n,r){let i={apiKey:t.apiKey,operationId:e};return n!==void 0&&(i.intervalMs=n),r!==void 0&&(i.timeoutMs=r),i}var ou=class{client;credentialStore;isOpenCloudUploadEnabled;maxFileSizeBytes;constructor(e){this.client=e.client,this.credentialStore=e.credentialStore,this.isOpenCloudUploadEnabled=e.isOpenCloudUploadEnabled,this.maxFileSizeBytes=e.maxFileSizeBytes??tm}getCapabilities(){return z_.map(({contentTypes:e,...n})=>n)}async uploadAsset(e){v5(this.isOpenCloudUploadEnabled());let n=await this.getRequiredCredential(),r=b5(e,n),i=L_(r.category),a=await x5(i,r.filePath,this.maxFileSizeBytes);try{let o={apiKey:n.apiKey,assetType:i.assetType,displayName:r.displayName,description:r.description??"",creatorType:r.creatorType,creatorId:r.creatorId,filePath:r.filePath,contentType:a};r.expectedPrice!==void 0&&(o.expectedPrice=r.expectedPrice);let s=await this.client.createAsset(o);if(r.waitForOperation){let c=_5(s);return c?await this.client.pollOperation(S5(n,c,r.operationPollIntervalMs,r.operationPollTimeoutMs)):s}return s}catch(o){throw new Error(M_(o instanceof Error?o.message:String(o),n))}}async updateAsset(e){v5(this.isOpenCloudUploadEnabled());let n=await this.getRequiredCredential(),r=b5(e,n),i=L_(r.category),a;if(r.filePath){if(!i.supportsContentUpdate)throw new Error(`${i.category} assets do not support content updates.`);a=await x5(i,r.filePath,this.maxFileSizeBytes)}try{let o={apiKey:n.apiKey,assetId:r.assetId,assetType:i.assetType,creatorType:r.creatorType,creatorId:r.creatorId};r.filePath&&(o.filePath=r.filePath),a!==void 0&&(o.contentType=a),r.displayName!==void 0&&(o.displayName=r.displayName),r.description!==void 0&&(o.description=r.description),r.updateMask!==void 0&&(o.updateMask=r.updateMask),r.expectedPrice!==void 0&&(o.expectedPrice=r.expectedPrice);let s=await this.client.updateAsset(o);if(r.waitForOperation){let c=_5(s);return c?await this.client.pollOperation(S5(n,c,r.operationPollIntervalMs,r.operationPollTimeoutMs)):s}return s}catch(o){throw new Error(M_(o instanceof Error?o.message:String(o),n))}}async getAsset(e){let n=await this.getRequiredCredential();try{let r={apiKey:n.apiKey,assetId:e.assetId};return e.readMask!==void 0&&(r.readMask=e.readMask),await this.client.getAsset(r)}catch(r){throw new Error(M_(r instanceof Error?r.message:String(r),n))}}async getOperation(e){let n=await this.getRequiredCredential();try{return await this.client.getOperation({apiKey:n.apiKey,operationId:e.operationId})}catch(r){throw new Error(M_(r instanceof Error?r.message:String(r),n))}}async getRequiredCredential(){let e=await this.credentialStore.getCredentialForUse();if(!e)throw new Error("Configure a Roblox Open Cloud API key in WEPPY Dashboard before using Open Cloud asset upload.");return e}};import w5 from"node:fs";import rn from"node:path";Ix();var Rye=/^asset_(image|decal|audio|mesh|model|video|animation)_\d+_[a-z0-9]+$/;function Tye(t){if(!Number.isInteger(t)||t<0)throw new Error(`Invalid place ID: ${t}`)}function Aye(t,e){try{return w5.statSync(rn.join(t,e,".sync-meta.json")).isFile()}catch{return!1}}function Oye(t,e){Tye(e.placeId);let n=`place_${e.placeId}`,r=e.placeName?Ml(e.placeName):"",i=r?`${n}_${r}`:n,a=[];try{let o=new RegExp(`^place_${e.placeId}(?:_.*)?$`);a=w5.readdirSync(t,{withFileTypes:!0}).filter(s=>s.isDirectory()&&o.test(s.name)).map(s=>s.name).sort()}catch{return i}return r&&a.includes(i)?i:a.find(o=>Aye(t,o))??(a.includes(i)?i:null)??a[0]??i}function aA(t){let e=rn.resolve(t.projectSyncRoot),n=F_(t.category).folder,r=t.scope.kind==="place"?rn.join(e,Oye(e,t.scope),"assets",n):rn.join(e,"shared-assets",n);return{root:r,inbox:rn.join(r,"inbox"),index:rn.join(r,".asset-library-index.json")}}function $ye(t){let e=Rye.exec(t);return e?.[1]?e[1]:null}function nm(t,e){let n=$ye(t);return n?e?n===e:!0:!1}function U_(t,e){if(!nm(t,e))throw new Error(`Invalid asset ID: ${t}`)}function mi(t,e){let n=rn.relative(rn.resolve(t),rn.resolve(e));return n===""||!n.startsWith("..")&&!rn.isAbsolute(n)}function Dye(t){U_(t.assetId,t.category);let e=aA(t),n=rn.resolve(e.root,t.assetId);if(!mi(e.root,n))throw new Error(`Invalid asset path for ${t.assetId}`);return n}function q_(t){let e=Dye(t),n=rn.resolve(e,t.relativeFileName);if(!mi(e,n))throw new Error(`Invalid asset file path for ${t.assetId}`);return n}function rm(t,e){return rn.relative(rn.resolve(t),rn.resolve(e)).split(rn.sep).join("/")}var k5=20*1024*1024,Lye=200;function E5(t,e){return t.kind!==e.kind?!1:t.kind==="shared"&&e.kind==="shared"?!0:t.kind==="place"&&e.kind==="place"&&t.placeId===e.placeId}function R5(t,e){let n=Ht.extname(t).toLowerCase(),r=F_(e);if(!r.extensions.includes(n))return null;let i=r.contentTypes[n];return i?{canonicalExt:n,mimeType:i}:null}function sA(t,e,n){if(e!=="image"&&e!=="decal")return!0;let r=Ht.extname(t).toLowerCase();return r===".png"?n.length>=8&&n[0]===137&&n[1]===80&&n[2]===78&&n[3]===71&&n[4]===13&&n[5]===10&&n[6]===26&&n[7]===10:r===".jpg"||r===".jpeg"?n.length>=3&&n[0]===255&&n[1]===216&&n[2]===255:r===".bmp"?n.length>=2&&n[0]===66&&n[1]===77:r===".tga"?n.length>0:!1}function T5(t){return Nye("sha256").update(t).digest("hex")}function V_(t){return t.now?.()??Date.now()}function zye(t){return(t.randomId?.()??oA().replace(/-/g,"").slice(0,6)).toLowerCase().replace(/[^a-z0-9]/g,"").slice(0,12)||"asset"}function A5(t,e){let n=Math.floor(V_(t)/1e3);for(let r=0;r<20;r++){let i=zye(t),a=r===0?`asset_${t.category}_${n}_${i}`:`asset_${t.category}_${n}_${i}${r}`;if(!e.has(a))return a}return`asset_${t.category}_${n}_${oA().replace(/-/g,"").slice(0,10)}`}function O5(t){let e=Ht.parse(t).name.trim();return e.length>0?e:t}function $5(t){if(t.mimeType!=="image/png")throw new Error("Asset Library preview must be an image/png thumbnail");if(Ht.basename(t.fileName).toLowerCase()!=="thumbnail.png")throw new Error("Asset Library preview file must be thumbnail.png");if(!sA("thumbnail.png","image",t.content))throw new Error("Asset Library preview is not a valid PNG file");return{fileName:"thumbnail.png",content:t.content}}async function cA(t,e){let n=`${t}.tmp.${oA().slice(0,8)}`;await B_(n,JSON.stringify(e,null,2),"utf8"),await P5(n,t)}async function D5(t,e){try{let n=await I5(Ht.join(e,"asset.json"),"utf8"),r=JSON.parse(n);return!nm(r.id,t.category)||r.category!==t.category||!E5(r.scope,t.scope)?null:r}catch{return null}}async function im(t,e){let n;try{n=await C5(e.root,{withFileTypes:!0})}catch(i){if(i?.code==="ENOENT")return[];throw i}let r=[];for(let i of n.sort((a,o)=>a.name.localeCompare(o.name))){if(!i.isDirectory()||!nm(i.name,t.category))continue;let a=Ht.join(e.root,i.name),o=await D5(t,a);o&&r.push(o)}return r.sort((i,a)=>a.createdAt.localeCompare(i.createdAt)||a.id.localeCompare(i.id))}async function su(t,e,n){if(U_(n.id,t.category),n.category!==t.category||!E5(n.scope,t.scope))throw new Error(`Asset metadata does not match library scope/category: ${n.id}`);let r=Ht.join(e.root,n.id);if(!mi(e.root,r))throw new Error(`Invalid asset path for ${n.id}`);await am(r,{recursive:!0}),await cA(Ht.join(r,"asset.json"),n)}async function N5(t,e){await am(t.root,{recursive:!0});let n={version:1,generatedAt:new Date().toISOString(),assets:e.map(r=>r.id)};await cA(t.index,n)}function Ji(t,e,n){return{fileName:t,reason:e,message:n}}async function gi(t){let e=aA(t);return await am(e.inbox,{recursive:!0}),e}async function j5(t){let e=await gi(t),n=await im(t,e);return await N5(e,n),n}async function Zt(t,e){U_(e,t.category);let n=await gi(t),r=Ht.join(n.root,e);if(!mi(n.root,r))throw new Error(`Invalid asset path for ${e}`);let i=await D5(t,r);if(!i)throw new Error(`Asset not found: ${e}`);return i}async function cu(t){let e=await gi(t),n=await im(t,e),r={version:1,generatedAt:new Date().toISOString(),assets:n.map(i=>i.id)};return await cA(e.index,r),r}async function M5(t){let e=await gi(t),n=await im(t,e),r=new Set(n.map(p=>p.id)),i=new Set(n.map(p=>p.file.sha256)),a=[],o=[],s=t.maxFileSizeBytes??k5,c=t.maxFilesPerRescan??Lye,l;try{l=await C5(e.inbox,{withFileTypes:!0})}catch(p){if(p?.code==="ENOENT")l=[];else throw p}let u=l.sort((p,f)=>p.name.localeCompare(f.name));for(let p=0;p<u.length;p++){let f=u[p];if(p>=c){o.push(Ji(f.name,"maxFileCount","rescan file count limit exceeded"));continue}if(f.name.startsWith(".")){o.push(Ji(f.name,"hidden","hidden or system file"));continue}if(f.isSymbolicLink()){o.push(Ji(f.name,"symlink","symlink files are not followed"));continue}if(f.isDirectory()){o.push(Ji(f.name,"nestedDirectory","nested directories are not scanned"));continue}if(!f.isFile()){o.push(Ji(f.name,"unsupportedType","unsupported inbox entry type"));continue}let m=R5(f.name,t.category);if(!m){o.push(Ji(f.name,"unsupportedType",`unsupported ${t.category} extension`));continue}let g=Ht.join(e.inbox,f.name),h=await Mye(g);if(h.size>s){o.push(Ji(f.name,"oversized","asset file is larger than the configured limit"));continue}let v=await I5(g);if(!sA(f.name,t.category,v)){o.push(Ji(f.name,"invalidSignature","file signature does not match the extension"));continue}let x=T5(v);if(i.has(x)){o.push(Ji(f.name,"duplicate","asset content already exists in Asset Library"));continue}let _=A5(t,r);r.add(_),i.add(x);let P=Ht.join(e.root,_),w=`original${m.canonicalExt}`;await am(P,{recursive:!0}),await P5(g,Ht.join(P,w));let D=new Date(V_(t)).toISOString(),M={version:1,id:_,category:t.category,scope:t.scope,status:"localOnly",displayName:O5(f.name),description:"",source:{kind:"generated",originalPath:rm(t.projectSyncRoot,g)},file:{original:w,preview:null,mimeType:m.mimeType,sha256:x,sizeBytes:h.size,width:null,height:null,durationMs:null},roblox:{uploaded:!1},usage:{lastScannedAt:null,scanSource:null,references:[]},createdAt:D,updatedAt:D};await su(t,e,M),a.push(M)}let d=await im(t,e);return await N5(e,d),{assets:d,adopted:a,skipped:o,adoptedCount:a.length,skippedCount:o.length}}async function L5(t){let e=await gi(t),n=R5(t.originalFileName,t.category);if(!n)throw new Error(`Unsupported ${t.category} extension for Asset Library export`);let r=t.maxFileSizeBytes??k5;if(t.content.length>r)throw new Error("asset file is larger than the configured limit");if(!sA(t.originalFileName,t.category,t.content))throw new Error("file signature does not match the extension");let i=await im(t,e),a=T5(t.content),o=i.find(h=>h.file.sha256===a);if(o)return{asset:o,deduplicated:!0};let s=new Set(i.map(h=>h.id)),c=A5(t,s),l=Ht.join(e.root,c);if(!mi(e.root,l))throw new Error(`Invalid asset path for ${c}`);let u=`original${n.canonicalExt}`;await am(l,{recursive:!0}),await B_(Ht.join(l,u),t.content);let d=null;if(t.preview){let h=$5(t.preview);d=h.fileName,await B_(Ht.join(l,h.fileName),h.content)}let p=new Date(V_(t)).toISOString(),f=t.roblox??{uploaded:!1},m=f.uploaded&&f.assetId?"uploaded":"localOnly",g={version:1,id:c,category:t.category,scope:t.scope,status:m,displayName:t.displayName?.trim()||O5(t.originalFileName),description:t.description??"",source:{...t.source,originalPath:rm(t.projectSyncRoot,Ht.join(l,u))},file:{original:u,preview:d,mimeType:n.mimeType,sha256:a,sizeBytes:t.content.length,width:null,height:null,durationMs:null},roblox:f,usage:{lastScannedAt:null,scanSource:null,references:[]},...t.rbxm?{rbxm:t.rbxm}:{},createdAt:p,updatedAt:p};return await su(t,e,g),await cu(t),{asset:g,deduplicated:!1}}async function z5(t){let e=await gi(t),n=await Zt(t,t.assetId),r=$5(t.preview),i=q_({...t,relativeFileName:r.fileName});await B_(i,r.content);let a={...n,file:{...n.file,preview:r.fileName},...n.rbxm&&t.rbxmThumbnail?{rbxm:{...n.rbxm,thumbnail:t.rbxmThumbnail}}:{},updatedAt:new Date(V_(t)).toISOString()};return await su(t,e,a),await cu(t),{asset:a}}async function F5(t,e,n){let r=await gi(t),i=await Zt(t,e),a={...i,displayName:typeof n.displayName=="string"?n.displayName:i.displayName,description:typeof n.description=="string"?n.description:i.description,source:{...i.source,...n.source?.agent!==void 0?{agent:n.source.agent}:{},...n.source?.contextId!==void 0?{contextId:n.source.contextId}:{},...n.source?.prompt!==void 0?{prompt:n.source.prompt}:{}},updatedAt:new Date().toISOString()};return await su(t,r,a),await cu(t),a}async function U5(t,e,n){let r=await gi(t),a={...await Zt(t,e),usage:n,updatedAt:new Date().toISOString()};return await su(t,r,a),await cu(t),a}async function q5(t,e){let n=await gi(t);await Zt(t,e);let r=Ht.join(n.root,e);if(!mi(n.root,r))throw new Error(`Invalid asset path for ${e}`);return await jye(r,{recursive:!0}),await cu(t),{assetId:e,removed:1}}async function uo(t){let e=await gi(t);return await su(t,e,t.asset),await cu(t),t.asset}async function lu(t){let e=await Zt(t,t.assetId);return q_({...t,relativeFileName:e.file.original})}async function B5(t){let e=await Zt(t,t.assetId);return q_({...t,relativeFileName:e.file.preview??e.file.original})}var qye="https://create.roblox.com/dashboard/creations/store",Bye="manage_assets_import_rbxm",uA="manage_assets_generate_thumbnail",Vye="manage_assets_review_model";var dA=new Set([Bye,uA]),pA=new Set(["manage_assets_export_selection_rbxm","manage_assets_export_path_rbxm",Vye]),Hye=new Set(["model","animation"]);function rt(t){return t&&typeof t=="object"?t:null}function Zye(t){if(typeof t!="string"||!Hye.has(t))throw new Error(`Unsupported Asset Library .rbxm round-trip category: ${String(t??"(missing)")}`);return t}function Wye(t){if(typeof t=="number"&&Number.isInteger(t)&&t>=0)return t;if(typeof t=="string"&&t.trim().length>0){let e=Number.parseInt(t,10);if(Number.isInteger(e)&&e>=0)return e}return null}function V5(t,e){for(let n of t.pluginClients.values())if(!(typeof n.placeId!="number"||!Number.isFinite(n.placeId))&&!(e!==void 0&&n.placeId!==e))return{placeId:n.placeId,...n.placeName?{placeName:n.placeName}:{}};return null}function fA(t,e){let n=bt(t.config.dataDir),r=Zye(e.category),i=typeof e.scope=="string"?e.scope:"place",a=typeof e.assetLibraryAssetId=="string"&&e.assetLibraryAssetId.length>0?e.assetLibraryAssetId:void 0;if(i==="shared")return{projectSyncRoot:n,scope:{kind:"shared"},category:r,...a?{assetId:a}:{}};if(i!=="place")throw new Error(`Invalid Asset Library scope: ${i}`);let o=Wye(e.placeId),s=t.syncController?.getDefaultRuntimePlaceId()??null,c=o??s??V5(t)?.placeId??null;if(c===null)throw new Error("No placeId is available for Asset Library .rbxm round-trip.");let l=V5(t,c);return{projectSyncRoot:n,scope:{kind:"place",placeId:c,...l?.placeName?{placeName:l.placeName}:{}},category:r,...a?{assetId:a}:{}}}function Gye(t){if(Uye.extname(t.file.original).toLowerCase()!==".rbxm")throw new Error(`Asset Library Studio round-trip supports original.rbxm only. Unsupported original file: ${t.file.original}`)}function Kye(t,e){if(typeof t!="string"||t.trim().length===0)throw new Error(`${e} is missing`);return Buffer.from(t,"base64")}function Jye(t,e){let n=rt(e),i={kind:n?.kind==="generation"||typeof t.prompt=="string"?"generated":"studioExport",originalPath:"studio:selection"};if(n){let a=typeof n.path=="string"?n.path:typeof n.kind=="string"?n.kind:void 0;a&&(i.originalPath=`studio:${a}`);let o=ge(n.prompt,1e3);o&&(i.prompt=o)}if(!i.prompt){let a=ge(t.prompt,1e3);a&&(i.prompt=a)}return typeof t.contextId=="string"&&(i.contextId=t.contextId),i}function G5(t){let e=rt(t);if(!e)return;let n={};typeof e.width=="number"&&(n.width=e.width),typeof e.height=="number"&&(n.height=e.height),typeof e.source=="string"&&(n.source=e.source),typeof e.error=="string"&&(n.error=e.error);let r=om(e.attempts);return r.length>0&&(n.attempts=r),Object.keys(n).length>0?n:void 0}function ge(t,e){return typeof t!="string"?null:t.slice(0,e)}function Yye(t){if(typeof t!="string")return null;let e=t.trim();return/^\d+$/.test(e)?e:null}function H5(t){return`rbxassetid://${t}`}function Z5(t){return`${qye}/${t}/configure`}function W5(t){return`assets/${t}`}function pr(t){return typeof t=="number"&&Number.isFinite(t)?t:void 0}function K5(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.name,256),i=ge(n.className,128),a=ge(n.path,512);return r===null||i===null||a===null?[]:[{name:r,className:i,path:a}]}):[]}function Xye(t){let e=rt(t);if(!e)return{};let n={};for(let[r,i]of Object.entries(e).slice(0,100))typeof i!="number"||!Number.isFinite(i)||i<0||(n[r.slice(0,128)]=Math.floor(i));return n}function Qye(t){return Array.isArray(t)?t.slice(0,200).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.path,512),i=ge(n.property,128),a=ge(n.value,1024);if(r===null||i===null||a===null)return[];let o=ge(n.assetId,64);return[{path:r,property:i,value:a,...o?{assetId:o}:{}}]}):[]}function om(t){return Array.isArray(t)?t.slice(0,8).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.method,80),i=n.status==="success"||n.status==="failed"||n.status==="skipped"?n.status:null;if(r===null||i===null)return[];let a=ge(n.message,512);return[{method:r,status:i,...a?{message:a}:{}}]}):[]}function eve(t,e){let n=t.thumbnailMode==="auto"?"auto":"none";if(n==="none")return{mode:n,status:"skipped",message:"Thumbnail generation disabled"};let r=G5(e),i=rt(e),a=typeof i?.pngBase64=="string"&&i.pngBase64.length>0,o=typeof i?.base64Rgba=="string"&&i.base64Rgba.length>0&&i.format==="rgba8"&&typeof i.width=="number"&&typeof i.height=="number";if(r&&(a||o)){let s=pr(r.width),c=pr(r.height),l=om(i?.attempts);return{mode:n,status:"generated",...s!==void 0?{width:s}:{},...c!==void 0?{height:c}:{},...typeof r.source=="string"?{source:r.source.slice(0,128)}:{},...l.length>0?{attempts:l}:{}}}if(r&&typeof r.error=="string"){let s=om(rt(e)?.attempts);return{mode:n,status:"failed",message:r.error.slice(0,512),...s.length>0?{attempts:s}:{}}}return{mode:n,status:"skipped",message:"Thumbnail was not returned"}}function tve(t,e){let n=rt(t);if(!n)return e;let r=n.mode==="auto"||n.mode==="none"?n.mode:e.mode,i=n.status==="generated"||n.status==="skipped"||n.status==="failed"?n.status:e.status,a=ge(n.message,512),o=pr(n.width),s=pr(n.height),c=ge(n.source,128),l=om(n.attempts);return{mode:r,status:i,...a?{message:a}:{},...o!==void 0?{width:o}:{},...s!==void 0?{height:s}:{},...c?{source:c}:{},...l.length>0?{attempts:l}:{}}}function lA(t,e=0){if(e>3)return;if(typeof t=="string")return t.slice(0,512);if(typeof t=="boolean")return t;if(typeof t=="number")return Number.isFinite(t)?t:void 0;if(Array.isArray(t))return t.slice(0,50).flatMap(i=>{let a=lA(i,e+1);return a===void 0?[]:[a]});let n=rt(t);if(!n)return;let r={};for(let[i,a]of Object.entries(n).slice(0,50)){let o=lA(a,e+1);o!==void 0&&(r[i.slice(0,128)]=o)}return r}function nve(t){let e=rt(t),n=pr(e?.x),r=pr(e?.y),i=pr(e?.z);if(!(n===void 0||r===void 0||i===void 0))return{x:n,y:r,z:i}}function rve(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=n.severity==="info"||n.severity==="warning"||n.severity==="error"?n.severity:null,i=ge(n.category,80),a=ge(n.code,120),o=ge(n.path,512),s=ge(n.message,512);if(!r||i===null||a===null||o===null||s===null)return[];let c=ge(n.suggestion,512);return[{severity:r,category:i,code:a,path:o,message:s,...c?{suggestion:c}:{}}]}):[]}function ive(t){let e=rt(t);if(!e)return;let n=e.readiness==="ready"||e.readiness==="review"||e.readiness==="blocked"?e.readiness:null;if(!n)return;let r=lA(e.summary),i=ge(e.reviewedAt,64),a=K5(e.roots);return{readiness:n,...i?{reviewedAt:i}:{},...a.length>0?{roots:a}:{},summary:rt(r)??{},findings:rve(e.findings)}}function ave(t){let e=rt(t);if(!e)return;let n={};for(let[r,i]of Object.entries(e).slice(0,16))typeof i=="string"&&(n[r.slice(0,128)]=i.slice(0,256)),typeof i=="number"&&Number.isFinite(i)&&(n[r.slice(0,128)]=i),typeof i=="boolean"&&(n[r.slice(0,128)]=i);return Object.keys(n).length>0?n:void 0}function ove(t){let e=rt(t);if(!e)return;let n=ge(e.provider,120);if(!n)return;let r=ge(e.generatedAt,64),i=ge(e.prompt,1e3),a=e.schemaMode==="predefined"||e.schemaMode==="custom"?e.schemaMode:void 0,o=e.predefinedSchema==="Body1"||e.predefinedSchema==="Car5"?e.predefinedSchema:void 0,s=Array.isArray(e.schemaGroups)?e.schemaGroups.slice(0,50).flatMap(f=>{let m=ge(f,120);return m?[m]:[]}):void 0,c=nve(e.requestedSize),l=pr(e.maxTriangles),u=ge(e.targetParent,512),d=ge(e.path,512),p=ave(e.metadata);return{provider:n,...r?{generatedAt:r}:{},...i?{prompt:i}:{},...a?{schemaMode:a}:{},...o?{predefinedSchema:o}:{},...s&&s.length>0?{schemaGroups:s}:{},...c?{requestedSize:c}:{},...l!==void 0?{maxTriangles:Math.floor(l)}:{},...typeof e.generateTextures=="boolean"?{generateTextures:e.generateTextures}:{},...u?{targetParent:u}:{},...d?{path:d}:{},...p?{metadata:p}:{}}}function sve(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.path,512),i=n.assetType==="Mesh"||n.assetType==="Image"||n.assetType==="Model"?n.assetType:null,a=n.status==="uploaded"||n.status==="failed"?n.status:null;if(r===null||i===null||a===null)return[];let o=ge(n.assetId,64),s=ge(n.assetUri,128),c=n.creatorType==="user"||n.creatorType==="group"?n.creatorType:void 0,l=ge(n.creatorId,64),u=ge(n.sourceProperty,128),d=ge(n.uploadedAt,64),p=ge(n.message,512);return[{path:r,assetType:i,status:a,...o?{assetId:o}:{},...s?{assetUri:s}:{},...c?{creatorType:c}:{},...l?{creatorId:l}:{},...u?{sourceProperty:u}:{},...d?{uploadedAt:d}:{},...p?{message:p}:{}}]}):[]}function cve(t){let e=rt(t);if(!e||e.uploaded!==!0)return;let n=Yye(e.assetId);if(!n)return;let r=ge(e.uploadedAt,64)??new Date().toISOString(),i=e.creatorType==="user"||e.creatorType==="group"?e.creatorType:void 0,a=ge(e.creatorId,64);return{uploaded:!0,assetId:n,assetUri:H5(n),assetWebUrl:Z5(n),remotePath:W5(n),uploadedAt:r,uploadAttempts:[{startedAt:r,finishedAt:r,status:"uploaded",assetRole:"primary",...i?{creatorType:i}:{},...a?{creatorId:a}:{},assetId:n,assetUri:H5(n),assetWebUrl:Z5(n),remotePath:W5(n)}]}}function lve(t){let e=rt(t.value),n=K5(e?.roots),r=Xye(e?.classCounts),i=Qye(e?.resourceReferences),a=ive(e?.review),o=ove(e?.generation),s=sve(e?.studioUploads),c=pr(e?.exportedCount)??pr(t.exportedCount)??n.length;return{exportedCount:Math.max(0,Math.floor(c)),roots:n,classCounts:r,resourceReferences:i,thumbnail:tve(e?.thumbnail,t.fallbackThumbnail),...a?{review:a}:{},...o?{generation:o}:{},...s.length>0?{studioUploads:s}:{}}}function uve(t){return t.length>=8&&t[0]===137&&t[1]===80&&t[2]===78&&t[3]===71&&t[4]===13&&t[5]===10&&t[6]===26&&t[7]===10}function J5(t){let e=rt(t);if(!e)return;let n=null;if(typeof e.pngBase64=="string"&&e.pngBase64.length>0?n=Buffer.from(e.pngBase64,"base64"):typeof e.base64Rgba=="string"&&e.base64Rgba.length>0&&e.format==="rgba8"&&typeof e.width=="number"&&typeof e.height=="number"&&(n=Buffer.from(y5(e.base64Rgba,e.width,e.height),"base64")),!!n){if(!uve(n))throw new Error("Thumbnail payload is not a valid PNG image.");return{fileName:"thumbnail.png",content:n,mimeType:"image/png"}}}function dve(t,e){let n=e instanceof Error?e.message:String(e);return t.thumbnail.status!=="generated"?t:{...t,thumbnail:{...t.thumbnail,status:"failed",message:`Thumbnail payload could not be stored: ${n}`.slice(0,512)}}}async function Y5(t){if(!dA.has(t.command))return t.params;let e=fA(t.ctx,t.params);if(!e.assetId)throw new Error("assetLibraryAssetId is required for Asset Library .rbxm round-trip.");let n=await Zt(e,e.assetId);Gye(n);let r=await lu({...e,assetId:n.id}),i=await Fye(r);return{...t.params,__assetLibraryRbxmBase64:i.toString("base64"),__assetLibraryOriginalFile:n.file.original}}async function X5(t){if(!pA.has(t.command)||!t.result.success)return t.result;let e=rt(t.result.data);if(!e||typeof e.rbxmBase64!="string"||e.rbxmBase64.trim().length===0)return t.result;let n=fA(t.ctx,t.params),r=Kye(e.rbxmBase64,"Asset Library .rbxm export payload"),i=typeof t.params.displayName=="string"?t.params.displayName:void 0,a=typeof t.params.description=="string"?t.params.description:void 0,o=`${i?.trim()||"studio-export"}.rbxm`,s,c=null;try{s=J5(e.thumbnail)}catch(f){c=f,s=void 0}let l=lve({value:e.rbxm,exportedCount:e.exportedCount,fallbackThumbnail:eve(t.params,e.thumbnail)});c&&(l=dve(l,c));let u=cve(e.roblox),d=await L5({projectSyncRoot:n.projectSyncRoot,scope:n.scope,category:n.category,originalFileName:o,content:r,...i!==void 0?{displayName:i}:{},...a!==void 0?{description:a}:{},source:Jye(t.params,e.source),...s?{preview:s}:{},rbxm:l,...u?{roblox:u}:{}}),p=G5(e.thumbnail);return{...t.result,data:{asset:d.asset,deduplicated:d.deduplicated,...typeof e.byteLength=="number"?{byteLength:e.byteLength}:{},...typeof e.exportedCount=="number"?{exportedCount:e.exportedCount}:{},...e.source!==void 0?{source:e.source}:{},...p?{thumbnail:p}:{}}}}async function Q5(t){if(!t.result.success)return t.result;let e=rt(t.result.data),n=rt(e?.thumbnail),r;try{r=J5(n)}catch(d){return{...t.result,success:!1,error:d instanceof Error?d.message:String(d)}}if(!n||!r)return{...t.result,success:!1,error:typeof n?.error=="string"?n.error:"Thumbnail payload is missing from Asset Library thumbnail generation result."};let i=pr(n.width),a=pr(n.height),o=ge(n.source,128),s=om(n.attempts),c={mode:"auto",status:"generated",...i!==void 0?{width:i}:{},...a!==void 0?{height:a}:{},...o?{source:o}:{},...s.length>0?{attempts:s}:{}},l=fA(t.ctx,t.params);if(!l.assetId)throw new Error("assetLibraryAssetId is required for Asset Library thumbnail generation.");let u=await z5({projectSyncRoot:l.projectSyncRoot,scope:l.scope,category:l.category,assetId:l.assetId,preview:r,rbxmThumbnail:c});return{...t.result,data:{asset:u.asset,...i!==void 0?{width:i}:{},...a!==void 0?{height:a}:{},...o?{source:o}:{}}}}function pve(t){if(t===null||typeof t!="object")return;let e=t.proFallback;if(e===null||typeof e!="object")return;let n=e;if(typeof n.executedCommand!="string")return;let r=Array.isArray(n.alternatives)?n.alternatives.filter(i=>typeof i=="string"):void 0;return{executedCommand:n.executedCommand,...typeof n.requestedCommand=="string"?{requestedCommand:n.requestedCommand}:{},...r?{alternatives:r}:{}}}var fve=/^Pro action '[^']+' is blocked in Basic mode\. Basic fallback '([^']+)' failed: (.*)$/s,mve=/^Pro action '[^']+' is blocked in Basic mode\.(?! Basic fallback ')/,gve=/instance not found|not found in|parent not found/,hve=/is required|missing required/,yve=/unknown action|unknown command/,vve=/must be|invalid|cannot/;function bve(t){let e=fve.exec(t);return e?{fallbackCommand:e[1],reason:e[2]}:null}function xve(t){return mve.test(t)}function _ve(t){let e=t.toLowerCase();return gve.test(e)?"not_found":hve.test(e)?"missing_param":yve.test(e)?"unknown_action":vve.test(e)?"validation":"other"}function mA(t){return t.errorType==="bridge_error"||t.errorType==="command_timeout"||t.errorType==="plugin_runtime"||t.errorType==="exception"||t.errorType==="device_blocked"||t.failureOrigin==="bridge"||t.failureOrigin==="plugin_runtime"||t.failureOrigin==="server_exception"||t.failureOrigin==="product_bug"||t.failureOrigin==="unknown"||t.recoverability==="retry"||t.recoverability==="wait_connection"||t.recoverability==="unknown"?"error":"warning"}function uu(t){if(t.resultSuccess){let e=pve(t.resultData);return e?{kind:"success_fallback",fallbackCommand:e.executedCommand,...e.alternatives?{alternatives:e.alternatives}:{}}:{kind:"success_ok"}}if(!t.resultError)return{kind:"error"};if(t.tier==="pro"){let e=bve(t.resultError);if(e)return{kind:"blocked_fallback_failed",fallbackCommand:e.fallbackCommand,blockedDetail:_ve(e.reason)};if(xve(t.resultError))return{kind:"blocked_unsupported"}}return t.failureClassification?{kind:mA(t.failureClassification)}:{kind:"error"}}function Se(t,e,n,r,i={}){return{errorType:t,errorDetail:e,failureOrigin:n,recoverability:r,...i}}function Sve(t){let e=t.toLowerCase();return/^\s*compilation error:/.test(e)?Se("execution_failed","compile_error","agent_request","code_fix",{validationStage:"plugin_handler"}):/^\s*result too large:/.test(e)?Se("execution_failed","result_too_large","agent_request","code_fix",{validationStage:"plugin_handler"}):/^\s*execution timed out after/.test(e)?Se("execution_failed","execution_timeout","agent_request","code_fix",{validationStage:"plugin_handler"}):/potentially dangerous infinite loop|blocked in sandbox|access to .* is blocked|forbidden|not allowed|cannot access/.test(e)?Se("execution_failed","blocked_source","roblox_policy","code_fix",{validationStage:"plugin_handler"}):null}function wve(t){let e=t.toLowerCase();return/startline and endline must be provided together/.test(e)||/startline must be a positive integer/.test(e)||/endline must be a positive integer/.test(e)||/endline must be >= startline/.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"schema"}):null}function e9(t){let e=t.toLowerCase();return/upstream_server_down/.test(e)?Se("bridge_error","upstream_down","bridge","wait_connection"):/^http [45]\d\d/.test(e)?Se("bridge_error","http_error","bridge","retry"):/duplicate request\s*id/.test(e)?Se("bridge_error","duplicate_request_id","bridge","code_fix"):/timeout/.test(e)?Se("command_timeout","timeout","bridge","retry"):/econnrefused|socket hang up|econnreset|epipe|network/.test(e)?Se("bridge_error","connection","bridge","wait_connection"):/abort/.test(e)?Se("command_timeout","aborted","bridge","retry"):/runtime error|traceback|attempt to/.test(e)?Se("plugin_runtime","runtime_error","plugin_runtime","code_fix"):/created instance, but failed to set \d+ propert/.test(e)?Se("execution_failed","property_apply_failed","agent_request","fix_params",{validationStage:"plugin_handler",partialSuccess:"true"}):/failed to set property/.test(e)?Se("execution_failed","property_apply_failed","agent_request","fix_params",{validationStage:"plugin_handler"}):/parent(?: instance)? not found/.test(e)?Se("execution_failed","parent_not_found","agent_request","fix_params",{validationStage:"plugin_handler"}):/(?:instance|path|root|source instance|ancestor instance) not found|target\s+(?:path\s+)?(?:['"`][^'"`]+['"`]\s+)?not found|not found in|no synced file found for instance/.test(e)?Se("execution_failed","not_found","user_project_state","fix_params",{validationStage:"plugin_handler"}):/is required|missing required/.test(e)?Se("execution_failed","missing_param","agent_request","fix_params",{validationStage:"schema"}):/invalid classname|invalid class/.test(e)?Se("execution_failed","invalid_class","agent_request","fix_params",{validationStage:"plugin_handler"}):/unknown action|unknown command/.test(e)?Se("execution_failed","unknown_action","agent_request","fix_params",{validationStage:"dispatcher"}):/failed to insert asset/.test(e)?Se("execution_failed","asset_error","roblox_policy","fix_params",{validationStage:"roblox_api"}):/failed to read property|property access denied/.test(e)?Se("execution_failed","property_error","agent_request","fix_params",{validationStage:"plugin_handler"}):/forbidden (?:path|parent path)|exceeds (?:total lines|max(?:imum)?(?: length)?)|is not (?:a|an) /.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"plugin_handler"}):/sync controller not available|project sync is not initialized|no active sync place|not found in sync cache/.test(e)?Se("execution_failed","sync_not_ready","user_project_state","wait_connection",{validationStage:"preflight"}):/cannot capture edit-mode screenshot while a playtest is active|play-mode screenshot capture is not supported/.test(e)?Se("execution_failed","unsupported_context","roblox_policy","no_retry",{validationStage:"preflight"}):/editableimage api is not enabled|allow mesh \/ image apis|allow http requests/.test(e)?Se("execution_failed","feature_disabled","roblox_policy","no_retry",{validationStage:"preflight"}):/must be|invalid|cannot/.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"plugin_handler"}):Se("execution_failed","other","unknown","unknown")}function du(t,e){if(t==="manage_scripts_get_source"){let r=wve(e);if(r)return r}if(t==="execute_luau"){let r=Sve(e);if(r)return r}let n=e9(e);return t==="execute_luau"&&n.errorDetail==="runtime_error"&&/^\s*runtime error:/i.test(e)?Se("execution_failed","runtime_error","agent_request","code_fix"):n}function t9(t){let n=(t instanceof Error?t.message:String(t)).toLowerCase();return/timeout/.test(n)?Se("command_timeout","timeout","bridge","retry"):/econnrefused|socket hang up|network|econnreset|epipe/.test(n)?Se("bridge_error","connection","bridge","wait_connection"):/eaddrinuse/.test(n)?Se("bridge_error","port_in_use","bridge","no_retry"):Se("exception","unexpected","server_exception","code_fix")}W_();import{randomBytes as Tve}from"node:crypto";var Ave=["manage_ui_create_tree","manage_ui_update","manage_ui_delete"],c9=["manage_ui_preview","manage_ui_check"],Ove=["game_genre","ui_role","style_family","layout_family","device_policy","safe_area_policy","existing_ui_strategy"];function SA(t){return t&&typeof t=="object"?t:void 0}function xA(t){return typeof t=="number"&&Number.isFinite(t)?t:0}function G_(t){let e=SA(t);if(!e)return;let n={};for(let r of Ove){let i=e[r];typeof i=="string"&&i.trim().length>0&&(n[r]=i)}return Object.keys(n).length>0?n:void 0}function _A(t){let e=G_(t.qualityPlanSummary);if(e)return e;let n=SA(t.contextSummary),r=G_(n?.qualityPlanSummary);if(r)return r;let i=G_(n?.qualityPlan);if(i)return i;let a=G_(n?.quality_plan);if(a)return a}function l9(t,e){return e?{...t??{},...e}:t}function $ve(t){return typeof t=="string"?{snapshotId:t}:t&&typeof t=="object"?{snapshotId:typeof t.snapshotId=="string"?t.snapshotId:null,...t.designCheckSummary!==void 0&&{designCheckSummary:t.designCheckSummary},...t.capturedAt!==void 0&&{capturedAt:t.capturedAt}}:{snapshotId:null}}function u9(t,e,n,r,i){if(!e)return;let a=xA(e.priority_high),o=xA(e.priority_medium),s=xA(e.priority_low),c=typeof e.total=="number"&&Number.isFinite(e.total)?e.total:a+o+s,l=n??(typeof e.target=="string"?e.target:void 0);return{source:t,...l!==void 0&&{targetPath:l},...typeof r=="string"&&{snapshotId:r},...i!==void 0&&{capturedAt:i},priority_high:a,priority_medium:o,priority_low:s,total:c}}function d9(t,e){if(!e)return t;if(!t)return e;let n=t.targetPath===e.targetPath?t.targetPath:void 0,r=t.snapshotId===e.snapshotId?t.snapshotId:void 0;return{source:e.source,...n!==void 0&&{targetPath:n},...r!==void 0&&{snapshotId:r},...e.capturedAt!==void 0&&{capturedAt:e.capturedAt},priority_high:t.priority_high+e.priority_high,priority_medium:t.priority_medium+e.priority_medium,priority_low:t.priority_low+e.priority_low,total:t.total+e.total}}function Dve(t){let e=SA(t);if(e)for(let n of["userMessage","intent","expectedBehavior"]){let r=e[n];if(typeof r=="string"&&r.trim().length>0)return r.trim().slice(0,80)}}function Nve(){return{source:"unavailable",priority_high:0,priority_medium:0,priority_low:0,total:0}}function p9(t){let e=t.now??Date.now,n=null,r=null,i=u=>`${u}_${e()}_${Tve(3).toString("hex")}`,a=()=>{r&&(clearTimeout(r),r=null)},o=()=>{a(),r=setTimeout(()=>{c("idle_timeout")},t.idleMs)},s=async u=>{try{return $ve(await t.capturePreview(u))}catch{return{snapshotId:null}}},c=async u=>{if(!n)return;a();let d=n;n=null;let p={},f;for(let h of d.affectedPaths)if(d.afterSnapshotsPathPolicy[h]==="skip")p[h]=null;else{let v=await s(h);p[h]=v.snapshotId,f=d9(f,u9("after_snapshot",v.designCheckSummary,h,v.snapshotId,v.capturedAt))}let m=f??d.latestDesignCheckSummary??Nve(),g={requestId:d.requestId,...d.contextId!==void 0&&{contextId:d.contextId},...d.label!==void 0&&{label:d.label},startedAt:d.startedAtIso,closedAt:new Date(e()).toISOString(),closeReason:u,ok:d.ok,affectedPaths:Array.from(d.affectedPaths).sort(),mutationCount:d.mutationCount,beforeSnapshots:d.beforeSnapshots,afterSnapshots:p,childMutationIds:d.childMutationIds,...d.qualityPlanSummary!==void 0&&{qualityPlanSummary:d.qualityPlanSummary},postChangeDesignCheckSummary:m};await a9(t.placeDir,g)},l=u=>({requestId:i("req"),contextId:u.contextId,label:Dve(u.contextSummary),startedAtIso:new Date(e()).toISOString(),startedAtMs:e(),affectedPaths:new Set,beforeSnapshots:{},afterSnapshotsPathPolicy:{},childMutationIds:[],mutationCount:0,ok:!0,qualityPlanSummary:_A(u),latestDesignCheckSummary:void 0,pendingMutation:void 0});return{async beforeMutation(u){if(c9.includes(u.command)){if(n){let p=i("mut");n.qualityPlanSummary=l9(n.qualityPlanSummary,_A(u)),n.pendingMutation={mutationId:p,startedMs:e(),args:u}}return}if(!Ave.includes(u.command))return;n&&n.contextId!==u.contextId?await c("context_change"):n&&a(),n||(n=l(u)),n.qualityPlanSummary=l9(n.qualityPlanSummary,_A(u)),u.targetPath&&!(u.targetPath in n.beforeSnapshots)&&(n.affectedPaths.add(u.targetPath),u.command==="manage_ui_create_tree"?n.beforeSnapshots[u.targetPath]=null:n.beforeSnapshots[u.targetPath]=(await s(u.targetPath)).snapshotId,u.command==="manage_ui_delete"?n.afterSnapshotsPathPolicy[u.targetPath]="skip":u.targetPath in n.afterSnapshotsPathPolicy||(n.afterSnapshotsPathPolicy[u.targetPath]="capture"));let d=i("mut");n.pendingMutation={mutationId:d,startedMs:e(),args:u}},async afterMutation(u){if(!n?.pendingMutation)return;let{mutationId:d,args:p}=n.pendingMutation,f={mutationId:d,requestId:n.requestId,ts:new Date(e()).toISOString(),command:p.command,origin:p.origin,...p.targetPath!==void 0&&{targetPath:p.targetPath},...p.briefId!==void 0&&{briefId:p.briefId},...u.diffSummary!==void 0&&{diffSummary:u.diffSummary},...u.changeDetails!==void 0&&{changeDetails:u.changeDetails},ok:u.ok,...u.error!==void 0&&{error:u.error},durationMs:u.durationMs};if(await o9(t.placeDir,f),n.pendingMutation=void 0,c9.includes(p.command)){n.latestDesignCheckSummary=d9(n.latestDesignCheckSummary,u9("check_results",u.designCheckSummary,p.targetPath,u.snapshotId,u.capturedAt));return}if(n.mutationCount++,n.childMutationIds.push(d),u.ok||(n.ok=!1),!n.contextId){await c("legacy_single");return}o()},async flushNow(){n&&await c("explicit")}}}var T9=100,gbe=12e4,hbe=15e3,A9=new Set(["manage_ui_create_tree","manage_ui_update","manage_ui_delete"]);function ybe(t,e){return`License required for internal command ${t}. ${e??"Activate Pro license to use this feature."}`}var vbe={Text:{category:"text",label:"\uD14D\uC2A4\uD2B8"},PlaceholderText:{category:"text",label:"\uD50C\uB808\uC774\uC2A4\uD640\uB354"},TextColor3:{category:"color",label:"\uAE00\uC790\uC0C9"},BackgroundColor3:{category:"color",label:"\uBC30\uACBD\uC0C9"},BorderColor3:{category:"color",label:"\uD14C\uB450\uB9AC\uC0C9"},ImageColor3:{category:"color",label:"\uC774\uBBF8\uC9C0\uC0C9"},Size:{category:"size",label:"\uC0AC\uC774\uC988"},TextSize:{category:"size",label:"\uAE00\uC790 \uD06C\uAE30"},Position:{category:"layout",label:"\uC704\uCE58"},AnchorPoint:{category:"layout",label:"\uC575\uCEE4"},Rotation:{category:"layout",label:"\uD68C\uC804"},LayoutOrder:{category:"layout",label:"\uB808\uC774\uC544\uC6C3 \uC21C\uC11C"},Visible:{category:"state",label:"\uD45C\uC2DC \uC0C1\uD0DC"},Active:{category:"state",label:"\uD65C\uC131 \uC0C1\uD0DC"},Interactable:{category:"state",label:"\uC0C1\uD638\uC791\uC6A9 \uC0C1\uD0DC"},Selectable:{category:"state",label:"\uC120\uD0DD \uAC00\uB2A5"},Enabled:{category:"state",label:"\uD65C\uC131\uD654"},Image:{category:"asset",label:"\uC774\uBBF8\uC9C0"},Texture:{category:"asset",label:"\uD14D\uC2A4\uCC98"},SoundId:{category:"asset",label:"\uC0AC\uC6B4\uB4DC"}},bbe={text:"\uD14D\uC2A4\uD2B8",color:"\uCEEC\uB7EC",size:"\uC0AC\uC774\uC988",layout:"\uB808\uC774\uC544\uC6C3",state:"\uC0C1\uD0DC",asset:"\uC5D0\uC14B",property:"\uC18D\uC131"},xbe=Object.entries($s).reduce((t,[e,n])=>{for(let r of n.validActions)t[`${e}_${r}`]=e;return t},{});function I9(t){return{toolName:xbe[t]||t,commandName:t}}function C9(t,e){if(typeof t.contextId=="string"||!e||typeof e!="object")return t;let n=e.contextId;return typeof n=="string"?{...t,contextId:n}:t}function K_(t,e){if(t!=="manage_sync_status_current_place")return e;let{placeId:n,...r}=e;return r}function _be(t,e){let n=e.routing;return{requestId:t,success:!1,error:e.message,errorCode:e.code,routing:n,data:{routing:n}}}async function Sbe(t,e){let n=t.syncController;if(!n)return null;try{let r=e.placeId,i=n.getDefaultRuntimePlaceId(),a=null;if(typeof r=="number"&&Number.isFinite(r))a=r;else if(typeof r=="string"&&r.trim().length>0){let s=Number.parseInt(r,10);Number.isFinite(s)&&(a=s)}if(a===null&&(a=i),a===null||!Number.isFinite(a))return null;let o=a===i?n.getDefaultRuntimePlaceName():null;return typeof o=="string"&&o.length>0?await n.config.resolvePlaceRoot(a,o):n.config.getPlaceRoot(a)}catch{return null}}function wbe(t){let e=t.tree;if(!e||typeof e!="object")return;let n=e,r=typeof n.name=="string"&&n.name.length>0?n.name:void 0;return r?`${typeof n.parent=="string"&&n.parent.length>0?n.parent:"StarterGui"}.${r}`:void 0}function Ibe(t,e){let n=e.targetPath;if(typeof n=="string"&&n.length>0)return n;if(t==="manage_ui_create_tree")return wbe(e)}function Cbe(t){let e=vbe[t];if(e)return e;let n=t.toLowerCase();return n.includes("color")?{category:"color",label:"\uC0C9\uC0C1"}:t==="Size"||n.endsWith("size")||n.includes("scale")?{category:"size",label:"\uC0AC\uC774\uC988"}:n.includes("position")||n.includes("anchor")||n.includes("rotation")||n.includes("layout")?{category:"layout",label:"\uB808\uC774\uC544\uC6C3"}:n.includes("visible")||n.includes("active")||n.includes("enabled")||n.includes("selectable")||n.includes("interactable")?{category:"state",label:"\uC0C1\uD0DC"}:n.includes("image")||n.includes("texture")||n.includes("sound")||n.includes("asset")?{category:"asset",label:"\uC5D0\uC14B"}:n.includes("text")||n.includes("placeholder")?{category:"text",label:"\uD14D\uC2A4\uD2B8"}:{category:"property",label:t}}function P9(t,e){return Object.prototype.hasOwnProperty.call(t,e)}function Pbe(t){if(!t||typeof t!="object")return new Map;let e=t,n=e.changed_properties??e.changedProperties;if(!Array.isArray(n))return new Map;let r=new Map;for(let i of n){if(!i||typeof i!="object")continue;let a=i,o=a.property;if(typeof o!="string"||o.length===0)continue;let s=P9(a,"before"),c=P9(a,"after");r.set(o,{...s&&{before:a.before},...c&&{after:a.after},hasBefore:s,hasAfter:c})}return r}function O9(t,e){let r=t.changes?.properties;if(!r||typeof r!="object")return;let i=Pbe(e),a=Object.entries(r).map(([o,s])=>{let c=Cbe(o),l=i.get(o),u={property:o,category:c.category,label:c.label,after:l?.hasAfter?l.after:s};return l?.hasBefore&&(u.before=l.before),u});return a.length>0?a:void 0}function $9(t){if(!t||t.length===0)return;let e=new Map;for(let i of t)e.set(i.category,(e.get(i.category)??0)+1);let r=["text","color","size","layout","state","asset","property"].map(i=>{let a=e.get(i)??0;return a>0?`${bbe[i]} ${a}\uAC1C`:null}).filter(i=>i!==null);return r.length>0?`${r.join(", ")} \uBCC0\uACBD`:void 0}function k9(t,e){if(t==="manage_ui_update"){let n=e.changes,r=$9(O9(e));if(r)return r;let i=n?.properties?Object.keys(n.properties).length:0,a=Array.isArray(n?.addChildren)?n.addChildren.length:0,o=Array.isArray(n?.removeChildren)?n.removeChildren.length:0;return`${i} props, +${a}, -${o}`}if(t==="manage_ui_create_tree")return"tree \uC0DD\uC131";if(t==="manage_ui_delete")return"\uC81C\uAC70\uB428"}function ym(t){return t&&typeof t=="object"?t:void 0}function J_(t,e){let n=t[e];return typeof n=="number"&&Number.isFinite(n)?n:0}function D9(t){let e=ym(t),n=ym(e?.design_check_summary);if(n)return{priority_high:J_(n,"priority_high"),priority_medium:J_(n,"priority_medium"),priority_low:J_(n,"priority_low"),total:J_(n,"total"),...typeof n.scope=="string"&&{scope:n.scope},...typeof n.target=="string"&&{target:n.target}}}function N9(t){let n=ym(t)?.snapshot_id;return typeof n=="string"?n:null}function E9(t){if(typeof t=="string"&&t.trim().length>0)return t;if(typeof t=="number"&&Number.isFinite(t)){let e=t<1e10?t*1e3:t;return new Date(e).toISOString()}}function j9(t){let e=ym(t),n=ym(e?.meta);return E9(n?.captured_at)??E9(n?.evaluated_at)}function kbe(t,e){let n=t.uiStudioRecorders.get(e);if(n)return n;let r=p9({placeDir:e,idleMs:hbe,capturePreview:async i=>{try{let a=await fr(t,"manage_ui_preview",{targetPath:i},X_());if(!a.success||!a.data||typeof a.data!="object")return null;let o=D9(a.data),s=j9(a.data);return{snapshotId:N9(a.data),...o!==void 0&&{designCheckSummary:o},...s!==void 0&&{capturedAt:s}}}catch{return null}}});return t.uiStudioRecorders.set(e,r),r}async function Ebe(t,e,n){if(!A9.has(e))return null;let r=await Sbe(t,n);if(!r)return null;let i=kbe(t,r),a=e,o=typeof n.contextId=="string"?n.contextId:void 0,s=n.contextSummary,c=s!==void 0&&typeof s=="object"?s:void 0,l=Ibe(a,n),u=typeof n.briefId=="string"?n.briefId:void 0,d={command:a,...o!==void 0&&{contextId:o},...c!==void 0&&{contextSummary:c},...l!==void 0&&{targetPath:l},...u!==void 0&&{briefId:u},origin:n.__origin==="dashboard"?"dashboard":"ai"};try{return await i.beforeMutation(d),{recorder:i,command:a,params:n,startedAt:Date.now()}}catch(p){return y.debug("UI Studio recorder beforeMutation \uC2E4\uD328 (\uBB34\uC2DC)",{error:p}),null}}async function R9(t,e){if(t)try{let n=t.command==="manage_ui_update"?O9(t.params,e.data):void 0,r=t.command==="manage_ui_update"?$9(n)??k9(t.command,t.params):k9(t.command,t.params),i=D9(e.data),a=N9(e.data),o=j9(e.data);await t.recorder.afterMutation({ok:e.success,durationMs:Date.now()-t.startedAt,...r!==void 0&&{diffSummary:r},...n!==void 0&&{changeDetails:n},...e.error!==void 0&&{error:e.error},...i!==void 0&&{designCheckSummary:i},...a!==null&&{snapshotId:a},...o!==void 0&&{capturedAt:o}})}catch(n){y.debug("UI Studio recorder afterMutation \uC2E4\uD328 (\uBB34\uC2DC)",{error:n})}}async function Y_(t,e,n,r,i,a){if(!t.historyManager)return;let o=!i.success&&i.error?du(n,i.error):void 0,s=uu({resultSuccess:i.success,resultData:i.data,resultError:i.error,tier:Gn(n),...o?{failureClassification:o}:{}});if(i.success){let u=s.kind==="success_fallback"&&i.data&&typeof i.data=="object"?{...i.data,outcomeStatus:"fallback",requestedCommand:n,executedCommand:s.fallbackCommand,...s.alternatives?{alternatives:s.alternatives}:{}}:i.data,d=K_(n,r);i.routing?await t.historyManager.recordSuccess(e,d,u,a,n,void 0,i.routing):await t.historyManager.recordSuccess(e,d,u,a,n);return}if(s.kind==="blocked_unsupported"){await t.historyManager.recordBlockedOutcome(e,K_(n,r),i.error||"Pro action blocked in Basic mode","blocked_unsupported",{executionTimeMs:a,command:n,...i.routing?{routing:i.routing}:{}});return}if(s.kind==="blocked_fallback_failed"){await t.historyManager.recordBlockedOutcome(e,K_(n,r),i.error||"Pro action blocked in Basic mode","blocked_fallback_failed",{executionTimeMs:a,command:n,...s.fallbackCommand?{fallbackCommand:s.fallbackCommand}:{},...s.blockedDetail?{blockedDetail:s.blockedDetail}:{},...i.routing?{routing:i.routing}:{}});return}let c=s.kind==="warning"?t.historyManager.recordWarning.bind(t.historyManager):t.historyManager.recordFailure.bind(t.historyManager),l=K_(n,r);i.routing?await c(e,l,i.error||"Unknown error",a,i.errorCode??o?.errorType.toUpperCase(),n,void 0,i.routing):await c(e,l,i.error||"Unknown error",a,i.errorCode??o?.errorType.toUpperCase(),n)}function PA(t,e,n){let r=t.pendingCommands.get(e)||[];r.length>=T9&&r.shift(),r.push(n),t.pendingCommands.set(e,r)}function Rbe(t,e){t.globalPendingCommands.length>=T9&&t.globalPendingCommands.shift(),t.globalPendingCommands.push(e)}function M9(t,e,n){let r=X_(),i={requestId:r,command:e.command,params:e.params,timestamp:Date.now(),queueTimeoutMs:e.queueTimeoutMs,ackedTimeoutMs:e.ackedTimeoutMs,state:kn.QUEUED,targetClientId:n,resolve:()=>{},reject:a=>{y.debug("Auxiliary playtest stop command ended without awaited response",{requestId:r,targetClientId:n,error:a.message})},timeoutId:null};return t.commandQueue.set(r,i),i.timeoutId=setTimeout(()=>{qx(t,i,i.queueTimeoutMs)},i.queueTimeoutMs),{event:"command",id:r,data:{command:i.command,requestId:r,params:i.params}}}function Tbe(t,e,n,r){if(!Qf(e.data.command))return;let i=t.commandQueue.get(e.data.requestId);if(!i)return;L9(t,i);let a=n.filter(o=>o.clientId!==r);for(let o of a){let s=M9(t,i,o.clientId);PA(t,o.clientId,s)}a.length>0&&y.info("Fan-out playtest stop command to active plugin clients",{requestId:e.data.requestId,primaryClientId:r,auxiliaryClientIds:a.map(o=>o.clientId)})}function L9(t,e,n){for(let r of f5)setTimeout(()=>{let a=n?[...new Set(n)]:[...new Set($n(t).map(o=>o.clientId))];for(let o of a){if(!t.pluginClients.get(o))continue;let c=M9(t,e,o);PA(t,o,c)}y.info("Retry playtest stop command to active plugin clients",{sourceRequestId:e.requestId,delayMs:r,targetClientIds:a}),Hl(t)},r).unref?.()}function z9(t){return t==="clientId"||t==="targetAlias"||t==="placeId"}function Abe(t,e,n){if(!n||!Qf(e.data.command))return!1;let r=t.commandQueue.get(e.data.requestId)?.routing?.selectionMode;return!z9(r)}function Obe(t,e,n){y.debug("Broadcasting command",{command:e.data.command,requestId:e.data.requestId,targetClientId:n||"all",activeWebsocketClients:$n(t).length});let r=n;if(n){PA(t,n,e);let i=t.commandQueue.get(e.data.requestId),a=i?.routing?.selectionMode;if(i&&Qf(e.data.command)&&z9(a))L9(t,i,[n]);else if(Abe(t,e,n)){let o=$n(t).sort((s,c)=>c.lastSeen-s.lastSeen);Tbe(t,e,o,n),r=void 0}}else Rbe(t,e);Hl(t,r)}async function F9(t,e,n){let r=Date.now(),i="",a={};try{let o=e.body;i=o.command??"",a=o.params||{};let s=o.requestId;if(o.instanceId||(t.serverLastCommandAt=Date.now()),o.instanceId){let m=t.mcpInstances.get(o.instanceId);m&&(m.lastCommandAt=Date.now(),m.lastSeen=m.lastCommandAt)}let c=I9(i),l=typeof o.timeout=="number"&&Number.isFinite(o.timeout)&&o.timeout>0?{timeout:o.timeout}:void 0,u=o.instanceId?t.mcpInstances.get(o.instanceId)?.sessionId??t.sessionId:t.sessionId;if(!i){n.status(400).json({error:"Missing command"});return}if(y.debug("Received execute request",{command:i,requestId:s}),i==="manage_camera_play_screenshot"){let m="manage_camera.play_screenshot is not supported. Screenshot capture is available only in Edit mode via manage_camera.screenshot.",g=Date.now()-r;t.historyManager&&await t.historyManager.recordFailure("manage_camera",a,m,g,"UNSUPPORTED_COMMAND",i),n.json({requestId:s,success:!1,error:m});return}if(i==="get_cached_selection"){let m=a.maxAge,g=Xf(t,m!==void 0?m:3e4),h=Date.now()-r;if(!g){let _={requestId:s,success:!0,data:{cached:!1,message:"No cached selection data available. The plugin may not be connected or no selection changes have occurred yet."}};t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,_.data,h,c.commandName),n.json(_);return}let v=Date.now()-g.timestamp,x={cached:!0,selection:g.selection,count:g.count,timestamp:g.timestamp,age:v};t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,x,h,c.commandName),n.json({requestId:s,success:!0,data:x});return}if(i==="get_connection_info"){let m=await $_(t),g=Date.now()-r;t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,m,g,c.commandName),n.json({requestId:s,success:!0,data:m});return}if(N_(i)==="internal"){if(!t.internalCommandExecutor){n.status(503).json({requestId:s,success:!1,error:`Internal command executor is not initialized for command: ${i}`});return}if(Gn(i)==="pro"){if(!t.licenseState){n.status(503).json({requestId:s,success:!1,error:`License state manager is not initialized for internal command: ${i}`});return}let x=await t.licenseState.evaluateProAccess();if(!x.allowed){let _=ybe(i,x.reason),P=Date.now()-r;t.historyManager&&await Y_(t,c.toolName,c.commandName,a,{success:!1,error:_},P),n.json({requestId:s,success:!1,error:_});return}}let m={...a,__sessionId:u},g=await t.internalCommandExecutor(i,m),h=Date.now()-r,v=C9(m,g.data);t.historyManager&&await Y_(t,c.toolName,c.commandName,v,{success:g.success,data:g.data,error:g.error||"Internal command failed"},h),n.json({requestId:s,...g});return}let d=await fr(t,i,a,s,l),p=Date.now()-r,f={...C9(a,d.data),__sessionId:u};t.historyManager&&await Y_(t,c.toolName,c.commandName,f,d,p),n.json(d)}catch(o){let s=Date.now()-r,c=Wn(o);if(t.historyManager&&i){let l=I9(i);await t.historyManager.recordFailure(l.toolName,a,c,s,"EXCEPTION",l.commandName)}y.error("Execute request failed",o),n.status(500).json({success:!1,error:c})}}async function U9(t,e,n){let r=Date.now(),i=e.body,a=i.action;if(!a||typeof a!="string"){n.status(400).json({success:!1,error:"Missing required field: action"});return}if(!new Set(["get","set","get_all","set_multiple","get_attr","set_attr","get_all_attrs","delete_attr","add_tag","remove_tag","check_tag","get_tags","get_tagged"]).has(a)){n.status(400).json({success:!1,error:`Unsupported action: ${a}`});return}let s=`manage_properties_${a}`,c=X_(),{action:l,...u}=i;try{t.serverLastCommandAt=Date.now();let d=await fr(t,s,u,c),p=Date.now()-r;t.historyManager&&await Y_(t,"manage_properties",s,u,d,p),n.json(d)}catch(d){let p=Date.now()-r,f=Wn(d);t.historyManager&&await t.historyManager.recordFailure("manage_properties",u,f,p,"EXCEPTION",s),y.error("/api/properties \uC694\uCCAD \uCC98\uB9AC \uC2E4\uD328",d),n.status(500).json({success:!1,error:f})}}async function fr(t,e,n,r,i){if(y.debug("Executing command locally",{command:e,requestId:r}),$8(t,r)){let d=`Duplicate requestId '${r}' for command '${e}'. Generate a unique requestId for each command.`;return y.warn("Duplicate execute request rejected",{command:e,requestId:r}),{requestId:r,success:!1,error:d}}let a;try{a=D_(t,$n(t),n,e)}catch(d){if(d instanceof gn)return y.warn("Command target selection failed",{command:e,requestId:r,errorCode:d.code,routing:d.routing}),_be(r,d);throw d}let o=A9.has(e)?await Ebe(t,e,n):null,s=t.config.requestTimeout,c=i?.timeout??Math.max(t.config.requestTimeout,gbe),l=dA.has(e)?await Y5({ctx:t,command:e,params:n}):n,u=new Promise((d,p)=>{let f=Date.now(),m={requestId:r,command:e,params:l,timestamp:f,queueTimeoutMs:s,ackedTimeoutMs:c,state:kn.QUEUED,...a.targetClientId?{targetClientId:a.targetClientId}:{},routing:a.routing,resolve:d,reject:p,timeoutId:null};t.commandQueue.set(r,m),Mx(t,a.targetClientId,f),m.timeoutId=setTimeout(()=>{qx(t,m,s)},s)});return Obe(t,{event:"command",id:X_(),data:{command:e,requestId:r,params:l}},a.targetClientId),u.then(async d=>{let p=d;if(e==="manage_ui_preview"&&d.success&&d.data)try{let{processPreviewResult:f,resolvePreviewPlaceDirFromCtx:m}=await Promise.resolve().then(()=>(CA(),IA)),g=await m(t,n),h=await f("manage_ui_preview",d.data,g);p={...d,data:h.data,...h.mcpContent?{mcpContent:h.mcpContent}:{}}}catch(f){y.warn("preview post-processing failed",{error:f instanceof Error?f.message:String(f)})}if(e==="manage_ui_check"&&d.success&&d.data&&n.includeVisualAnalysis===!0)try{let{resolvePreviewPlaceDirFromCtx:f}=await Promise.resolve().then(()=>(CA(),IA)),{processCheckResult:m}=await Promise.resolve().then(()=>(w9(),S9)),g=await f(t,n),h=await m("manage_ui_check",d.data,g,n);p={...p,data:h.data}}catch(f){y.warn("check visual post-processing failed",{error:f instanceof Error?f.message:String(f)})}return pA.has(e)?p=await X5({ctx:t,command:e,params:n,result:p}):e===uA&&(p=await Q5({ctx:t,params:n,result:p})),p}).then(async d=>(await R9(o,{success:d.success,...d.data!==void 0&&{data:d.data},...d.error!==void 0&&{error:d.error}}),d),async d=>{throw await R9(o,{success:!1,error:Wn(d)}),d})}ae();Fi();function Q_(t,e){let n={};e.provider!==void 0&&(n.provider=e.provider),e.tier!==void 0&&(n.tier=e.tier),e.status!==void 0&&(n.status=e.status),e.canUsePro!==void 0&&(n.canUsePro=e.canUsePro),e.cleared===!0&&(n.cleared=!0),ot(t,"license",n)}function yi(t,e,n,r){t.status(e).json({success:!1,error:{code:n,message:r}})}function $be(t){if(typeof t!="string")return;let e=t.trim().toLowerCase();return e.length>0?e:void 0}function eS(t,e){if(e==="plugin")return t;let n={...t};return delete n.sessionToken,n}function vm(t,e,n,r){let i=$be(r??e.query.provider)??"auto";return t.licenseState?.supportsProvider(i)===!1?(yi(n,400,"LICENSE_PROVIDER_UNSUPPORTED",`provider "${i}" is not supported`),null):i}function bm(t,e){return t.licenseState?!0:(yi(e,503,"LICENSE_NOT_INITIALIZED","License system is not initialized"),!1)}function Dbe(t){if(!t||typeof t!="object")return!1;let e=t;return(e.canUsePro===!0||e.canUsePro===!1)&&typeof e.status=="string"&&typeof e.checkedAt=="number"}function xm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=typeof i?.licenseKey=="string"?i.licenseKey:"";if(!a.trim()){yi(n,400,"LICENSE_KEY_REQUIRED","licenseKey is required");return}let o=vm(t,e,n,i?.provider);if(!o)return;let s=typeof i?.pluginClientId=="string"?i.pluginClientId:typeof e.query.clientId=="string"?e.query.clientId:void 0,c=typeof i?.deviceId=="string"?i.deviceId:void 0,l={licenseKey:a,provider:o,clientType:r};s&&(l.pluginClientId=s),c&&(l.deviceId=c),t.licenseState.activateGateway(l).then(u=>{t.analyticsManager?.setTier(u.canUsePro?"pro":"basic"),Q_(t,{provider:u.provider,tier:u.canUsePro?"pro":"basic",status:u.status,canUsePro:u.canUsePro}),n.json(eS(u,r))}).catch(u=>{y.warn("License activate failed",{error:u instanceof Error?u.message:"unknown_error"}),yi(n,502,"LICENSE_ACTIVATE_FAILED",u instanceof Error?u.message:"License activation failed")})}function _m(t,e,n,r="plugin"){if(!bm(t,n))return;let i=vm(t,e,n);if(i)try{let a=t.licenseState.getStatus(i);t.analyticsManager?.setTier(a.canUsePro?"pro":"basic"),n.json(eS(a,r))}catch(a){y.warn("License status check failed",{error:a instanceof Error?a.message:"unknown_error"}),yi(n,502,"LICENSE_STATUS_FAILED",a instanceof Error?a.message:"License status check failed")}}function Sm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=vm(t,e,n,i?.provider);if(!a)return;let o={provider:a,clientType:r};r==="plugin"&&typeof i?.sessionToken=="string"&&i.sessionToken.trim()&&(o.sessionToken=i.sessionToken.trim()),typeof i?.pluginClientId=="string"&&(o.pluginClientId=i.pluginClientId),typeof i?.deviceId=="string"&&(o.deviceId=i.deviceId),t.licenseState.refreshGateway(o).then(s=>{t.analyticsManager?.setTier(s.canUsePro?"pro":"basic"),Q_(t,{provider:s.provider,tier:s.canUsePro?"pro":"basic",status:s.status,canUsePro:s.canUsePro}),n.json(eS(s,r))}).catch(s=>{y.warn("License refresh failed",{error:s instanceof Error?s.message:"unknown_error"}),yi(n,502,"LICENSE_REFRESH_FAILED",s instanceof Error?s.message:"License refresh failed")})}function wm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=vm(t,e,n,i?.provider);a&&t.licenseState.resetGateway({provider:a,clientType:r}).then(o=>{t.analyticsManager?.setTier("basic"),Q_(t,{provider:o.provider,tier:"basic",status:o.status,canUsePro:o.canUsePro,cleared:!0}),n.json(eS(o,r))}).catch(o=>{y.warn("License reset failed",{error:o instanceof Error?o.message:"unknown_error"}),yi(n,502,"LICENSE_RESET_FAILED",o instanceof Error?o.message:"License reset failed")})}function kA(t,e,n){if(!bm(t,n))return;let r=e.body,i=vm(t,e,n,r?.provider);if(!i)return;if(r?.clientType!=="plugin"){yi(n,400,"LICENSE_CLIENT_TYPE_INVALID","clientType must be plugin");return}let a=typeof r?.sessionToken=="string"&&r.sessionToken.trim()?r.sessionToken.trim():void 0,o=Dbe(r?.snapshot)?r.snapshot:void 0;if(!o&&!a){yi(n,400,"LICENSE_BOOTSTRAP_REQUIRED","snapshot or sessionToken is required");return}let s={provider:i,clientType:"plugin"};o&&(s.snapshot=o),a&&(s.sessionToken=a),t.licenseState.bootstrap(s).then(c=>{t.analyticsManager?.setTier(c.canUsePro?"pro":"basic"),Q_(t,{provider:c.provider,tier:c.canUsePro?"pro":"basic",status:c.status,canUsePro:c.canUsePro}),n.json({ok:!0})}).catch(c=>{y.warn("License bootstrap failed",{error:c instanceof Error?c.message:"unknown_error"}),yi(n,502,"LICENSE_BOOTSTRAP_FAILED",c instanceof Error?c.message:"License bootstrap failed")})}function q9(t){t.app.post("/license/bootstrap",(e,n)=>kA(t,e,n)),t.app.post("/license/activate",(e,n)=>xm(t,e,n,"plugin")),t.app.post("/license/refresh",(e,n)=>Sm(t,e,n,"plugin")),t.app.post("/license/reset",(e,n)=>wm(t,e,n,"plugin")),t.app.get("/license/status",(e,n)=>_m(t,e,n,"plugin"))}vt();ae();import{promises as tS}from"fs";import EA from"path";function Nbe(t){let e=t.config.appDataDir??lt();return EA.join(e,"observability","logs")}async function hu(t,e,n){let r=e.query.clientId;if(r&&t.pluginClients.has(r)){let i=t.pluginClients.get(r);i.lastSeen=Date.now()}try{let i=e.body;if(!i||!Array.isArray(i.logs)){y.warn("Invalid logs request",{body:i}),n.status(400).json({error:"Invalid request body"});return}let a=Nbe(t);await tS.mkdir(a,{recursive:!0});let c=`plugin-${new Date().toISOString().split("T")[0]}.log`,l=EA.join(a,c),u=EA.join(a,"current.log"),d=i.logs.map(p=>`[${new Date(p.timestamp*1e3).toISOString().replace("T"," ").substring(0,19)}] [${p.level}] ${p.message}`).join(`
|
|
529
|
+
`),r.index.setFormatVersion(Pt);let f=ys(r.index.toSyncIndexData());return await this.fileOps.writeFileAtomic(o,f),r.formatVersion=Pt,r.writer.setFormatVersion(Pt),await r.fileWatcher?.endFullSyncReplacement(),this.preview(e.placeId)}catch(p){throw await this.rollback(l,c,r,u),p}}async buildPlan(e){let n=this.ctx.places.get(e);if(!n)throw new Ki(404,"place_not_found");let r=this.ctx.config.getSyncRoot(),i=Rt.dirname(n.index.getExplorerRoot()),a=n.index.getExplorerRoot();if(n.formatVersion!==ut){let x=ZB(ys({blockers:[],changes:[],fromVersion:ut,placeId:e,toVersion:Pt}));return{placeId:e,fromVersion:ut,toVersion:Pt,status:"not_required",previewFingerprint:x,userSourceModified:0,summary:{add:0,modify:0,delete:0,blocked:0},changes:[],blockers:[],operations:new Map}}let s=await Jhe(r,a),c=new Set(s.map(x=>x.absolutePath)),l=[],u=new Map;for(let x of s){let _=await Yhe(x,c);_&&(l.push(_.change),u.set(_.change.path,_.after))}let d=await this.planManagedIgnore(r);d&&(l.push(d.change),u.set(d.change.path,d.after)),l.sort(eye);let p=await this.collectBlockers(r,n);p.sort(tye);let f=Rt.join(i,".sync-index.json"),m=await this.readFileOrNull(f),g=[...n.index.getAllFileHashes().keys()].map(x=>{let _=b_(r,x);if(Ps(_)!=="canonical_mirror")return null;let w=n.index.getHashPair(x);return{path:_,fileHash:w.fileHash??null,studioHash:w.studioHash??null}}).filter(x=>x!==null).sort((x,_)=>x.path.localeCompare(_.path)),h=ZB(ys({blockers:p,changes:l,fromVersion:ut,indexHash:m?Os(m):null,indexState:g,placeId:e,toVersion:Pt})),v={add:l.filter(x=>x.operation==="add").length,modify:l.filter(x=>x.operation==="modify").length,delete:l.filter(x=>x.operation==="delete").length,blocked:p.length};return{placeId:e,fromVersion:ut,toVersion:Pt,status:p.length>0?"blocked":"ready",previewFingerprint:h,userSourceModified:0,summary:v,changes:l,blockers:p,operations:u}}async planManagedIgnore(e){let n=Rt.join(e,".gitignore"),r=await this.readFileOrNull(n),i=r?.toString("utf8")??"",a=Buffer.from(VT(i),"utf8");return r?.equals(a)?null:{change:{path:".gitignore",ownership:"generated",operation:r===null?"add":"modify",reason:"runtime_ignore_policy",...r!==null?{beforeHash:Os(r)}:{},afterHash:Os(a)},after:a}}async readFileOrNull(e){return this.fileOps.readFile(e).catch(n=>{if(n.code==="ENOENT")return null;throw n})}async captureOriginals(e,n,r,i){let a=[];for(let o of n){let s=Rt.resolve(e,o.path);a.push({absolutePath:s,content:await this.readFileOrNull(s)})}return a.push({absolutePath:r,content:await this.readFileOrNull(r)}),a.push({absolutePath:i,content:await this.readFileOrNull(i)}),a}async writeBackup(e,n,r){await this.fileOps.mkdir(n);for(let i of r){if(i.content===null)continue;let a=b_(e,i.absolutePath);await this.fileOps.copyFile(i.absolutePath,Rt.join(n,"files",a))}}async applyOperations(e,n,r,i){let a=new Map(i.map(o=>[o.absolutePath,o.content]));for(let o of r.changes){let s=Rt.resolve(e,o.path),c=r.operations.get(o.path);if(c===void 0)throw new Error(`Missing migration operation content: ${o.path}`);if(n.fileWatcher?.suppressPath(s,c===null?"missing":n.index.computeHash(c.toString("utf8"))),c===null?await this.fileOps.unlink(s):await this.fileOps.writeFileAtomic(s,c),o.ownership!=="canonical_mirror")continue;if(c===null){n.index.removeHash(s);continue}let l=a.get(s);(l?n.index.getFileStatus(s,n.index.computeHash(l.toString("utf8"))):"synced")==="studio-modified"?n.index.updateFileHash(s,c.toString("utf8")):n.index.updateBothHashes(s,c.toString("utf8"))}}async assertUserSourcesUnchanged(e,n){let r=await WB(e);if(!rye(n,r))throw new Ki(409,"source_mutation_detected")}async rollback(e,n,r,i){let a;for(let o of[...e].reverse())try{o.content===null?await this.fileOps.unlink(o.absolutePath).catch(s=>{if(s.code!=="ENOENT")throw s}):await this.fileOps.writeFileAtomic(o.absolutePath,o.content)}catch(s){a??=s}r.index.clearAllHashes();for(let[o,s]of i.studioHashes)r.index.updateHashByValue(o,s);for(let[o,s]of i.fileHashes)r.index.updateFileHashByValue(o,s);if(r.index.setFormatVersion(ut),r.formatVersion=ut,r.writer.setFormatVersion(ut),await Mr.rm(n,{recursive:!0,force:!0}),await r.fileWatcher?.endFullSyncReplacement(),a)throw a}async collectBlockers(e,n){let r=[];(n.fileWatcher?.getPendingCount()??0)>0&&r.push({reason:"reverse_pending"});for(let i of n.index.getAllFileHashes().keys()){let a=b_(e,i);if(Ps(a)!=="canonical_mirror")continue;let o=await Qhe(i);if(o===null){r.push({path:a,reason:"local_canonical_change"});continue}let s=n.index.getFileStatus(i,n.index.computeHash(o.toString("utf8")));s==="conflict"?r.push({path:a,reason:"conflict"}):s==="file-modified"&&r.push({path:a,reason:"local_canonical_change"})}return nye(r)}};async function Jhe(t,e){let n=[];async function r(i){let a=await Mr.readdir(i,{withFileTypes:!0}).catch(o=>{if(o.code==="ENOENT")return[];throw o});for(let o of a){let s=Rt.join(i,o.name);if(o.isDirectory()){await r(s);continue}Xhe(o.name)&&n.push({absolutePath:s,relativePath:b_(t,s),content:await Mr.readFile(s)})}}return await r(e),n.sort((i,a)=>i.relativePath.localeCompare(a.relativePath))}async function Yhe(t,e){let n=JSON.parse(t.content.toString("utf8")),r=Os(t.content);if(t.absolutePath.endsWith(".props.json")){let o=n,s=t.absolutePath.replace(/\.props\.json$/,".value.json");if(LT(o,e.has(s)))return{change:{path:t.relativePath,ownership:"canonical_mirror",operation:"delete",reason:"redundant_empty_metadata",beforeHash:r},after:null}}let i="serializer_regeneration";Rt.basename(t.absolutePath)==="_tree.json"&&n!==null&&typeof n=="object"&&!Array.isArray(n)&&Object.prototype.hasOwnProperty.call(n,"syncedAt")&&(delete n.syncedAt,i="volatile_metadata_removal");let a=Buffer.from(ys(n),"utf8");return t.content.equals(a)?null:{change:{path:t.relativePath,ownership:"canonical_mirror",operation:"modify",reason:i,beforeHash:r,afterHash:Os(a)},after:a}}function Xhe(t){return t==="_tree.json"||t.endsWith(".props.json")||t.endsWith(".value.json")}function b_(t,e){return Rt.relative(t,e).replaceAll(Rt.sep,"/")}function Os(t){return Ghe("sha256").update(t).digest("hex")}function ZB(t){return Os(Buffer.from(t,"utf8"))}function Qhe(t){return Mr.readFile(t).catch(e=>{if(e.code==="ENOENT")return null;throw e})}function eye(t,e){return t.path.localeCompare(e.path)||t.operation.localeCompare(e.operation)||t.reason.localeCompare(e.reason)}function tye(t,e){return(t.path??"").localeCompare(e.path??"")||t.reason.localeCompare(e.reason)}function nye(t){let e=new Set;return t.filter(n=>{let r=`${n.path??""}\0${n.reason}`;return e.has(r)?!1:(e.add(r),!0)})}async function WB(t){let e=new Map;async function n(r){let i=await Mr.readdir(r,{withFileTypes:!0}).catch(a=>{if(a.code==="ENOENT")return[];throw a});for(let a of i){let o=Rt.join(r,a.name);a.isDirectory()?await n(o):(a.name.endsWith(".server.luau")||a.name.endsWith(".client.luau")||a.name.endsWith(".module.luau"))&&e.set(Rt.relative(t,o).replaceAll(Rt.sep,"/"),Os(await Mr.readFile(o)))}}return await n(t),e}function rye(t,e){if(t.size!==e.size)return!1;for(let[n,r]of t)if(e.get(n)!==r)return!1;return!0}Ui();ae();var iye=5;function GB(t){if(!t||typeof t!="object")return;let e=t;if(Array.isArray(e.instances))for(let n of e.instances)Array.isArray(n.properties)&&n.properties.length===0&&(n.properties={}),Array.isArray(n.attributes)&&n.attributes.length===0&&(n.attributes={});if(Array.isArray(e.changes))for(let n of e.changes)Array.isArray(n.properties)&&n.properties.length===0&&(n.properties={}),Array.isArray(n.attributes)&&n.attributes.length===0&&(n.attributes={})}function aye(t){return t.type==="instanceAdded"||t.type==="instanceRemoved"||t.type==="instanceRenamed"||t.type==="instanceMoved"||t.type==="scriptSourceChanged"}var pi=class{config;places;apiHandler;changeProcessor;initHandler;reverseHandler;migrationService;reverseDetectorFactory;placeDisposals=new Map;activeFullSyncPlaceId=null;activeRuntimeSyncPlaceId=null;currentConnectedPlaceId=null;currentConnectedPlaceName=null;constructor(e,n={}){this.config=new wx(e,n),this.reverseDetectorFactory=n.reverseDetectorFactory??(r=>new l_(r.explorerRoot,r.syncIndex,{placeId:r.placeId})),this.apiHandler=new g_(this),this.changeProcessor=new f_(this),this.initHandler=new h_(this),this.reverseHandler=new v_(this),this.places=new o_({max:iye,dispose:(r,i)=>{this.trackPlaceDisposal(r,i)}}),this.migrationService=new x_(this)}getSyncRoot(){return this.config.getSyncRoot()}async getOrCreatePlaceContext(e,n){let r=this.places.get(e);if(r&&n){let i=this.config.getPlaceRoot(e),a=await this.config.resolvePlaceRoot(e,n);a!==i&&(y.info("Place root migrated, recreating context",{placeId:e,from:i,to:a}),this.places.delete(e),r=void 0)}if(!r){await this.waitForPlaceDisposal(e);let i=await this.config.resolvePlaceRoot(e,n),a=HT.join(i,"explorer"),o=await r8(i),s=o.formatVersion;o.recovery&&y.warn("Recovered corrupt sync index",{indexPath:o.recovery.indexPath,quarantinePath:o.recovery.quarantinePath,formatVersion:o.recovery.formatVersion,reason:o.recovery.reason}),await ZT.mkdir(i,{recursive:!0}),await ZT.mkdir(a,{recursive:!0});let c=new eu(i,a,s);await c.loadFromDisk();let l=new tu(this.config,c,e,s),u=new c_(this.config,c,i);if(l.startChangeLogFlusher(),r={placeId:e,placeName:"",formatVersion:s,pendingIndexRecovery:o.recovery??null,index:c,writer:l,reader:u,fileWatcher:null,state:"idle",activeClientId:null,activeFullSyncSessionId:null,instanceCount:0,scriptCount:0,lastFullSync:null,lastIncrementalSync:null,tmpIndex:null,tmpWriter:null,incompleteSyncTimer:null,syncInitRequestsInFlight:0,changesSinceLastSave:0,directions:{...gs},applyModes:{...hs},autoApplyDeletes:!1,forwardRestoreQueue:[],syncProgress:null,collisionDirMap:null,activeSyncIdentityScope:null},this.places.set(e,r),r.pendingIndexRecovery){let d=r.pendingIndexRecovery;l.appendHistory({timestamp:new Date().toISOString(),type:"indexRecovery",direction:"forward",source:"studio",path:d.indexPath,details:JSON.stringify({quarantinePath:d.quarantinePath,formatVersion:d.formatVersion,reason:d.reason})}),await l.flushHistory(),r.pendingIndexRecovery=null}y.info("Created new place context",{placeId:e,placeRoot:i})}return r}async handleSyncInit(e,n){try{GB(e.body);let r=LB(e.body);if(!r.success){n.status(400).json({error:"Validation error",message:r.error});return}let i=r.data,a=i.phase==="start"?i.placeId??null:i.phase==="chunk"||i.phase==="complete"?this.activeFullSyncPlaceId:null;if(a==null){n.status(400).json({error:"Missing placeId",message:"placeId is required in start phase or must be set by previous start"});return}switch(i.phase){case"start":this.setCurrentConnectedPlace(a,i.placeName),await this.initHandler.handleInitStart(a,i,n);break;case"chunk":await this.initHandler.handleInitChunk(a,i,n);break;case"complete":await this.initHandler.handleInitComplete(a,i,n);break}}catch(r){this.sendError(n,r,"handleSyncInit")}}async handleSyncUpdate(e,n){try{GB(e.body);let r=zB(e.body);if(!r.success){n.status(400).json({error:"Validation error",message:r.error});return}let i=r.data,a=i.placeId??this.getDefaultRuntimePlaceId();if(a==null){n.status(400).json({error:"Missing placeId",message:"placeId is required in body or must have an active sync session"});return}let o=await this.getOrCreatePlaceContext(a);if(this.setCurrentConnectedPlace(a,o.placeName||this.currentConnectedPlaceName),o.activeFullSyncSessionId!==null||o.state==="initializing"){n.status(409).json({error:"Conflict",message:`Full sync in progress for place ${a}`});return}o.activeClientId=i.clientId,this.touchRuntimePlace(a);let s=NB(o,i.changes);y.info("Sync update received",{placeId:a,clientId:i.clientId,changeCount:s.length,receivedCount:i.changes.length,types:s.map(m=>m.type)});let c=[],l=[],u=0,d=!1,p=new Map;for(let m of s)try{let g=await this.changeProcessor.processChangeForPlace(o,m,p);g?l.push(g):(u++,aye(m)&&(d=!0))}catch(g){let h="path"in m?m.path:"oldPath"in m?m.oldPath:"unknown";c.push({path:h,error:g instanceof Error?g.message:String(g)})}for(let m of p.values())try{await u_(o,m)}catch(g){c.push({path:m.instancePath,error:g instanceof Error?g.message:String(g)})}if(d)try{let m=this.config.getSyncRoot(),g=this.config.getPlaceRoot(a);await Tx(m,g,o.formatVersion,o.writer),await zl(m,o.writer)}catch(m){y.warn("Failed to refresh sourcemaps after incremental sync update",{placeId:a,error:m instanceof Error?m.message:String(m)})}o.changesSinceLastSave+=u,o.changesSinceLastSave>=MB&&(await o.index.saveToDisk(),o.changesSinceLastSave=0),o.lastIncrementalSync=new Date().toISOString();let f={processed:u,failed:c.length,errors:c,syncedAt:o.lastIncrementalSync};l.length>0&&(f.conflicts=l),n.status(200).json(f)}catch(r){this.sendError(n,r,"handleSyncUpdate")}}getDefaultRuntimePlaceId(){return this.currentConnectedPlaceId}getDefaultRuntimePlaceName(){if(this.currentConnectedPlaceName)return this.currentConnectedPlaceName;if(this.currentConnectedPlaceId!==null&&this.currentConnectedPlaceId!==void 0){let e=this.places.get(this.currentConnectedPlaceId);if(e?.placeName)return e.placeName}return null}setCurrentConnectedPlace(e,n){if(this.currentConnectedPlaceId=e,e==null){this.currentConnectedPlaceName=null;return}if(typeof n=="string"&&n.length>0){this.currentConnectedPlaceName=n;let i=this.places.get(e);i&&(i.placeName=n);return}let r=this.places.get(e);r?.placeName&&(this.currentConnectedPlaceName=r.placeName)}clearCurrentConnectedPlaceIfMatch(e){this.currentConnectedPlaceId===e&&(this.currentConnectedPlaceId=null,this.currentConnectedPlaceName=null)}touchRuntimePlace(e){this.activeRuntimeSyncPlaceId=e}clearRuntimePlaceIfMatch(e){this.activeRuntimeSyncPlaceId===e&&(this.activeRuntimeSyncPlaceId=null)}resolveQueryPlaceId(e,n="runtime"){let r=e.query.placeId;if(r){let i=parseInt(r,10);if(!isNaN(i))return i}return n==="full"?this.activeFullSyncPlaceId:this.getDefaultRuntimePlaceId()}async handleSyncStatus(e,n){try{let r=u=>({state:"idle",instanceCount:0,scriptCount:0,lastFullSync:null,lastIncrementalSync:null,syncRoot:u,activeClientId:null,reverseSyncAvailable:!1,modifiedFileCount:0,autoApplyDeletes:!1,reverseDetectorActive:!1,reverseDetectorMode:gt,fileWatcherActive:!1}),i=this.resolveQueryPlaceId(e);if(i==null){let u=r(this.config.getSyncRoot());n.status(200).json(u);return}let a=this.places.get(i);if(!a){let u=r(this.config.getPlaceRoot(i));n.status(200).json(u);return}let o=a.fileWatcher?.getPendingCount()??0,s=a.fileWatcher?.isActivelyScanning()??!1,c=a.fileWatcher!==null;this.touchRuntimePlace(i);let l={state:a.state,instanceCount:a.instanceCount,scriptCount:a.scriptCount,lastFullSync:a.lastFullSync,lastIncrementalSync:a.lastIncrementalSync,syncRoot:this.config.getPlaceRoot(i),activeClientId:a.activeClientId,reverseSyncAvailable:o>0,modifiedFileCount:o,applyModes:a.applyModes,autoApplyDeletes:a.autoApplyDeletes,directions:a.directions,reverseDetectorActive:s,reverseDetectorMode:gt,fileWatcherActive:c,forwardOnlyClasses:[...Ll]};n.status(200).json(l)}catch(r){this.sendError(n,r,"handleSyncStatus")}}async handleSyncStop(e,n){try{let r=e.body,i=r.placeId??this.getDefaultRuntimePlaceId(),a=Zf(r);if(y.info("handleSyncStop requested",{placeId:i,clientId:r.clientId??null,identityScope:a,reason:r.reason??"requested"}),i==null){n.status(200).json({status:"idle",state:"idle",placeId:null,message:"No active sync place"});return}let o=this.places.get(i);if(!o){y.info("handleSyncStop no place context",{placeId:i,clientId:r.clientId??null}),n.status(200).json({status:"idle",state:"idle",placeId:i,message:`No sync context for place ${i}`});return}let s=!!(r.clientId&&o.activeClientId&&r.clientId!==o.activeClientId),c=o.activeFullSyncSessionId!==null||o.state==="syncing"||o.state==="initializing",l=!!(a&&o.activeSyncIdentityScope&&a===o.activeSyncIdentityScope);if(s&&c&&!l){y.warn("handleSyncStop rejected due to active client mismatch",{placeId:i,requestedClientId:r.clientId,activeClientId:o.activeClientId,requestedIdentityScope:a,activeIdentityScope:o.activeSyncIdentityScope,state:o.state,activeFullSyncSessionId:o.activeFullSyncSessionId}),n.status(409).json({error:"Conflict",message:`This sync session belongs to client ${o.activeClientId}`});return}s&&l&&y.info("handleSyncStop accepted stale client cleanup by identity scope",{placeId:i,requestedClientId:r.clientId,activeClientId:o.activeClientId,identityScope:a,state:o.state});let u=o.activeFullSyncSessionId,d=o.state,p=o.fileWatcher!==null;if(u&&(this.initHandler.clearPreserveLocalFiles(u),this.initHandler.clearPendingServiceTrees(u)),o.fileWatcher&&(y.info("handleSyncStop suspending reverse detector",{placeId:i,state:o.state,activeClientId:o.activeClientId,mode:gt}),o.fileWatcher.beginFullSyncReplacement()),o.incompleteSyncTimer&&(clearTimeout(o.incompleteSyncTimer),o.incompleteSyncTimer=null),u){let f=this.config.getPlaceRoot(i),m=HT.join(f,`explorer_tmp_${u}`);await ZT.rm(m,{recursive:!0,force:!0}).catch(()=>{})}o.tmpWriter&&(o.tmpWriter.stopChangeLogFlusher(),o.tmpWriter=null),o.tmpIndex=null,o.collisionDirMap=null,o.activeSyncIdentityScope=null,o.syncInitRequestsInFlight=0,o.activeFullSyncSessionId=null,o.syncProgress=null,o.state="idle",o.activeClientId=null,o.instanceCount=0,o.scriptCount=0,o.forwardRestoreQueue=[],this.activeFullSyncPlaceId===i&&(this.activeFullSyncPlaceId=null),this.clearRuntimePlaceIfMatch(i),y.info("handleSyncStop responding idle",{placeId:i,previousState:d,activeFullSyncSessionId:u,hadWatcher:p}),y.info("Sync stopped",{placeId:i,reason:r.reason??"requested"}),n.status(200).json({status:"stopped",state:"idle",placeId:i})}catch(r){this.sendError(n,r,"handleSyncStop")}}async initialize(){try{await this.config.loadFromMeta(),await HB(this.config.getSyncRoot()),await this.initHandler.cleanupStaleTempDirs(),y.info("SyncController initialized")}catch(e){y.error("SyncController initialization failed",e instanceof Error?e:new Error(String(e)))}}async previewMigration(e){return this.migrationService.preview(e)}async applyMigration(e){return this.migrationService.apply(e)}async shutdown(){try{y.info("SyncController shutdown: clearing place contexts",{placeCount:this.places.size}),this.places.clear(),await Promise.all(this.placeDisposals.values()),y.info("SyncController shut down")}catch(e){y.error("SyncController shutdown error",e instanceof Error?e:new Error(String(e)))}}trackPlaceDisposal(e,n){let r=this.disposePlaceContext(e,n).catch(i=>{y.error("Place context dispose failed",i instanceof Error?i:new Error(String(i)))});this.placeDisposals.set(n,r),r.then(()=>{this.placeDisposals.get(n)===r&&this.placeDisposals.delete(n)})}async waitForPlaceDisposal(e){await this.placeDisposals.get(e)}async disposePlaceContext(e,n){y.info("Disposing place context (LRU eviction)",{placeId:n}),this.activeFullSyncPlaceId===n&&(this.activeFullSyncPlaceId=null);let r=e.index.toSyncIndexData(),i=e.fileWatcher,a=e.tmpWriter;e.fileWatcher=null,e.tmpWriter=null,e.incompleteSyncTimer&&(clearTimeout(e.incompleteSyncTimer),e.incompleteSyncTimer=null),e.activeFullSyncSessionId&&this.initHandler.clearPendingServiceTrees(e.activeFullSyncSessionId),e.tmpIndex=null,e.collisionDirMap=null,e.activeSyncIdentityScope=null,e.syncInitRequestsInFlight=0;let o=[e.index.savePersistenceStateToDisk(r).catch(s=>{y.error("Error saving index during dispose",s)}),e.writer.stopChangeLogFlusher().catch(s=>{y.error("LRU dispose \uC911 changelog flush \uC2E4\uD328",s)})];i&&(y.info("Disposing place context: stopping reverse detector",{placeId:n,reason:"lru-dispose",mode:gt}),o.push(i.stop("lru-dispose").catch(s=>{y.error("Error stopping reverse detector during dispose",s)}))),a&&o.push(a.stopChangeLogFlusher().catch(s=>{y.error("LRU dispose \uC911 \uC784\uC2DC changelog flush \uC2E4\uD328",s)})),await Promise.all(o),e.index.clearAllMaps()}async atomicWriteFile(e,n){await fn(e,n)}async handlePreCheck(e,n){try{await this.apiHandler.handlePreCheck(e,n)}catch(r){this.sendError(n,r,"handlePreCheck")}}async handleSyncDirections(e,n){try{await this.apiHandler.handleSyncDirections(e,n)}catch(r){this.sendError(n,r,"handleSyncDirections")}}async handleForwardRestoreList(e,n){try{await this.apiHandler.handleForwardRestoreList(e,n)}catch(r){this.sendError(n,r,"handleForwardRestoreList")}}async handleReversePending(e,n){try{await this.reverseHandler.handleReversePending(e,n)}catch(r){this.sendError(n,r,"handleReversePending")}}async handleReverseSyncChanges(e,n){try{await this.reverseHandler.handleReverseSyncChanges(e,n)}catch(r){this.sendError(n,r,"handleReverseSyncChanges")}}async handleReverseSyncResult(e,n){try{await this.reverseHandler.handleReverseSyncResult(e,n)}catch(r){this.sendError(n,r,"handleReverseSyncResult")}}async handleResolveConflict(e,n){try{await this.reverseHandler.handleResolveConflict(e,n)}catch(r){this.sendError(n,r,"handleResolveConflict")}}async handleReverseRescan(e,n){try{await this.reverseHandler.handleReverseRescan(e,n)}catch(r){this.sendError(n,r,"handleReverseRescan")}}async handleSyncHistory(e,n){try{await this.apiHandler.handleSyncHistory(e,n)}catch(r){this.sendError(n,r,"handleSyncHistory")}}async startFileWatcherForPlace(e){if(e.state!=="syncing"){y.debug("Skipping reverse detector start - place not syncing",{placeId:e.placeId,state:e.state});return}if(e.fileWatcher){if(e.fileWatcher.isActivelyScanning()){y.info("startFileWatcherForPlace: reusing active reverse detector",{placeId:e.placeId,mode:gt});return}y.info("startFileWatcherForPlace: resuming paused reverse detector",{placeId:e.placeId,mode:gt}),e.fileWatcher.endFullSyncReplacement();return}let n=this.createReverseChangeDetector(e);this.configureReverseChangeDetector(e,n),e.fileWatcher=n,n.start().then(()=>{e.fileWatcher===n&&y.info("Reverse detector started for reverse sync",{placeId:e.placeId,mode:gt})}).catch(r=>{y.warn("Failed to start reverse detector",{placeId:e.placeId,mode:gt,error:r instanceof Error?r.message:String(r)}),e.fileWatcher===n&&(e.fileWatcher=null)})}createReverseChangeDetector(e){return this.reverseDetectorFactory({explorerRoot:HT.join(this.config.getPlaceRoot(e.placeId),"explorer"),syncIndex:e.index,placeId:e.placeId})}configureReverseChangeDetector(e,n){e.writer.setOnWriteCallback((r,i,a)=>{n.suppressPath(r,i,a)}),n.setDirectionChecker(r=>{let i=t8(r);return e.directions[i]}),n.setOnForwardViolation(r=>{e.forwardRestoreQueue.includes(r)||(e.forwardRestoreQueue.push(r),y.info("Forward violation queued for restore",{placeId:e.placeId,relativePath:r,queueSize:e.forwardRestoreQueue.length}))})}getStatusSummary(){return this.apiHandler.getStatusSummary()}getDirectionForCategory(e){return this.apiHandler.getDirectionForCategory(e)}getStatusDirect(e){return this.apiHandler.getStatusDirect(e)}async getHistoryDirect(e,n){return this.apiHandler.getHistoryDirect(e,n)}getDirectionsDirect(e){return this.apiHandler.getDirectionsDirect(e)}getProgressDirect(e){return this.apiHandler.getProgressDirect(e)}async readSyncedFile(e,n){return this.apiHandler.readSyncedFile(e,n)}async writeSyncedFile(e,n,r){await this.apiHandler.writeSyncedFile(e,n,r)}async executeViaDisk(e,n){return this.apiHandler.executeViaDisk(e,n)}sendError(e,n,r){let i=n instanceof Error?n.message:String(n);if(i.includes("Path traversal detected")){e.status(403).json({error:"Forbidden",message:i});return}let a=n.code;if(a==="ENOSPC"||a==="EPERM"||a==="EACCES"){y.warn(`SyncController.${r} disk error`,{code:a,message:i}),e.status(500).json({error:"Disk error",message:i,code:a,operation:r});return}y.error(`SyncController.${r} failed`,n instanceof Error?n:new Error(i)),e.status(500).json({error:"Internal error",message:`${r}: ${i}`})}};import{randomUUID as oye}from"crypto";function KB(t,e){let n=oye(),r=n.replace(/-/g,"").substring(0,8).toUpperCase(),i=`${r.substring(0,4)}-${r.substring(4,8)}`;return{config:t,app:e,instanceId:n,sessionId:i,startTime:Date.now(),baseUrl:`http://${t.httpHost}:${t.httpPort}`,commandQueue:new Map,pendingCommands:new Map,globalPendingCommands:[],totalCommandsProcessed:0,pluginClients:new Map,pluginCommandSessionsByClientId:new Map,pluginCommandClientIdsByProcessToken:new Map,mcpInstances:new Map,cachedSelectionMap:new Map,studioRoutingMode:"recentPriority",pinnedTargetClientId:null,isClientMode:!1,clientModeHealthTimer:null,clientModeConsecutiveHealthFailures:0,clientModeUpstreamReachable:!0,clientModeUpstreamContextCaptureEnabled:!0,clientModeLastHealthSuccessAt:null,clientModeLastHealthFailureAt:null,clientModeLastHealthError:null,shuttingDown:!1,onUpstreamPermanentlyDown:null,clientModeIdleTimeoutMs:t.clientModeIdleTimeoutMs??36e5,clientModeIdleWatchdogTimer:null,shutdownFn:null,historyManager:null,analyticsManager:null,executionContextManager:null,licenseState:null,syncController:null,internalCommandExecutor:null,dashboardFolderPicker:null,assetLibraryOpenCloudServiceFactory:null,projectChangesCleanupScheduler:null,activeSyncOwnerInstanceId:null,activeProjectRoot:null,pendingDashboardSyncRootPin:null,playtestControlCommand:null,dashboardSyncRootSwitchInFlight:!1,uiStudioRecorders:new Map,aiClientName:"",pluginVersion:"",syncedSessionToken:null,serverLastCommandAt:null}}var JB=Dt(Ya(),1);ae();function YB(t){let e=JB.default.json({limit:"5mb"});t.app.use((n,r,i)=>{if(n.path.startsWith("/sync/")){i();return}e(n,r,i)}),t.app.use((n,r,i)=>{r.setHeader("Access-Control-Allow-Origin","http://localhost:3002"),r.setHeader("Access-Control-Allow-Methods","GET, POST, OPTIONS"),r.setHeader("Access-Control-Allow-Headers","Content-Type"),i()}),t.app.use((n,r,i)=>{y.debug(`${n.method} ${n.path}`,{ip:n.ip}),i()})}Ua();import{randomUUID as X_}from"crypto";Ua();ae();function sye(){let t=process.env.WEPPY_ROBLOX_MCP_VERSION?.trim();return t||null}var nt=sye()??"2.11.3";Fi();Vn();Yf();no();ql();Ua();no();var r5="studio-",lye=/^studio-[1-9]\d*$/;function I_(t){return lye.test(t)}function i5(t,e){let n=new Set;for(let r of t)e!==void 0&&r.clientId===e||r.targetAlias&&I_(r.targetAlias)&&n.add(r.targetAlias);return n}function uye(t,e){let n=i5(t,e),r=1;for(;n.has(`${r5}${r}`);)r+=1;return`${r5}${r}`}function C_(t,e){let n=i5(t,e.clientId);return e.targetAlias&&I_(e.targetAlias)&&!n.has(e.targetAlias)||(e.targetAlias=uye(t,e.clientId)),e.targetAlias}ql();function P_(t){for(let e of t)C_(t,e)}function k_(t){let e={clientId:t.clientId,targetAlias:t.targetAlias??t.clientId.slice(0,8),lastSeen:t.lastSeen,connectedAt:t.connectedAt,transport:"websocket",connectionState:t.commandSessionState??He.CONNECTED};return t.placeId!==void 0&&(e.placeId=t.placeId),t.placeName!==void 0&&(e.placeName=t.placeName),t.pluginVersion!==void 0&&(e.pluginVersion=t.pluginVersion),t.studioVersion!==void 0&&(e.studioVersion=t.studioVersion),t.lastRoutedAt!==void 0&&(e.lastRoutedAt=t.lastRoutedAt),t.processToken!==void 0&&(e.processToken=t.processToken),t.inFlightRequestId!==void 0&&(e.inFlightRequestId=t.inFlightRequestId),t.studioState!==void 0&&(e.studioState=t.studioState),t.studioStateSource!==void 0&&(e.studioStateSource=t.studioStateSource),t.studioStateUpdatedAt!==void 0&&(e.studioStateUpdatedAt=t.studioStateUpdatedAt),t.playtestMode!==void 0&&(e.playtestMode=t.playtestMode),e}function QT(t){let e=$n(t);return P_(e),jf(e.map(k_),null)}function E_(t){let e=new Set;t.aiClientName&&e.add(t.aiClientName);for(let n of t.mcpInstances.values())n.aiClientName&&e.add(n.aiClientName);return Array.from(e)}function a5(t){let n=Date.now();for(let[r,i]of t.mcpInstances)i.lastSeen&&n-i.lastSeen>15e3&&(t.mcpInstances.delete(r),i.sessionId&&t.executionContextManager?.endSession(i.sessionId),y.debug("Removed stale MCP instance",{instanceId:r,lastSeen:i.lastSeen}))}function o5(t,e,n){let r=e.query.clientId;if(r&&t.pluginClients.has(r)){let i=t.pluginClients.get(r);i.lastSeen=Date.now()}try{let i=e.body;if(!i||!Array.isArray(i.selection)||typeof i.count!="number"){y.warn("Invalid selection update request",{body:i}),n.status(400).json({error:"Invalid request body"});return}let a=r||"unknown",o=Date.now();t.cachedSelectionMap.set(a,{selection:i.selection,count:i.count,timestamp:o,clientId:a}),y.debug("Selection cache updated",{count:i.count,clientId:a,timestamp:o}),n.json({status:"ok",timestamp:o})}catch(i){y.error("Error handling selection update",i),n.status(500).json({error:"Internal server error"})}}function s5(t,e,n){let r=parseInt(e.query.maxAge)||3e4,i=Xf(t,r);i?n.json({cached:!0,...i}):n.json({cached:!1,message:"No cached selection available"})}function Xf(t,e=3e4,n){if(t.cachedSelectionMap.size===0)return null;let r;if(n)r=t.cachedSelectionMap.get(n);else for(let a of t.cachedSelectionMap.values())(!r||a.timestamp>r.timestamp)&&(r=a);if(!r)return null;let i=Date.now()-r.timestamp;return e===0||i<=e?r:null}function eA(t,e){let n=t.pluginClients.get(e.clientId),r=Date.now(),i=[...t.pluginClients.values()].filter(c=>c.clientId===e.clientId||c.commandSessionState!==He.DISCONNECTED),a=n??{clientId:e.clientId,connectedAt:r,lastSeen:r,commandsProcessed:0,connectionType:"polling"},o=C_(i,a),s={clientId:e.clientId,targetAlias:o,projectName:e.projectName??n?.projectName,placeName:e.placeName??n?.placeName,placeId:e.placeId??n?.placeId,pluginVersion:e.pluginVersion??n?.pluginVersion,studioVersion:e.studioVersion??n?.studioVersion,connectedAt:n?.connectedAt||r,lastSeen:r,commandsProcessed:n?.commandsProcessed||0,connectionType:n?.connectionType||"polling",inFlightRequestId:n?.inFlightRequestId,studioState:n?.studioState,studioStateSource:n?.studioStateSource,studioStateUpdatedAt:n?.studioStateUpdatedAt,playtestMode:n?.playtestMode,...n?.commandSessionState?{commandSessionState:n.commandSessionState}:{},...n?.processToken?{processToken:n.processToken}:{}};return t.pluginClients.set(e.clientId,s),t.syncController&&typeof t.syncController.setCurrentConnectedPlace=="function"&&typeof e.placeId=="number"&&Number.isFinite(e.placeId)&&t.syncController.setCurrentConnectedPlace(e.placeId,e.placeName??null),t.pendingCommands.has(e.clientId)||t.pendingCommands.set(e.clientId,[]),e.pluginVersion&&(t.pluginVersion=e.pluginVersion),typeof s.placeId=="number"&&Number.isFinite(s.placeId)&&Yx(t,s.placeId,s.placeName??null),t.analyticsManager&&(e.pluginVersion&&t.analyticsManager.setPluginVersion(e.pluginVersion),t.analyticsManager.trackPluginConnected()),y.info("Plugin client registered",{clientId:e.clientId,targetAlias:o,projectName:e.projectName,placeName:e.placeName,isReconnect:!!n}),{clientInfo:s,sessionId:t.sessionId,mcpVersion:nt,mcpInstanceCount:t.mcpInstances.size+1,aiClientNames:E_(t)}}function tA(t,e){let n=t.pluginClients.get(e),r=t.pluginClients.has(e),i=n?.commandSessionState===He.CONNECTED;if(t.pluginClients.delete(e),t.pendingCommands.delete(e),r&&Ul(t,e),r&&t.syncController&&typeof t.syncController.clearCurrentConnectedPlaceIfMatch=="function"&&typeof n?.placeId=="number"&&Number.isFinite(n.placeId)){let a=[...t.pluginClients.values()].filter(o=>typeof o.placeId=="number"&&Number.isFinite(o.placeId)).sort((o,s)=>s.lastSeen-o.lastSeen)[0];a?t.syncController.setCurrentConnectedPlace?.(a.placeId??null,a.placeName??null):t.syncController.clearCurrentConnectedPlaceIfMatch(n.placeId)}return i&&Mf(t,e,"disconnected",n),y.info("Plugin client unregistered",{clientId:e,existed:r}),r}function R_(t,e,n){try{let r=e.body;if(!r.clientId){n.status(400).json({error:"Missing clientId"});return}let i=eA(t,{clientId:r.clientId,projectName:r.projectName,placeName:r.placeName,placeId:r.placeId,pluginVersion:r.pluginVersion,studioVersion:r.studioVersion});n.json({status:"ok",clientId:r.clientId,targetAlias:i.clientInfo.targetAlias,serverInstanceId:t.instanceId,sessionId:i.sessionId,mcpVersion:i.mcpVersion,connectedAt:i.clientInfo.connectedAt,aiClientNames:i.aiClientNames,serverStartTime:t.startTime,mcpInstanceCount:i.mcpInstanceCount})}catch(r){y.error("Error registering plugin client",r),n.status(500).json({error:"Internal server error"})}}function T_(t,e,n){let r=e.body?.clientId;if(!r){n.status(400).json({error:"Missing clientId"});return}let i=tA(t,r);n.json({status:"ok",existed:i})}function c5(t,e,n){try{let r=e.body;if(!r.instanceId){n.status(400).json({error:"Missing instanceId"});return}let i=Date.now(),a={instanceId:r.instanceId,...typeof r.sessionId=="string"?{sessionId:r.sessionId}:{},pid:r.pid,connectedAt:i,isServer:!1,lastSeen:i};r.aiClientName&&(a.aiClientName=r.aiClientName),r.cwd&&(a.cwd=r.cwd),"projectRoot"in r&&(a.projectRoot=r.projectRoot),t.mcpInstances.set(r.instanceId,a),ot(t,"mcp_status",{aiClientName:a.aiClientName??"Unknown",instanceId:r.instanceId,status:"registered"}),Zl(t,{timestamp:new Date().toISOString(),type:"mcp",status:"registered",instanceId:r.instanceId,message:`MCP registered \u2014 ${a.aiClientName??r.instanceId}`,...a.aiClientName?{aiClientName:a.aiClientName}:{}}),y.info("MCP instance registered (client mode)",{instanceId:r.instanceId,pid:r.pid,cwd:r.cwd}),n.json({status:"ok",instanceId:r.instanceId,serverInstanceId:t.instanceId,sessionId:t.sessionId,mcpVersion:nt,mcpInstanceCount:t.mcpInstances.size+1})}catch(r){y.error("Error registering MCP instance",r),n.status(500).json({error:"Internal server error"})}}function l5(t,e,n){let r=e.body?.instanceId;if(!r){n.status(400).json({error:"Missing instanceId"});return}let i=t.mcpInstances.get(r),a=!!i;t.mcpInstances.delete(r),i?.sessionId&&t.executionContextManager?.endSession(i.sessionId),a&&(ot(t,"mcp_status",{aiClientName:i?.aiClientName??"Unknown",instanceId:r,status:"unregistered"}),Zl(t,{timestamp:new Date().toISOString(),type:"mcp",status:"unregistered",instanceId:r,message:`MCP unregistered \u2014 ${i?.aiClientName??r}`,...i?.aiClientName?{aiClientName:i.aiClientName}:{}})),y.info("MCP instance unregistered",{instanceId:r,existed:a}),n.json({status:"ok",existed:a})}function u5(t,e,n){let{instanceId:r,aiClientName:i}=e.body;if(r&&i){let a=t.mcpInstances.get(r);a&&(a.aiClientName=i)}n.json({status:"ok"})}function d5(t){let e=3e4,n=Date.now(),r=Tr({appDataDir:t.config.appDataDir});for(let[a,o]of t.pluginClients)n-o.lastSeen>e&&(t.pluginClients.delete(a),t.pendingCommands.delete(a),Ul(t,a));a5(t);let i=$n(t);return P_(i),{serverInstanceId:t.instanceId,sessionId:t.sessionId,mcpVersion:nt,uptime:n-t.startTime,serverStartTime:t.startTime,serverExecutable:process.execPath,serverHost:t.config.httpHost,serverPort:t.config.httpPort,serverPid:process.pid,pluginClients:i.map(k_),studioRoutingMode:t.studioRoutingMode,pinnedTargetClientId:t.pinnedTargetClientId,mcpInstances:[{instanceId:t.instanceId,pid:process.pid,connectedAt:t.startTime,isServer:!0,cwd:process.cwd(),projectRoot:r,lastSeen:n,...t.aiClientName?{aiClientName:t.aiClientName}:{}},...Array.from(t.mcpInstances.values())],mcpInstanceCount:t.mcpInstances.size+1}}function A_(t,e){e.json(d5(t))}function O_(t,e,n){let r=e.query.instanceId;r&&t.mcpInstances.has(r)&&(t.mcpInstances.get(r).lastSeen=Date.now()),a5(t);let i=$n(t);P_(i);let s={...{status:"online",connectedClients:i.length,queuedCommands:B8(t),uptime:Date.now()-t.startTime,version:nt,enableContextCapture:t.executionContextManager?.isEnabled()??t.config.enableContextCapture??!0,isClientMode:t.isClientMode,shuttingDown:t.shuttingDown,pid:process.pid,sessionId:t.sessionId,nodeVersion:process.version,studioRoutingMode:t.studioRoutingMode,pinnedTargetClientId:t.pinnedTargetClientId},instanceId:t.instanceId,mcpInstanceCount:t.mcpInstances.size+1,aiClientNames:E_(t),pluginVersion:t.pluginVersion||void 0,dashboardSseClients:t.dashboardSseClients?.size??0,websocketClients:i.length,pluginClients:i.map(k_),...t.isClientMode?{upstream:{reachable:t.clientModeUpstreamReachable,consecutiveFailures:t.clientModeConsecutiveHealthFailures,lastSuccessAt:t.clientModeLastHealthSuccessAt,lastFailureAt:t.clientModeLastHealthFailureAt,lastError:t.clientModeLastHealthError,baseUrl:t.baseUrl}}:{}};n.json(s)}function p5(t,e,n,r){let i=e.ip||e.socket.remoteAddress||"";if(!(i==="127.0.0.1"||i==="::1"||i==="::ffff:127.0.0.1"||i==="localhost")){y.warn("Shutdown request rejected from non-localhost",{ip:i}),n.status(403).json({error:"Forbidden: localhost only"});return}y.info("Shutdown request received, initiating graceful shutdown",{requestedBy:i,uptime:Date.now()-t.startTime}),n.json({status:"shutting_down",message:"Server will shutdown gracefully",pid:process.pid}),setTimeout(async()=>{try{await r(),y.info("Graceful shutdown completed"),process.exit(0)}catch(o){y.error("Error during graceful shutdown",o),process.exit(1)}},100)}async function $_(t){if(t.isClientMode)try{let e=await fetch(`${t.baseUrl}/connection-info`);if(e.ok)return await e.json()}catch(e){y.warn("Failed to fetch connection info from server",{error:e})}return d5(t)}no();var ht={bridgeRunTest:"manage_studio_run_test_bridge",placeInfo:"system_info_place_info",clearLogs:"manage_logs_clear",createScript:"manage_scripts_create",getLogs:"manage_logs_get",deleteScript:"manage_scripts_delete",canonical:{playStart:"manage_studio_play_start",playStop:"manage_studio_play_stop",playPause:"manage_studio_play_pause",playResume:"manage_studio_play_resume",playStatus:"manage_studio_play_status",runTest:"manage_studio_run_test"}},pye=new Set([ht.canonical.runTest]),fye=new Set([ht.canonical.playStop]),D2e=new Set([ht.canonical.playStart,ht.canonical.playStop,ht.canonical.playPause,ht.canonical.playResume,ht.canonical.playStatus]);function fi(t){return pye.has(t)}function Qf(t){return fye.has(t)}var L2e=ht.canonical.playStop,f5=[5e3,15e3];ql();var mye=new Set(["manage_assets_export_selection_rbxm","manage_assets_export_path_rbxm","manage_assets_review_model","manage_assets_generate_model","manage_assets_import_rbxm","manage_assets_generate_thumbnail"]),gn=class t extends Error{code;routing;constructor(e,n,r){super(n),this.name="CommandTargetSelectionError",this.code=e,this.routing=r,Object.setPrototypeOf(this,t.prototype)}};function gye(t={},e){let n={},r=t.clientId,i=t.targetAlias,a=t.placeId;if(r!==void 0){if(typeof r!="string"||r.trim().length===0)throw new gn("invalid_target_selector","clientId target selector must be a non-empty string",{selectionMode:"clientId",...typeof r=="string"?{requestedClientId:r.trim()}:{}});n.requestedClientId=r.trim()}if(i!==void 0){if(typeof i!="string"||i.trim().length===0)throw new gn("invalid_target_selector","targetAlias target selector must be a non-empty string",{selectionMode:"targetAlias",...typeof i=="string"?{requestedTargetAlias:i.trim()}:{}});n.requestedTargetAlias=i.trim()}if(a!==void 0&&hye(e,t)){if(typeof a!="number"||!Number.isFinite(a))throw new gn("invalid_target_selector","placeId target selector must be a finite number",{selectionMode:"placeId"});n.requestedPlaceId=a}return n}function D_(t,e,n={},r){let i=gye(n,r),a=v8(e,t.studioRoutingMode==="pinned"?t.pinnedTargetClientId:null);if(i.requestedClientId!==void 0)return yye(a,i);if(i.requestedTargetAlias!==void 0)return vye(a,i);if(i.requestedPlaceId!==void 0)return bye(a,i);if(t.studioRoutingMode==="pinned"&&t.pinnedTargetClientId!==null){let s=a.find(c=>c.clientId===t.pinnedTargetClientId);if(s)return{targetClientId:s.clientId,routing:Lr("pinnedTarget",i,s)}}let o=a[0];return o?{targetClientId:o.clientId,routing:Lr("recentPriority",i,o)}:{routing:{selectionMode:"globalQueue"}}}function hye(t,e){return!t||!mye.has(t)?!0:e.scope==="shared"}function yye(t,e){let n=t.find(r=>r.clientId===e.requestedClientId);if(!n)throw new gn("target_client_not_found",`Target client not found: ${e.requestedClientId}`,Lr("clientId",e));if(e.requestedTargetAlias!==void 0&&n.targetAlias!==e.requestedTargetAlias)throw new gn("target_selector_mismatch",`Target client ${n.clientId} does not match targetAlias ${e.requestedTargetAlias}`,Lr("clientId",e,n));return m5("clientId",e,n),{targetClientId:n.clientId,routing:Lr("clientId",e,n)}}function vye(t,e){let n=t.find(r=>r.targetAlias!==void 0&&I_(r.targetAlias)&&r.targetAlias===e.requestedTargetAlias);if(!n)throw new gn("target_alias_not_found",`Target alias not found: ${e.requestedTargetAlias}`,Lr("targetAlias",e));return m5("targetAlias",e,n),{targetClientId:n.clientId,routing:Lr("targetAlias",e,n)}}function bye(t,e){let n=t.filter(i=>i.placeId===e.requestedPlaceId);if(n.length===0)throw new gn("target_place_not_found",`Target place not found: ${e.requestedPlaceId}`,Lr("placeId",e));if(n.length>1)throw new gn("target_place_ambiguous",`Target place is ambiguous: ${e.requestedPlaceId}`,Lr("placeId",e));let r=n[0];return{targetClientId:r.clientId,routing:Lr("placeId",e,r)}}function m5(t,e,n){if(e.requestedPlaceId!==void 0&&n.placeId!==e.requestedPlaceId)throw new gn("target_selector_mismatch",`Target client ${n.clientId} is not connected to placeId ${e.requestedPlaceId}`,Lr(t,e,n))}function Lr(t,e,n){let r={selectionMode:t};return e.requestedClientId!==void 0&&(r.requestedClientId=e.requestedClientId),e.requestedTargetAlias!==void 0&&(r.requestedTargetAlias=e.requestedTargetAlias),e.requestedPlaceId!==void 0&&(r.requestedPlaceId=e.requestedPlaceId),n!==void 0&&(r.actualClientId=n.clientId,n.targetAlias!==void 0&&(r.actualTargetAlias=n.targetAlias),n.placeId!==void 0&&(r.actualPlaceId=n.placeId),n.placeName!==void 0&&(r.actualPlaceName=n.placeName)),r}aT();ae();Gf();var $s={query_instances:{discriminator:"action",validActions:new Set(["get","children","find_child","find_descendant","wait_for_child","class_info","search_name","search_class","search_property","search_tag","file_tree","project_structure","descendants","ancestors"]),allowedParams:{query_instances_get:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"]),query_instances_children:new Set(["path","sessionDebugId","siblingIndex","recursive","maxDepth","placeId","clientId","targetAlias"]),query_instances_find_child:new Set(["path","childName","placeId","clientId","targetAlias"]),query_instances_find_descendant:new Set(["path","descendantName","placeId","clientId","targetAlias"]),query_instances_wait_for_child:new Set(["path","childName","timeout","placeId","clientId","targetAlias"]),query_instances_class_info:new Set(["className","placeId","clientId","targetAlias"]),query_instances_search_name:new Set(["root","query","caseSensitive","maxResults","placeId","clientId","targetAlias"]),query_instances_search_class:new Set(["className","root","includeSubclasses","maxResults","placeId","clientId","targetAlias"]),query_instances_search_property:new Set(["root","propertyName","propertyValue","maxResults","placeId","clientId","targetAlias"]),query_instances_search_tag:new Set(["root","tag","maxResults","placeId","clientId","targetAlias"]),query_instances_file_tree:new Set(["maxDepth","root","includeServices","placeId","clientId","targetAlias"]),query_instances_project_structure:new Set(["root","depth","placeId","clientId","targetAlias"]),query_instances_descendants:new Set(["path","sessionDebugId","siblingIndex","maxResults","placeId","clientId","targetAlias"]),query_instances_ancestors:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"])},paramAliases:{query_instances_search_name:{query:"pattern"},query_instances_search_property:{root:"rootPath"},query_instances_search_tag:{root:"rootPath"},query_instances_project_structure:{root:"rootPath"}}},mutate_instances:{discriminator:"action",validActions:new Set(["create","create_with_props","delete","clone","move","rename","pivot","create_tree","mass_create","mass_delete","mass_duplicate","smart_duplicate","scatter"]),allowedParams:{mutate_instances_create:new Set(["className","parent","name","properties","placeId","clientId","targetAlias"]),mutate_instances_create_with_props:new Set(["className","parent","name","properties","placeId","clientId","targetAlias"]),mutate_instances_delete:new Set(["path","sessionDebugId","siblingIndex","placeId","clientId","targetAlias"]),mutate_instances_clone:new Set(["path","sourcePath","sessionDebugId","siblingIndex","targetParent","newName","placeId","clientId","targetAlias"]),mutate_instances_move:new Set(["path","sessionDebugId","siblingIndex","newParent","placeId","clientId","targetAlias"]),mutate_instances_rename:new Set(["path","sessionDebugId","siblingIndex","newName","placeId","clientId","targetAlias"]),mutate_instances_pivot:new Set(["path","sessionDebugId","siblingIndex","position","cframe","offset","placeId","clientId","targetAlias"]),mutate_instances_create_tree:new Set(["parent","tree","placeId","clientId","targetAlias"]),mutate_instances_mass_create:new Set(["instances","placeId","clientId","targetAlias"]),mutate_instances_mass_delete:new Set(["paths","placeId","clientId","targetAlias"]),mutate_instances_mass_duplicate:new Set(["targetParent","paths","placeId","clientId","targetAlias"]),mutate_instances_smart_duplicate:new Set(["path","sessionDebugId","siblingIndex","targetParent","offset","count","placeId","clientId","targetAlias"]),mutate_instances_scatter:new Set(["templatePaths","region","count","seed","maxSlope","avoidWater","alignToNormal","scaleJitter","minSpacing","parentName","placeId","clientId","targetAlias"])},paramAliases:{mutate_instances_clone:{path:"sourcePath"},mutate_instances_smart_duplicate:{spacing:"offset"}}},manage_properties:{discriminator:"action",validActions:new Set(["get","set","get_all","set_multiple","get_attr","set_attr","get_all_attrs","delete_attr","add_tag","remove_tag","check_tag","get_tags","get_tagged","set_calculated","set_relative","mass_set","mass_get","modify_children"]),allowedParams:{manage_properties_get:new Set(["path","property","placeId","clientId","targetAlias"]),manage_properties_set:new Set(["path","property","value","placeId","clientId","targetAlias"]),manage_properties_get_all:new Set(["path","includeReadOnly","placeId","clientId","targetAlias"]),manage_properties_set_multiple:new Set(["path","properties","placeId","clientId","targetAlias"]),manage_properties_get_attr:new Set(["path","attribute","placeId","clientId","targetAlias"]),manage_properties_set_attr:new Set(["path","value","attribute","placeId","clientId","targetAlias"]),manage_properties_get_all_attrs:new Set(["path","placeId","clientId","targetAlias"]),manage_properties_delete_attr:new Set(["path","attribute","placeId","clientId","targetAlias"]),manage_properties_add_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_remove_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_check_tag:new Set(["path","tag","placeId","clientId","targetAlias"]),manage_properties_get_tags:new Set(["path","placeId","clientId","targetAlias"]),manage_properties_get_tagged:new Set(["tagName","root","maxResults","placeId","clientId","targetAlias"]),manage_properties_set_calculated:new Set(["path","expression","variables","propertyName","placeId","clientId","targetAlias"]),manage_properties_set_relative:new Set(["path","value","operation","amount","propertyName","placeId","clientId","targetAlias"]),manage_properties_mass_set:new Set(["paths","propertyName","propertyValue","placeId","clientId","targetAlias"]),manage_properties_mass_get:new Set(["paths","propertyName","placeId","clientId","targetAlias"]),manage_properties_modify_children:new Set(["parentPath","modifications","propertyName","propertyValue","filter","recursive","placeId","clientId","targetAlias"])},paramAliases:{manage_properties_get_tagged:{tagName:"tag",root:"rootPath"},manage_properties_set_relative:{amount:"value"}}},manage_scripts:{discriminator:"action",validActions:new Set(["get_source","set_source","create","delete","edit_replace","edit_insert","edit_delete","search","replace","get_dependencies"]),allowedParams:{manage_scripts_get_source:new Set(["path","startLine","endLine","placeId","clientId","targetAlias"]),manage_scripts_set_source:new Set(["path","source","placeId","clientId","targetAlias"]),manage_scripts_create:new Set(["source","scriptType","parent","name","placeId","clientId","targetAlias"]),manage_scripts_delete:new Set(["path","placeId","clientId","targetAlias"]),manage_scripts_edit_replace:new Set(["path","startLine","endLine","newLines","placeId","clientId","targetAlias"]),manage_scripts_edit_insert:new Set(["path","lines","afterLine","content","placeId","clientId","targetAlias"]),manage_scripts_edit_delete:new Set(["path","startLine","endLine","placeId","clientId","targetAlias"]),manage_scripts_search:new Set(["path","pattern","caseSensitive","wholeWord","usePattern","maxResults","placeId","clientId","targetAlias"]),manage_scripts_replace:new Set(["path","pattern","replacement","usePattern","dryRun","placeId","clientId","targetAlias"]),manage_scripts_get_dependencies:new Set(["path","placeId","clientId","targetAlias"])},paramAliases:{manage_scripts_edit_replace:{newLines:"newContent"},manage_scripts_edit_insert:{lines:"content"},manage_scripts_replace:{pattern:"searchPattern"}}},manage_ui:{discriminator:"action",validActions:new Set(["design_brief","create_tree","update","delete","preview","check"]),allowedParams:{manage_ui_design_brief:new Set(["brief","placeId","clientId","targetAlias"]),manage_ui_create_tree:new Set(["briefId","tree","placeId","clientId","targetAlias"]),manage_ui_update:new Set(["targetPath","changes","briefId","placeId","clientId","targetAlias"]),manage_ui_delete:new Set(["targetPath","placeId","clientId","targetAlias"]),manage_ui_preview:new Set(["targetPath","briefId","placeId","clientId","targetAlias"]),manage_ui_check:new Set(["targetPath","briefId","includeVisualAnalysis","snapshotId","placeId","clientId","targetAlias"])}},manage_lighting:{discriminator:"action",validActions:new Set(["lighting","atmosphere","sky","terrain_props","time","mood"]),allowedParams:{manage_lighting_lighting:new Set(["properties","placeId","clientId","targetAlias"]),manage_lighting_atmosphere:new Set(["properties","createIfMissing","placeId","clientId","targetAlias"]),manage_lighting_sky:new Set(["properties","createIfMissing","placeId","clientId","targetAlias"]),manage_lighting_terrain_props:new Set(["properties","placeId","clientId","targetAlias"]),manage_lighting_time:new Set(["time","clockTime","placeId","clientId","targetAlias"]),manage_lighting_mood:new Set(["preset","overrides","placeId","clientId","targetAlias"])}},manage_selection:{discriminator:"action",validActions:new Set(["get","set","clear","cached","context","details","add","remove","watch"]),allowedParams:{manage_selection_get:new Set(["placeId","clientId","targetAlias"]),manage_selection_set:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_clear:new Set(["placeId","clientId","targetAlias"]),manage_selection_cached:new Set(["maxAge"]),manage_selection_context:new Set(["includeSource","includeProperties","includeChildren","placeId","clientId","targetAlias"]),manage_selection_details:new Set(["maxDepth","includeAncestors","placeId","clientId","targetAlias"]),manage_selection_add:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_remove:new Set(["paths","placeId","clientId","targetAlias"]),manage_selection_watch:new Set(["placeId","clientId","targetAlias"])}},manage_camera:{discriminator:"action",validActions:new Set(["info","focus_path","focus_position","suggest","screenshot"]),allowedParams:{manage_camera_info:new Set(["placeId","clientId","targetAlias"]),manage_camera_focus_path:new Set(["path","distance","duration","offset","respectAutoFocusSetting","placeId","clientId","targetAlias"]),manage_camera_focus_position:new Set(["position","distance","duration","offset","lookAt","respectAutoFocusSetting","placeId","clientId","targetAlias"]),manage_camera_suggest:new Set(["path","placeId","clientId","targetAlias"]),manage_camera_screenshot:new Set(["placeId","clientId","targetAlias"])},paramAliases:{manage_camera_suggest:{path:"targetPath"}}},manage_tween:{discriminator:"action",validActions:new Set(["create","play","pause","cancel"]),allowedParams:{manage_tween_create:new Set(["path","tweenInfo","properties","placeId","clientId","targetAlias"]),manage_tween_play:new Set(["tweenId","placeId","clientId","targetAlias"]),manage_tween_pause:new Set(["tweenId","placeId","clientId","targetAlias"]),manage_tween_cancel:new Set(["tweenId","placeId","clientId","targetAlias"])}},manage_audio:{discriminator:"action",validActions:new Set(["play","stop","pause","resume","set_listener"]),allowedParams:{manage_audio_play:new Set(["path","soundId","volume","looped","playbackSpeed","placeId","clientId","targetAlias"]),manage_audio_stop:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_pause:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_resume:new Set(["path","placeId","clientId","targetAlias"]),manage_audio_set_listener:new Set(["listenerType","listenerPath","placeId","clientId","targetAlias"])}},manage_animation:{discriminator:"action",validActions:new Set(["load","play","stop","get_tracks"]),allowedParams:{manage_animation_load:new Set(["path","animationId","placeId","clientId","targetAlias"]),manage_animation_play:new Set(["path","trackId","speed","fadeTime","weight","priority","placeId","clientId","targetAlias"]),manage_animation_stop:new Set(["path","trackId","fadeTime","placeId","clientId","targetAlias"]),manage_animation_get_tracks:new Set(["path","placeId","clientId","targetAlias"])}},manage_physics:{discriminator:"action",validActions:new Set(["register_group","set_collidable","get_groups"]),allowedParams:{manage_physics_register_group:new Set(["groupName","placeId","clientId","targetAlias"]),manage_physics_set_collidable:new Set(["group1","group2","collidable","placeId","clientId","targetAlias"]),manage_physics_get_groups:new Set(["placeId","clientId","targetAlias"])}},manage_effects:{discriminator:"action",validActions:new Set(["emit","clear","toggle"]),allowedParams:{manage_effects_emit:new Set(["path","count","placeId","clientId","targetAlias"]),manage_effects_clear:new Set(["path","placeId","clientId","targetAlias"]),manage_effects_toggle:new Set(["path","enabled","placeId","clientId","targetAlias"])}},manage_terrain:{discriminator:"action",validActions:new Set(["fill_block","fill_ball","fill_cylinder","fill_wedge","clear_region","clear_bounds","replace_material","colors_get","colors_set","read_voxel","read_voxels","write_voxels","generate","smooth"]),allowedParams:{manage_terrain_fill_block:new Set(["cframe","size","placeId","clientId","targetAlias"]),manage_terrain_fill_ball:new Set(["center","radius","placeId","clientId","targetAlias"]),manage_terrain_fill_cylinder:new Set(["cframe","radius","height","placeId","clientId","targetAlias"]),manage_terrain_fill_wedge:new Set(["cframe","size","placeId","clientId","targetAlias"]),manage_terrain_clear_region:new Set(["region","placeId","clientId","targetAlias"]),manage_terrain_clear_bounds:new Set(["min","max","placeId","clientId","targetAlias"]),manage_terrain_replace_material:new Set(["material","region","sourceMaterial","targetMaterial","placeId","clientId","targetAlias"]),manage_terrain_colors_get:new Set(["material","placeId","clientId","targetAlias"]),manage_terrain_colors_set:new Set(["material","color","placeId","clientId","targetAlias"]),manage_terrain_read_voxel:new Set(["position","placeId","clientId","targetAlias"]),manage_terrain_read_voxels:new Set(["region","resolution","placeId","clientId","targetAlias"]),manage_terrain_write_voxels:new Set(["region","resolution","materials","occupancy","placeId","clientId","targetAlias"]),manage_terrain_generate:new Set(["region","preset","seed","baseHeight","amplitude","frequency","octaves","persistence","waterLevel","edgeBlend","materialPalette","layers","placeId","clientId","targetAlias"]),manage_terrain_smooth:new Set(["region","intensity","placeId","clientId","targetAlias"])}},spatial_query:{discriminator:"action",validActions:new Set(["raycast","find_ground","check_placement","multi_raycast","scan_area","find_flat","find_spawn","analyze_walkable","spatial_map","find_space","bounds","snap_grid","collision"]),allowedParams:{spatial_query_raycast:new Set(["origin","direction","filterType","filterList","filterInstances","ignoreWater","placeId","clientId","targetAlias"]),spatial_query_find_ground:new Set(["maxDistance","position","filterList","filterInstances","offset","placeId","clientId","targetAlias"]),spatial_query_check_placement:new Set(["position","size","filterList","filterInstances","rotation","checkGround","placeId","clientId","targetAlias"]),spatial_query_multi_raycast:new Set(["filterType","filterList","filterInstances","ignoreWater","rays","placeId","clientId","targetAlias"]),spatial_query_scan_area:new Set(["size","filterList","filterInstances","center","resolution","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_flat:new Set(["searchArea","minSize","maxSlope","tolerance","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_spawn:new Set(["searchArea","spawnSize","minSpacing","preferOutdoor","count","placeId","clientId","targetAlias"]),spatial_query_analyze_walkable:new Set(["area","maxSlope","resolution","characterHeight","maxStepHeight","placeId","clientId","targetAlias"]),spatial_query_spatial_map:new Set(["path","rootPath","includeModels","maxResults","placeId","clientId","targetAlias"]),spatial_query_find_space:new Set(["size","searchArea","gridSize","gridSnap","padding","placeId","clientId","targetAlias"]),spatial_query_bounds:new Set(["path","paths","placeId","clientId","targetAlias"]),spatial_query_snap_grid:new Set(["gridSize","path","gridSnap","axes","placeId","clientId","targetAlias"]),spatial_query_collision:new Set(["position","path","ignorePaths","placeId","clientId","targetAlias"])},paramAliases:{spatial_query_spatial_map:{path:"rootPath"}}},manage_assets:{discriminator:"action",validActions:new Set(["insert","info","search","search_insert","insert_free","insert_package","export_selection_json","export_selection_rbxm","export_path_rbxm","review_model","generate_model","upload_asset","import_rbxm","generate_thumbnail"]),allowedParams:{manage_assets_insert:new Set(["assetId","parent","name","position","placeId","clientId","targetAlias"]),manage_assets_info:new Set(["assetId","placeId","clientId","targetAlias"]),manage_assets_search:new Set(["query","maxResults","category","sortType","placeId","clientId","targetAlias"]),manage_assets_search_insert:new Set(["parent","name","query","placeId","clientId","targetAlias"]),manage_assets_insert_free:new Set(["assetId","parent","name","position","placeId","clientId","targetAlias"]),manage_assets_insert_package:new Set(["assetId","parent","name","placeId","clientId","targetAlias"]),manage_assets_export_selection_json:new Set(["format","includeProperties","includeChildren","maxDepth","placeId","clientId","targetAlias"]),manage_assets_export_selection_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","clientId","targetAlias"]),manage_assets_export_path_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","sourcePath","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","clientId","targetAlias"]),manage_assets_review_model:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","sourcePath","displayName","description","thumbnailMode","uploadMode","uploadTemporaryAssets","creatorType","creatorId","exportToLibrary","expectedUse","expectedGroups","maxDescendants","maxDepth","readiness","clientId","targetAlias"]),manage_assets_generate_model:new Set(["contextId","contextSummary","replayMetadata","placeId","category","prompt","schemaMode","predefinedSchema","schemaGroups","size","maxTriangles","generateTextures","review","targetParent","name","displayName","expectedUse","expectedGroups","maxDescendants","maxDepth","readiness","anchorMode","clientId","targetAlias"]),manage_assets_upload_asset:new Set(["contextId","contextSummary","replayMetadata","placeId","category","assetType","sourcePath","displayName","description","creatorType","creatorId","clientId","targetAlias"]),manage_assets_import_rbxm:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","assetLibraryAssetId","targetParent","name","clientId","targetAlias"]),manage_assets_generate_thumbnail:new Set(["contextId","contextSummary","replayMetadata","scope","placeId","category","assetLibraryAssetId","clientId","targetAlias"])},paramAliases:{manage_assets_search:{maxResults:"limit"}}},manage_open_cloud_assets:{discriminator:"action",validActions:new Set(["preflight","credential_status","capabilities","upload","update","info","operation_status"]),allowedParams:{manage_open_cloud_assets_preflight:new Set(["filePath","category","creatorType","creatorId"]),manage_open_cloud_assets_credential_status:new Set([]),manage_open_cloud_assets_capabilities:new Set([]),manage_open_cloud_assets_upload:new Set(["contextId","contextSummary","replayMetadata","filePath","category","displayName","description","creatorType","creatorId","expectedPrice","waitForOperation","operationPollTimeoutMs","operationPollIntervalMs"]),manage_open_cloud_assets_update:new Set(["contextId","contextSummary","replayMetadata","assetId","filePath","category","displayName","description","creatorType","creatorId","expectedPrice","updateMask","waitForOperation","operationPollTimeoutMs","operationPollIntervalMs"]),manage_open_cloud_assets_info:new Set(["assetId","readMask"]),manage_open_cloud_assets_operation_status:new Set(["operationId"])}},manage_sync:{discriminator:"action",validActions:new Set(["status_current_place","history","directions","read_file","write_file","progress"]),allowedParams:{manage_sync_status_current_place:new Set([]),manage_sync_history:new Set(["placeId","query"]),manage_sync_directions:new Set(["placeId"]),manage_sync_read_file:new Set(["placeId","instancePath"]),manage_sync_write_file:new Set(["placeId","instancePath","content"]),manage_sync_progress:new Set([])}},workspace_state:{discriminator:"action",validActions:new Set(["sync","snapshot","changes","viewport","clear_history","metadata","scripts","selection_info","clear_cache"]),allowedParams:{workspace_state_sync:new Set(["includeMetadata","placeId","clientId","targetAlias"]),workspace_state_snapshot:new Set(["placeId","clientId","targetAlias"]),workspace_state_changes:new Set(["limit","placeId","clientId","targetAlias"]),workspace_state_viewport:new Set(["includeCameraInfo","includeSelectionBounds","placeId","clientId","targetAlias"]),workspace_state_clear_history:new Set(["placeId","clientId","targetAlias"]),workspace_state_metadata:new Set(["placeId","clientId","targetAlias"]),workspace_state_scripts:new Set(["placeId","clientId","targetAlias"]),workspace_state_selection_info:new Set(["placeId","clientId","targetAlias"]),workspace_state_clear_cache:new Set(["placeId","clientId","targetAlias"])}},manage_logs:{discriminator:"action",validActions:new Set(["get","clear","errors"]),allowedParams:{manage_logs_get:new Set(["level","limit","pattern","since","sinceSeq","placeId","clientId","targetAlias"]),manage_logs_clear:new Set(["placeId","clientId","targetAlias"]),manage_logs_errors:new Set(["limit","placeId","clientId","targetAlias"])},paramAliases:{manage_logs_get:{level:"type"}}},system_info:{discriminator:"action",validActions:new Set(["ping","connection","usage","place_info","services","preflight"]),allowedParams:{system_info_ping:new Set(["message","placeId","clientId","targetAlias"]),system_info_connection:new Set([]),system_info_usage:new Set(["placeId","clientId","targetAlias"]),system_info_place_info:new Set(["placeId","clientId","targetAlias"]),system_info_services:new Set(["placeId","clientId","targetAlias"]),system_info_preflight:new Set(["placeId","clientId","targetAlias"])}},manage_studio:{discriminator:"action",validActions:new Set(["toggle_ui_preview","play_start","play_stop","play_pause","play_resume","play_status","run_test"]),allowedParams:{manage_studio_toggle_ui_preview:new Set(["enabled","placeId","clientId","targetAlias"]),manage_studio_play_start:new Set(["mode","placeId","clientId","targetAlias"]),manage_studio_play_stop:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_pause:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_resume:new Set(["placeId","clientId","targetAlias"]),manage_studio_play_status:new Set(["placeId","clientId","targetAlias"]),manage_studio_run_test:new Set(["mode","script","test_name","timeout","placeId","clientId","targetAlias","contextId","contextSummary","replayMetadata"])}}};var xye={manage_selection_cached:"internal",manage_open_cloud_assets_preflight:"internal",manage_open_cloud_assets_credential_status:"internal",manage_open_cloud_assets_capabilities:"internal",manage_open_cloud_assets_upload:"internal",manage_open_cloud_assets_update:"internal",manage_open_cloud_assets_info:"internal",manage_open_cloud_assets_operation_status:"internal",manage_sync_status_current_place:"internal",manage_sync_history:"internal",manage_sync_directions:"internal",manage_sync_read_file:"internal",manage_sync_write_file:"internal",manage_sync_progress:"internal",system_info_connection:"internal",system_info_preflight:"internal",manage_studio_run_test:"internal"};function N_(t){return xye[t]||"plugin"}var g5=new Set(["batch_execute","execute_luau","extended_call_method","extended_call_methods","extended_get_properties","extended_get_property","extended_set_properties","extended_set_property","manage_animation_get_tracks","manage_animation_load","manage_animation_play","manage_animation_stop","manage_assets_export_path_rbxm","manage_assets_export_selection_json","manage_assets_export_selection_rbxm","manage_assets_generate_model","manage_assets_generate_thumbnail","manage_assets_import_rbxm","manage_assets_info","manage_assets_insert","manage_assets_insert_free","manage_assets_insert_package","manage_assets_review_model","manage_assets_search","manage_assets_search_insert","manage_assets_upload_asset","manage_audio_pause","manage_audio_play","manage_audio_resume","manage_audio_set_listener","manage_audio_stop","manage_camera_screenshot","manage_effects_clear","manage_effects_emit","manage_effects_toggle","manage_lighting_atmosphere","manage_lighting_lighting","manage_lighting_mood","manage_lighting_sky","manage_lighting_terrain_props","manage_lighting_time","manage_open_cloud_assets_capabilities","manage_open_cloud_assets_credential_status","manage_open_cloud_assets_info","manage_open_cloud_assets_operation_status","manage_open_cloud_assets_preflight","manage_open_cloud_assets_update","manage_open_cloud_assets_upload","manage_physics_get_groups","manage_physics_register_group","manage_physics_set_collidable","manage_properties_mass_get","manage_properties_mass_set","manage_properties_modify_children","manage_properties_set_calculated","manage_properties_set_relative","manage_scripts_replace","manage_selection_add","manage_selection_context","manage_selection_details","manage_selection_remove","manage_selection_watch","manage_studio_play_pause","manage_studio_play_resume","manage_studio_play_start","manage_studio_play_status","manage_studio_play_stop","manage_studio_run_test","manage_studio_toggle_ui_preview","manage_sync_directions","manage_sync_history","manage_sync_progress","manage_sync_read_file","manage_sync_status_current_place","manage_sync_write_file","manage_terrain_clear_bounds","manage_terrain_clear_region","manage_terrain_colors_get","manage_terrain_colors_set","manage_terrain_fill_ball","manage_terrain_fill_block","manage_terrain_fill_cylinder","manage_terrain_fill_wedge","manage_terrain_generate","manage_terrain_read_voxel","manage_terrain_read_voxels","manage_terrain_replace_material","manage_terrain_smooth","manage_terrain_write_voxels","manage_tween_cancel","manage_tween_create","manage_tween_pause","manage_tween_play","manage_ui_check","manage_ui_create_tree","manage_ui_delete","manage_ui_design_brief","manage_ui_preview","manage_ui_update","mutate_instances_create_tree","mutate_instances_mass_create","mutate_instances_mass_delete","mutate_instances_mass_duplicate","mutate_instances_scatter","mutate_instances_smart_duplicate","query_instances_ancestors","query_instances_descendants","query_instances_file_tree","query_instances_project_structure","query_instances_search_property","query_instances_search_tag","spatial_query_analyze_walkable","spatial_query_bounds","spatial_query_check_placement","spatial_query_collision","spatial_query_find_flat","spatial_query_find_ground","spatial_query_find_space","spatial_query_find_spawn","spatial_query_multi_raycast","spatial_query_raycast","spatial_query_scan_area","spatial_query_snap_grid","spatial_query_spatial_map","system_info_place_info","system_info_services","workspace_state_changes","workspace_state_clear_cache","workspace_state_clear_history","workspace_state_metadata","workspace_state_scripts","workspace_state_selection_info","workspace_state_snapshot","workspace_state_sync","workspace_state_viewport"]),nA=new Set(["system_info_connection","system_info_ping","system_info_preflight","system_info_usage"]);function Gn(t){return g5.has(t)?"pro":"basic"}ui();j_();import{readFile as Fye}from"node:fs/promises";import Uye from"node:path";import{createHash as Nye,randomUUID as oA}from"node:crypto";import{mkdir as am,readFile as I5,readdir as C5,rename as P5,rm as jye,stat as Mye,writeFile as B_}from"node:fs/promises";import Ht from"node:path";import{extname as Iye}from"node:path";import{constants as Cye}from"node:fs";import{access as Pye,stat as kye}from"node:fs/promises";var tm=20*1024*1024,z_=[{category:"image",assetType:"Image",folder:"images",extensions:[".png",".jpeg",".jpg",".bmp",".tga"],supportsContentUpdate:!1,contentTypes:{".png":"image/png",".jpeg":"image/jpeg",".jpg":"image/jpeg",".bmp":"image/bmp",".tga":"image/tga"}},{category:"decal",assetType:"Decal",folder:"decals",extensions:[".png",".jpeg",".jpg",".bmp",".tga"],supportsContentUpdate:!1,contentTypes:{".png":"image/png",".jpeg":"image/jpeg",".jpg":"image/jpeg",".bmp":"image/bmp",".tga":"image/tga"}},{category:"audio",assetType:"Audio",folder:"audio",extensions:[".mp3",".ogg",".wav",".flac"],supportsContentUpdate:!1,contentTypes:{".mp3":"audio/mpeg",".ogg":"audio/ogg",".wav":"audio/wav",".flac":"audio/flac"}},{category:"mesh",assetType:"Mesh",folder:"meshes",extensions:[".mesh"],supportsContentUpdate:!1,contentTypes:{".mesh":"application/octet-stream"}},{category:"model",assetType:"Model",folder:"models",extensions:[".fbx",".gltf",".glb",".rbxm",".rbxmx"],supportsContentUpdate:!0,contentTypes:{".fbx":"model/fbx",".gltf":"model/gltf+json",".glb":"model/gltf-binary",".rbxm":"model/x-rbxm",".rbxmx":"model/x-rbxm"}},{category:"video",assetType:"Video",folder:"videos",extensions:[".mp4",".mov"],supportsContentUpdate:!1,contentTypes:{".mp4":"video/mp4",".mov":"video/quicktime"}},{category:"animation",assetType:"Animation",folder:"animations",extensions:[".rbxm",".rbxmx"],supportsContentUpdate:!0,contentTypes:{".rbxm":"model/x-rbxm",".rbxmx":"model/x-rbxm"}}],Eye=new Map(z_.map(t=>[t.category,t]));function v5(t){if(!t)throw new Error("Open Cloud asset upload is disabled in WEPPY Dashboard settings.")}function M_(t,e){return t.split(e.apiKey).join("[redacted]")}function L_(t){let e=Eye.get(t);if(!e)throw new Error(`Unsupported asset category: ${t}`);return e}function F_(t){return L_(t)}async function iA(t,e,n=tm){let r=L_(t),i=Iye(e).toLowerCase(),a=r.contentTypes[i]??null,o=await kye(e),s=!0;try{await Pye(e,Cye.R_OK)}catch{s=!1}return{category:t,extension:i,contentType:a,formatValid:a!==null,sizeBytes:o.size,sizeValid:o.size<=n,maxFileSizeBytes:n,regularFile:o.isFile(),readable:s}}function b5(t,e){let n=t.creatorType??e.creatorType,r=t.creatorId??e.creatorId;if(!n||!r)throw new Error("creatorType and creatorId are required for Roblox Open Cloud asset upload/update.");return{...t,creatorType:n,creatorId:r}}async function x5(t,e,n){let r=await iA(t.category,e,n);if(!r.formatValid||!r.contentType)throw new Error(`Unsupported file extension ${r.extension||"(none)"} for ${t.category}.`);if(!r.regularFile)throw new Error("Asset path must reference a regular file.");if(!r.readable)throw new Error("Asset file is not readable.");if(!r.sizeValid)throw new Error(`Asset file is too large. Maximum size is ${n} bytes.`);return r.contentType}function _5(t){return typeof t.path=="string"&&t.path.startsWith("operations/")?t.path:null}function S5(t,e,n,r){let i={apiKey:t.apiKey,operationId:e};return n!==void 0&&(i.intervalMs=n),r!==void 0&&(i.timeoutMs=r),i}var ou=class{client;credentialStore;isOpenCloudUploadEnabled;maxFileSizeBytes;constructor(e){this.client=e.client,this.credentialStore=e.credentialStore,this.isOpenCloudUploadEnabled=e.isOpenCloudUploadEnabled,this.maxFileSizeBytes=e.maxFileSizeBytes??tm}getCapabilities(){return z_.map(({contentTypes:e,...n})=>n)}async uploadAsset(e){v5(this.isOpenCloudUploadEnabled());let n=await this.getRequiredCredential(),r=b5(e,n),i=L_(r.category),a=await x5(i,r.filePath,this.maxFileSizeBytes);try{let o={apiKey:n.apiKey,assetType:i.assetType,displayName:r.displayName,description:r.description??"",creatorType:r.creatorType,creatorId:r.creatorId,filePath:r.filePath,contentType:a};r.expectedPrice!==void 0&&(o.expectedPrice=r.expectedPrice);let s=await this.client.createAsset(o);if(r.waitForOperation){let c=_5(s);return c?await this.client.pollOperation(S5(n,c,r.operationPollIntervalMs,r.operationPollTimeoutMs)):s}return s}catch(o){throw new Error(M_(o instanceof Error?o.message:String(o),n))}}async updateAsset(e){v5(this.isOpenCloudUploadEnabled());let n=await this.getRequiredCredential(),r=b5(e,n),i=L_(r.category),a;if(r.filePath){if(!i.supportsContentUpdate)throw new Error(`${i.category} assets do not support content updates.`);a=await x5(i,r.filePath,this.maxFileSizeBytes)}try{let o={apiKey:n.apiKey,assetId:r.assetId,assetType:i.assetType,creatorType:r.creatorType,creatorId:r.creatorId};r.filePath&&(o.filePath=r.filePath),a!==void 0&&(o.contentType=a),r.displayName!==void 0&&(o.displayName=r.displayName),r.description!==void 0&&(o.description=r.description),r.updateMask!==void 0&&(o.updateMask=r.updateMask),r.expectedPrice!==void 0&&(o.expectedPrice=r.expectedPrice);let s=await this.client.updateAsset(o);if(r.waitForOperation){let c=_5(s);return c?await this.client.pollOperation(S5(n,c,r.operationPollIntervalMs,r.operationPollTimeoutMs)):s}return s}catch(o){throw new Error(M_(o instanceof Error?o.message:String(o),n))}}async getAsset(e){let n=await this.getRequiredCredential();try{let r={apiKey:n.apiKey,assetId:e.assetId};return e.readMask!==void 0&&(r.readMask=e.readMask),await this.client.getAsset(r)}catch(r){throw new Error(M_(r instanceof Error?r.message:String(r),n))}}async getOperation(e){let n=await this.getRequiredCredential();try{return await this.client.getOperation({apiKey:n.apiKey,operationId:e.operationId})}catch(r){throw new Error(M_(r instanceof Error?r.message:String(r),n))}}async getRequiredCredential(){let e=await this.credentialStore.getCredentialForUse();if(!e)throw new Error("Configure a Roblox Open Cloud API key in WEPPY Dashboard before using Open Cloud asset upload.");return e}};import w5 from"node:fs";import rn from"node:path";Ix();var Rye=/^asset_(image|decal|audio|mesh|model|video|animation)_\d+_[a-z0-9]+$/;function Tye(t){if(!Number.isInteger(t)||t<0)throw new Error(`Invalid place ID: ${t}`)}function Aye(t,e){try{return w5.statSync(rn.join(t,e,".sync-meta.json")).isFile()}catch{return!1}}function Oye(t,e){Tye(e.placeId);let n=`place_${e.placeId}`,r=e.placeName?Ml(e.placeName):"",i=r?`${n}_${r}`:n,a=[];try{let o=new RegExp(`^place_${e.placeId}(?:_.*)?$`);a=w5.readdirSync(t,{withFileTypes:!0}).filter(s=>s.isDirectory()&&o.test(s.name)).map(s=>s.name).sort()}catch{return i}return r&&a.includes(i)?i:a.find(o=>Aye(t,o))??(a.includes(i)?i:null)??a[0]??i}function aA(t){let e=rn.resolve(t.projectSyncRoot),n=F_(t.category).folder,r=t.scope.kind==="place"?rn.join(e,Oye(e,t.scope),"assets",n):rn.join(e,"shared-assets",n);return{root:r,inbox:rn.join(r,"inbox"),index:rn.join(r,".asset-library-index.json")}}function $ye(t){let e=Rye.exec(t);return e?.[1]?e[1]:null}function nm(t,e){let n=$ye(t);return n?e?n===e:!0:!1}function U_(t,e){if(!nm(t,e))throw new Error(`Invalid asset ID: ${t}`)}function mi(t,e){let n=rn.relative(rn.resolve(t),rn.resolve(e));return n===""||!n.startsWith("..")&&!rn.isAbsolute(n)}function Dye(t){U_(t.assetId,t.category);let e=aA(t),n=rn.resolve(e.root,t.assetId);if(!mi(e.root,n))throw new Error(`Invalid asset path for ${t.assetId}`);return n}function q_(t){let e=Dye(t),n=rn.resolve(e,t.relativeFileName);if(!mi(e,n))throw new Error(`Invalid asset file path for ${t.assetId}`);return n}function rm(t,e){return rn.relative(rn.resolve(t),rn.resolve(e)).split(rn.sep).join("/")}var k5=20*1024*1024,Lye=200;function E5(t,e){return t.kind!==e.kind?!1:t.kind==="shared"&&e.kind==="shared"?!0:t.kind==="place"&&e.kind==="place"&&t.placeId===e.placeId}function R5(t,e){let n=Ht.extname(t).toLowerCase(),r=F_(e);if(!r.extensions.includes(n))return null;let i=r.contentTypes[n];return i?{canonicalExt:n,mimeType:i}:null}function sA(t,e,n){if(e!=="image"&&e!=="decal")return!0;let r=Ht.extname(t).toLowerCase();return r===".png"?n.length>=8&&n[0]===137&&n[1]===80&&n[2]===78&&n[3]===71&&n[4]===13&&n[5]===10&&n[6]===26&&n[7]===10:r===".jpg"||r===".jpeg"?n.length>=3&&n[0]===255&&n[1]===216&&n[2]===255:r===".bmp"?n.length>=2&&n[0]===66&&n[1]===77:r===".tga"?n.length>0:!1}function T5(t){return Nye("sha256").update(t).digest("hex")}function V_(t){return t.now?.()??Date.now()}function zye(t){return(t.randomId?.()??oA().replace(/-/g,"").slice(0,6)).toLowerCase().replace(/[^a-z0-9]/g,"").slice(0,12)||"asset"}function A5(t,e){let n=Math.floor(V_(t)/1e3);for(let r=0;r<20;r++){let i=zye(t),a=r===0?`asset_${t.category}_${n}_${i}`:`asset_${t.category}_${n}_${i}${r}`;if(!e.has(a))return a}return`asset_${t.category}_${n}_${oA().replace(/-/g,"").slice(0,10)}`}function O5(t){let e=Ht.parse(t).name.trim();return e.length>0?e:t}function $5(t){if(t.mimeType!=="image/png")throw new Error("Asset Library preview must be an image/png thumbnail");if(Ht.basename(t.fileName).toLowerCase()!=="thumbnail.png")throw new Error("Asset Library preview file must be thumbnail.png");if(!sA("thumbnail.png","image",t.content))throw new Error("Asset Library preview is not a valid PNG file");return{fileName:"thumbnail.png",content:t.content}}async function cA(t,e){let n=`${t}.tmp.${oA().slice(0,8)}`;await B_(n,JSON.stringify(e,null,2),"utf8"),await P5(n,t)}async function D5(t,e){try{let n=await I5(Ht.join(e,"asset.json"),"utf8"),r=JSON.parse(n);return!nm(r.id,t.category)||r.category!==t.category||!E5(r.scope,t.scope)?null:r}catch{return null}}async function im(t,e){let n;try{n=await C5(e.root,{withFileTypes:!0})}catch(i){if(i?.code==="ENOENT")return[];throw i}let r=[];for(let i of n.sort((a,o)=>a.name.localeCompare(o.name))){if(!i.isDirectory()||!nm(i.name,t.category))continue;let a=Ht.join(e.root,i.name),o=await D5(t,a);o&&r.push(o)}return r.sort((i,a)=>a.createdAt.localeCompare(i.createdAt)||a.id.localeCompare(i.id))}async function su(t,e,n){if(U_(n.id,t.category),n.category!==t.category||!E5(n.scope,t.scope))throw new Error(`Asset metadata does not match library scope/category: ${n.id}`);let r=Ht.join(e.root,n.id);if(!mi(e.root,r))throw new Error(`Invalid asset path for ${n.id}`);await am(r,{recursive:!0}),await cA(Ht.join(r,"asset.json"),n)}async function N5(t,e){await am(t.root,{recursive:!0});let n={version:1,generatedAt:new Date().toISOString(),assets:e.map(r=>r.id)};await cA(t.index,n)}function Ji(t,e,n){return{fileName:t,reason:e,message:n}}async function gi(t){let e=aA(t);return await am(e.inbox,{recursive:!0}),e}async function j5(t){let e=await gi(t),n=await im(t,e);return await N5(e,n),n}async function Zt(t,e){U_(e,t.category);let n=await gi(t),r=Ht.join(n.root,e);if(!mi(n.root,r))throw new Error(`Invalid asset path for ${e}`);let i=await D5(t,r);if(!i)throw new Error(`Asset not found: ${e}`);return i}async function cu(t){let e=await gi(t),n=await im(t,e),r={version:1,generatedAt:new Date().toISOString(),assets:n.map(i=>i.id)};return await cA(e.index,r),r}async function M5(t){let e=await gi(t),n=await im(t,e),r=new Set(n.map(p=>p.id)),i=new Set(n.map(p=>p.file.sha256)),a=[],o=[],s=t.maxFileSizeBytes??k5,c=t.maxFilesPerRescan??Lye,l;try{l=await C5(e.inbox,{withFileTypes:!0})}catch(p){if(p?.code==="ENOENT")l=[];else throw p}let u=l.sort((p,f)=>p.name.localeCompare(f.name));for(let p=0;p<u.length;p++){let f=u[p];if(p>=c){o.push(Ji(f.name,"maxFileCount","rescan file count limit exceeded"));continue}if(f.name.startsWith(".")){o.push(Ji(f.name,"hidden","hidden or system file"));continue}if(f.isSymbolicLink()){o.push(Ji(f.name,"symlink","symlink files are not followed"));continue}if(f.isDirectory()){o.push(Ji(f.name,"nestedDirectory","nested directories are not scanned"));continue}if(!f.isFile()){o.push(Ji(f.name,"unsupportedType","unsupported inbox entry type"));continue}let m=R5(f.name,t.category);if(!m){o.push(Ji(f.name,"unsupportedType",`unsupported ${t.category} extension`));continue}let g=Ht.join(e.inbox,f.name),h=await Mye(g);if(h.size>s){o.push(Ji(f.name,"oversized","asset file is larger than the configured limit"));continue}let v=await I5(g);if(!sA(f.name,t.category,v)){o.push(Ji(f.name,"invalidSignature","file signature does not match the extension"));continue}let x=T5(v);if(i.has(x)){o.push(Ji(f.name,"duplicate","asset content already exists in Asset Library"));continue}let _=A5(t,r);r.add(_),i.add(x);let P=Ht.join(e.root,_),w=`original${m.canonicalExt}`;await am(P,{recursive:!0}),await P5(g,Ht.join(P,w));let D=new Date(V_(t)).toISOString(),M={version:1,id:_,category:t.category,scope:t.scope,status:"localOnly",displayName:O5(f.name),description:"",source:{kind:"generated",originalPath:rm(t.projectSyncRoot,g)},file:{original:w,preview:null,mimeType:m.mimeType,sha256:x,sizeBytes:h.size,width:null,height:null,durationMs:null},roblox:{uploaded:!1},usage:{lastScannedAt:null,scanSource:null,references:[]},createdAt:D,updatedAt:D};await su(t,e,M),a.push(M)}let d=await im(t,e);return await N5(e,d),{assets:d,adopted:a,skipped:o,adoptedCount:a.length,skippedCount:o.length}}async function L5(t){let e=await gi(t),n=R5(t.originalFileName,t.category);if(!n)throw new Error(`Unsupported ${t.category} extension for Asset Library export`);let r=t.maxFileSizeBytes??k5;if(t.content.length>r)throw new Error("asset file is larger than the configured limit");if(!sA(t.originalFileName,t.category,t.content))throw new Error("file signature does not match the extension");let i=await im(t,e),a=T5(t.content),o=i.find(h=>h.file.sha256===a);if(o)return{asset:o,deduplicated:!0};let s=new Set(i.map(h=>h.id)),c=A5(t,s),l=Ht.join(e.root,c);if(!mi(e.root,l))throw new Error(`Invalid asset path for ${c}`);let u=`original${n.canonicalExt}`;await am(l,{recursive:!0}),await B_(Ht.join(l,u),t.content);let d=null;if(t.preview){let h=$5(t.preview);d=h.fileName,await B_(Ht.join(l,h.fileName),h.content)}let p=new Date(V_(t)).toISOString(),f=t.roblox??{uploaded:!1},m=f.uploaded&&f.assetId?"uploaded":"localOnly",g={version:1,id:c,category:t.category,scope:t.scope,status:m,displayName:t.displayName?.trim()||O5(t.originalFileName),description:t.description??"",source:{...t.source,originalPath:rm(t.projectSyncRoot,Ht.join(l,u))},file:{original:u,preview:d,mimeType:n.mimeType,sha256:a,sizeBytes:t.content.length,width:null,height:null,durationMs:null},roblox:f,usage:{lastScannedAt:null,scanSource:null,references:[]},...t.rbxm?{rbxm:t.rbxm}:{},createdAt:p,updatedAt:p};return await su(t,e,g),await cu(t),{asset:g,deduplicated:!1}}async function z5(t){let e=await gi(t),n=await Zt(t,t.assetId),r=$5(t.preview),i=q_({...t,relativeFileName:r.fileName});await B_(i,r.content);let a={...n,file:{...n.file,preview:r.fileName},...n.rbxm&&t.rbxmThumbnail?{rbxm:{...n.rbxm,thumbnail:t.rbxmThumbnail}}:{},updatedAt:new Date(V_(t)).toISOString()};return await su(t,e,a),await cu(t),{asset:a}}async function F5(t,e,n){let r=await gi(t),i=await Zt(t,e),a={...i,displayName:typeof n.displayName=="string"?n.displayName:i.displayName,description:typeof n.description=="string"?n.description:i.description,source:{...i.source,...n.source?.agent!==void 0?{agent:n.source.agent}:{},...n.source?.contextId!==void 0?{contextId:n.source.contextId}:{},...n.source?.prompt!==void 0?{prompt:n.source.prompt}:{}},updatedAt:new Date().toISOString()};return await su(t,r,a),await cu(t),a}async function U5(t,e,n){let r=await gi(t),a={...await Zt(t,e),usage:n,updatedAt:new Date().toISOString()};return await su(t,r,a),await cu(t),a}async function q5(t,e){let n=await gi(t);await Zt(t,e);let r=Ht.join(n.root,e);if(!mi(n.root,r))throw new Error(`Invalid asset path for ${e}`);return await jye(r,{recursive:!0}),await cu(t),{assetId:e,removed:1}}async function uo(t){let e=await gi(t);return await su(t,e,t.asset),await cu(t),t.asset}async function lu(t){let e=await Zt(t,t.assetId);return q_({...t,relativeFileName:e.file.original})}async function B5(t){let e=await Zt(t,t.assetId);return q_({...t,relativeFileName:e.file.preview??e.file.original})}var qye="https://create.roblox.com/dashboard/creations/store",Bye="manage_assets_import_rbxm",uA="manage_assets_generate_thumbnail",Vye="manage_assets_review_model";var dA=new Set([Bye,uA]),pA=new Set(["manage_assets_export_selection_rbxm","manage_assets_export_path_rbxm",Vye]),Hye=new Set(["model","animation"]);function rt(t){return t&&typeof t=="object"?t:null}function Zye(t){if(typeof t!="string"||!Hye.has(t))throw new Error(`Unsupported Asset Library .rbxm round-trip category: ${String(t??"(missing)")}`);return t}function Wye(t){if(typeof t=="number"&&Number.isInteger(t)&&t>=0)return t;if(typeof t=="string"&&t.trim().length>0){let e=Number.parseInt(t,10);if(Number.isInteger(e)&&e>=0)return e}return null}function V5(t,e){for(let n of t.pluginClients.values())if(!(typeof n.placeId!="number"||!Number.isFinite(n.placeId))&&!(e!==void 0&&n.placeId!==e))return{placeId:n.placeId,...n.placeName?{placeName:n.placeName}:{}};return null}function fA(t,e){let n=bt(t.config.dataDir),r=Zye(e.category),i=typeof e.scope=="string"?e.scope:"place",a=typeof e.assetLibraryAssetId=="string"&&e.assetLibraryAssetId.length>0?e.assetLibraryAssetId:void 0;if(i==="shared")return{projectSyncRoot:n,scope:{kind:"shared"},category:r,...a?{assetId:a}:{}};if(i!=="place")throw new Error(`Invalid Asset Library scope: ${i}`);let o=Wye(e.placeId),s=t.syncController?.getDefaultRuntimePlaceId()??null,c=o??s??V5(t)?.placeId??null;if(c===null)throw new Error("No placeId is available for Asset Library .rbxm round-trip.");let l=V5(t,c);return{projectSyncRoot:n,scope:{kind:"place",placeId:c,...l?.placeName?{placeName:l.placeName}:{}},category:r,...a?{assetId:a}:{}}}function Gye(t){if(Uye.extname(t.file.original).toLowerCase()!==".rbxm")throw new Error(`Asset Library Studio round-trip supports original.rbxm only. Unsupported original file: ${t.file.original}`)}function Kye(t,e){if(typeof t!="string"||t.trim().length===0)throw new Error(`${e} is missing`);return Buffer.from(t,"base64")}function Jye(t,e){let n=rt(e),i={kind:n?.kind==="generation"||typeof t.prompt=="string"?"generated":"studioExport",originalPath:"studio:selection"};if(n){let a=typeof n.path=="string"?n.path:typeof n.kind=="string"?n.kind:void 0;a&&(i.originalPath=`studio:${a}`);let o=ge(n.prompt,1e3);o&&(i.prompt=o)}if(!i.prompt){let a=ge(t.prompt,1e3);a&&(i.prompt=a)}return typeof t.contextId=="string"&&(i.contextId=t.contextId),i}function G5(t){let e=rt(t);if(!e)return;let n={};typeof e.width=="number"&&(n.width=e.width),typeof e.height=="number"&&(n.height=e.height),typeof e.source=="string"&&(n.source=e.source),typeof e.error=="string"&&(n.error=e.error);let r=om(e.attempts);return r.length>0&&(n.attempts=r),Object.keys(n).length>0?n:void 0}function ge(t,e){return typeof t!="string"?null:t.slice(0,e)}function Yye(t){if(typeof t!="string")return null;let e=t.trim();return/^\d+$/.test(e)?e:null}function H5(t){return`rbxassetid://${t}`}function Z5(t){return`${qye}/${t}/configure`}function W5(t){return`assets/${t}`}function pr(t){return typeof t=="number"&&Number.isFinite(t)?t:void 0}function K5(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.name,256),i=ge(n.className,128),a=ge(n.path,512);return r===null||i===null||a===null?[]:[{name:r,className:i,path:a}]}):[]}function Xye(t){let e=rt(t);if(!e)return{};let n={};for(let[r,i]of Object.entries(e).slice(0,100))typeof i!="number"||!Number.isFinite(i)||i<0||(n[r.slice(0,128)]=Math.floor(i));return n}function Qye(t){return Array.isArray(t)?t.slice(0,200).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.path,512),i=ge(n.property,128),a=ge(n.value,1024);if(r===null||i===null||a===null)return[];let o=ge(n.assetId,64);return[{path:r,property:i,value:a,...o?{assetId:o}:{}}]}):[]}function om(t){return Array.isArray(t)?t.slice(0,8).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.method,80),i=n.status==="success"||n.status==="failed"||n.status==="skipped"?n.status:null;if(r===null||i===null)return[];let a=ge(n.message,512);return[{method:r,status:i,...a?{message:a}:{}}]}):[]}function eve(t,e){let n=t.thumbnailMode==="auto"?"auto":"none";if(n==="none")return{mode:n,status:"skipped",message:"Thumbnail generation disabled"};let r=G5(e),i=rt(e),a=typeof i?.pngBase64=="string"&&i.pngBase64.length>0,o=typeof i?.base64Rgba=="string"&&i.base64Rgba.length>0&&i.format==="rgba8"&&typeof i.width=="number"&&typeof i.height=="number";if(r&&(a||o)){let s=pr(r.width),c=pr(r.height),l=om(i?.attempts);return{mode:n,status:"generated",...s!==void 0?{width:s}:{},...c!==void 0?{height:c}:{},...typeof r.source=="string"?{source:r.source.slice(0,128)}:{},...l.length>0?{attempts:l}:{}}}if(r&&typeof r.error=="string"){let s=om(rt(e)?.attempts);return{mode:n,status:"failed",message:r.error.slice(0,512),...s.length>0?{attempts:s}:{}}}return{mode:n,status:"skipped",message:"Thumbnail was not returned"}}function tve(t,e){let n=rt(t);if(!n)return e;let r=n.mode==="auto"||n.mode==="none"?n.mode:e.mode,i=n.status==="generated"||n.status==="skipped"||n.status==="failed"?n.status:e.status,a=ge(n.message,512),o=pr(n.width),s=pr(n.height),c=ge(n.source,128),l=om(n.attempts);return{mode:r,status:i,...a?{message:a}:{},...o!==void 0?{width:o}:{},...s!==void 0?{height:s}:{},...c?{source:c}:{},...l.length>0?{attempts:l}:{}}}function lA(t,e=0){if(e>3)return;if(typeof t=="string")return t.slice(0,512);if(typeof t=="boolean")return t;if(typeof t=="number")return Number.isFinite(t)?t:void 0;if(Array.isArray(t))return t.slice(0,50).flatMap(i=>{let a=lA(i,e+1);return a===void 0?[]:[a]});let n=rt(t);if(!n)return;let r={};for(let[i,a]of Object.entries(n).slice(0,50)){let o=lA(a,e+1);o!==void 0&&(r[i.slice(0,128)]=o)}return r}function nve(t){let e=rt(t),n=pr(e?.x),r=pr(e?.y),i=pr(e?.z);if(!(n===void 0||r===void 0||i===void 0))return{x:n,y:r,z:i}}function rve(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=n.severity==="info"||n.severity==="warning"||n.severity==="error"?n.severity:null,i=ge(n.category,80),a=ge(n.code,120),o=ge(n.path,512),s=ge(n.message,512);if(!r||i===null||a===null||o===null||s===null)return[];let c=ge(n.suggestion,512);return[{severity:r,category:i,code:a,path:o,message:s,...c?{suggestion:c}:{}}]}):[]}function ive(t){let e=rt(t);if(!e)return;let n=e.readiness==="ready"||e.readiness==="review"||e.readiness==="blocked"?e.readiness:null;if(!n)return;let r=lA(e.summary),i=ge(e.reviewedAt,64),a=K5(e.roots);return{readiness:n,...i?{reviewedAt:i}:{},...a.length>0?{roots:a}:{},summary:rt(r)??{},findings:rve(e.findings)}}function ave(t){let e=rt(t);if(!e)return;let n={};for(let[r,i]of Object.entries(e).slice(0,16))typeof i=="string"&&(n[r.slice(0,128)]=i.slice(0,256)),typeof i=="number"&&Number.isFinite(i)&&(n[r.slice(0,128)]=i),typeof i=="boolean"&&(n[r.slice(0,128)]=i);return Object.keys(n).length>0?n:void 0}function ove(t){let e=rt(t);if(!e)return;let n=ge(e.provider,120);if(!n)return;let r=ge(e.generatedAt,64),i=ge(e.prompt,1e3),a=e.schemaMode==="predefined"||e.schemaMode==="custom"?e.schemaMode:void 0,o=e.predefinedSchema==="Body1"||e.predefinedSchema==="Car5"?e.predefinedSchema:void 0,s=Array.isArray(e.schemaGroups)?e.schemaGroups.slice(0,50).flatMap(f=>{let m=ge(f,120);return m?[m]:[]}):void 0,c=nve(e.requestedSize),l=pr(e.maxTriangles),u=ge(e.targetParent,512),d=ge(e.path,512),p=ave(e.metadata);return{provider:n,...r?{generatedAt:r}:{},...i?{prompt:i}:{},...a?{schemaMode:a}:{},...o?{predefinedSchema:o}:{},...s&&s.length>0?{schemaGroups:s}:{},...c?{requestedSize:c}:{},...l!==void 0?{maxTriangles:Math.floor(l)}:{},...typeof e.generateTextures=="boolean"?{generateTextures:e.generateTextures}:{},...u?{targetParent:u}:{},...d?{path:d}:{},...p?{metadata:p}:{}}}function sve(t){return Array.isArray(t)?t.slice(0,100).flatMap(e=>{let n=rt(e);if(!n)return[];let r=ge(n.path,512),i=n.assetType==="Mesh"||n.assetType==="Image"||n.assetType==="Model"?n.assetType:null,a=n.status==="uploaded"||n.status==="failed"?n.status:null;if(r===null||i===null||a===null)return[];let o=ge(n.assetId,64),s=ge(n.assetUri,128),c=n.creatorType==="user"||n.creatorType==="group"?n.creatorType:void 0,l=ge(n.creatorId,64),u=ge(n.sourceProperty,128),d=ge(n.uploadedAt,64),p=ge(n.message,512);return[{path:r,assetType:i,status:a,...o?{assetId:o}:{},...s?{assetUri:s}:{},...c?{creatorType:c}:{},...l?{creatorId:l}:{},...u?{sourceProperty:u}:{},...d?{uploadedAt:d}:{},...p?{message:p}:{}}]}):[]}function cve(t){let e=rt(t);if(!e||e.uploaded!==!0)return;let n=Yye(e.assetId);if(!n)return;let r=ge(e.uploadedAt,64)??new Date().toISOString(),i=e.creatorType==="user"||e.creatorType==="group"?e.creatorType:void 0,a=ge(e.creatorId,64);return{uploaded:!0,assetId:n,assetUri:H5(n),assetWebUrl:Z5(n),remotePath:W5(n),uploadedAt:r,uploadAttempts:[{startedAt:r,finishedAt:r,status:"uploaded",assetRole:"primary",...i?{creatorType:i}:{},...a?{creatorId:a}:{},assetId:n,assetUri:H5(n),assetWebUrl:Z5(n),remotePath:W5(n)}]}}function lve(t){let e=rt(t.value),n=K5(e?.roots),r=Xye(e?.classCounts),i=Qye(e?.resourceReferences),a=ive(e?.review),o=ove(e?.generation),s=sve(e?.studioUploads),c=pr(e?.exportedCount)??pr(t.exportedCount)??n.length;return{exportedCount:Math.max(0,Math.floor(c)),roots:n,classCounts:r,resourceReferences:i,thumbnail:tve(e?.thumbnail,t.fallbackThumbnail),...a?{review:a}:{},...o?{generation:o}:{},...s.length>0?{studioUploads:s}:{}}}function uve(t){return t.length>=8&&t[0]===137&&t[1]===80&&t[2]===78&&t[3]===71&&t[4]===13&&t[5]===10&&t[6]===26&&t[7]===10}function J5(t){let e=rt(t);if(!e)return;let n=null;if(typeof e.pngBase64=="string"&&e.pngBase64.length>0?n=Buffer.from(e.pngBase64,"base64"):typeof e.base64Rgba=="string"&&e.base64Rgba.length>0&&e.format==="rgba8"&&typeof e.width=="number"&&typeof e.height=="number"&&(n=Buffer.from(y5(e.base64Rgba,e.width,e.height),"base64")),!!n){if(!uve(n))throw new Error("Thumbnail payload is not a valid PNG image.");return{fileName:"thumbnail.png",content:n,mimeType:"image/png"}}}function dve(t,e){let n=e instanceof Error?e.message:String(e);return t.thumbnail.status!=="generated"?t:{...t,thumbnail:{...t.thumbnail,status:"failed",message:`Thumbnail payload could not be stored: ${n}`.slice(0,512)}}}async function Y5(t){if(!dA.has(t.command))return t.params;let e=fA(t.ctx,t.params);if(!e.assetId)throw new Error("assetLibraryAssetId is required for Asset Library .rbxm round-trip.");let n=await Zt(e,e.assetId);Gye(n);let r=await lu({...e,assetId:n.id}),i=await Fye(r);return{...t.params,__assetLibraryRbxmBase64:i.toString("base64"),__assetLibraryOriginalFile:n.file.original}}async function X5(t){if(!pA.has(t.command)||!t.result.success)return t.result;let e=rt(t.result.data);if(!e||typeof e.rbxmBase64!="string"||e.rbxmBase64.trim().length===0)return t.result;let n=fA(t.ctx,t.params),r=Kye(e.rbxmBase64,"Asset Library .rbxm export payload"),i=typeof t.params.displayName=="string"?t.params.displayName:void 0,a=typeof t.params.description=="string"?t.params.description:void 0,o=`${i?.trim()||"studio-export"}.rbxm`,s,c=null;try{s=J5(e.thumbnail)}catch(f){c=f,s=void 0}let l=lve({value:e.rbxm,exportedCount:e.exportedCount,fallbackThumbnail:eve(t.params,e.thumbnail)});c&&(l=dve(l,c));let u=cve(e.roblox),d=await L5({projectSyncRoot:n.projectSyncRoot,scope:n.scope,category:n.category,originalFileName:o,content:r,...i!==void 0?{displayName:i}:{},...a!==void 0?{description:a}:{},source:Jye(t.params,e.source),...s?{preview:s}:{},rbxm:l,...u?{roblox:u}:{}}),p=G5(e.thumbnail);return{...t.result,data:{asset:d.asset,deduplicated:d.deduplicated,...typeof e.byteLength=="number"?{byteLength:e.byteLength}:{},...typeof e.exportedCount=="number"?{exportedCount:e.exportedCount}:{},...e.source!==void 0?{source:e.source}:{},...p?{thumbnail:p}:{}}}}async function Q5(t){if(!t.result.success)return t.result;let e=rt(t.result.data),n=rt(e?.thumbnail),r;try{r=J5(n)}catch(d){return{...t.result,success:!1,error:d instanceof Error?d.message:String(d)}}if(!n||!r)return{...t.result,success:!1,error:typeof n?.error=="string"?n.error:"Thumbnail payload is missing from Asset Library thumbnail generation result."};let i=pr(n.width),a=pr(n.height),o=ge(n.source,128),s=om(n.attempts),c={mode:"auto",status:"generated",...i!==void 0?{width:i}:{},...a!==void 0?{height:a}:{},...o?{source:o}:{},...s.length>0?{attempts:s}:{}},l=fA(t.ctx,t.params);if(!l.assetId)throw new Error("assetLibraryAssetId is required for Asset Library thumbnail generation.");let u=await z5({projectSyncRoot:l.projectSyncRoot,scope:l.scope,category:l.category,assetId:l.assetId,preview:r,rbxmThumbnail:c});return{...t.result,data:{asset:u.asset,...i!==void 0?{width:i}:{},...a!==void 0?{height:a}:{},...o?{source:o}:{}}}}function pve(t){if(t===null||typeof t!="object")return;let e=t.proFallback;if(e===null||typeof e!="object")return;let n=e;if(typeof n.executedCommand!="string")return;let r=Array.isArray(n.alternatives)?n.alternatives.filter(i=>typeof i=="string"):void 0;return{executedCommand:n.executedCommand,...typeof n.requestedCommand=="string"?{requestedCommand:n.requestedCommand}:{},...r?{alternatives:r}:{}}}var fve=/^Pro action '[^']+' is blocked in Basic mode\. Basic fallback '([^']+)' failed: (.*)$/s,mve=/^Pro action '[^']+' is blocked in Basic mode\.(?! Basic fallback ')/,gve=/instance not found|not found in|parent not found/,hve=/is required|missing required/,yve=/unknown action|unknown command/,vve=/must be|invalid|cannot/;function bve(t){let e=fve.exec(t);return e?{fallbackCommand:e[1],reason:e[2]}:null}function xve(t){return mve.test(t)}function _ve(t){let e=t.toLowerCase();return gve.test(e)?"not_found":hve.test(e)?"missing_param":yve.test(e)?"unknown_action":vve.test(e)?"validation":"other"}function mA(t){return t.errorType==="bridge_error"||t.errorType==="command_timeout"||t.errorType==="plugin_runtime"||t.errorType==="exception"||t.errorType==="device_blocked"||t.failureOrigin==="bridge"||t.failureOrigin==="plugin_runtime"||t.failureOrigin==="server_exception"||t.failureOrigin==="product_bug"||t.failureOrigin==="unknown"||t.recoverability==="retry"||t.recoverability==="wait_connection"||t.recoverability==="unknown"?"error":"warning"}function uu(t){if(t.resultSuccess){let e=pve(t.resultData);return e?{kind:"success_fallback",fallbackCommand:e.executedCommand,...e.alternatives?{alternatives:e.alternatives}:{}}:{kind:"success_ok"}}if(!t.resultError)return{kind:"error"};if(t.tier==="pro"){let e=bve(t.resultError);if(e)return{kind:"blocked_fallback_failed",fallbackCommand:e.fallbackCommand,blockedDetail:_ve(e.reason)};if(xve(t.resultError))return{kind:"blocked_unsupported"}}return t.failureClassification?{kind:mA(t.failureClassification)}:{kind:"error"}}function Se(t,e,n,r,i={}){return{errorType:t,errorDetail:e,failureOrigin:n,recoverability:r,...i}}function Sve(t){let e=t.toLowerCase();return/^\s*compilation error:/.test(e)?Se("execution_failed","compile_error","agent_request","code_fix",{validationStage:"plugin_handler"}):/^\s*result too large:/.test(e)?Se("execution_failed","result_too_large","agent_request","code_fix",{validationStage:"plugin_handler"}):/^\s*execution timed out after/.test(e)?Se("execution_failed","execution_timeout","agent_request","code_fix",{validationStage:"plugin_handler"}):/potentially dangerous infinite loop|blocked in sandbox|access to .* is blocked|forbidden|not allowed|cannot access/.test(e)?Se("execution_failed","blocked_source","roblox_policy","code_fix",{validationStage:"plugin_handler"}):null}function wve(t){let e=t.toLowerCase();return/startline and endline must be provided together/.test(e)||/startline must be a positive integer/.test(e)||/endline must be a positive integer/.test(e)||/endline must be >= startline/.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"schema"}):null}function e9(t){let e=t.toLowerCase();return/upstream_server_down/.test(e)?Se("bridge_error","upstream_down","bridge","wait_connection"):/^http [45]\d\d/.test(e)?Se("bridge_error","http_error","bridge","retry"):/duplicate request\s*id/.test(e)?Se("bridge_error","duplicate_request_id","bridge","code_fix"):/timeout/.test(e)?Se("command_timeout","timeout","bridge","retry"):/econnrefused|socket hang up|econnreset|epipe|network/.test(e)?Se("bridge_error","connection","bridge","wait_connection"):/abort/.test(e)?Se("command_timeout","aborted","bridge","retry"):/runtime error|traceback|attempt to/.test(e)?Se("plugin_runtime","runtime_error","plugin_runtime","code_fix"):/created instance, but failed to set \d+ propert/.test(e)?Se("execution_failed","property_apply_failed","agent_request","fix_params",{validationStage:"plugin_handler",partialSuccess:"true"}):/failed to set property/.test(e)?Se("execution_failed","property_apply_failed","agent_request","fix_params",{validationStage:"plugin_handler"}):/parent(?: instance)? not found/.test(e)?Se("execution_failed","parent_not_found","agent_request","fix_params",{validationStage:"plugin_handler"}):/(?:instance|path|root|source instance|ancestor instance) not found|target\s+(?:path\s+)?(?:['"`][^'"`]+['"`]\s+)?not found|not found in|no synced file found for instance/.test(e)?Se("execution_failed","not_found","user_project_state","fix_params",{validationStage:"plugin_handler"}):/is required|missing required/.test(e)?Se("execution_failed","missing_param","agent_request","fix_params",{validationStage:"schema"}):/invalid classname|invalid class/.test(e)?Se("execution_failed","invalid_class","agent_request","fix_params",{validationStage:"plugin_handler"}):/unknown action|unknown command/.test(e)?Se("execution_failed","unknown_action","agent_request","fix_params",{validationStage:"dispatcher"}):/failed to insert asset/.test(e)?Se("execution_failed","asset_error","roblox_policy","fix_params",{validationStage:"roblox_api"}):/failed to read property|property access denied/.test(e)?Se("execution_failed","property_error","agent_request","fix_params",{validationStage:"plugin_handler"}):/forbidden (?:path|parent path)|exceeds (?:total lines|max(?:imum)?(?: length)?)|is not (?:a|an) /.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"plugin_handler"}):/sync controller not available|project sync is not initialized|no active sync place|not found in sync cache/.test(e)?Se("execution_failed","sync_not_ready","user_project_state","wait_connection",{validationStage:"preflight"}):/cannot capture edit-mode screenshot while a playtest is active|play-mode screenshot capture is not supported/.test(e)?Se("execution_failed","unsupported_context","roblox_policy","no_retry",{validationStage:"preflight"}):/editableimage api is not enabled|allow mesh \/ image apis|allow http requests/.test(e)?Se("execution_failed","feature_disabled","roblox_policy","no_retry",{validationStage:"preflight"}):/must be|invalid|cannot/.test(e)?Se("execution_failed","validation","agent_request","fix_params",{validationStage:"plugin_handler"}):Se("execution_failed","other","unknown","unknown")}function du(t,e){if(t==="manage_scripts_get_source"){let r=wve(e);if(r)return r}if(t==="execute_luau"){let r=Sve(e);if(r)return r}let n=e9(e);return t==="execute_luau"&&n.errorDetail==="runtime_error"&&/^\s*runtime error:/i.test(e)?Se("execution_failed","runtime_error","agent_request","code_fix"):n}function t9(t){let n=(t instanceof Error?t.message:String(t)).toLowerCase();return/timeout/.test(n)?Se("command_timeout","timeout","bridge","retry"):/econnrefused|socket hang up|network|econnreset|epipe/.test(n)?Se("bridge_error","connection","bridge","wait_connection"):/eaddrinuse/.test(n)?Se("bridge_error","port_in_use","bridge","no_retry"):Se("exception","unexpected","server_exception","code_fix")}W_();import{randomBytes as Tve}from"node:crypto";var Ave=["manage_ui_create_tree","manage_ui_update","manage_ui_delete"],c9=["manage_ui_preview","manage_ui_check"],Ove=["game_genre","ui_role","style_family","layout_family","device_policy","safe_area_policy","existing_ui_strategy"];function SA(t){return t&&typeof t=="object"?t:void 0}function xA(t){return typeof t=="number"&&Number.isFinite(t)?t:0}function G_(t){let e=SA(t);if(!e)return;let n={};for(let r of Ove){let i=e[r];typeof i=="string"&&i.trim().length>0&&(n[r]=i)}return Object.keys(n).length>0?n:void 0}function _A(t){let e=G_(t.qualityPlanSummary);if(e)return e;let n=SA(t.contextSummary),r=G_(n?.qualityPlanSummary);if(r)return r;let i=G_(n?.qualityPlan);if(i)return i;let a=G_(n?.quality_plan);if(a)return a}function l9(t,e){return e?{...t??{},...e}:t}function $ve(t){return typeof t=="string"?{snapshotId:t}:t&&typeof t=="object"?{snapshotId:typeof t.snapshotId=="string"?t.snapshotId:null,...t.designCheckSummary!==void 0&&{designCheckSummary:t.designCheckSummary},...t.capturedAt!==void 0&&{capturedAt:t.capturedAt}}:{snapshotId:null}}function u9(t,e,n,r,i){if(!e)return;let a=xA(e.priority_high),o=xA(e.priority_medium),s=xA(e.priority_low),c=typeof e.total=="number"&&Number.isFinite(e.total)?e.total:a+o+s,l=n??(typeof e.target=="string"?e.target:void 0);return{source:t,...l!==void 0&&{targetPath:l},...typeof r=="string"&&{snapshotId:r},...i!==void 0&&{capturedAt:i},priority_high:a,priority_medium:o,priority_low:s,total:c}}function d9(t,e){if(!e)return t;if(!t)return e;let n=t.targetPath===e.targetPath?t.targetPath:void 0,r=t.snapshotId===e.snapshotId?t.snapshotId:void 0;return{source:e.source,...n!==void 0&&{targetPath:n},...r!==void 0&&{snapshotId:r},...e.capturedAt!==void 0&&{capturedAt:e.capturedAt},priority_high:t.priority_high+e.priority_high,priority_medium:t.priority_medium+e.priority_medium,priority_low:t.priority_low+e.priority_low,total:t.total+e.total}}function Dve(t){let e=SA(t);if(e)for(let n of["userMessage","intent","expectedBehavior"]){let r=e[n];if(typeof r=="string"&&r.trim().length>0)return r.trim().slice(0,80)}}function Nve(){return{source:"unavailable",priority_high:0,priority_medium:0,priority_low:0,total:0}}function p9(t){let e=t.now??Date.now,n=null,r=null,i=u=>`${u}_${e()}_${Tve(3).toString("hex")}`,a=()=>{r&&(clearTimeout(r),r=null)},o=()=>{a(),r=setTimeout(()=>{c("idle_timeout")},t.idleMs)},s=async u=>{try{return $ve(await t.capturePreview(u))}catch{return{snapshotId:null}}},c=async u=>{if(!n)return;a();let d=n;n=null;let p={},f;for(let h of d.affectedPaths)if(d.afterSnapshotsPathPolicy[h]==="skip")p[h]=null;else{let v=await s(h);p[h]=v.snapshotId,f=d9(f,u9("after_snapshot",v.designCheckSummary,h,v.snapshotId,v.capturedAt))}let m=f??d.latestDesignCheckSummary??Nve(),g={requestId:d.requestId,...d.contextId!==void 0&&{contextId:d.contextId},...d.label!==void 0&&{label:d.label},startedAt:d.startedAtIso,closedAt:new Date(e()).toISOString(),closeReason:u,ok:d.ok,affectedPaths:Array.from(d.affectedPaths).sort(),mutationCount:d.mutationCount,beforeSnapshots:d.beforeSnapshots,afterSnapshots:p,childMutationIds:d.childMutationIds,...d.qualityPlanSummary!==void 0&&{qualityPlanSummary:d.qualityPlanSummary},postChangeDesignCheckSummary:m};await a9(t.placeDir,g)},l=u=>({requestId:i("req"),contextId:u.contextId,label:Dve(u.contextSummary),startedAtIso:new Date(e()).toISOString(),startedAtMs:e(),affectedPaths:new Set,beforeSnapshots:{},afterSnapshotsPathPolicy:{},childMutationIds:[],mutationCount:0,ok:!0,qualityPlanSummary:_A(u),latestDesignCheckSummary:void 0,pendingMutation:void 0});return{async beforeMutation(u){if(c9.includes(u.command)){if(n){let p=i("mut");n.qualityPlanSummary=l9(n.qualityPlanSummary,_A(u)),n.pendingMutation={mutationId:p,startedMs:e(),args:u}}return}if(!Ave.includes(u.command))return;n&&n.contextId!==u.contextId?await c("context_change"):n&&a(),n||(n=l(u)),n.qualityPlanSummary=l9(n.qualityPlanSummary,_A(u)),u.targetPath&&!(u.targetPath in n.beforeSnapshots)&&(n.affectedPaths.add(u.targetPath),u.command==="manage_ui_create_tree"?n.beforeSnapshots[u.targetPath]=null:n.beforeSnapshots[u.targetPath]=(await s(u.targetPath)).snapshotId,u.command==="manage_ui_delete"?n.afterSnapshotsPathPolicy[u.targetPath]="skip":u.targetPath in n.afterSnapshotsPathPolicy||(n.afterSnapshotsPathPolicy[u.targetPath]="capture"));let d=i("mut");n.pendingMutation={mutationId:d,startedMs:e(),args:u}},async afterMutation(u){if(!n?.pendingMutation)return;let{mutationId:d,args:p}=n.pendingMutation,f={mutationId:d,requestId:n.requestId,ts:new Date(e()).toISOString(),command:p.command,origin:p.origin,...p.targetPath!==void 0&&{targetPath:p.targetPath},...p.briefId!==void 0&&{briefId:p.briefId},...u.diffSummary!==void 0&&{diffSummary:u.diffSummary},...u.changeDetails!==void 0&&{changeDetails:u.changeDetails},ok:u.ok,...u.error!==void 0&&{error:u.error},durationMs:u.durationMs};if(await o9(t.placeDir,f),n.pendingMutation=void 0,c9.includes(p.command)){n.latestDesignCheckSummary=d9(n.latestDesignCheckSummary,u9("check_results",u.designCheckSummary,p.targetPath,u.snapshotId,u.capturedAt));return}if(n.mutationCount++,n.childMutationIds.push(d),u.ok||(n.ok=!1),!n.contextId){await c("legacy_single");return}o()},async flushNow(){n&&await c("explicit")}}}var T9=100,gbe=12e4,hbe=15e3,A9=new Set(["manage_ui_create_tree","manage_ui_update","manage_ui_delete"]);function ybe(t,e){return`License required for internal command ${t}. ${e??"Activate Pro license to use this feature."}`}var vbe={Text:{category:"text",label:"\uD14D\uC2A4\uD2B8"},PlaceholderText:{category:"text",label:"\uD50C\uB808\uC774\uC2A4\uD640\uB354"},TextColor3:{category:"color",label:"\uAE00\uC790\uC0C9"},BackgroundColor3:{category:"color",label:"\uBC30\uACBD\uC0C9"},BorderColor3:{category:"color",label:"\uD14C\uB450\uB9AC\uC0C9"},ImageColor3:{category:"color",label:"\uC774\uBBF8\uC9C0\uC0C9"},Size:{category:"size",label:"\uC0AC\uC774\uC988"},TextSize:{category:"size",label:"\uAE00\uC790 \uD06C\uAE30"},Position:{category:"layout",label:"\uC704\uCE58"},AnchorPoint:{category:"layout",label:"\uC575\uCEE4"},Rotation:{category:"layout",label:"\uD68C\uC804"},LayoutOrder:{category:"layout",label:"\uB808\uC774\uC544\uC6C3 \uC21C\uC11C"},Visible:{category:"state",label:"\uD45C\uC2DC \uC0C1\uD0DC"},Active:{category:"state",label:"\uD65C\uC131 \uC0C1\uD0DC"},Interactable:{category:"state",label:"\uC0C1\uD638\uC791\uC6A9 \uC0C1\uD0DC"},Selectable:{category:"state",label:"\uC120\uD0DD \uAC00\uB2A5"},Enabled:{category:"state",label:"\uD65C\uC131\uD654"},Image:{category:"asset",label:"\uC774\uBBF8\uC9C0"},Texture:{category:"asset",label:"\uD14D\uC2A4\uCC98"},SoundId:{category:"asset",label:"\uC0AC\uC6B4\uB4DC"}},bbe={text:"\uD14D\uC2A4\uD2B8",color:"\uCEEC\uB7EC",size:"\uC0AC\uC774\uC988",layout:"\uB808\uC774\uC544\uC6C3",state:"\uC0C1\uD0DC",asset:"\uC5D0\uC14B",property:"\uC18D\uC131"},xbe=Object.entries($s).reduce((t,[e,n])=>{for(let r of n.validActions)t[`${e}_${r}`]=e;return t},{});function I9(t){return{toolName:xbe[t]||t,commandName:t}}function C9(t,e){if(typeof t.contextId=="string"||!e||typeof e!="object")return t;let n=e.contextId;return typeof n=="string"?{...t,contextId:n}:t}function K_(t,e){if(t!=="manage_sync_status_current_place")return e;let{placeId:n,...r}=e;return r}function _be(t,e){let n=e.routing;return{requestId:t,success:!1,error:e.message,errorCode:e.code,routing:n,data:{routing:n}}}async function Sbe(t,e){let n=t.syncController;if(!n)return null;try{let r=e.placeId,i=n.getDefaultRuntimePlaceId(),a=null;if(typeof r=="number"&&Number.isFinite(r))a=r;else if(typeof r=="string"&&r.trim().length>0){let s=Number.parseInt(r,10);Number.isFinite(s)&&(a=s)}if(a===null&&(a=i),a===null||!Number.isFinite(a))return null;let o=a===i?n.getDefaultRuntimePlaceName():null;return typeof o=="string"&&o.length>0?await n.config.resolvePlaceRoot(a,o):n.config.getPlaceRoot(a)}catch{return null}}function wbe(t){let e=t.tree;if(!e||typeof e!="object")return;let n=e,r=typeof n.name=="string"&&n.name.length>0?n.name:void 0;return r?`${typeof n.parent=="string"&&n.parent.length>0?n.parent:"StarterGui"}.${r}`:void 0}function Ibe(t,e){let n=e.targetPath;if(typeof n=="string"&&n.length>0)return n;if(t==="manage_ui_create_tree")return wbe(e)}function Cbe(t){let e=vbe[t];if(e)return e;let n=t.toLowerCase();return n.includes("color")?{category:"color",label:"\uC0C9\uC0C1"}:t==="Size"||n.endsWith("size")||n.includes("scale")?{category:"size",label:"\uC0AC\uC774\uC988"}:n.includes("position")||n.includes("anchor")||n.includes("rotation")||n.includes("layout")?{category:"layout",label:"\uB808\uC774\uC544\uC6C3"}:n.includes("visible")||n.includes("active")||n.includes("enabled")||n.includes("selectable")||n.includes("interactable")?{category:"state",label:"\uC0C1\uD0DC"}:n.includes("image")||n.includes("texture")||n.includes("sound")||n.includes("asset")?{category:"asset",label:"\uC5D0\uC14B"}:n.includes("text")||n.includes("placeholder")?{category:"text",label:"\uD14D\uC2A4\uD2B8"}:{category:"property",label:t}}function P9(t,e){return Object.prototype.hasOwnProperty.call(t,e)}function Pbe(t){if(!t||typeof t!="object")return new Map;let e=t,n=e.changed_properties??e.changedProperties;if(!Array.isArray(n))return new Map;let r=new Map;for(let i of n){if(!i||typeof i!="object")continue;let a=i,o=a.property;if(typeof o!="string"||o.length===0)continue;let s=P9(a,"before"),c=P9(a,"after");r.set(o,{...s&&{before:a.before},...c&&{after:a.after},hasBefore:s,hasAfter:c})}return r}function O9(t,e){let r=t.changes?.properties;if(!r||typeof r!="object")return;let i=Pbe(e),a=Object.entries(r).map(([o,s])=>{let c=Cbe(o),l=i.get(o),u={property:o,category:c.category,label:c.label,after:l?.hasAfter?l.after:s};return l?.hasBefore&&(u.before=l.before),u});return a.length>0?a:void 0}function $9(t){if(!t||t.length===0)return;let e=new Map;for(let i of t)e.set(i.category,(e.get(i.category)??0)+1);let r=["text","color","size","layout","state","asset","property"].map(i=>{let a=e.get(i)??0;return a>0?`${bbe[i]} ${a}\uAC1C`:null}).filter(i=>i!==null);return r.length>0?`${r.join(", ")} \uBCC0\uACBD`:void 0}function k9(t,e){if(t==="manage_ui_update"){let n=e.changes,r=$9(O9(e));if(r)return r;let i=n?.properties?Object.keys(n.properties).length:0,a=Array.isArray(n?.addChildren)?n.addChildren.length:0,o=Array.isArray(n?.removeChildren)?n.removeChildren.length:0;return`${i} props, +${a}, -${o}`}if(t==="manage_ui_create_tree")return"tree \uC0DD\uC131";if(t==="manage_ui_delete")return"\uC81C\uAC70\uB428"}function ym(t){return t&&typeof t=="object"?t:void 0}function J_(t,e){let n=t[e];return typeof n=="number"&&Number.isFinite(n)?n:0}function D9(t){let e=ym(t),n=ym(e?.design_check_summary);if(n)return{priority_high:J_(n,"priority_high"),priority_medium:J_(n,"priority_medium"),priority_low:J_(n,"priority_low"),total:J_(n,"total"),...typeof n.scope=="string"&&{scope:n.scope},...typeof n.target=="string"&&{target:n.target}}}function N9(t){let n=ym(t)?.snapshot_id;return typeof n=="string"?n:null}function E9(t){if(typeof t=="string"&&t.trim().length>0)return t;if(typeof t=="number"&&Number.isFinite(t)){let e=t<1e10?t*1e3:t;return new Date(e).toISOString()}}function j9(t){let e=ym(t),n=ym(e?.meta);return E9(n?.captured_at)??E9(n?.evaluated_at)}function kbe(t,e){let n=t.uiStudioRecorders.get(e);if(n)return n;let r=p9({placeDir:e,idleMs:hbe,capturePreview:async i=>{try{let a=await fr(t,"manage_ui_preview",{targetPath:i},X_());if(!a.success||!a.data||typeof a.data!="object")return null;let o=D9(a.data),s=j9(a.data);return{snapshotId:N9(a.data),...o!==void 0&&{designCheckSummary:o},...s!==void 0&&{capturedAt:s}}}catch{return null}}});return t.uiStudioRecorders.set(e,r),r}async function Ebe(t,e,n){if(!A9.has(e))return null;let r=await Sbe(t,n);if(!r)return null;let i=kbe(t,r),a=e,o=typeof n.contextId=="string"?n.contextId:void 0,s=n.contextSummary,c=s!==void 0&&typeof s=="object"?s:void 0,l=Ibe(a,n),u=typeof n.briefId=="string"?n.briefId:void 0,d={command:a,...o!==void 0&&{contextId:o},...c!==void 0&&{contextSummary:c},...l!==void 0&&{targetPath:l},...u!==void 0&&{briefId:u},origin:n.__origin==="dashboard"?"dashboard":"ai"};try{return await i.beforeMutation(d),{recorder:i,command:a,params:n,startedAt:Date.now()}}catch(p){return y.debug("UI Studio recorder beforeMutation \uC2E4\uD328 (\uBB34\uC2DC)",{error:p}),null}}async function R9(t,e){if(t)try{let n=t.command==="manage_ui_update"?O9(t.params,e.data):void 0,r=t.command==="manage_ui_update"?$9(n)??k9(t.command,t.params):k9(t.command,t.params),i=D9(e.data),a=N9(e.data),o=j9(e.data);await t.recorder.afterMutation({ok:e.success,durationMs:Date.now()-t.startedAt,...r!==void 0&&{diffSummary:r},...n!==void 0&&{changeDetails:n},...e.error!==void 0&&{error:e.error},...i!==void 0&&{designCheckSummary:i},...a!==null&&{snapshotId:a},...o!==void 0&&{capturedAt:o}})}catch(n){y.debug("UI Studio recorder afterMutation \uC2E4\uD328 (\uBB34\uC2DC)",{error:n})}}async function Y_(t,e,n,r,i,a){if(!t.historyManager)return;let o=!i.success&&i.error?du(n,i.error):void 0,s=uu({resultSuccess:i.success,resultData:i.data,resultError:i.error,tier:Gn(n),...o?{failureClassification:o}:{}});if(i.success){let u=s.kind==="success_fallback"&&i.data&&typeof i.data=="object"?{...i.data,outcomeStatus:"fallback",requestedCommand:n,executedCommand:s.fallbackCommand,...s.alternatives?{alternatives:s.alternatives}:{}}:i.data,d=K_(n,r);i.routing?await t.historyManager.recordSuccess(e,d,u,a,n,void 0,i.routing):await t.historyManager.recordSuccess(e,d,u,a,n);return}if(s.kind==="blocked_unsupported"){await t.historyManager.recordBlockedOutcome(e,K_(n,r),i.error||"Pro action blocked in Basic mode","blocked_unsupported",{executionTimeMs:a,command:n,...i.routing?{routing:i.routing}:{}});return}if(s.kind==="blocked_fallback_failed"){await t.historyManager.recordBlockedOutcome(e,K_(n,r),i.error||"Pro action blocked in Basic mode","blocked_fallback_failed",{executionTimeMs:a,command:n,...s.fallbackCommand?{fallbackCommand:s.fallbackCommand}:{},...s.blockedDetail?{blockedDetail:s.blockedDetail}:{},...i.routing?{routing:i.routing}:{}});return}let c=s.kind==="warning"?t.historyManager.recordWarning.bind(t.historyManager):t.historyManager.recordFailure.bind(t.historyManager),l=K_(n,r);i.routing?await c(e,l,i.error||"Unknown error",a,i.errorCode??o?.errorType.toUpperCase(),n,void 0,i.routing):await c(e,l,i.error||"Unknown error",a,i.errorCode??o?.errorType.toUpperCase(),n)}function PA(t,e,n){let r=t.pendingCommands.get(e)||[];r.length>=T9&&r.shift(),r.push(n),t.pendingCommands.set(e,r)}function Rbe(t,e){t.globalPendingCommands.length>=T9&&t.globalPendingCommands.shift(),t.globalPendingCommands.push(e)}function M9(t,e,n){let r=X_(),i={requestId:r,command:e.command,params:e.params,timestamp:Date.now(),queueTimeoutMs:e.queueTimeoutMs,ackedTimeoutMs:e.ackedTimeoutMs,state:kn.QUEUED,targetClientId:n,resolve:()=>{},reject:a=>{y.debug("Auxiliary playtest stop command ended without awaited response",{requestId:r,targetClientId:n,error:a.message})},timeoutId:null};return t.commandQueue.set(r,i),i.timeoutId=setTimeout(()=>{qx(t,i,i.queueTimeoutMs)},i.queueTimeoutMs),{event:"command",id:r,data:{command:i.command,requestId:r,params:i.params}}}function Tbe(t,e,n,r){if(!Qf(e.data.command))return;let i=t.commandQueue.get(e.data.requestId);if(!i)return;L9(t,i);let a=n.filter(o=>o.clientId!==r);for(let o of a){let s=M9(t,i,o.clientId);PA(t,o.clientId,s)}a.length>0&&y.info("Fan-out playtest stop command to active plugin clients",{requestId:e.data.requestId,primaryClientId:r,auxiliaryClientIds:a.map(o=>o.clientId)})}function L9(t,e,n){for(let r of f5)setTimeout(()=>{let a=n?[...new Set(n)]:[...new Set($n(t).map(o=>o.clientId))];for(let o of a){if(!t.pluginClients.get(o))continue;let c=M9(t,e,o);PA(t,o,c)}y.info("Retry playtest stop command to active plugin clients",{sourceRequestId:e.requestId,delayMs:r,targetClientIds:a}),Hl(t)},r).unref?.()}function z9(t){return t==="clientId"||t==="targetAlias"||t==="placeId"}function Abe(t,e,n){if(!n||!Qf(e.data.command))return!1;let r=t.commandQueue.get(e.data.requestId)?.routing?.selectionMode;return!z9(r)}function Obe(t,e,n){y.debug("Broadcasting command",{command:e.data.command,requestId:e.data.requestId,targetClientId:n||"all",activeWebsocketClients:$n(t).length});let r=n;if(n){PA(t,n,e);let i=t.commandQueue.get(e.data.requestId),a=i?.routing?.selectionMode;if(i&&Qf(e.data.command)&&z9(a))L9(t,i,[n]);else if(Abe(t,e,n)){let o=$n(t).sort((s,c)=>c.lastSeen-s.lastSeen);Tbe(t,e,o,n),r=void 0}}else Rbe(t,e);Hl(t,r)}async function F9(t,e,n){let r=Date.now(),i="",a={};try{let o=e.body;i=o.command??"",a=o.params||{};let s=o.requestId;if(o.instanceId||(t.serverLastCommandAt=Date.now()),o.instanceId){let m=t.mcpInstances.get(o.instanceId);m&&(m.lastCommandAt=Date.now(),m.lastSeen=m.lastCommandAt)}let c=I9(i),l=typeof o.timeout=="number"&&Number.isFinite(o.timeout)&&o.timeout>0?{timeout:o.timeout}:void 0,u=o.instanceId?t.mcpInstances.get(o.instanceId)?.sessionId??t.sessionId:t.sessionId;if(!i){n.status(400).json({error:"Missing command"});return}if(y.debug("Received execute request",{command:i,requestId:s}),i==="manage_camera_play_screenshot"){let m="manage_camera.play_screenshot is not supported. Screenshot capture is available only in Edit mode via manage_camera.screenshot.",g=Date.now()-r;t.historyManager&&await t.historyManager.recordFailure("manage_camera",a,m,g,"UNSUPPORTED_COMMAND",i),n.json({requestId:s,success:!1,error:m});return}if(i==="get_cached_selection"){let m=a.maxAge,g=Xf(t,m!==void 0?m:3e4),h=Date.now()-r;if(!g){let _={requestId:s,success:!0,data:{cached:!1,message:"No cached selection data available. The plugin may not be connected or no selection changes have occurred yet."}};t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,_.data,h,c.commandName),n.json(_);return}let v=Date.now()-g.timestamp,x={cached:!0,selection:g.selection,count:g.count,timestamp:g.timestamp,age:v};t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,x,h,c.commandName),n.json({requestId:s,success:!0,data:x});return}if(i==="get_connection_info"){let m=await $_(t),g=Date.now()-r;t.historyManager&&await t.historyManager.recordSuccess(c.toolName,a,m,g,c.commandName),n.json({requestId:s,success:!0,data:m});return}if(N_(i)==="internal"){if(!t.internalCommandExecutor){n.status(503).json({requestId:s,success:!1,error:`Internal command executor is not initialized for command: ${i}`});return}if(Gn(i)==="pro"){if(!t.licenseState){n.status(503).json({requestId:s,success:!1,error:`License state manager is not initialized for internal command: ${i}`});return}let x=await t.licenseState.evaluateProAccess();if(!x.allowed){let _=ybe(i,x.reason),P=Date.now()-r;t.historyManager&&await Y_(t,c.toolName,c.commandName,a,{success:!1,error:_},P),n.json({requestId:s,success:!1,error:_});return}}let m={...a,__sessionId:u},g=await t.internalCommandExecutor(i,m),h=Date.now()-r,v=C9(m,g.data);t.historyManager&&await Y_(t,c.toolName,c.commandName,v,{success:g.success,data:g.data,error:g.error||"Internal command failed"},h),n.json({requestId:s,...g});return}let d=await fr(t,i,a,s,l),p=Date.now()-r,f={...C9(a,d.data),__sessionId:u};t.historyManager&&await Y_(t,c.toolName,c.commandName,f,d,p),n.json(d)}catch(o){let s=Date.now()-r,c=Wn(o);if(t.historyManager&&i){let l=I9(i);await t.historyManager.recordFailure(l.toolName,a,c,s,"EXCEPTION",l.commandName)}y.error("Execute request failed",o),n.status(500).json({success:!1,error:c})}}async function U9(t,e,n){let r=Date.now(),i=e.body,a=i.action;if(!a||typeof a!="string"){n.status(400).json({success:!1,error:"Missing required field: action"});return}if(!new Set(["get","set","get_all","set_multiple","get_attr","set_attr","get_all_attrs","delete_attr","add_tag","remove_tag","check_tag","get_tags","get_tagged"]).has(a)){n.status(400).json({success:!1,error:`Unsupported action: ${a}`});return}let s=`manage_properties_${a}`,c=X_(),{action:l,...u}=i;try{t.serverLastCommandAt=Date.now();let d=await fr(t,s,u,c),p=Date.now()-r;t.historyManager&&await Y_(t,"manage_properties",s,u,d,p),n.json(d)}catch(d){let p=Date.now()-r,f=Wn(d);t.historyManager&&await t.historyManager.recordFailure("manage_properties",u,f,p,"EXCEPTION",s),y.error("/api/properties \uC694\uCCAD \uCC98\uB9AC \uC2E4\uD328",d),n.status(500).json({success:!1,error:f})}}async function fr(t,e,n,r,i){if(y.debug("Executing command locally",{command:e,requestId:r}),$8(t,r)){let d=`Duplicate requestId '${r}' for command '${e}'. Generate a unique requestId for each command.`;return y.warn("Duplicate execute request rejected",{command:e,requestId:r}),{requestId:r,success:!1,error:d}}let a;try{a=D_(t,$n(t),n,e)}catch(d){if(d instanceof gn)return y.warn("Command target selection failed",{command:e,requestId:r,errorCode:d.code,routing:d.routing}),_be(r,d);throw d}let o=A9.has(e)?await Ebe(t,e,n):null,s=t.config.requestTimeout,c=i?.timeout??Math.max(t.config.requestTimeout,gbe),l=dA.has(e)?await Y5({ctx:t,command:e,params:n}):n,u=new Promise((d,p)=>{let f=Date.now(),m={requestId:r,command:e,params:l,timestamp:f,queueTimeoutMs:s,ackedTimeoutMs:c,state:kn.QUEUED,...a.targetClientId?{targetClientId:a.targetClientId}:{},routing:a.routing,resolve:d,reject:p,timeoutId:null};t.commandQueue.set(r,m),Mx(t,a.targetClientId,f),m.timeoutId=setTimeout(()=>{qx(t,m,s)},s)});return Obe(t,{event:"command",id:X_(),data:{command:e,requestId:r,params:l}},a.targetClientId),u.then(async d=>{let p=d;if(e==="manage_ui_preview"&&d.success&&d.data)try{let{processPreviewResult:f,resolvePreviewPlaceDirFromCtx:m}=await Promise.resolve().then(()=>(CA(),IA)),g=await m(t,n),h=await f("manage_ui_preview",d.data,g);p={...d,data:h.data,...h.mcpContent?{mcpContent:h.mcpContent}:{}}}catch(f){y.warn("preview post-processing failed",{error:f instanceof Error?f.message:String(f)})}if(e==="manage_ui_check"&&d.success&&d.data&&n.includeVisualAnalysis===!0)try{let{resolvePreviewPlaceDirFromCtx:f}=await Promise.resolve().then(()=>(CA(),IA)),{processCheckResult:m}=await Promise.resolve().then(()=>(w9(),S9)),g=await f(t,n),h=await m("manage_ui_check",d.data,g,n);p={...p,data:h.data}}catch(f){y.warn("check visual post-processing failed",{error:f instanceof Error?f.message:String(f)})}return pA.has(e)?p=await X5({ctx:t,command:e,params:n,result:p}):e===uA&&(p=await Q5({ctx:t,params:n,result:p})),p}).then(async d=>(await R9(o,{success:d.success,...d.data!==void 0&&{data:d.data},...d.error!==void 0&&{error:d.error}}),d),async d=>{throw await R9(o,{success:!1,error:Wn(d)}),d})}ae();Fi();function Q_(t,e){let n={};e.provider!==void 0&&(n.provider=e.provider),e.tier!==void 0&&(n.tier=e.tier),e.status!==void 0&&(n.status=e.status),e.canUsePro!==void 0&&(n.canUsePro=e.canUsePro),e.cleared===!0&&(n.cleared=!0),ot(t,"license",n)}function yi(t,e,n,r){t.status(e).json({success:!1,error:{code:n,message:r}})}function $be(t){if(typeof t!="string")return;let e=t.trim().toLowerCase();return e.length>0?e:void 0}function eS(t,e){if(e==="plugin")return t;let n={...t};return delete n.sessionToken,n}function vm(t,e,n,r){let i=$be(r??e.query.provider)??"auto";return t.licenseState?.supportsProvider(i)===!1?(yi(n,400,"LICENSE_PROVIDER_UNSUPPORTED",`provider "${i}" is not supported`),null):i}function bm(t,e){return t.licenseState?!0:(yi(e,503,"LICENSE_NOT_INITIALIZED","License system is not initialized"),!1)}function Dbe(t){if(!t||typeof t!="object")return!1;let e=t;return(e.canUsePro===!0||e.canUsePro===!1)&&typeof e.status=="string"&&typeof e.checkedAt=="number"}function xm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=typeof i?.licenseKey=="string"?i.licenseKey:"";if(!a.trim()){yi(n,400,"LICENSE_KEY_REQUIRED","licenseKey is required");return}let o=vm(t,e,n,i?.provider);if(!o)return;let s=typeof i?.pluginClientId=="string"?i.pluginClientId:typeof e.query.clientId=="string"?e.query.clientId:void 0,c=typeof i?.deviceId=="string"?i.deviceId:void 0,l={licenseKey:a,provider:o,clientType:r};s&&(l.pluginClientId=s),c&&(l.deviceId=c),t.licenseState.activateGateway(l).then(u=>{t.analyticsManager?.setTier(u.canUsePro?"pro":"basic"),Q_(t,{provider:u.provider,tier:u.canUsePro?"pro":"basic",status:u.status,canUsePro:u.canUsePro}),n.json(eS(u,r))}).catch(u=>{y.warn("License activate failed",{error:u instanceof Error?u.message:"unknown_error"}),yi(n,502,"LICENSE_ACTIVATE_FAILED",u instanceof Error?u.message:"License activation failed")})}function _m(t,e,n,r="plugin"){if(!bm(t,n))return;let i=vm(t,e,n);if(i)try{let a=t.licenseState.getStatus(i);t.analyticsManager?.setTier(a.canUsePro?"pro":"basic"),n.json(eS(a,r))}catch(a){y.warn("License status check failed",{error:a instanceof Error?a.message:"unknown_error"}),yi(n,502,"LICENSE_STATUS_FAILED",a instanceof Error?a.message:"License status check failed")}}function Sm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=vm(t,e,n,i?.provider);if(!a)return;let o={provider:a,clientType:r};r==="plugin"&&typeof i?.sessionToken=="string"&&i.sessionToken.trim()&&(o.sessionToken=i.sessionToken.trim()),typeof i?.pluginClientId=="string"&&(o.pluginClientId=i.pluginClientId),typeof i?.deviceId=="string"&&(o.deviceId=i.deviceId),t.licenseState.refreshGateway(o).then(s=>{t.analyticsManager?.setTier(s.canUsePro?"pro":"basic"),Q_(t,{provider:s.provider,tier:s.canUsePro?"pro":"basic",status:s.status,canUsePro:s.canUsePro}),n.json(eS(s,r))}).catch(s=>{y.warn("License refresh failed",{error:s instanceof Error?s.message:"unknown_error"}),yi(n,502,"LICENSE_REFRESH_FAILED",s instanceof Error?s.message:"License refresh failed")})}function wm(t,e,n,r="plugin"){if(!bm(t,n))return;let i=e.body,a=vm(t,e,n,i?.provider);a&&t.licenseState.resetGateway({provider:a,clientType:r}).then(o=>{t.analyticsManager?.setTier("basic"),Q_(t,{provider:o.provider,tier:"basic",status:o.status,canUsePro:o.canUsePro,cleared:!0}),n.json(eS(o,r))}).catch(o=>{y.warn("License reset failed",{error:o instanceof Error?o.message:"unknown_error"}),yi(n,502,"LICENSE_RESET_FAILED",o instanceof Error?o.message:"License reset failed")})}function kA(t,e,n){if(!bm(t,n))return;let r=e.body,i=vm(t,e,n,r?.provider);if(!i)return;if(r?.clientType!=="plugin"){yi(n,400,"LICENSE_CLIENT_TYPE_INVALID","clientType must be plugin");return}let a=typeof r?.sessionToken=="string"&&r.sessionToken.trim()?r.sessionToken.trim():void 0,o=Dbe(r?.snapshot)?r.snapshot:void 0;if(!o&&!a){yi(n,400,"LICENSE_BOOTSTRAP_REQUIRED","snapshot or sessionToken is required");return}let s={provider:i,clientType:"plugin"};o&&(s.snapshot=o),a&&(s.sessionToken=a),t.licenseState.bootstrap(s).then(c=>{t.analyticsManager?.setTier(c.canUsePro?"pro":"basic"),Q_(t,{provider:c.provider,tier:c.canUsePro?"pro":"basic",status:c.status,canUsePro:c.canUsePro}),n.json({ok:!0})}).catch(c=>{y.warn("License bootstrap failed",{error:c instanceof Error?c.message:"unknown_error"}),yi(n,502,"LICENSE_BOOTSTRAP_FAILED",c instanceof Error?c.message:"License bootstrap failed")})}function q9(t){t.app.post("/license/bootstrap",(e,n)=>kA(t,e,n)),t.app.post("/license/activate",(e,n)=>xm(t,e,n,"plugin")),t.app.post("/license/refresh",(e,n)=>Sm(t,e,n,"plugin")),t.app.post("/license/reset",(e,n)=>wm(t,e,n,"plugin")),t.app.get("/license/status",(e,n)=>_m(t,e,n,"plugin"))}vt();ae();import{promises as tS}from"fs";import EA from"path";function Nbe(t){let e=t.config.appDataDir??lt();return EA.join(e,"observability","logs")}async function hu(t,e,n){let r=e.query.clientId;if(r&&t.pluginClients.has(r)){let i=t.pluginClients.get(r);i.lastSeen=Date.now()}try{let i=e.body;if(!i||!Array.isArray(i.logs)){y.warn("Invalid logs request",{body:i}),n.status(400).json({error:"Invalid request body"});return}let a=Nbe(t);await tS.mkdir(a,{recursive:!0});let c=`plugin-${new Date().toISOString().split("T")[0]}.log`,l=EA.join(a,c),u=EA.join(a,"current.log"),d=i.logs.map(p=>`[${new Date(p.timestamp*1e3).toISOString().replace("T"," ").substring(0,19)}] [${p.level}] ${p.message}`).join(`
|
|
530
530
|
`)+`
|
|
531
531
|
`;await tS.appendFile(l,d,"utf-8");try{let p="";try{p=await tS.readFile(u,"utf-8")}catch{}let m=(p+d).split(`
|
|
532
532
|
`).slice(-500).join(`
|