@imdeadpool/guardex 5.0.11 → 5.0.13

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.
@@ -12,6 +12,8 @@ AUTO_CLEANUP_RAW="${MUSAFETY_CODEX_AUTO_CLEANUP:-true}"
12
12
  AUTO_WAIT_FOR_MERGE_RAW="${MUSAFETY_CODEX_WAIT_FOR_MERGE:-true}"
13
13
  OPENSPEC_AUTO_INIT_RAW="${MUSAFETY_OPENSPEC_AUTO_INIT:-true}"
14
14
  OPENSPEC_PLAN_SLUG_OVERRIDE="${MUSAFETY_OPENSPEC_PLAN_SLUG:-}"
15
+ OPENSPEC_CHANGE_SLUG_OVERRIDE="${MUSAFETY_OPENSPEC_CHANGE_SLUG:-}"
16
+ OPENSPEC_CAPABILITY_SLUG_OVERRIDE="${MUSAFETY_OPENSPEC_CAPABILITY_SLUG:-}"
15
17
 
16
18
  normalize_bool() {
17
19
  local raw="${1:-}"
@@ -150,6 +152,27 @@ resolve_openspec_plan_slug() {
150
152
  sanitize_slug "${branch_name//\//-}" "$task_slug"
151
153
  }
152
154
 
155
+ resolve_openspec_change_slug() {
156
+ local branch_name="$1"
157
+ local task_slug
158
+ task_slug="$(sanitize_slug "$TASK_NAME" "task")"
159
+ if [[ -n "$OPENSPEC_CHANGE_SLUG_OVERRIDE" ]]; then
160
+ sanitize_slug "$OPENSPEC_CHANGE_SLUG_OVERRIDE" "$task_slug"
161
+ return 0
162
+ fi
163
+ sanitize_slug "${branch_name//\//-}" "$task_slug"
164
+ }
165
+
166
+ resolve_openspec_capability_slug() {
167
+ local task_slug
168
+ task_slug="$(sanitize_slug "$TASK_NAME" "task")"
169
+ if [[ -n "$OPENSPEC_CAPABILITY_SLUG_OVERRIDE" ]]; then
170
+ sanitize_slug "$OPENSPEC_CAPABILITY_SLUG_OVERRIDE" "$task_slug"
171
+ return 0
172
+ fi
173
+ sanitize_slug "$task_slug" "general-behavior"
174
+ }
175
+
153
176
  hydrate_local_helper_in_worktree() {
154
177
  local worktree="$1"
155
178
  local relative_path="$2"
@@ -192,13 +215,6 @@ resolve_start_base_branch() {
192
215
  return 0
193
216
  fi
194
217
 
195
- local current_branch
196
- current_branch="$(git -C "$repo_root" rev-parse --abbrev-ref HEAD 2>/dev/null || true)"
197
- if [[ -n "$current_branch" && "$current_branch" != "HEAD" ]]; then
198
- printf '%s' "$current_branch"
199
- return 0
200
- fi
201
-
202
218
  printf 'dev'
203
219
  }
204
220
 
@@ -338,30 +354,20 @@ has_origin_remote() {
338
354
  }
339
355
 
340
356
  resolve_worktree_base_branch() {
341
- local wt="$1"
357
+ local _wt="$1"
342
358
  if [[ "$BASE_BRANCH_EXPLICIT" -eq 1 && -n "$BASE_BRANCH" ]]; then
343
359
  printf '%s' "$BASE_BRANCH"
344
360
  return 0
345
361
  fi
346
362
 
347
- local branch
348
- branch="$(git -C "$wt" rev-parse --abbrev-ref HEAD 2>/dev/null || true)"
349
- if [[ -z "$branch" || "$branch" == "HEAD" ]]; then
350
- return 0
351
- fi
352
-
353
- local stored_base
354
- stored_base="$(git -C "$repo_root" config --get "branch.${branch}.musafetyBase" || true)"
355
- if [[ -n "$stored_base" ]]; then
356
- printf '%s' "$stored_base"
357
- return 0
358
- fi
359
-
360
363
  local configured_base
361
364
  configured_base="$(git -C "$repo_root" config --get multiagent.baseBranch || true)"
362
365
  if [[ -n "$configured_base" ]]; then
363
366
  printf '%s' "$configured_base"
367
+ return 0
364
368
  fi
369
+
370
+ printf 'dev'
365
371
  }
366
372
 
367
373
  sync_worktree_with_base() {
@@ -443,6 +449,43 @@ ensure_openspec_plan_workspace() {
443
449
  echo "[codex-agent] OpenSpec plan workspace: ${wt}/openspec/plan/${plan_slug}"
444
450
  }
445
451
 
452
+ ensure_openspec_change_workspace() {
453
+ local wt="$1"
454
+ local branch="$2"
455
+
456
+ if [[ "$OPENSPEC_AUTO_INIT" -ne 1 ]]; then
457
+ return 0
458
+ fi
459
+
460
+ hydrate_local_helper_in_worktree "$wt" "scripts/openspec/init-change-workspace.sh"
461
+
462
+ local openspec_script="${wt}/scripts/openspec/init-change-workspace.sh"
463
+ if [[ ! -f "$openspec_script" ]]; then
464
+ echo "[codex-agent] Missing OpenSpec change init script in sandbox: ${openspec_script}" >&2
465
+ echo "[codex-agent] Run 'gx setup --target ${repo_root}' and retry." >&2
466
+ return 1
467
+ fi
468
+ if [[ ! -x "$openspec_script" ]]; then
469
+ chmod +x "$openspec_script" 2>/dev/null || true
470
+ fi
471
+
472
+ local change_slug capability_slug init_output=""
473
+ change_slug="$(resolve_openspec_change_slug "$branch")"
474
+ capability_slug="$(resolve_openspec_capability_slug)"
475
+ if ! init_output="$(
476
+ cd "$wt"
477
+ bash "scripts/openspec/init-change-workspace.sh" "$change_slug" "$capability_slug" 2>&1
478
+ )"; then
479
+ printf '%s\n' "$init_output" >&2
480
+ echo "[codex-agent] OpenSpec workspace initialization failed for change '${change_slug}'." >&2
481
+ return 1
482
+ fi
483
+ if [[ -n "$init_output" ]]; then
484
+ printf '%s\n' "$init_output"
485
+ fi
486
+ echo "[codex-agent] OpenSpec change workspace: ${wt}/openspec/changes/${change_slug}"
487
+ }
488
+
446
489
  worktree_has_changes() {
447
490
  local wt="$1"
448
491
  if ! git -C "$wt" diff --quiet -- . ":(exclude).omx/state/agent-file-locks.json"; then
@@ -598,12 +641,18 @@ looks_like_conflict_failure() {
598
641
  run_finish_flow() {
599
642
  local wt="$1"
600
643
  local branch="$2"
644
+ local finish_base_branch=""
601
645
  local finish_output=""
602
646
  local -a finish_args
603
647
 
604
648
  finish_args=(--branch "$branch")
605
- if [[ "$BASE_BRANCH_EXPLICIT" -eq 1 ]]; then
606
- finish_args+=(--base "$BASE_BRANCH")
649
+ if [[ "$BASE_BRANCH_EXPLICIT" -eq 1 && -n "$BASE_BRANCH" ]]; then
650
+ finish_base_branch="$BASE_BRANCH"
651
+ else
652
+ finish_base_branch="$(resolve_worktree_base_branch "$wt")"
653
+ fi
654
+ if [[ -n "$finish_base_branch" ]]; then
655
+ finish_args+=(--base "$finish_base_branch")
607
656
  fi
608
657
  if [[ "$AUTO_CLEANUP" -eq 1 ]]; then
609
658
  finish_args+=(--cleanup)
@@ -613,9 +662,11 @@ run_finish_flow() {
613
662
  fi
614
663
 
615
664
  if has_origin_remote; then
616
- if command -v gh >/dev/null 2>&1 || command -v "${MUSAFETY_GH_BIN:-gh}" >/dev/null 2>&1; then
617
- finish_args+=(--via-pr)
665
+ if ! command -v "${MUSAFETY_GH_BIN:-gh}" >/dev/null 2>&1 && ! command -v gh >/dev/null 2>&1; then
666
+ echo "[codex-agent] Auto-finish requires GitHub CLI for PR flow; command not found: ${MUSAFETY_GH_BIN:-gh}" >&2
667
+ return 2
618
668
  fi
669
+ finish_args+=(--via-pr)
619
670
  else
620
671
  echo "[codex-agent] No origin remote detected; skipping auto-finish merge/PR pipeline." >&2
621
672
  return 2
@@ -631,7 +682,7 @@ run_finish_flow() {
631
682
  if [[ "$AUTO_REVIEW_ON_CONFLICT" -eq 1 ]] && looks_like_conflict_failure "$finish_output"; then
632
683
  echo "[codex-agent] Auto-finish hit conflicts. Launching Codex conflict-review pass in sandbox..." >&2
633
684
  local review_prompt
634
- review_prompt="Resolve git conflicts for branch ${branch} against ${BASE_BRANCH:-base branch}, then commit the resolution in this sandbox worktree and exit."
685
+ review_prompt="Resolve git conflicts for branch ${branch} against ${finish_base_branch:-dev}, then commit the resolution in this sandbox worktree and exit."
635
686
 
636
687
  (
637
688
  cd "$wt"
@@ -665,6 +716,10 @@ if [[ -z "$worktree_branch" || "$worktree_branch" == "HEAD" ]]; then
665
716
  exit 1
666
717
  fi
667
718
 
719
+ if ! ensure_openspec_change_workspace "$worktree_path" "$worktree_branch"; then
720
+ exit 1
721
+ fi
722
+
668
723
  if ! ensure_openspec_plan_workspace "$worktree_path" "$worktree_branch"; then
669
724
  exit 1
670
725
  fi
@@ -735,7 +790,7 @@ else
735
790
  if [[ "$auto_finish_completed" -eq 1 ]]; then
736
791
  echo "[codex-agent] Branch kept intentionally. Cleanup on demand: gx cleanup --branch \"${worktree_branch}\""
737
792
  else
738
- echo "[codex-agent] If finished, merge with: bash scripts/agent-branch-finish.sh --branch \"${worktree_branch}\" --via-pr"
793
+ echo "[codex-agent] If finished, merge with: bash scripts/agent-branch-finish.sh --branch \"${worktree_branch}\" --base dev --via-pr --wait-for-merge"
739
794
  echo "[codex-agent] Cleanup on demand: gx cleanup --branch \"${worktree_branch}\""
740
795
  fi
741
796
  fi
@@ -0,0 +1,87 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+
4
+ if [[ $# -lt 1 || $# -gt 2 ]]; then
5
+ echo "Usage: $0 <change-slug> [capability-slug]"
6
+ echo "Example: $0 add-dashboard-live-usage runtime-migration"
7
+ exit 1
8
+ fi
9
+
10
+ CHANGE_SLUG="$1"
11
+ CAPABILITY_SLUG="${2:-$CHANGE_SLUG}"
12
+
13
+ if [[ "$CHANGE_SLUG" =~ [^a-z0-9-] ]]; then
14
+ echo "Error: change slug must be kebab-case (lowercase letters, numbers, hyphens)."
15
+ exit 1
16
+ fi
17
+
18
+ if [[ "$CAPABILITY_SLUG" =~ [^a-z0-9-] ]]; then
19
+ echo "Error: capability slug must be kebab-case (lowercase letters, numbers, hyphens)."
20
+ exit 1
21
+ fi
22
+
23
+ CHANGE_DIR="openspec/changes/${CHANGE_SLUG}"
24
+ SPEC_DIR="${CHANGE_DIR}/specs/${CAPABILITY_SLUG}"
25
+ TODAY="$(date -u +%Y-%m-%d)"
26
+
27
+ mkdir -p "$SPEC_DIR"
28
+
29
+ if [[ ! -f "${CHANGE_DIR}/.openspec.yaml" ]]; then
30
+ cat > "${CHANGE_DIR}/.openspec.yaml" <<YAMLEOF
31
+ schema: spec-driven
32
+ created: ${TODAY}
33
+ YAMLEOF
34
+ fi
35
+
36
+ if [[ ! -f "${CHANGE_DIR}/proposal.md" ]]; then
37
+ cat > "${CHANGE_DIR}/proposal.md" <<PROPOSALEOF
38
+ ## Why
39
+
40
+ - TODO: describe the user/problem outcome this change addresses.
41
+
42
+ ## What Changes
43
+
44
+ - TODO: summarize the intended behavior and scope.
45
+
46
+ ## Impact
47
+
48
+ - TODO: call out risks, rollout notes, and affected surfaces.
49
+ PROPOSALEOF
50
+ fi
51
+
52
+ if [[ ! -f "${CHANGE_DIR}/tasks.md" ]]; then
53
+ cat > "${CHANGE_DIR}/tasks.md" <<TASKSEOF
54
+ ## 1. Specification
55
+
56
+ - [ ] 1.1 Finalize proposal scope and acceptance criteria for \`${CHANGE_SLUG}\`.
57
+ - [ ] 1.2 Define normative requirements in \`specs/${CAPABILITY_SLUG}/spec.md\`.
58
+
59
+ ## 2. Implementation
60
+
61
+ - [ ] 2.1 Implement scoped behavior changes.
62
+ - [ ] 2.2 Add/update focused regression coverage.
63
+
64
+ ## 3. Verification
65
+
66
+ - [ ] 3.1 Run targeted project verification commands.
67
+ - [ ] 3.2 Run \`openspec validate ${CHANGE_SLUG} --type change --strict\`.
68
+ - [ ] 3.3 Run \`openspec validate --specs\`.
69
+ TASKSEOF
70
+ fi
71
+
72
+ if [[ ! -f "${SPEC_DIR}/spec.md" ]]; then
73
+ cat > "${SPEC_DIR}/spec.md" <<SPECEOF
74
+ ## ADDED Requirements
75
+
76
+ ### Requirement: ${CAPABILITY_SLUG} behavior
77
+ The system SHALL enforce ${CAPABILITY_SLUG} behavior as defined by this change.
78
+
79
+ #### Scenario: Baseline acceptance
80
+ - **WHEN** ${CAPABILITY_SLUG} behavior is exercised
81
+ - **THEN** the expected outcome is produced
82
+ - **AND** regressions are covered by tests.
83
+ SPECEOF
84
+ fi
85
+
86
+ echo "[guardex] OpenSpec change workspace ready: ${CHANGE_DIR}"
87
+ echo "[guardex] OpenSpec change spec scaffold: ${SPEC_DIR}/spec.md"