Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 7 additions & 6 deletions .claude/agents/test.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ make clean-envs && test/bats/bin/bats tests/04-pgtle.bats
✅ **DO THIS**:
```bash
test/bats/bin/bats tests/04-pgtle.bats # Auto-rebuilds if needed
DEBUG=5 test/bats/bin/bats tests/04-pgtle.bats # For investigation
TESTDEBUG=5 test/bats/bin/bats tests/04-pgtle.bats # For investigation
```

**ONLY clean when debugging the cleanup mechanism itself** and you MUST document what cleanup failure you're investigating.
Expand Down Expand Up @@ -228,11 +228,11 @@ test/bats/bin/bats tests/test-pgtle-install.bats

### Debugging
```bash
DEBUG=2 test/bats/bin/bats tests/01-meta.bats # Debug output
TESTDEBUG=2 test/bats/bin/bats tests/01-meta.bats # Debug output
test/bats/bin/bats --verbose tests/01-meta.bats # BATS verbose mode
```

**Debug levels**: 10 (critical), 20 (significant), 30 (general), 40 (verbose), 50+ (maximum)
**Debug levels** (set via `TESTDEBUG`): 1 (pollution/critical), 2 (major workflow), 3 (detailed state), 5 (verbose internals)

---

Expand All @@ -247,7 +247,8 @@ Tests set these automatically (from `tests/helpers.bash`):
- `PGXNBRANCH` - Branch to use (defaults to `master`)
- `TEST_TEMPLATE` - Template directory (defaults to `${TOPDIR}/template`)
- `PG_LOCATION` - PostgreSQL installation path
- `DEBUG` - Debug level (0-5)
- `TESTDEBUG` - Test infrastructure debug level (0-5); controls helpers.bash debug() output
- `DEBUG` - pgxntool script debug level; controls debug() in pgxntool/lib.sh (independent of TESTDEBUG)

---

Expand Down Expand Up @@ -292,7 +293,7 @@ test/bats/bin/bats tests/04-pgtle.bats # Auto-rebuilds foundation via ensure_fo
### Debugging Test Failures

1. Read test output (which assertion failed?)
2. Use DEBUG mode: `DEBUG=5 test/bats/bin/bats tests/test-name.bats`
2. Use TESTDEBUG mode: `TESTDEBUG=5 test/bats/bin/bats tests/test-name.bats`
3. Inspect environment: `cd .envs/sequential/repo && ls -la`
4. Check state markers: `ls .envs/sequential/.bats-state/`
5. **Work top-down**: Fix earliest failure first (downstream failures often cascade)
Expand Down Expand Up @@ -361,7 +362,7 @@ make test
test/bats/bin/bats tests/04-pgtle.bats

# Debug
DEBUG=5 test/bats/bin/bats tests/04-pgtle.bats
TESTDEBUG=5 test/bats/bin/bats tests/04-pgtle.bats

# Test infrastructure
make test-recursion
Expand Down
20 changes: 10 additions & 10 deletions .claude/settings.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,17 @@
"permissions": {
"allow": [
"Bash(make:*)",
"Bash(DEBUG=1 make:*)",
"Bash(DEBUG=2 make:*)",
"Bash(DEBUG=3 make:*)",
"Bash(DEBUG=4 make:*)",
"Bash(DEBUG=5 make:*)",
"Bash(TESTDEBUG=1 make:*)",
"Bash(TESTDEBUG=2 make:*)",
"Bash(TESTDEBUG=3 make:*)",
"Bash(TESTDEBUG=4 make:*)",
"Bash(TESTDEBUG=5 make:*)",
"Bash(test/bats/bin/bats:*)",
"Bash(DEBUG=1 test/bats/bin/bats:*)",
"Bash(DEBUG=2 test/bats/bin/bats:*)",
"Bash(DEBUG=3 test/bats/bin/bats:*)",
"Bash(DEBUG=4 test/bats/bin/bats:*)",
"Bash(DEBUG=5 test/bats/bin/bats:*)",
"Bash(TESTDEBUG=1 test/bats/bin/bats:*)",
"Bash(TESTDEBUG=2 test/bats/bin/bats:*)",
"Bash(TESTDEBUG=3 test/bats/bin/bats:*)",
"Bash(TESTDEBUG=4 test/bats/bin/bats:*)",
"Bash(TESTDEBUG=5 test/bats/bin/bats:*)",
"Edit",
"WebFetch",

Expand Down
12 changes: 12 additions & 0 deletions .claude/skills/commit/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,18 @@ bash .claude/skills/commit/scripts/gather-repo-info.sh ../pgxntool .

Review output. Identify which repos have changes.

### 2b. Check Debug Level Distribution (pgxntool .sh changes only)

If `../pgxntool/*.sh` files are in the diff, scan each changed file:

1. Collect all `debug N` call levels
2. Note whether the file contains loops (`for`, `while`)
3. Flag if: file has loops AND every debug call uses a single-digit level (1-9)
4. Flag if: file has 5+ debug calls AND they all use the exact same level

This is **advisory only** — present any findings in Step 5 and let the user decide.
If nothing looks off, say nothing (don't add noise to the common case).

### 3. Check HISTORY.asc (pgxntool changes only)

Read `../pgxntool/HISTORY.asc`. Determine if changes are significant and user-visible:
Expand Down
10 changes: 10 additions & 0 deletions .claude/skills/test/scripts/run-tests.sh
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,16 @@

set -euo pipefail

# Set PGPORT from PGCLUSTER if not already set, so pg_regress and other raw
# PostgreSQL binaries use the correct cluster (Debian pg_wrapper handles
# PGCLUSTER but raw binaries only respect PGPORT).
if [ -z "${PGPORT:-}" ] && [ -n "${PGCLUSTER:-}" ]; then
_port=$(pg_lsclusters -h 2>/dev/null | awk -v c="$PGCLUSTER" \
'BEGIN{split(c,a,"/"); v=a[1]; n=a[2]} $1==v && $2==n {print $3; exit}')
[ -n "$_port" ] && export PGPORT=$_port
unset _port
fi

# Determine log directory (per-project, based on working directory)
LOG_DIR="/tmp/pgxntool-test-logs$(pwd | sed 's/\//_/g')"
mkdir -p "$LOG_DIR"
Expand Down
2 changes: 1 addition & 1 deletion template-multi-extension/ext_beta.control
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
comment = 'Beta extension for multi-extension testing'
default_version = '2.5.0' # DO NOT REMOVE: trailing comment exercises parse_control_file comment handling (issue #25)
default_version = '2.5.0' # DO NOT REMOVE: multiple spaces before comment exercises parse_control_file whitespace trimming (issues #25, #26)
requires = 'plpgsql'
1 change: 1 addition & 0 deletions template/test/expected/base.out
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
\set ECHO none

single_ext_ok
2 changes: 2 additions & 0 deletions template/test/expected/pgxntool-test.out
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
\set ECHO none
1..1
ok 1
# TRANSACTION INTENTIONALLY LEFT OPEN!
3 changes: 3 additions & 0 deletions template/test/sql/base.sql
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
\set ECHO none
-- DO NOT REMOVE: pg_regress runs psql with echo-all, so without this the SQL
-- input is echoed into the output and never matches expected/base.out.
\a
\t
SELECT pg_sleep(.1);
Expand Down
5 changes: 5 additions & 0 deletions template/test/sql/pgxntool-test.sql
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
\set ECHO none
-- DO NOT REMOVE: pg_regress runs psql with echo-all, so without this every
-- input line (including all of setup.sql) is echoed into the output and never
-- matches expected/pgxntool-test.out. This mirrors the standard pgxntool pgtap
-- convention (every test file starts with \set ECHO none).
\i test/pgxntool/setup.sql

SELECT plan(1);
Expand Down
6 changes: 4 additions & 2 deletions test/lib/helpers.bash
Original file line number Diff line number Diff line change
Expand Up @@ -70,13 +70,15 @@ error() {

# Debug output function
# Usage: debug LEVEL "message"
# Outputs message if DEBUG >= LEVEL
# Outputs message if TESTDEBUG >= LEVEL
# Uses TESTDEBUG (not DEBUG) to avoid conflating test infrastructure verbosity
# with pgxntool script verbosity — set them independently as needed.
debug() {
local level=$1
shift
local message="$*"

if [ "${DEBUG:-0}" -ge "$level" ]; then
if [ "${TESTDEBUG:-0}" -ge "$level" ]; then
out -f "DEBUG[$level]: $message"
fi
}
Expand Down
27 changes: 27 additions & 0 deletions test/sequential/04-pgtle.bats
Original file line number Diff line number Diff line change
Expand Up @@ -228,6 +228,33 @@ teardown_file() {
rm -f empty.control
}

@test "pgtle: parse_control_file handles whitespace before trailing comment" {
# Multiple spaces and a tab before a comment would leave stray whitespace after
# comment removal if only a single space was stripped (issue #26 follow-up to #25).
# Verify parse_control_file correctly strips all trailing whitespace so pgtle.sh
# finds the versioned SQL file and succeeds.

# Multiple spaces before comment
printf "default_version = '7.7.7' # multiple spaces\n" > wspace_test.control
echo "SELECT 1;" > sql/wspace_test--7.7.7.sql

run "$TEST_REPO/pgxntool/pgtle.sh" --extension wspace_test --pgtle-version 1.5.0+
assert_success
assert_file_exists "pg_tle/1.5.0+/wspace_test.sql"

# Tab before comment
printf "default_version = '6.6.6'\t# tab before comment\n" > tab_test.control
echo "SELECT 1;" > sql/tab_test--6.6.6.sql

run "$TEST_REPO/pgxntool/pgtle.sh" --extension tab_test --pgtle-version 1.5.0+
assert_success
assert_file_exists "pg_tle/1.5.0+/tab_test.sql"

# Cleanup
rm -f wspace_test.control sql/wspace_test--7.7.7.sql pg_tle/1.5.0+/wspace_test.sql
rm -f tab_test.control sql/tab_test--6.6.6.sql pg_tle/1.5.0+/tab_test.sql
}

@test "pgtle: warning on module_pathname in control" {
# Create a C extension control file
echo "comment = 'C extension'" > cext.control
Expand Down
20 changes: 14 additions & 6 deletions test/standard/make-results.bats
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,6 @@
# Not tested here:
# - make results when already up-to-date (idempotent case). Safe to re-run,
# but the extra make test invocation adds non-trivial time for little value.
# - verify-results behavior (blocking make results when tests fail) is tested
# separately in test-verify-results.bats.

load ../lib/helpers

Expand Down Expand Up @@ -73,11 +71,21 @@ setup() {
[ -d "test/output" ] || echo "$output" | grep -q "diff"
}

@test "make results is blocked by verify-results when tests fail" {
# The previous test ran make test which failed (mismatch), creating regression.diffs.
# With the fixed ordering (results: test verify-results), make results re-runs
# make test first (still fails → regression.diffs), then verify-results blocks.
# This test verifies that verify-results correctly intercepts failing results.
run make results
assert_failure
assert_contains "$output" "Cannot run 'make results'"
}

@test "make results updates expected output" {
# Run make results to fix the expected output.
# Must disable verify-results: the previous test created a mismatch, which caused
# make test to generate regression.diffs. verify-results blocks make results when
# regression.diffs exists, so we bypass it here to test the fix-mismatch workflow.
# Run make results with verify-results disabled to actually fix the mismatch.
# regression.diffs still exists from the previous test's make test run.
# Disabling verify-results lets make results run make test and copy the fresh
# results to expected/, fixing the mismatch.
run make PGXNTOOL_ENABLE_VERIFY_RESULTS=no results
assert_success
}
Expand Down
12 changes: 7 additions & 5 deletions test/standard/multi-extension.bats
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,10 @@
# - sql/ext_beta.sql
# - META.in.json (with provides for both extensions)
#
# Note: ext_beta.control intentionally has a trailing comment on default_version.
# This exercises pgtle.sh's parse_control_file to catch the quote-before-comment bug
# (issue #25). Do not remove the comment from ext_beta.control.
# Note: ext_beta.control intentionally has MULTIPLE spaces before the trailing comment
# on default_version. This exercises parse_control_file's whitespace trimming to catch
# both the single-space-only bug (issue #25) and the multiple-spaces bug (issue #26).
# Do not reduce the spaces or remove the comment from ext_beta.control.

load ../lib/helpers

Expand Down Expand Up @@ -112,8 +113,9 @@ setup() {
run make all
assert_success

# Also verify pgtle generation works — ext_beta.control has a trailing comment on
# default_version to exercise parse_control_file's comment handling (issue #25).
# Also verify pgtle generation works — ext_beta.control has multiple spaces before
# a trailing comment on default_version to exercise parse_control_file whitespace
# trimming (issues #25, #26).
run make pgtle
assert_success
}
Expand Down
45 changes: 22 additions & 23 deletions test/standard/test-verify-results.bats
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,10 @@
# Validates that verify-results correctly blocks make results when tests are
# failing, detects pgtap failures, and can be disabled.
#
# Separate from make-results.bats because verify-results is pure file-checking
# logic that doesn't require PostgreSQL. Keeping it in its own suite means these
# tests always run, even when PostgreSQL is unavailable (make-results.bats skips
# entirely in that case).
# NOTE: pgxntool makes verify-results depend on test (verify-results: test), so
# `make verify-results` re-runs the suite and therefore requires PostgreSQL. The
# pgtap-detection cases below plant files in test/results/ (which survive the
# fresh test run) rather than a regression.diffs (which the fresh run overwrites).

load ../lib/helpers

Expand All @@ -29,38 +29,37 @@ setup() {
assert_success
}

@test "verify-results has no dependencies on test execution" {
@test "verify-results depends on test execution" {
# pgxntool makes verify-results depend on test (verify-results: test) so that
# `make results` re-runs the tests and checks the FRESH regression.diffs, even
# under make -j. Confirm the dependency is wired: a dry-run of verify-results
# must include the installcheck recipe pulled in via the test target.
run make -n verify-results 2>&1
assert_success
assert_not_contains "$output" "installcheck"
assert_contains "$output" "installcheck"
}

@test "regression.diffs blocks both verify-results and make results" {
cat > test/regression.diffs <<'EOF'
*** test/expected/test.out
--- test/results/test.out
***************
*** 1 ****
! expected
--- 1 ----
! actual
EOF
@test "verify-results blocks when a test actually fails" {
# verify-results depends on test, so `make verify-results` re-runs the suite.
# A planted regression.diffs would just be overwritten by that fresh run, so
# force a REAL failure by corrupting an expected file, then confirm
# verify-results refuses to let make results proceed.
echo >> test/expected/base.out

run make verify-results
assert_failure
assert_contains "$output" "Tests are failing"
assert_contains "$output" "Cannot run 'make results'"

# make results itself should also be blocked
run make results
assert_failure
assert_contains "$output" "Cannot run 'make results'"

# State left for next test (regression.diffs still present)
# Restore clean state for the tests that follow.
run git checkout -- test/expected/base.out
assert_success
rm -f test/regression.diffs
}

@test "verify-results can be disabled" {
# regression.diffs still present from previous test
# With verify-results disabled, results depends only on test, so its dry-run
# never mentions the verify-results block message.
run make -n results PGXNTOOL_ENABLE_VERIFY_RESULTS=no 2>&1
assert_success
# Check that verify-results recipe commands are not in the dry-run output.
Expand Down
Loading