@pushary/agent-hooks 1.3.0 → 1.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (90) hide show
  1. package/CHANGELOG.md +24 -0
  2. package/README.md +1 -1
  3. package/data/SKILL.md +3 -3
  4. package/data/cursor-plugin/skills/pushary/SKILL.md +2 -2
  5. package/data/vscode-plugin/skills/pushary/SKILL.md +2 -2
  6. package/dist/bin/pushary-bell-hook.js +20 -20
  7. package/dist/bin/pushary-bell.js +9 -9
  8. package/dist/bin/pushary-claude.js +20 -20
  9. package/dist/bin/pushary-clean.js +472 -94
  10. package/dist/bin/pushary-codex-bridge.js +11 -11
  11. package/dist/bin/pushary-codex-hook.js +30 -28
  12. package/dist/bin/pushary-codex.js +7 -7
  13. package/dist/bin/pushary-connect.js +9 -9
  14. package/dist/bin/pushary-cowork.js +5 -5
  15. package/dist/bin/pushary-daemon.js +26 -26
  16. package/dist/bin/pushary-disconnect.js +13 -13
  17. package/dist/bin/pushary-doctor.js +86 -24
  18. package/dist/bin/pushary-elicitation-hook.js +19 -19
  19. package/dist/bin/pushary-gemini-bridge.js +10 -10
  20. package/dist/bin/pushary-gemini-hook.js +21 -21
  21. package/dist/bin/pushary-hook.js +34 -44
  22. package/dist/bin/pushary-login.js +10 -10
  23. package/dist/bin/pushary-logout.js +7 -7
  24. package/dist/bin/pushary-mode.js +5 -5
  25. package/dist/bin/pushary-notification-hook.js +22 -22
  26. package/dist/bin/pushary-opencode-hook.js +21 -21
  27. package/dist/bin/pushary-permission-denied-hook.js +26 -26
  28. package/dist/bin/pushary-permission-hook.js +32 -31
  29. package/dist/bin/pushary-post-hook.js +22 -22
  30. package/dist/bin/pushary-prompt-hook.js +22 -22
  31. package/dist/bin/pushary-session-end-hook.js +22 -22
  32. package/dist/bin/pushary-session-start-hook.js +24 -24
  33. package/dist/bin/pushary-setup.js +39 -60
  34. package/dist/bin/pushary-stats.js +4 -4
  35. package/dist/bin/pushary-status.js +13 -13
  36. package/dist/bin/pushary-stop-hook.js +22 -22
  37. package/dist/bin/pushary-stopfailure-hook.js +22 -22
  38. package/dist/bin/pushary-suggestions.js +2 -2
  39. package/dist/bin/pushary-transcript-register.js +18 -18
  40. package/dist/bin/pushary-transcripts.js +8 -8
  41. package/dist/bin/pushary-upgrade.js +17 -17
  42. package/dist/bin/pushary-wait.js +5 -5
  43. package/dist/bin/pushary.js +1 -1
  44. package/dist/{chunk-3AIFWTVB.js → chunk-2TOTCUJC.js} +2 -2
  45. package/dist/{chunk-X3KIGNIP.js → chunk-43Z3RLS5.js} +83 -24
  46. package/dist/{chunk-YF4JDCU4.js → chunk-5F5QQMCA.js} +1 -1
  47. package/dist/{chunk-ZHL62DRA.js → chunk-5IBVIMWT.js} +3 -3
  48. package/dist/{chunk-BYGEZI7B.js → chunk-5MSBI6NP.js} +1 -1
  49. package/dist/{chunk-WPJS3OZH.js → chunk-7IEB2GV4.js} +100 -9
  50. package/dist/{chunk-2PLEJ7SY.js → chunk-7PQZYCEP.js} +1 -1
  51. package/dist/{chunk-OE6U2AXM.js → chunk-A7XIL2WD.js} +3 -3
  52. package/dist/{chunk-A2URMNFM.js → chunk-BYAXXBNO.js} +1 -1
  53. package/dist/{chunk-DON24PNT.js → chunk-D4TNSUDY.js} +1 -1
  54. package/dist/{chunk-EU6JH7KU.js → chunk-ESLLVHDY.js} +8 -8
  55. package/dist/{chunk-LZQVAEWP.js → chunk-FAH3D74E.js} +2 -1
  56. package/dist/{chunk-MU275U5A.js → chunk-GIXLZFEY.js} +2 -2
  57. package/dist/{chunk-4V24U44H.js → chunk-GLPWCQ6V.js} +2 -2
  58. package/dist/{chunk-BL4SQNO6.js → chunk-GS5EI2YL.js} +1 -1
  59. package/dist/{chunk-EKQAKSGI.js → chunk-H25UB3CG.js} +1 -1
  60. package/dist/{chunk-BNDHXPTQ.js → chunk-HGN6VZTY.js} +20 -13
  61. package/dist/{chunk-WXXDHGTZ.js → chunk-IF46POXX.js} +5 -4
  62. package/dist/{chunk-A5ZWYQFV.js → chunk-JCWCTBYH.js} +4 -4
  63. package/dist/{chunk-IAEVVUXO.js → chunk-KZIXHLPQ.js} +1 -1
  64. package/dist/{chunk-FGVNU7XD.js → chunk-NBCTKC4Z.js} +34 -3
  65. package/dist/{chunk-XBO42HKH.js → chunk-NYHNLMQO.js} +12 -3
  66. package/dist/{chunk-K4TAUYUJ.js → chunk-O5L2OJBB.js} +3 -3
  67. package/dist/{chunk-DVO4SZMJ.js → chunk-O6RN46OS.js} +3 -3
  68. package/dist/{chunk-POAFXBNH.js → chunk-P4JVVJ2D.js} +1 -1
  69. package/dist/{chunk-E7WBNGJS.js → chunk-Q4UAMWXK.js} +1 -1
  70. package/dist/{chunk-KS4P6F3R.js → chunk-RGZY77CD.js} +4 -4
  71. package/dist/{chunk-K7UIAE7I.js → chunk-RQM5SMMR.js} +2 -2
  72. package/dist/{chunk-UVXNYYHG.js → chunk-S3CLZSV3.js} +6 -6
  73. package/dist/{chunk-B3S4SF3D.js → chunk-S3EUZZJB.js} +1 -1
  74. package/dist/{chunk-XBJW4MV5.js → chunk-SGZ3IAWF.js} +1 -1
  75. package/dist/{chunk-YKLCWWEI.js → chunk-SGZJ5LYH.js} +1 -1
  76. package/dist/{chunk-4LL6LG5X.js → chunk-T7E75EKA.js} +4 -3
  77. package/dist/{chunk-GOQHN2UH.js → chunk-TWWLVOPB.js} +1 -1
  78. package/dist/{chunk-RVDHN2TJ.js → chunk-U4FB623J.js} +2 -2
  79. package/dist/{chunk-RHLUJE4H.js → chunk-UCGQEAKZ.js} +1 -1
  80. package/dist/{chunk-KPNGPRYU.js → chunk-UIN3RD2U.js} +4 -4
  81. package/dist/{chunk-XEXOHUJ6.js → chunk-UTYTPDWN.js} +4 -4
  82. package/dist/{chunk-EJZCV5G4.js → chunk-VENQSVKA.js} +1 -1
  83. package/dist/{chunk-EYMMU5HC.js → chunk-XJWMPQ6X.js} +1 -1
  84. package/dist/{chunk-JYEGOYQC.js → chunk-YYRZPEMA.js} +1 -1
  85. package/dist/{chunk-N43EQPJK.js → chunk-ZIGGEKZW.js} +41 -7
  86. package/dist/{reapply-FUCAKR6Z.js → reapply-B3S2LRMT.js} +9 -9
  87. package/dist/src/index.d.ts +20 -17
  88. package/dist/src/index.js +13 -13
  89. package/package.json +1 -1
  90. /package/dist/{chunk-KBITFQST.js → chunk-P32LPT2L.js} +0 -0
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  guardBinary
3
- } from "./chunk-RHLUJE4H.js";
3
+ } from "./chunk-UCGQEAKZ.js";
4
4
 
5
5
  // src/bell/install.ts
6
6
  import { join } from "path";
@@ -1,16 +1,16 @@
1
1
  import {
2
2
  NOTIFICATION_MATCHED_TYPES,
3
3
  POSTTOOLUSE_MIRRORED_TOOLS
4
- } from "./chunk-IAEVVUXO.js";
4
+ } from "./chunk-KZIXHLPQ.js";
5
5
  import {
6
6
  isProtectedByScope,
7
7
  registerHookEntry
8
- } from "./chunk-RHLUJE4H.js";
8
+ } from "./chunk-UCGQEAKZ.js";
9
9
  import {
10
10
  CLAUDE_PRETOOLUSE_MATCHER,
11
11
  HOOK_BUDGETS,
12
12
  HOOK_LOCATOR_BINARY
13
- } from "./chunk-WPJS3OZH.js";
13
+ } from "./chunk-7IEB2GV4.js";
14
14
 
15
15
  // src/gemini-config.ts
16
16
  var GEMINI_HOOK_BINARY = "pushary-gemini-hook";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  readTranscriptPreference
3
- } from "./chunk-XBO42HKH.js";
3
+ } from "./chunk-NYHNLMQO.js";
4
4
 
5
5
  // src/transcript-setting.ts
6
6
  var transcriptEnvironmentPreference = () => {
@@ -13,7 +13,7 @@ import {
13
13
  import {
14
14
  isValidApiKey,
15
15
  normalizeKeyScope
16
- } from "./chunk-WPJS3OZH.js";
16
+ } from "./chunk-7IEB2GV4.js";
17
17
 
18
18
  // src/session.ts
19
19
  var samePusharyAccount = (left, right) => left.kind === "ok" && right.kind === "ok" && left.identity.workspaceId !== "" && left.identity.workspaceId === right.identity.workspaceId && left.identity.siteId === right.identity.siteId;
@@ -3,19 +3,19 @@ import {
3
3
  loadPin,
4
4
  savePin,
5
5
  verifyRecipients
6
- } from "./chunk-YKLCWWEI.js";
6
+ } from "./chunk-SGZJ5LYH.js";
7
7
  import {
8
8
  hookOwnerOf
9
- } from "./chunk-XEXOHUJ6.js";
9
+ } from "./chunk-UTYTPDWN.js";
10
10
  import {
11
11
  ensureDaemonRunning
12
- } from "./chunk-KS4P6F3R.js";
12
+ } from "./chunk-RGZY77CD.js";
13
13
  import {
14
14
  buildTranscriptRecords,
15
15
  decodePublicKey,
16
16
  generateSessionKey,
17
17
  wrapSessionKey
18
- } from "./chunk-B3S4SF3D.js";
18
+ } from "./chunk-S3EUZZJB.js";
19
19
  import {
20
20
  fetchTranscriptRecipients,
21
21
  uploadTranscriptRecords
@@ -23,17 +23,17 @@ import {
23
23
  import {
24
24
  transcriptEnvironmentPreference,
25
25
  transcriptsEnabled
26
- } from "./chunk-A2URMNFM.js";
26
+ } from "./chunk-BYAXXBNO.js";
27
27
  import {
28
28
  codexHome,
29
29
  pusharyDir
30
- } from "./chunk-RHLUJE4H.js";
30
+ } from "./chunk-UCGQEAKZ.js";
31
31
  import {
32
32
  readTranscriptPreference
33
- } from "./chunk-XBO42HKH.js";
33
+ } from "./chunk-NYHNLMQO.js";
34
34
  import {
35
35
  writeJsonAtomic
36
- } from "./chunk-4LL6LG5X.js";
36
+ } from "./chunk-T7E75EKA.js";
37
37
  import {
38
38
  getApiKey,
39
39
  getBaseUrl
@@ -59,7 +59,7 @@ var COMMAND_LIST = [
59
59
  },
60
60
  { name: "doctor", module: "pushary-doctor", summary: "Verify your Pushary installation is working" },
61
61
  { name: "disconnect", module: "pushary-disconnect", summary: "Turn off one agent (claude|codex|gemini|cursor)" },
62
- { name: "clean", module: "pushary-clean", summary: "Remove all Pushary configuration (--yes for non-interactive)" },
62
+ { name: "clean", module: "pushary-clean", summary: "Remove Pushary from this machine (--everything: the Mac app's setup too, --dry-run: preview)" },
63
63
  { name: "mode", module: "pushary-mode", summary: "Choose where approval requests appear" },
64
64
  { name: "wait", module: "pushary-wait", summary: 'Show or set the "wait for your phone" ladder (pushary wait 45)' },
65
65
  { name: "stats", module: "pushary-stats", summary: "Show the approval moments your agents hit while not connected" },
@@ -98,6 +98,7 @@ var COMMAND_OPTIONS = {
98
98
  ],
99
99
  clean: [
100
100
  ["--dry-run", "List everything it would remove and change nothing"],
101
+ ["--everything", "Also remove what the Mac app set up: quits it, then its keychain items, local state and editor extension"],
101
102
  ["--yes", "Remove everything without asking"]
102
103
  ],
103
104
  transcripts: [
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  pusharyDir
3
- } from "./chunk-RHLUJE4H.js";
3
+ } from "./chunk-UCGQEAKZ.js";
4
4
  import {
5
5
  readJsonSafe
6
- } from "./chunk-4LL6LG5X.js";
6
+ } from "./chunk-T7E75EKA.js";
7
7
 
8
8
  // src/process-ownership.ts
9
9
  import { createHash, randomUUID } from "crypto";
@@ -2,10 +2,10 @@ import {
2
2
  resolveBinary,
3
3
  resolveGlobalPackageVersion,
4
4
  resolvePackageVersionFromBinary
5
- } from "./chunk-RHLUJE4H.js";
5
+ } from "./chunk-UCGQEAKZ.js";
6
6
  import {
7
7
  MANAGED_PROVIDERS
8
- } from "./chunk-WPJS3OZH.js";
8
+ } from "./chunk-7IEB2GV4.js";
9
9
 
10
10
  // src/live-capabilities.ts
11
11
  var CLAUDE_BRIDGE_CAPABILITY = "claude-bridge";
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  describeKeyCheck,
3
3
  keyCheckFromResponse
4
- } from "./chunk-DON24PNT.js";
4
+ } from "./chunk-D4TNSUDY.js";
5
5
  import {
6
6
  createIo
7
7
  } from "./chunk-5RUIFDTP.js";
@@ -3,7 +3,7 @@ import {
3
3
  decodePublicKey,
4
4
  generateSessionKey,
5
5
  wrapSessionKey
6
- } from "./chunk-B3S4SF3D.js";
6
+ } from "./chunk-S3EUZZJB.js";
7
7
  import {
8
8
  fetchTranscriptRecipients,
9
9
  uploadTranscriptRecords
@@ -3,36 +3,40 @@ import {
3
3
  addPusharyToolPermissions,
4
4
  isPusharyHook,
5
5
  removeClaudeMcpServers
6
- } from "./chunk-ZHL62DRA.js";
6
+ } from "./chunk-5IBVIMWT.js";
7
7
  import {
8
8
  CLAUDE_HOOK_EVENTS,
9
9
  addGeminiMcpServer,
10
10
  removeGeminiMcpServer
11
- } from "./chunk-OE6U2AXM.js";
11
+ } from "./chunk-A7XIL2WD.js";
12
12
  import {
13
13
  CLAUDE_CODE_AGENT,
14
14
  parseApplyPatchFiles
15
- } from "./chunk-WXXDHGTZ.js";
15
+ } from "./chunk-IF46POXX.js";
16
16
  import {
17
17
  guardBinary,
18
18
  holdBudgetOf,
19
19
  registerHookEntry
20
- } from "./chunk-RHLUJE4H.js";
20
+ } from "./chunk-UCGQEAKZ.js";
21
21
  import {
22
22
  PHONE_ANSWERED_TOOLS,
23
23
  hookCompatibleProfile,
24
+ hookCompatibleProfileBySource,
24
25
  toToolLookup,
25
26
  withHookHoldBudget
26
- } from "./chunk-WPJS3OZH.js";
27
+ } from "./chunk-7IEB2GV4.js";
27
28
 
28
29
  // src/compatible-config.ts
29
30
  import { homedir } from "os";
30
31
  import { isAbsolute, join, resolve } from "path";
31
32
  var AGENT_FLAG = "--agent";
33
+ var SOURCE_FLAG = "--source";
32
34
  var agentArgument = (profile) => `${AGENT_FLAG}=${profile.agentType}`;
33
35
  var profileFromArgv = (argv) => {
34
36
  const named = namedAgent(argv);
35
- return named ? hookCompatibleProfile(named) : void 0;
37
+ if (named !== void 0) return hookCompatibleProfile(named);
38
+ const source = namedSource(argv);
39
+ return source === void 0 ? void 0 : hookCompatibleProfileBySource(source);
36
40
  };
37
41
  var activeIdentity = (argv) => {
38
42
  const profile = profileFromArgv(argv);
@@ -42,10 +46,18 @@ var namedAgent = (argv) => {
42
46
  const prefix = `${AGENT_FLAG}=`;
43
47
  return argv.find((argument) => argument.startsWith(prefix))?.slice(prefix.length);
44
48
  };
49
+ var namedSource = (argv) => {
50
+ const inline = argv.find((argument) => argument.startsWith(`${SOURCE_FLAG}=`));
51
+ if (inline) return inline.slice(SOURCE_FLAG.length + 1);
52
+ const index = argv.indexOf(SOURCE_FLAG);
53
+ return index === -1 ? void 0 : argv[index + 1] ?? "";
54
+ };
45
55
  var activeHookSource = (argv) => {
46
56
  const named = namedAgent(argv);
47
- if (named === void 0) return "claude";
48
- return hookCompatibleProfile(named)?.source ?? null;
57
+ if (named !== void 0) return hookCompatibleProfile(named)?.source ?? null;
58
+ const source = namedSource(argv);
59
+ if (source === void 0) return "claude";
60
+ return source === "claude" ? "claude" : hookCompatibleProfileBySource(source)?.source ?? null;
49
61
  };
50
62
  var PATCH_INPUT_KEYS = ["command", "patch", "input"];
51
63
  var patchedFiles = (toolInput) => [...new Set(PATCH_INPUT_KEYS.flatMap((key) => parseApplyPatchFiles(toolInput[key])))];
@@ -62,10 +74,6 @@ var normalizeToolCall = (profile, input) => {
62
74
  const lookup = lookupFor(profile, input);
63
75
  return { ...input, tool_name: lookup.tool, tool_input: lookup.input };
64
76
  };
65
- var unreadableTool = (profile, input) => {
66
- if (!profile || !input.tool_name) return void 0;
67
- return lookupFor(profile, input).unreadable ? input.tool_name : void 0;
68
- };
69
77
  var underHome = (segments, home = homedir()) => join(home, ...segments);
70
78
  var compatibleConfigFile = (profile, home) => underHome(profile.configFile, home);
71
79
  var compatibleMcpFile = (profile, home) => profile.mcp ? underHome(profile.mcp.file, home) : null;
@@ -215,7 +223,6 @@ export {
215
223
  activeIdentity,
216
224
  activeHookSource,
217
225
  normalizeToolCall,
218
- unreadableTool,
219
226
  compatibleConfigFile,
220
227
  compatibleMcpFile,
221
228
  compatibleInstructionsFile,
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  NOTIFICATION_PUSH_TYPES,
3
3
  POSTTOOLUSE_MIRROR_ONLY_TOOLS
4
- } from "./chunk-IAEVVUXO.js";
4
+ } from "./chunk-KZIXHLPQ.js";
5
5
  import {
6
6
  cancelQuestion,
7
7
  isPolicyConfig,
@@ -10,13 +10,13 @@ import {
10
10
  } from "./chunk-LGXUGYUH.js";
11
11
  import {
12
12
  getMachineId
13
- } from "./chunk-K7UIAE7I.js";
13
+ } from "./chunk-RQM5SMMR.js";
14
14
  import {
15
15
  withRetry
16
16
  } from "./chunk-EYRGBYZG.js";
17
17
  import {
18
18
  reportedInstallSource
19
- } from "./chunk-POAFXBNH.js";
19
+ } from "./chunk-P4JVVJ2D.js";
20
20
  import {
21
21
  getApiKey,
22
22
  getBaseUrl
@@ -44,7 +44,7 @@ import {
44
44
  resolveAutoResolveOrigin,
45
45
  resolvePolicy,
46
46
  toToolLookup
47
- } from "./chunk-WPJS3OZH.js";
47
+ } from "./chunk-7IEB2GV4.js";
48
48
 
49
49
  // src/policy.ts
50
50
  import { createHash } from "crypto";
@@ -2004,6 +2004,7 @@ export {
2004
2004
  preToolUseTimeoutDecision,
2005
2005
  readLastPrompt,
2006
2006
  CLAUDE_CODE_AGENT,
2007
+ AUTO_DECISION_WINDOW_MS,
2007
2008
  reportEvent,
2008
2009
  settleQuestionsForToolUse,
2009
2010
  handlePostToolUse,
@@ -1,17 +1,17 @@
1
1
  import {
2
2
  canonicalGateInputs
3
- } from "./chunk-WXXDHGTZ.js";
3
+ } from "./chunk-IF46POXX.js";
4
4
  import {
5
5
  canonicalJson
6
- } from "./chunk-RHLUJE4H.js";
6
+ } from "./chunk-UCGQEAKZ.js";
7
7
  import {
8
8
  writeFileAtomic
9
- } from "./chunk-4LL6LG5X.js";
9
+ } from "./chunk-T7E75EKA.js";
10
10
  import {
11
11
  BLOCKED_ACTION_GRANT_TTL_SECONDS,
12
12
  blockedActionIdentity,
13
13
  shouldDeferToNativeMode
14
- } from "./chunk-WPJS3OZH.js";
14
+ } from "./chunk-7IEB2GV4.js";
15
15
 
16
16
  // src/native-defer.ts
17
17
  var nativeDeferOptions = () => {
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  PRETOOLUSE_GATED_TOOLS
3
- } from "./chunk-WPJS3OZH.js";
3
+ } from "./chunk-7IEB2GV4.js";
4
4
 
5
5
  // src/claude-tools.ts
6
6
  var POSTTOOLUSE_MIRROR_ONLY_TOOLS = ["TodoWrite", "Task", "WebFetch", "WebSearch"];
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  resolvePathBinary
3
- } from "./chunk-RHLUJE4H.js";
3
+ } from "./chunk-UCGQEAKZ.js";
4
4
 
5
5
  // src/hermes-config.ts
6
6
  import { execFileSync } from "child_process";
@@ -233,8 +233,35 @@ var runHermesPythonScript = (python, script, ...args) => {
233
233
  }
234
234
  };
235
235
 
236
- // src/cli/dry-run.ts
236
+ // src/skills-cli.ts
237
237
  import { execSync } from "child_process";
238
+ var PUSHARY_SKILL_SOURCE = "Pushary/pushary-skill";
239
+ var PUSHARY_SKILL_NAME = "pushary";
240
+ var installSkillViaSkillsCli = (agent) => {
241
+ try {
242
+ execSync(`npx -y skills@latest add ${PUSHARY_SKILL_SOURCE}@${PUSHARY_SKILL_NAME} -y -g --agent ${agent}`, {
243
+ stdio: "pipe",
244
+ timeout: 9e4
245
+ });
246
+ return true;
247
+ } catch {
248
+ return false;
249
+ }
250
+ };
251
+ var installAgentSkill = async (request, effects) => {
252
+ if (request.skillsCliInUse) {
253
+ const startedAt = effects.now();
254
+ if (effects.runSkillsCli(request.agent)) {
255
+ const modifiedAt = effects.skillModifiedAt(request.agentSkillDir);
256
+ if (modifiedAt !== null && modifiedAt >= startedAt) return "skills-cli";
257
+ }
258
+ }
259
+ await effects.writePackagedSkill(request.agentSkillDir);
260
+ return "packaged-copy";
261
+ };
262
+
263
+ // src/cli/dry-run.ts
264
+ import { execSync as execSync2 } from "child_process";
238
265
  import { rmSync as rmSync2, writeFileSync as writeFileSync2 } from "fs";
239
266
  var createGuards = (isDryRun, note) => ({
240
267
  write: (path, contents) => {
@@ -247,7 +274,7 @@ var createGuards = (isDryRun, note) => ({
247
274
  },
248
275
  exec: (command, options, describe) => {
249
276
  if (isDryRun()) return note("run ", describe);
250
- execSync(command, options);
277
+ execSync2(command, options);
251
278
  }
252
279
  });
253
280
  var describeService = (effects) => {
@@ -271,6 +298,10 @@ export {
271
298
  HERMES_CONFIG_SCRIPT,
272
299
  resolveHermesPython,
273
300
  runHermesPythonScript,
301
+ PUSHARY_SKILL_SOURCE,
302
+ PUSHARY_SKILL_NAME,
303
+ installSkillViaSkillsCli,
304
+ installAgentSkill,
274
305
  createGuards,
275
306
  describeSetupSideEffects
276
307
  };
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  resolveInstallSourceFor
3
- } from "./chunk-POAFXBNH.js";
3
+ } from "./chunk-P4JVVJ2D.js";
4
4
  import {
5
5
  backupFile,
6
6
  readJsonSafe,
7
7
  writeFileAtomic,
8
8
  writeJsonAtomic
9
- } from "./chunk-4LL6LG5X.js";
9
+ } from "./chunk-T7E75EKA.js";
10
10
  import {
11
11
  configFilePath
12
12
  } from "./chunk-2UMNXADU.js";
@@ -102,6 +102,13 @@ var OUR_EXPORT = /^[ \t]*export[ \t]+PUSHARY_API_KEY=(['"]?)(pk_[a-f0-9]+\.[a-f0
102
102
  var MENTIONS_KEY = /PUSHARY_API_KEY/;
103
103
  var isComment = (line) => line.trimStart().startsWith("#");
104
104
  var exportLine = (apiKey) => `export PUSHARY_API_KEY='${apiKey}'`;
105
+ var LOGOUT_MARK = "# removed by pushary logout";
106
+ var disabledExportLine = (line) => `# ${line.trim()} ${LOGOUT_MARK}`;
107
+ var isDisabledExport = (line) => {
108
+ const trimmed = line.trim();
109
+ if (!isComment(trimmed) || !trimmed.endsWith(LOGOUT_MARK)) return false;
110
+ return OUR_EXPORT.test(trimmed.slice(1, -LOGOUT_MARK.length).trim());
111
+ };
105
112
  var keyPrefix = (key) => key.split(".")[0] ?? key;
106
113
  var rcResult = (kind, over = {}) => ({
107
114
  kind,
@@ -233,7 +240,7 @@ var clearKey = (options = {}) => {
233
240
  const next = lines.map((line) => {
234
241
  if (!OUR_EXPORT.test(line)) return line;
235
242
  rcLinesDisabled += 1;
236
- return `# ${line.trim()} # removed by pushary logout`;
243
+ return disabledExportLine(line);
237
244
  });
238
245
  if (rcLinesDisabled > 0) writeFileSync2(real, next.join("\n"));
239
246
  } catch {
@@ -283,11 +290,13 @@ var readKeySource = () => {
283
290
  };
284
291
 
285
292
  export {
293
+ CANDIDATE_RCS,
286
294
  resolveShellRc,
287
295
  installClaudeAlias,
288
296
  removeClaudeAlias,
289
297
  KEY_FILE_MODE,
290
298
  exportLine,
299
+ isDisabledExport,
291
300
  keyPrefix,
292
301
  writeKey,
293
302
  clearKey,
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  openCodeConfigDirFrom
3
- } from "./chunk-E7WBNGJS.js";
3
+ } from "./chunk-Q4UAMWXK.js";
4
4
  import {
5
5
  codexHomeFrom
6
- } from "./chunk-RHLUJE4H.js";
6
+ } from "./chunk-UCGQEAKZ.js";
7
7
  import {
8
8
  HOOK_COMPATIBLE_PROFILES
9
- } from "./chunk-WPJS3OZH.js";
9
+ } from "./chunk-7IEB2GV4.js";
10
10
 
11
11
  // src/vscode-config.ts
12
12
  import { homedir } from "os";
@@ -2,17 +2,17 @@ import {
2
2
  CLAUDE_HOOK_EVENTS,
3
3
  GEMINI_HOOK_EVENTS,
4
4
  hasGeminiHooks
5
- } from "./chunk-OE6U2AXM.js";
5
+ } from "./chunk-A7XIL2WD.js";
6
6
  import {
7
7
  CODEX_HOOK_EVENTS,
8
8
  hasCodexHooks,
9
9
  holdBudgetOf
10
- } from "./chunk-RHLUJE4H.js";
10
+ } from "./chunk-UCGQEAKZ.js";
11
11
  import {
12
12
  CURSOR_GATE_EVENTS,
13
13
  HOOK_LOCATOR_BINARY,
14
14
  hookCommandHoldBudget
15
- } from "./chunk-WPJS3OZH.js";
15
+ } from "./chunk-7IEB2GV4.js";
16
16
 
17
17
  // src/diagnostics/wiring.ts
18
18
  var record = (value) => value && typeof value === "object" && !Array.isArray(value) ? value : null;
@@ -3,7 +3,7 @@ import {
3
3
  } from "./chunk-2UMNXADU.js";
4
4
  import {
5
5
  normalizeInstallSource
6
- } from "./chunk-WPJS3OZH.js";
6
+ } from "./chunk-7IEB2GV4.js";
7
7
 
8
8
  // src/install-source.ts
9
9
  import { readFileSync } from "fs";
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  HOOK_BUDGETS,
3
3
  OPENCODE_APPROVAL_EVENT
4
- } from "./chunk-WPJS3OZH.js";
4
+ } from "./chunk-7IEB2GV4.js";
5
5
 
6
6
  // src/opencode-plugin.ts
7
7
  var OPENCODE_PLUGIN_MARKER = "pushary-opencode-plugin w1";
@@ -4,23 +4,23 @@ import {
4
4
  } from "./chunk-XHKBHWLX.js";
5
5
  import {
6
6
  getMachineId
7
- } from "./chunk-K7UIAE7I.js";
7
+ } from "./chunk-RQM5SMMR.js";
8
8
  import {
9
9
  pusharyDir,
10
10
  resolveGlobalBinary
11
- } from "./chunk-RHLUJE4H.js";
11
+ } from "./chunk-UCGQEAKZ.js";
12
12
  import {
13
13
  getPackageVersion
14
14
  } from "./chunk-DINDL2CF.js";
15
15
  import {
16
16
  readControlMode
17
- } from "./chunk-XBO42HKH.js";
17
+ } from "./chunk-NYHNLMQO.js";
18
18
  import {
19
19
  readJsonSafe,
20
20
  writeFileAtomic,
21
21
  writeJsonAtomic,
22
22
  writeJsonAtomicDurable
23
- } from "./chunk-4LL6LG5X.js";
23
+ } from "./chunk-T7E75EKA.js";
24
24
  import {
25
25
  getApiKey
26
26
  } from "./chunk-2UMNXADU.js";
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  pusharyDir
3
- } from "./chunk-RHLUJE4H.js";
3
+ } from "./chunk-UCGQEAKZ.js";
4
4
  import {
5
5
  writeFileAtomic
6
- } from "./chunk-4LL6LG5X.js";
6
+ } from "./chunk-T7E75EKA.js";
7
7
 
8
8
  // src/identity.ts
9
9
  import { randomUUID } from "crypto";
@@ -1,18 +1,18 @@
1
1
  import {
2
2
  detectClaudeVersion
3
- } from "./chunk-XBJW4MV5.js";
3
+ } from "./chunk-SGZ3IAWF.js";
4
4
  import {
5
5
  addClaudeMcpServer,
6
6
  addPusharyHooks,
7
7
  addPusharyToolPermissions
8
- } from "./chunk-ZHL62DRA.js";
8
+ } from "./chunk-5IBVIMWT.js";
9
9
  import {
10
10
  claudeUnprovenHolds,
11
11
  claudeWired,
12
12
  codexUnprovenHolds,
13
13
  codexWired,
14
14
  geminiWired
15
- } from "./chunk-DVO4SZMJ.js";
15
+ } from "./chunk-O6RN46OS.js";
16
16
  import {
17
17
  CLAUDE_HOOK_BINARY,
18
18
  CLAUDE_HOOK_EVENTS,
@@ -24,7 +24,7 @@ import {
24
24
  needsReregistration,
25
25
  registrationSignatures,
26
26
  supportedClaudeEvents
27
- } from "./chunk-OE6U2AXM.js";
27
+ } from "./chunk-A7XIL2WD.js";
28
28
  import {
29
29
  CODEX_HOOK_BINARY,
30
30
  addCodexHookTrust,
@@ -44,12 +44,12 @@ import {
44
44
  registrationHolderOf,
45
45
  resolveGlobalBinary,
46
46
  vscodePluginMcp
47
- } from "./chunk-RHLUJE4H.js";
47
+ } from "./chunk-UCGQEAKZ.js";
48
48
  import {
49
49
  readJsonSafe,
50
50
  writeFileAtomic,
51
51
  writeJsonAtomic
52
- } from "./chunk-4LL6LG5X.js";
52
+ } from "./chunk-T7E75EKA.js";
53
53
 
54
54
  // src/reapply.ts
55
55
  import { dirname, join } from "path";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  redactSecrets
3
- } from "./chunk-WPJS3OZH.js";
3
+ } from "./chunk-7IEB2GV4.js";
4
4
 
5
5
  // src/crypto.ts
6
6
  import nacl from "tweetnacl";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  parseVersion
3
- } from "./chunk-OE6U2AXM.js";
3
+ } from "./chunk-A7XIL2WD.js";
4
4
 
5
5
  // src/setup/agent-probe.ts
6
6
  import { execSync } from "child_process";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  writeJsonAtomicDurable
3
- } from "./chunk-4LL6LG5X.js";
3
+ } from "./chunk-T7E75EKA.js";
4
4
 
5
5
  // src/transcript-recipient-pin.ts
6
6
  import { existsSync, mkdirSync, readFileSync, rmSync } from "fs";
@@ -1,5 +1,5 @@
1
1
  // src/cli/fsx.ts
2
- import { copyFileSync, existsSync, fsyncSync, mkdirSync, openSync, closeSync, readFileSync, renameSync, unlinkSync, writeFileSync } from "fs";
2
+ import { copyFileSync, lstatSync, realpathSync, existsSync, fsyncSync, mkdirSync, openSync, closeSync, readFileSync, renameSync, unlinkSync, writeFileSync } from "fs";
3
3
  import { dirname, join } from "path";
4
4
  var readJsonSafe = (filePath) => {
5
5
  let raw;
@@ -24,7 +24,8 @@ var backupFile = (filePath) => {
24
24
  return target;
25
25
  };
26
26
  var writeFileAtomic = (filePath, contents, mode, encoding = "utf-8") => {
27
- const dir = dirname(filePath);
27
+ const target = lstatSync(filePath, { throwIfNoEntry: false })?.isSymbolicLink() ? realpathSync(filePath) : filePath;
28
+ const dir = dirname(target);
28
29
  if (!existsSync(dir)) mkdirSync(dir, { recursive: true });
29
30
  const temp = join(dir, `.${process.pid}-${stamp()}.pushary-tmp`);
30
31
  try {
@@ -35,7 +36,7 @@ var writeFileAtomic = (filePath, contents, mode, encoding = "utf-8") => {
35
36
  } finally {
36
37
  closeSync(handle);
37
38
  }
38
- renameSync(temp, filePath);
39
+ renameSync(temp, target);
39
40
  } catch (err) {
40
41
  try {
41
42
  if (existsSync(temp)) unlinkSync(temp);
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  renderCommandHelp
3
- } from "./chunk-LZQVAEWP.js";
3
+ } from "./chunk-FAH3D74E.js";
4
4
  import {
5
5
  getPackageVersion
6
6
  } from "./chunk-DINDL2CF.js";
@@ -15,10 +15,10 @@ import {
15
15
  } from "./chunk-EYRGBYZG.js";
16
16
  import {
17
17
  reportedInstallSource
18
- } from "./chunk-POAFXBNH.js";
18
+ } from "./chunk-P4JVVJ2D.js";
19
19
  import {
20
20
  isAnswerSource
21
- } from "./chunk-WPJS3OZH.js";
21
+ } from "./chunk-7IEB2GV4.js";
22
22
 
23
23
  // src/reach.ts
24
24
  var reachVerdict = (channels) => {