@volter/supercode-teams 0.2.42 → 0.2.43
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/connector/index.mjs +32 -4
- package/package.json +1 -1
package/connector/index.mjs
CHANGED
|
@@ -401,20 +401,48 @@ export class TeamsConnector {
|
|
|
401
401
|
this.save();
|
|
402
402
|
}
|
|
403
403
|
capture(options) {
|
|
404
|
+
if(!options.preloaded&&this.largeSession(options))return Promise.resolve(this.captureLarge(options));
|
|
404
405
|
const work=this.work.then(()=>this.captureSerial(options)).then(receipt=>{this.clearSessionProblem(options.harness,options.nativeSessionId);return receipt;});
|
|
405
406
|
this.work=work.catch(()=>{});
|
|
406
407
|
return work;
|
|
407
408
|
}
|
|
408
|
-
|
|
409
|
+
largeSession({locator}){
|
|
410
|
+
try{return locator?.storage?.kind==='file'&&statSync(realpathSync(locator.storage.path)).size>=LARGE_CAPTURE_BYTES;}catch{return false;}
|
|
411
|
+
}
|
|
412
|
+
// A large transcript's load takes seconds to minutes. It runs in a lane of its own, outside the serial capture
|
|
413
|
+
// queue, so no small session's capture waits behind it; only the capture of what it loaded joins the queue.
|
|
414
|
+
captureLarge(options){
|
|
415
|
+
(this.largeQueue??=new Map()).set(`${options.harness}:${options.nativeSessionId}`,options);
|
|
416
|
+
if(!this.largeLane)this.largeLane=this.runLargeLane().finally(()=>{this.largeLane=null;});
|
|
417
|
+
return null;
|
|
418
|
+
}
|
|
419
|
+
async runLargeLane(){
|
|
420
|
+
while(this.largeQueue.size&&!this.abort.signal.aborted){
|
|
421
|
+
const [key,options]=this.largeQueue.entries().next().value;this.largeQueue.delete(key);
|
|
422
|
+
try{
|
|
423
|
+
const artifactBefore=statSync(realpathSync(options.locator.storage.path));
|
|
424
|
+
this.largeCaptures??=new Map();const last=this.largeCaptures.get(key);
|
|
425
|
+
if(last!=null&&this.clock.nowMs()-last<LARGE_CAPTURE_EVERY_MS)continue;
|
|
426
|
+
this.largeCaptures.set(key,this.clock.nowMs());
|
|
427
|
+
const loaded=await this.core.session(options.locator).load({timeoutMs:Math.max(30000,Math.ceil(artifactBefore.size/(1024*1024))*1000)});
|
|
428
|
+
await this.capture({...options,preloaded:{loaded,artifactBefore}});
|
|
429
|
+
}catch(error){
|
|
430
|
+
if(this.abort.signal.aborted)return;
|
|
431
|
+
this.noteSessionProblem(options,error);
|
|
432
|
+
process.stderr.write(`supercode teams: ${options.harness} session ${options.nativeSessionId} not synced: ${error.message}\n`);
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
}
|
|
436
|
+
async captureSerial({locator,descriptor=null,harness,nativeSessionId,visibility='restricted',ruleId=null,ruleRevision=null,coverage={completeness:'complete',reasons:[],missing:[]},backfill='all',rootPath=null,configuration=null,stamp,preloaded=null}) {
|
|
409
437
|
if(this.state.outbox.length)await this.flushSerial();
|
|
410
438
|
// Discovery hands each session the configuration its beat fetched; a follow event fetches its own.
|
|
411
439
|
if(stamp===undefined)stamp=this.sessionStamp({locator,descriptor});
|
|
412
440
|
if(!configuration)configuration=await this.configuration();const rule=configuration.rules.find(item=>item.id===ruleId&&item.revision===ruleRevision&&item.state==='active');if(!rule)throw Object.assign(new Error('sync rule is absent, inactive, or stale'),{code:'forbidden'});visibility=rule.visibility;
|
|
413
441
|
const artifactSource=locator?.storage?.kind==='file'&&existsSync(locator.storage.path)?realpathSync(locator.storage.path):null;
|
|
414
|
-
const artifactBefore=artifactSource?statSync(artifactSource):null;
|
|
442
|
+
const artifactBefore=preloaded?preloaded.artifactBefore:artifactSource?statSync(artifactSource):null;
|
|
415
443
|
const large=(artifactBefore?.size??0)>=LARGE_CAPTURE_BYTES,sessionKey=`${harness}:${nativeSessionId}`;
|
|
416
|
-
if(large){this.largeCaptures??=new Map();const last=this.largeCaptures.get(sessionKey);if(last!=null&&this.clock.nowMs()-last<LARGE_CAPTURE_EVERY_MS)return null;this.largeCaptures.set(sessionKey,this.clock.nowMs());}
|
|
417
|
-
const loaded=await this.core.session(locator).load(large?{timeoutMs:Math.max(30000,Math.ceil(artifactBefore.size/(1024*1024))*1000)}:undefined),configuredBackfill=rule.backfill??backfill??'all',backfillPolicy=typeof configuredBackfill==='string'?{mode:configuredBackfill,since:null}:configuredBackfill;
|
|
444
|
+
if(large&&!preloaded){this.largeCaptures??=new Map();const last=this.largeCaptures.get(sessionKey);if(last!=null&&this.clock.nowMs()-last<LARGE_CAPTURE_EVERY_MS)return null;this.largeCaptures.set(sessionKey,this.clock.nowMs());}
|
|
445
|
+
const loaded=preloaded?preloaded.loaded:await this.core.session(locator).load(large?{timeoutMs:Math.max(30000,Math.ceil(artifactBefore.size/(1024*1024))*1000)}:undefined),configuredBackfill=rule.backfill??backfill??'all',backfillPolicy=typeof configuredBackfill==='string'?{mode:configuredBackfill,since:null}:configuredBackfill;
|
|
418
446
|
const key=`${harness}:${nativeSessionId}`,previous=this.state.origins[key]??null;
|
|
419
447
|
let messages=(loaded.messages??loaded.turns??[]).map((entry,index)=>{const value=entry.value??Object.fromEntries(Object.entries(entry).filter(([key])=>!['id','native_key','recorded_at','timestamp'].includes(key)));return{native_key:entry.id??entry.native_key??String(index),recorded_at:recordedAt(entry),value};});
|
|
420
448
|
// A session published without its native bundle is captured again, with the same messages, once the bundle can be built.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@volter/supercode-teams",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.43",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "A machine daemon serving this machine's doors, and a local or remote Teams server for shared session discovery, OpenTelemetry ingestion and access to enrolled machines.",
|
|
6
6
|
"license": "MIT",
|