@crowdedkingdoms/crowdyjs 15.9.0-test.1 → 15.10.0-dev.1

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/MIGRATION.md CHANGED
@@ -1,3 +1,20 @@
1
+ # CrowdyJS v15.10 — portal GitHub guard, Agent session resume
2
+
3
+ **Nothing removed.** `15.10.0` (2026-09-09). No ck-api version dependency.
4
+
5
+ - `portal.completeEntry(search?)` returns `null` without calling the API when
6
+ the query has `github`, `installation_id`, or `setup_action`. A GitHub App
7
+ install callback that lands on a game origin no longer overwrites the play
8
+ token. Plain `?code=&state=` from hosted sign-in is unchanged.
9
+ - `CrowdyStudioAgentController.initialize()` lists sessions and reopens the
10
+ remembered / most recent resumable session for the same app + project before
11
+ calling `createSession`. Pass `sessionMemory` to control where the last
12
+ session id is kept (defaults to `localStorage`). Closed or revoked sessions
13
+ are never resumed. New exports: `pickResumableAgentSession`,
14
+ `agentSessionMemoryKey`, `StudioSessionMemory`.
15
+ - Internal: agent error redaction and two path/slug helpers are linear scans
16
+ with identical matches.
17
+
1
18
  # CrowdyJS v15.9 — nearbyGrids, player_joined, bindPolicyJson
2
19
 
3
20
  **Nothing removed.** `15.9.0` (2026-09-10). Tracks ck-api `v1.93.0`.
@@ -1 +1 @@
1
- {"version":3,"file":"bootstrap-rediscover.d.ts","sourceRoot":"","sources":["../src/bootstrap-rediscover.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAMH,MAAM,WAAW,0BAA0B;IACzC;;;;;OAKG;IACH,YAAY,EAAE,MAAM,CAAC;IACrB,uEAAuE;IACvE,QAAQ,EAAE,MAAM,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC;IAC1C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IACzB,MAAM,CAAC,EAAE;QAAE,IAAI,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAA;KAAE,CAAC;CAC3C;AAOD,wBAAgB,yBAAyB,CACvC,OAAO,EAAE,0BAA0B,GAClC,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI,KAAK,OAAO,CAAC;IACnC,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CACvB,GAAG,IAAI,CAAC,CAgER"}
1
+ {"version":3,"file":"bootstrap-rediscover.d.ts","sourceRoot":"","sources":["../src/bootstrap-rediscover.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAMH,MAAM,WAAW,0BAA0B;IACzC;;;;;OAKG;IACH,YAAY,EAAE,MAAM,CAAC;IACrB,uEAAuE;IACvE,QAAQ,EAAE,MAAM,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC;IAC1C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IACzB,MAAM,CAAC,EAAE;QAAE,IAAI,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAA;KAAE,CAAC;CAC3C;AAcD,wBAAgB,yBAAyB,CACvC,OAAO,EAAE,0BAA0B,GAClC,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI,KAAK,OAAO,CAAC;IACnC,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CACvB,GAAG,IAAI,CAAC,CAgER"}
@@ -15,9 +15,16 @@ const BOOTSTRAP_QUERY = `query CrowdyJsRediscover($appId: BigInt!) {
15
15
  gameClientBootstrap(appId: $appId) { gameApiUrl gameApiWsUrl discoveryUrl }
16
16
  }`;
17
17
  function graphqlEndpoint(origin) {
18
- const trimmed = origin.replace(/\/+$/, '');
18
+ const trimmed = stripTrailingSlashes(origin);
19
19
  return trimmed.endsWith('/graphql') ? trimmed : `${trimmed}/graphql`;
20
20
  }
21
+ /** Drop trailing `/`. Same span as `/\/+$/`, linear scan. */
22
+ function stripTrailingSlashes(origin) {
23
+ let end = origin.length;
24
+ while (end > 0 && origin.charCodeAt(end - 1) === 47)
25
+ end -= 1;
26
+ return end === origin.length ? origin : origin.slice(0, end);
27
+ }
21
28
  export function createBootstrapRediscover(options) {
22
29
  return async (subscribedAppId) => {
23
30
  const appId = options.appId ?? subscribedAppId;
@@ -2,6 +2,7 @@ import { type AgentErrorV1 } from './errors.js';
2
2
  import type { CrowdyAgentBrowserToolDispatcher } from './browser-dispatcher.js';
3
3
  import type { CrowdyAgentApprovalV1, CrowdyAgentBudgetV1, CrowdyAgentCheckpointV1, CrowdyAgentEventV1, CrowdyAgentLeaseV1, CrowdyAgentMessageV1, CrowdyAgentMode, CrowdyAgentPreemptionReason, CrowdyAgentRegisteredToolV1, CrowdyAgentSessionV1, CrowdyAgentToolTimelineItemV1 } from './types.js';
4
4
  import type { CrowdyAgentCreateSessionInputV1, CrowdyStudioAgentTransportV1 } from './transport.js';
5
+ import { type StudioSessionMemory } from './session-resume.js';
5
6
  export type CrowdyStudioAgentConnectionState = 'DISCONNECTED' | 'ATTACHING' | 'REPLAYING' | 'CONNECTED' | 'RECONNECTING' | 'ERROR';
6
7
  export interface CrowdyStudioAgentStateV1 {
7
8
  readonly connection: CrowdyStudioAgentConnectionState;
@@ -46,6 +47,8 @@ export interface CrowdyStudioAgentControllerOptionsV1 {
46
47
  readonly onLeaseChanged?: (lease: CrowdyAgentLeaseV1) => void;
47
48
  readonly createIdempotencyKey?: (operation: string) => string;
48
49
  readonly historyPageSize?: number;
50
+ /** Remember the last attached session so Studio remount can reopen it. */
51
+ readonly sessionMemory?: StudioSessionMemory;
49
52
  readonly maxRetainedEvents?: number;
50
53
  readonly autoReconnect?: boolean;
51
54
  readonly reconnectDelayMs?: number;
@@ -129,6 +132,11 @@ export declare class CrowdyStudioAgentController {
129
132
  private stopWorkspaceRenewal;
130
133
  private scheduleReconnect;
131
134
  private loadRemoteContext;
135
+ private resolveOrCreateSession;
136
+ private findResumableSession;
137
+ private sessionMemory;
138
+ private readRememberedSession;
139
+ private rememberSession;
132
140
  private assertProjectBinding;
133
141
  private mutationContext;
134
142
  private nextKey;
@@ -1 +1 @@
1
- {"version":3,"file":"controller.d.ts","sourceRoot":"","sources":["../../src/crowdy-agent/controller.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"controller.d.ts","sourceRoot":"","sources":["../../src/crowdy-agent/controller.ts"],"names":[],"mappings":"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"}
@@ -1,6 +1,7 @@
1
1
  import { CrowdyAgentError, toAgentError, } from './errors.js';
2
2
  import { isDecimalString } from './schema.js';
3
3
  import { CROWDY_AGENT_EVENT_TYPES } from './types.js';
4
+ import { agentSessionMemoryKey, browserSessionMemory, pickResumableAgentSession, } from './session-resume.js';
4
5
  /**
5
6
  * Durable session client for the `crowdy.studio-agent/1` protocol. The
6
7
  * transport is injectable and contains no generated GraphQL dependency.
@@ -79,25 +80,11 @@ export class CrowdyStudioAgentController {
79
80
  this.assertProjectBinding(session, binding?.projectId, Boolean(this.options.resolveProjectBinding));
80
81
  }
81
82
  else {
82
- const configured = typeof this.options.createSession === 'function'
83
- ? await this.options.createSession()
84
- : this.options.createSession;
85
- const createInput = {
86
- ...configured,
87
- ...(this.options.resolveProjectBinding
88
- ? binding?.projectId
89
- ? { projectId: binding.projectId }
90
- : { projectId: undefined }
91
- : {}),
92
- ...(binding?.gridId ? { gridId: binding.gridId } : {}),
93
- };
94
- if (createInput.mode === 'BUILD' && !createInput.projectId) {
95
- throw new CrowdyAgentError('AGENT_CONTEXT_CHANGED', 'BUILD requires the currently selected saved Crowdy Studio project');
96
- }
97
- session = await this.options.transport.createSession(createInput);
83
+ session = await this.resolveOrCreateSession(binding);
98
84
  this.assertProjectBinding(session, binding?.projectId, Boolean(this.options.resolveProjectBinding));
99
85
  }
100
86
  this.update({ session, lastError: null });
87
+ this.rememberSession(session);
101
88
  await this.attach('ATTACHING');
102
89
  }
103
90
  /**
@@ -955,6 +942,69 @@ export class CrowdyStudioAgentController {
955
942
  budget,
956
943
  };
957
944
  }
945
+ async resolveOrCreateSession(binding) {
946
+ const configured = typeof this.options.createSession === 'function'
947
+ ? await this.options.createSession()
948
+ : this.options.createSession;
949
+ const createInput = {
950
+ ...configured,
951
+ ...(this.options.resolveProjectBinding
952
+ ? binding?.projectId
953
+ ? { projectId: binding.projectId }
954
+ : { projectId: undefined }
955
+ : {}),
956
+ ...(binding?.gridId ? { gridId: binding.gridId } : {}),
957
+ };
958
+ if (createInput.mode === 'BUILD' && !createInput.projectId) {
959
+ throw new CrowdyAgentError('AGENT_CONTEXT_CHANGED', 'BUILD requires the currently selected saved Crowdy Studio project');
960
+ }
961
+ const existing = await this.findResumableSession(createInput);
962
+ if (existing)
963
+ return existing;
964
+ return this.options.transport.createSession(createInput);
965
+ }
966
+ async findResumableSession(createInput) {
967
+ try {
968
+ const listed = await this.options.transport.listSessions({
969
+ appId: createInput.appId,
970
+ first: 40,
971
+ });
972
+ const picked = pickResumableAgentSession(listed.nodes, {
973
+ projectId: createInput.projectId,
974
+ gridId: createInput.gridId,
975
+ preferredSessionId: this.readRememberedSession(createInput.appId, createInput.projectId),
976
+ });
977
+ if (!picked)
978
+ return null;
979
+ const session = await this.options.transport.getSession(picked.sessionId);
980
+ if (session.status === 'CLOSED' || session.status === 'REVOKED') {
981
+ return null;
982
+ }
983
+ return session;
984
+ }
985
+ catch {
986
+ return null;
987
+ }
988
+ }
989
+ sessionMemory() {
990
+ return this.options.sessionMemory ?? browserSessionMemory();
991
+ }
992
+ readRememberedSession(appId, projectId) {
993
+ try {
994
+ return this.sessionMemory()?.get(agentSessionMemoryKey(appId, projectId)) ?? null;
995
+ }
996
+ catch {
997
+ return null;
998
+ }
999
+ }
1000
+ rememberSession(session) {
1001
+ try {
1002
+ this.sessionMemory()?.set(agentSessionMemoryKey(session.appId, session.projectId), session.sessionId);
1003
+ }
1004
+ catch {
1005
+ // Private mode / missing storage must not block attach.
1006
+ }
1007
+ }
958
1008
  assertProjectBinding(session, expectedProjectId, enforceSelection) {
959
1009
  if (session.mode === 'BUILD' && !session.projectId) {
960
1010
  throw new CrowdyAgentError('AGENT_CONTEXT_CHANGED', 'BUILD session is not bound to a Crowdy Studio project');
@@ -98,10 +98,140 @@ export function toAgentError(error, fallback = 'AGENT_TOOL_FAILED') {
98
98
  };
99
99
  }
100
100
  function sanitizeAgentText(value) {
101
- const normalized = value
102
- .replace(/[\u0000-\u0008\u000b\u000c\u000e-\u001f\u007f]/gu, ' ')
103
- .replace(/\b(?:bearer|token|secret|api[_ -]?key)\s*[:=]?\s*[^\s,;]+/giu, '[redacted]')
101
+ const normalized = redactAgentSecrets(replaceControlChars(value))
104
102
  .trim()
105
103
  .slice(0, 512);
106
104
  return normalized || 'Agent operation failed';
107
105
  }
106
+ /** Same span as `/[\u0000-\u0008\u000b\u000c\u000e-\u001f\u007f]/gu` → space. */
107
+ function replaceControlChars(value) {
108
+ let changed = false;
109
+ let out = '';
110
+ for (let i = 0; i < value.length; i += 1) {
111
+ const c = value.charCodeAt(i);
112
+ if (c <= 0x08 ||
113
+ c === 0x0b ||
114
+ c === 0x0c ||
115
+ (c >= 0x0e && c <= 0x1f) ||
116
+ c === 0x7f) {
117
+ out += ' ';
118
+ changed = true;
119
+ }
120
+ else {
121
+ out += value[i];
122
+ }
123
+ }
124
+ return changed ? out : value;
125
+ }
126
+ /**
127
+ * Same span as
128
+ * `/\b(?:bearer|token|secret|api[_ -]?key)\s*[:=]?\s*[^\s,;]+/giu`.
129
+ * Linear left-to-right scan; no nested quantifiers.
130
+ */
131
+ function redactAgentSecrets(value) {
132
+ const parts = [];
133
+ let i = 0;
134
+ let plainStart = 0;
135
+ while (i < value.length) {
136
+ const end = matchSecretSpanEnd(value, i);
137
+ if (end > i) {
138
+ if (i > plainStart)
139
+ parts.push(value.slice(plainStart, i));
140
+ parts.push('[redacted]');
141
+ i = end;
142
+ plainStart = i;
143
+ continue;
144
+ }
145
+ i += 1;
146
+ }
147
+ if (plainStart === 0)
148
+ return value;
149
+ if (plainStart < value.length)
150
+ parts.push(value.slice(plainStart));
151
+ return parts.join('');
152
+ }
153
+ function matchSecretSpanEnd(value, index) {
154
+ const afterKeyword = matchSecretKeywordEnd(value, index);
155
+ if (afterKeyword < 0)
156
+ return -1;
157
+ let j = afterKeyword;
158
+ while (j < value.length && isUnicodeSpaceCode(value.charCodeAt(j)))
159
+ j += 1;
160
+ const afterWs = j;
161
+ if (afterWs < value.length && (value[afterWs] === ':' || value[afterWs] === '=')) {
162
+ let k = afterWs + 1;
163
+ while (k < value.length && isUnicodeSpaceCode(value.charCodeAt(k)))
164
+ k += 1;
165
+ const withSep = consumeSecretToken(value, k);
166
+ if (withSep > 0)
167
+ return withSep;
168
+ }
169
+ return consumeSecretToken(value, afterWs);
170
+ }
171
+ function matchSecretKeywordEnd(value, index) {
172
+ if (index > 0 && isAsciiWordChar(value.charCodeAt(index - 1)))
173
+ return -1;
174
+ if (equalsIgnoreCaseAscii(value, index, 'bearer'))
175
+ return index + 6;
176
+ if (equalsIgnoreCaseAscii(value, index, 'token'))
177
+ return index + 5;
178
+ if (equalsIgnoreCaseAscii(value, index, 'secret'))
179
+ return index + 6;
180
+ if (!equalsIgnoreCaseAscii(value, index, 'api'))
181
+ return -1;
182
+ const sepAt = index + 3;
183
+ if (sepAt < value.length) {
184
+ const sep = value[sepAt];
185
+ if ((sep === '_' || sep === ' ' || sep === '-') &&
186
+ equalsIgnoreCaseAscii(value, sepAt + 1, 'key')) {
187
+ return sepAt + 4;
188
+ }
189
+ }
190
+ if (equalsIgnoreCaseAscii(value, index + 3, 'key'))
191
+ return index + 6;
192
+ return -1;
193
+ }
194
+ function consumeSecretToken(value, start) {
195
+ let k = start;
196
+ while (k < value.length) {
197
+ const ch = value[k];
198
+ if (isUnicodeSpaceCode(value.charCodeAt(k)) || ch === ',' || ch === ';')
199
+ break;
200
+ k += 1;
201
+ }
202
+ return k > start ? k : -1;
203
+ }
204
+ function equalsIgnoreCaseAscii(value, index, word) {
205
+ if (index + word.length > value.length)
206
+ return false;
207
+ for (let k = 0; k < word.length; k += 1) {
208
+ const ch = value[index + k];
209
+ if (ch.toLowerCase() !== word[k])
210
+ return false;
211
+ }
212
+ return true;
213
+ }
214
+ function isAsciiWordChar(code) {
215
+ return ((code >= 48 && code <= 57) ||
216
+ (code >= 65 && code <= 90) ||
217
+ (code >= 97 && code <= 122) ||
218
+ code === 95);
219
+ }
220
+ /** Unicode `White_Space` that JS `/\s/u` matches, plus U+FEFF. */
221
+ function isUnicodeSpaceCode(code) {
222
+ return (code === 0x09 ||
223
+ code === 0x0a ||
224
+ code === 0x0b ||
225
+ code === 0x0c ||
226
+ code === 0x0d ||
227
+ code === 0x20 ||
228
+ code === 0xa0 ||
229
+ code === 0x1680 ||
230
+ (code >= 0x2000 && code <= 0x200a) ||
231
+ code === 0x2028 ||
232
+ code === 0x2029 ||
233
+ code === 0x202f ||
234
+ code === 0x205f ||
235
+ code === 0x3000 ||
236
+ code === 0xfeff);
237
+ }
@@ -4,6 +4,7 @@ export declare const CROWDY_AGENT_TOOL_REGISTRY_V1: CrowdyAgentToolRegistry;
4
4
  export declare const CROWDY_AGENT_REGISTRY_V1: CrowdyAgentToolRegistry;
5
5
  export { CrowdyAgentBrowserToolDispatcher, type CrowdyAgentBrowserDispatcherOptionsV1, type CrowdyAgentBrowserToolContextV1, type CrowdyAgentBrowserToolHandlerV1, type CrowdyAgentBrowserToolHandlersV1, } from './browser-dispatcher.js';
6
6
  export { CrowdyStudioAgentController, CrowdyStudioAgentController as CrowdyStudioAgentClient, type CrowdyStudioAgentConnectionState, type CrowdyStudioAgentControllerOptionsV1, type CrowdyStudioAgentStateV1, } from './controller.js';
7
+ export { AGENT_SESSION_EMPTYISH_LAST_SEQ, agentSessionMemoryKey, pickResumableAgentSession, type AgentSessionResumeBinding, type StudioSessionMemory, } from './session-resume.js';
7
8
  export { CrowdyAgentGraphQLTransport, type CrowdyAgentGraphQLSubscriptionClient, type CrowdyAgentGraphQLTransportOptions, } from './graphql-transport.js';
8
9
  export { CROWDY_AGENT_ERROR_CODES, CrowdyAgentError, CrowdyAgentOutcomeUnknownError, toAgentError, type AgentErrorV1, type CrowdyAgentErrorCode, } from './errors.js';
9
10
  export { FORBIDDEN_AGENT_TOOL_SURFACES, CrowdyAgentToolRegistry, isDescriptorDigest, type CrowdyAgentRegistryFilter, } from './registry.js';
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/crowdy-agent/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,eAAe,CAAC;AAGxD,0DAA0D;AAC1D,eAAO,MAAM,6BAA6B,yBAEzC,CAAC;AACF,eAAO,MAAM,wBAAwB,yBAAgC,CAAC;AAEtE,OAAO,EACL,gCAAgC,EAChC,KAAK,qCAAqC,EAC1C,KAAK,+BAA+B,EACpC,KAAK,+BAA+B,EACpC,KAAK,gCAAgC,GACtC,MAAM,yBAAyB,CAAC;AACjC,OAAO,EACL,2BAA2B,EAC3B,2BAA2B,IAAI,uBAAuB,EACtD,KAAK,gCAAgC,EACrC,KAAK,oCAAoC,EACzC,KAAK,wBAAwB,GAC9B,MAAM,iBAAiB,CAAC;AACzB,OAAO,EACL,2BAA2B,EAC3B,KAAK,oCAAoC,EACzC,KAAK,kCAAkC,GACxC,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,wBAAwB,EACxB,gBAAgB,EAChB,8BAA8B,EAC9B,YAAY,EACZ,KAAK,YAAY,EACjB,KAAK,oBAAoB,GAC1B,MAAM,aAAa,CAAC;AACrB,OAAO,EACL,6BAA6B,EAC7B,uBAAuB,EACvB,kBAAkB,EAClB,KAAK,yBAAyB,GAC/B,MAAM,eAAe,CAAC;AACvB,OAAO,EACL,gCAAgC,EAChC,uBAAuB,EACvB,aAAa,EACb,UAAU,EACV,mBAAmB,EACnB,eAAe,EACf,YAAY,EACZ,uBAAuB,EACvB,KAAK,aAAa,EAClB,KAAK,UAAU,EACf,KAAK,eAAe,EACpB,KAAK,iBAAiB,EACtB,KAAK,cAAc,EACnB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,eAAe,EACpB,KAAK,2BAA2B,GACjC,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,gCAAgC,EAAE,MAAM,uBAAuB,CAAC;AACzE,OAAO,EACL,4BAA4B,EAC5B,+BAA+B,EAC/B,KAAK,+BAA+B,GACrC,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EACL,kCAAkC,EAClC,KAAK,yBAAyB,EAC9B,KAAK,uBAAuB,EAC5B,KAAK,+BAA+B,EACpC,KAAK,iBAAiB,EACtB,KAAK,sCAAsC,EAC3C,KAAK,8BAA8B,EACnC,KAAK,wBAAwB,EAC7B,KAAK,qBAAqB,EAC1B,KAAK,4BAA4B,GAClC,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,wBAAwB,EAAE,MAAM,YAAY,CAAC;AACtD,YAAY,EACV,yBAAyB,EACzB,yBAAyB,EACzB,qBAAqB,EACrB,4BAA4B,EAC5B,mBAAmB,EACnB,sBAAsB,EACtB,2BAA2B,EAC3B,uBAAuB,EACvB,0BAA0B,EAC1B,oBAAoB,EACpB,kBAAkB,EAClB,2BAA2B,EAC3B,sBAAsB,EACtB,kBAAkB,EAClB,oBAAoB,EACpB,eAAe,EACf,2BAA2B,EAC3B,0BAA0B,EAC1B,0BAA0B,EAC1B,2BAA2B,EAC3B,oBAAoB,EACpB,gBAAgB,EAChB,6BAA6B,EAC7B,wBAAwB,EACxB,oBAAoB,EACpB,yBAAyB,EACzB,wBAAwB,EACxB,2BAA2B,EAC3B,uBAAuB,EACvB,2BAA2B,EAC3B,2BAA2B,EAC3B,uBAAuB,EACvB,mBAAmB,EACnB,6BAA6B,GAC9B,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/crowdy-agent/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,eAAe,CAAC;AAGxD,0DAA0D;AAC1D,eAAO,MAAM,6BAA6B,yBAEzC,CAAC;AACF,eAAO,MAAM,wBAAwB,yBAAgC,CAAC;AAEtE,OAAO,EACL,gCAAgC,EAChC,KAAK,qCAAqC,EAC1C,KAAK,+BAA+B,EACpC,KAAK,+BAA+B,EACpC,KAAK,gCAAgC,GACtC,MAAM,yBAAyB,CAAC;AACjC,OAAO,EACL,2BAA2B,EAC3B,2BAA2B,IAAI,uBAAuB,EACtD,KAAK,gCAAgC,EACrC,KAAK,oCAAoC,EACzC,KAAK,wBAAwB,GAC9B,MAAM,iBAAiB,CAAC;AACzB,OAAO,EACL,+BAA+B,EAC/B,qBAAqB,EACrB,yBAAyB,EACzB,KAAK,yBAAyB,EAC9B,KAAK,mBAAmB,GACzB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EACL,2BAA2B,EAC3B,KAAK,oCAAoC,EACzC,KAAK,kCAAkC,GACxC,MAAM,wBAAwB,CAAC;AAChC,OAAO,EACL,wBAAwB,EACxB,gBAAgB,EAChB,8BAA8B,EAC9B,YAAY,EACZ,KAAK,YAAY,EACjB,KAAK,oBAAoB,GAC1B,MAAM,aAAa,CAAC;AACrB,OAAO,EACL,6BAA6B,EAC7B,uBAAuB,EACvB,kBAAkB,EAClB,KAAK,yBAAyB,GAC/B,MAAM,eAAe,CAAC;AACvB,OAAO,EACL,gCAAgC,EAChC,uBAAuB,EACvB,aAAa,EACb,UAAU,EACV,mBAAmB,EACnB,eAAe,EACf,YAAY,EACZ,uBAAuB,EACvB,KAAK,aAAa,EAClB,KAAK,UAAU,EACf,KAAK,eAAe,EACpB,KAAK,iBAAiB,EACtB,KAAK,cAAc,EACnB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,eAAe,EACpB,KAAK,2BAA2B,GACjC,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,gCAAgC,EAAE,MAAM,uBAAuB,CAAC;AACzE,OAAO,EACL,4BAA4B,EAC5B,+BAA+B,EAC/B,KAAK,+BAA+B,GACrC,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EACL,kCAAkC,EAClC,KAAK,yBAAyB,EAC9B,KAAK,uBAAuB,EAC5B,KAAK,+BAA+B,EACpC,KAAK,iBAAiB,EACtB,KAAK,sCAAsC,EAC3C,KAAK,8BAA8B,EACnC,KAAK,wBAAwB,EAC7B,KAAK,qBAAqB,EAC1B,KAAK,4BAA4B,GAClC,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,wBAAwB,EAAE,MAAM,YAAY,CAAC;AACtD,YAAY,EACV,yBAAyB,EACzB,yBAAyB,EACzB,qBAAqB,EACrB,4BAA4B,EAC5B,mBAAmB,EACnB,sBAAsB,EACtB,2BAA2B,EAC3B,uBAAuB,EACvB,0BAA0B,EAC1B,oBAAoB,EACpB,kBAAkB,EAClB,2BAA2B,EAC3B,sBAAsB,EACtB,kBAAkB,EAClB,oBAAoB,EACpB,eAAe,EACf,2BAA2B,EAC3B,0BAA0B,EAC1B,0BAA0B,EAC1B,2BAA2B,EAC3B,oBAAoB,EACpB,gBAAgB,EAChB,6BAA6B,EAC7B,wBAAwB,EACxB,oBAAoB,EACpB,yBAAyB,EACzB,wBAAwB,EACxB,2BAA2B,EAC3B,uBAAuB,EACvB,2BAA2B,EAC3B,2BAA2B,EAC3B,uBAAuB,EACvB,mBAAmB,EACnB,6BAA6B,GAC9B,MAAM,YAAY,CAAC"}
@@ -5,6 +5,7 @@ export const CROWDY_AGENT_TOOL_REGISTRY_V1 = new CrowdyAgentToolRegistry(CROWDY_
5
5
  export const CROWDY_AGENT_REGISTRY_V1 = CROWDY_AGENT_TOOL_REGISTRY_V1;
6
6
  export { CrowdyAgentBrowserToolDispatcher, } from './browser-dispatcher.js';
7
7
  export { CrowdyStudioAgentController, CrowdyStudioAgentController as CrowdyStudioAgentClient, } from './controller.js';
8
+ export { AGENT_SESSION_EMPTYISH_LAST_SEQ, agentSessionMemoryKey, pickResumableAgentSession, } from './session-resume.js';
8
9
  export { CrowdyAgentGraphQLTransport, } from './graphql-transport.js';
9
10
  export { CROWDY_AGENT_ERROR_CODES, CrowdyAgentError, CrowdyAgentOutcomeUnknownError, toAgentError, } from './errors.js';
10
11
  export { FORBIDDEN_AGENT_TOOL_SURFACES, CrowdyAgentToolRegistry, isDescriptorDigest, } from './registry.js';
@@ -0,0 +1,24 @@
1
+ import type { CrowdyAgentSessionV1 } from './types.js';
2
+ /**
3
+ * Fresh create+attach usually writes SESSION_CREATED, CLIENT_ATTACHED, and
4
+ * maybe MODE_SELECTED. Anything above this has a real turn.
5
+ */
6
+ export declare const AGENT_SESSION_EMPTYISH_LAST_SEQ = 3n;
7
+ export interface StudioSessionMemory {
8
+ get(key: string): string | null;
9
+ set(key: string, value: string): void;
10
+ }
11
+ export interface AgentSessionResumeBinding {
12
+ readonly projectId?: string;
13
+ readonly gridId?: string;
14
+ readonly preferredSessionId?: string | null;
15
+ }
16
+ export declare function agentSessionMemoryKey(appId: string, projectId?: string): string;
17
+ export declare function browserSessionMemory(): StudioSessionMemory | null;
18
+ /**
19
+ * Choose the session Studio should reopen instead of creating another empty
20
+ * one. Preferred id wins; otherwise a session that already has turns beats a
21
+ * pile of unused create-on-open leftovers; then latest `updatedAt`.
22
+ */
23
+ export declare function pickResumableAgentSession(sessions: readonly CrowdyAgentSessionV1[], binding: AgentSessionResumeBinding): CrowdyAgentSessionV1 | null;
24
+ //# sourceMappingURL=session-resume.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"session-resume.d.ts","sourceRoot":"","sources":["../../src/crowdy-agent/session-resume.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,YAAY,CAAC;AAKvD;;;GAGG;AACH,eAAO,MAAM,+BAA+B,KAAK,CAAC;AAElD,MAAM,WAAW,mBAAmB;IAClC,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAAC;IAChC,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;CACvC;AAED,MAAM,WAAW,yBAAyB;IACxC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,kBAAkB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAC7C;AAED,wBAAgB,qBAAqB,CACnC,KAAK,EAAE,MAAM,EACb,SAAS,CAAC,EAAE,MAAM,GACjB,MAAM,CAER;AAED,wBAAgB,oBAAoB,IAAI,mBAAmB,GAAG,IAAI,CAajE;AAED;;;;GAIG;AACH,wBAAgB,yBAAyB,CACvC,QAAQ,EAAE,SAAS,oBAAoB,EAAE,EACzC,OAAO,EAAE,yBAAyB,GACjC,oBAAoB,GAAG,IAAI,CA0B7B"}
@@ -0,0 +1,76 @@
1
+ /** Statuses that can be reattached after Studio closes. */
2
+ const REOPENABLE = new Set(['ACTIVE', 'PAUSED']);
3
+ /**
4
+ * Fresh create+attach usually writes SESSION_CREATED, CLIENT_ATTACHED, and
5
+ * maybe MODE_SELECTED. Anything above this has a real turn.
6
+ */
7
+ export const AGENT_SESSION_EMPTYISH_LAST_SEQ = 3n;
8
+ export function agentSessionMemoryKey(appId, projectId) {
9
+ return `ck-crowdy-studio-agent-session:${appId}:${projectId ?? '_'}`;
10
+ }
11
+ export function browserSessionMemory() {
12
+ try {
13
+ if (typeof window === 'undefined')
14
+ return null;
15
+ const storage = window.localStorage;
16
+ return {
17
+ get: (key) => storage.getItem(key),
18
+ set: (key, value) => {
19
+ storage.setItem(key, value);
20
+ },
21
+ };
22
+ }
23
+ catch {
24
+ return null;
25
+ }
26
+ }
27
+ /**
28
+ * Choose the session Studio should reopen instead of creating another empty
29
+ * one. Preferred id wins; otherwise a session that already has turns beats a
30
+ * pile of unused create-on-open leftovers; then latest `updatedAt`.
31
+ */
32
+ export function pickResumableAgentSession(sessions, binding) {
33
+ const candidates = sessions.filter((session) => sessionMatchesBinding(session, binding));
34
+ if (candidates.length === 0)
35
+ return null;
36
+ const preferredId = binding.preferredSessionId;
37
+ if (preferredId) {
38
+ const preferred = candidates.find((session) => session.sessionId === preferredId);
39
+ if (preferred)
40
+ return preferred;
41
+ }
42
+ const withTurns = candidates.filter((session) => eventSeq(session.lastEventSeq) > AGENT_SESSION_EMPTYISH_LAST_SEQ);
43
+ const pool = withTurns.length > 0 ? withTurns : candidates;
44
+ return ([...pool].sort((left, right) => {
45
+ const updated = right.updatedAt.localeCompare(left.updatedAt);
46
+ if (updated !== 0)
47
+ return updated;
48
+ const seq = eventSeq(right.lastEventSeq) - eventSeq(left.lastEventSeq);
49
+ return seq > 0n ? 1 : seq < 0n ? -1 : 0;
50
+ })[0] ?? null);
51
+ }
52
+ function sessionMatchesBinding(session, binding) {
53
+ if (!REOPENABLE.has(session.status))
54
+ return false;
55
+ if (binding.projectId) {
56
+ if (session.projectId !== binding.projectId)
57
+ return false;
58
+ }
59
+ else if (session.projectId) {
60
+ return false;
61
+ }
62
+ if (binding.gridId &&
63
+ session.gridId &&
64
+ session.gridId !== binding.gridId) {
65
+ return false;
66
+ }
67
+ return true;
68
+ }
69
+ function eventSeq(value) {
70
+ try {
71
+ return BigInt(value);
72
+ }
73
+ catch {
74
+ return 0n;
75
+ }
76
+ }
@@ -96,11 +96,31 @@ crowdy::register_module!(init: on_init, tick: on_tick, invoke: on_invoke);
96
96
  `;
97
97
  }
98
98
  function moduleName(value) {
99
- const slug = value
100
- .trim()
101
- .toLowerCase()
102
- .replace(/[^a-z0-9]+/gu, '-')
103
- .replace(/^-+|-+$/gu, '')
104
- .slice(0, 48);
99
+ const slug = slugModuleName(value).slice(0, 48);
105
100
  return slug || 'player-mod';
106
101
  }
102
+ /**
103
+ * Same span as trim + lower + `/[^a-z0-9]+/gu` → `-`, then `/^-+|-+$/gu`.
104
+ * Linear scan; non-ASCII and punctuation collapse to a single dash.
105
+ */
106
+ function slugModuleName(value) {
107
+ const trimmed = value.trim().toLowerCase();
108
+ let dashed = '';
109
+ let pendingDash = false;
110
+ let started = false;
111
+ for (const ch of trimmed) {
112
+ const code = ch.codePointAt(0) ?? 0;
113
+ const alnum = (code >= 97 && code <= 122) || (code >= 48 && code <= 57);
114
+ if (alnum) {
115
+ if (pendingDash && started)
116
+ dashed += '-';
117
+ dashed += ch;
118
+ started = true;
119
+ pendingDash = false;
120
+ }
121
+ else {
122
+ pendingDash = true;
123
+ }
124
+ }
125
+ return dashed;
126
+ }
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * GENERATED — do not edit. The operator tooling's
3
- * `sync-client-origins.mjs --write --tier test` writes this file, and
3
+ * `sync-client-origins.mjs --write --tier dev` writes this file, and
4
4
  * `check-sdk-default-origin.mjs` refuses it when it names the wrong tier or a
5
5
  * host that declaration does not carry. Regenerate; never hand-edit.
6
6
  *
@@ -10,14 +10,14 @@
10
10
  * than no default at all. Every fallback this SDK ever removed named a host that
11
11
  * was already dead. A generated file plus a gate is what makes this one different.
12
12
  *
13
- * Source: the operator's per-tier public CK API origin declaration, tier 'test'
13
+ * Source: the operator's per-tier public CK API origin declaration, tier 'dev'
14
14
  */
15
15
  /** The tier this build of the SDK is published for. */
16
- export declare const CROWDY_DEFAULT_TIER = "test";
16
+ export declare const CROWDY_DEFAULT_TIER = "dev";
17
17
  /** The public CK API origin for that tier. */
18
- export declare const CROWDY_DEFAULT_HTTP_ORIGIN = "https://ck.test.crowdedkingdoms.com";
18
+ export declare const CROWDY_DEFAULT_HTTP_ORIGIN = "https://ck.dev.crowdedkingdoms.com";
19
19
  /** The same host over WebSocket. A scheme is composed; a hostname is looked up. */
20
- export declare const CROWDY_DEFAULT_WS_ORIGIN = "wss://ck.test.crowdedkingdoms.com";
20
+ export declare const CROWDY_DEFAULT_WS_ORIGIN = "wss://ck.dev.crowdedkingdoms.com";
21
21
  /** The bare hostname, for callers that need to compare rather than dial. */
22
- export declare const CROWDY_DEFAULT_HOST = "ck.test.crowdedkingdoms.com";
22
+ export declare const CROWDY_DEFAULT_HOST = "ck.dev.crowdedkingdoms.com";
23
23
  //# sourceMappingURL=default-origin.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"default-origin.d.ts","sourceRoot":"","sources":["../src/default-origin.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,uDAAuD;AACvD,eAAO,MAAM,mBAAmB,SAAS,CAAC;AAE1C,8CAA8C;AAC9C,eAAO,MAAM,0BAA0B,wCAAwC,CAAC;AAEhF,mFAAmF;AACnF,eAAO,MAAM,wBAAwB,sCAAsC,CAAC;AAE5E,4EAA4E;AAC5E,eAAO,MAAM,mBAAmB,gCAAgC,CAAC"}
1
+ {"version":3,"file":"default-origin.d.ts","sourceRoot":"","sources":["../src/default-origin.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,uDAAuD;AACvD,eAAO,MAAM,mBAAmB,QAAQ,CAAC;AAEzC,8CAA8C;AAC9C,eAAO,MAAM,0BAA0B,uCAAuC,CAAC;AAE/E,mFAAmF;AACnF,eAAO,MAAM,wBAAwB,qCAAqC,CAAC;AAE3E,4EAA4E;AAC5E,eAAO,MAAM,mBAAmB,+BAA+B,CAAC"}
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * GENERATED — do not edit. The operator tooling's
3
- * `sync-client-origins.mjs --write --tier test` writes this file, and
3
+ * `sync-client-origins.mjs --write --tier dev` writes this file, and
4
4
  * `check-sdk-default-origin.mjs` refuses it when it names the wrong tier or a
5
5
  * host that declaration does not carry. Regenerate; never hand-edit.
6
6
  *
@@ -10,13 +10,13 @@
10
10
  * than no default at all. Every fallback this SDK ever removed named a host that
11
11
  * was already dead. A generated file plus a gate is what makes this one different.
12
12
  *
13
- * Source: the operator's per-tier public CK API origin declaration, tier 'test'
13
+ * Source: the operator's per-tier public CK API origin declaration, tier 'dev'
14
14
  */
15
15
  /** The tier this build of the SDK is published for. */
16
- export const CROWDY_DEFAULT_TIER = 'test';
16
+ export const CROWDY_DEFAULT_TIER = 'dev';
17
17
  /** The public CK API origin for that tier. */
18
- export const CROWDY_DEFAULT_HTTP_ORIGIN = 'https://ck.test.crowdedkingdoms.com';
18
+ export const CROWDY_DEFAULT_HTTP_ORIGIN = 'https://ck.dev.crowdedkingdoms.com';
19
19
  /** The same host over WebSocket. A scheme is composed; a hostname is looked up. */
20
- export const CROWDY_DEFAULT_WS_ORIGIN = 'wss://ck.test.crowdedkingdoms.com';
20
+ export const CROWDY_DEFAULT_WS_ORIGIN = 'wss://ck.dev.crowdedkingdoms.com';
21
21
  /** The bare hostname, for callers that need to compare rather than dial. */
22
- export const CROWDY_DEFAULT_HOST = 'ck.test.crowdedkingdoms.com';
22
+ export const CROWDY_DEFAULT_HOST = 'ck.dev.crowdedkingdoms.com';
@@ -1 +1 @@
1
- {"version":3,"file":"portal.d.ts","sourceRoot":"","sources":["../../src/domains/portal.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"portal.d.ts","sourceRoot":"","sources":["../../src/domains/portal.ts"],"names":[],"mappings":"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"}
@@ -319,6 +319,13 @@ export class PortalAPI {
319
319
  */
320
320
  async completeEntry(search) {
321
321
  const params = new URLSearchParams(search ?? defaultSearch());
322
+ // GitHub App install/OAuth also uses `code` + `state`. Those must not be
323
+ // exchanged as Overworld portal codes — that overwrites the play token.
324
+ if (params.has('github') ||
325
+ params.has('installation_id') ||
326
+ params.has('setup_action')) {
327
+ return null;
328
+ }
322
329
  const code = params.get('code');
323
330
  if (!code)
324
331
  return null;
package/dist/index.d.ts CHANGED
@@ -47,7 +47,7 @@
47
47
  * or internal tooling, never an untrusted browser.
48
48
  */
49
49
  /** The published package version. Mirrors `package.json`. */
50
- export declare const VERSION = "15.9.0-test.1";
50
+ export declare const VERSION = "15.10.0-dev.1";
51
51
  export { LbCookieStore } from './lb-cookie-store.js';
52
52
  export { CrowdyClient, createCrowdyClient, type CrowdyClientConfig, } from './crowdy-client.js';
53
53
  export { CROWDY_DEFAULT_TIER, CROWDY_DEFAULT_HOST, CROWDY_DEFAULT_HTTP_ORIGIN, CROWDY_DEFAULT_WS_ORIGIN, } from './default-origin.js';
package/dist/index.js CHANGED
@@ -47,7 +47,7 @@
47
47
  * or internal tooling, never an untrusted browser.
48
48
  */
49
49
  /** The published package version. Mirrors `package.json`. */
50
- export const VERSION = '15.9.0-test.1';
50
+ export const VERSION = '15.10.0-dev.1';
51
51
  export { LbCookieStore } from './lb-cookie-store.js';
52
52
  export { CrowdyClient, createCrowdyClient, } from './crowdy-client.js';
53
53
  // The tier this build defaults to, exported so a consumer can PRINT what it is
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@crowdedkingdoms/crowdyjs",
3
- "version": "15.9.0-test.1",
3
+ "version": "15.10.0-dev.1",
4
4
  "description": "Browser-first Crowded Kingdoms SDK with GraphQL, realtime, and local Rust authoring support",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",