ework-aio 0.2.2 → 0.2.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ework-aio",
3
- "version": "0.2.2",
3
+ "version": "0.2.3",
4
4
  "description": "All-in-one installer for ework (issue tracker) + ework-daemon (AI bridge) + opencode-ework (plugin). One command: npm i -g ework-aio && ework-aio install.",
5
5
  "type": "module",
6
6
  "license": "MIT",
package/src/cli.ts CHANGED
@@ -35,7 +35,7 @@ import {
35
35
  type ConfigArgs,
36
36
  } from "./commands/config.ts";
37
37
 
38
- const VERSION = "0.2.2-dev";
38
+ const VERSION = "0.2.3-dev";
39
39
 
40
40
  const USAGE = `ework-aio <command> [options]
41
41
 
@@ -592,14 +592,18 @@ async function bootstrapBot(opts: BootstrapBotOpts): Promise<string> {
592
592
  }
593
593
 
594
594
  // 3. Mint PAT via /me/tokens/create. Response is HTML containing the
595
- // clear-text token in `<input id="t" value="<40-hex>">`. We only get one
596
- // chance to see the clear-text must scrape it now.
595
+ // clear-text token. ework-web renders it inside `<code id="t">VALUE</code>`
596
+ // (verified at src/views/tokens.ts:141 in ework-web at time of writing);
597
+ // the legacy install.sh-era HTML used `<input id="t" value="VALUE">`. We
598
+ // scrape both shapes so an ework-web template change doesn't silently
599
+ // break install.
597
600
  //
598
601
  // S-3: pin redirect:"manual" so a PRG-style 303→GET doesn't land us on
599
602
  // a "token list" page where the clear-text value isn't present.
600
603
  //
601
- // S-2: scrape regex is attribute-order-independent accepts both
602
- // `<input id="t" value="...">` and `<input value="..." id="t">`.
604
+ // Token shape: 40 lowercase hex chars (ework-web createPat uses
605
+ // randomHex(20) 20 bytes 40 hex). Case-insensitive `i` flag for
606
+ // XHTML-style `<INPUT VALUE="...">` and uppercase hex (defensive).
603
607
  const patRes = await fetchImpl(`${opts.baseUrl}/me/tokens/create`, {
604
608
  method: "POST",
605
609
  headers: { Cookie: botCookie, "Content-Type": "application/x-www-form-urlencoded" },
@@ -612,14 +616,14 @@ async function bootstrapBot(opts: BootstrapBotOpts): Promise<string> {
612
616
  );
613
617
  }
614
618
  const patBody = await patRes.text();
615
- // S-2: scrape regex is attribute-order-independent — accepts both
616
- // `<input id="t" value="...">` and `<input value="..." id="t">`.
617
- // Case-insensitive (i flag) so XHTML-style `<INPUT VALUE="...">` from
618
- // ework-web template tweaks doesn't silently break scraping.
619
- const match = patBody.match(/<input[^>]*id="t"[^>]*value="([a-f0-9]{40})"/i)
620
- ?? patBody.match(/<input[^>]*value="([a-f0-9]{40})"[^>]*id="t"/i);
619
+ const match =
620
+ patBody.match(/<code[^>]*id="t"[^>]*>\s*([a-f0-9]{40})\s*<\/code>/i) ??
621
+ patBody.match(/<input[^>]*id="t"[^>]*value="([a-f0-9]{40})"/i) ??
622
+ patBody.match(/<input[^>]*value="([a-f0-9]{40})"[^>]*id="t"/i);
621
623
  if (!match || !match[1]) {
622
- throw new InstallError(`could not extract PAT from token-create response`);
624
+ throw new InstallError(
625
+ `could not extract PAT from token-create response (first 300 chars): ${patBody.slice(0, 300)}`,
626
+ );
623
627
  }
624
628
  return match[1];
625
629
  }