Skip to content
Closed
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
43 changes: 43 additions & 0 deletions docs/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,49 @@

All notable changes to ACE will be captured in this document. This project follows semantic versioning; the latest changes appear first.

## [v2.0.0] - 2026-04-21

### Added
- **Native PostgreSQL support.** `table-diff`, `table-repair`, and Merkle tree
operations now work on vanilla PostgreSQL (14+) without the spock extension.
ACE auto-detects whether spock is installed on each node and branches
accordingly; `spock-diff` and `repset-diff` return a clear error when spock
is not present.
- Native PG alternatives for replication origin and slot LSN queries using
`pg_subscription` and `pg_replication_origin` catalog tables.
- `--against-origin` now works on native PG logical replication setups by
resolving replication origin IDs to subscription names.
- Integration test suite for native PostgreSQL covering table-diff, table-repair
(unidirectional, bidirectional, fix-nulls, dry-run), Merkle tree operations,
and origin-tracked replication with repair.

### Changed
- ACE schema name in SQL templates is now quoted with `pgx.Identifier.Sanitize()`
to prevent SQL breakage with non-simple schema names (e.g., mixed case,
hyphens).
Comment on lines +21 to +24
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Description: Verify whether ACE schema creation/template paths sanitize schema identifiers.

rg -n -C3 'CreateSchema\(|aceSchema\(\)|pgx\.Identifier|\.Sanitize\(\)' --type go

Repository: pgEdge/ace

Length of output: 50366


🏁 Script executed:

fd -e sql -o -e tmpl -o -e tpl | head -20

Repository: pgEdge/ace

Length of output: 170


🏁 Script executed:

find . -name "*.sql" -o -name "*.tmpl" -o -name "*template*" | grep -v node_modules | head -30

Repository: pgEdge/ace

Length of output: 102


🏁 Script executed:

rg -l "CREATE SCHEMA|CreateSchema" --type sql --type tmpl --max-count 20

Repository: pgEdge/ace

Length of output: 82


🏁 Script executed:

cat -n db/queries/templates.go | head -100

Repository: pgEdge/ace

Length of output: 5019


🏁 Script executed:

rg -n "CreateSchema|GetCreateSchema" db/queries/

Repository: pgEdge/ace

Length of output: 512


🏁 Script executed:

sed -n '1510,1520p' db/queries/templates.go

Repository: pgEdge/ace

Length of output: 585


Clarify the scope of identifier sanitization in the release notes.

The CHANGELOG claim is inaccurate. The ACE schema name is sanitized via the aceSchema() Go function before being passed to CreateSchema, not within the SQL template itself. The CreateSchema SQL template (line 1510 in db/queries/templates.go) renders {{.SchemaName}} without calling .Sanitize(). While the final schema name is quoted (because m.aceSchema() at line 819 in internal/consistency/mtree/merkle.go returns a pre-sanitized string), the sanitization happens in Go code, not "in SQL templates" as the release note suggests. Revise line 22 to clarify that the schema name is now sanitized before SQL template rendering, not within the templates themselves.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@docs/CHANGELOG.md` around lines 21 - 24, Update the CHANGELOG entry to
accurately state that ACE schema names are sanitized in Go before template
rendering: change the wording so it says the schema name is sanitized by the
aceSchema() Go function (used by CreateSchema) prior to being passed into the
SQL template (the template still renders {{.SchemaName}} without calling
.Sanitize()); reference aceSchema() in internal/consistency/mtree/merkle.go and
the CreateSchema template in db/queries/templates.go to ensure the note
correctly attributes where sanitization occurs.

- `spock.xact_commit_timestamp_origin()` replaced with the standard PostgreSQL
function `pg_xact_commit_timestamp_origin()` in the `--against-origin` filter.
The two are functionally identical (spock's implementation is a thin wrapper
around the same PG core function).
- Spock detection is now per-node and lazy, supporting mixed clusters where some
nodes have spock and others do not.
- `SpockNodeNames` renamed to `NodeOriginNames` throughout the codebase to
reflect dual-mode (spock + native PG) usage.

### Fixed
- Recovery-mode auto-selection (`autoSelectSourceOfTruth`) silently used native
PG LSN queries on spock clusters because the connection pool was stored after
`fetchLSNsForNode` returned instead of before.
- `aceSchema` template function used `config.Cfg` (not thread-safe) instead of
`config.Get()`, risking data races during concurrent SIGHUP reloads.
- `repset-diff` child table-diff tasks did not inherit the parent's TaskStore,
causing each to open its own SQLite connection.
- `isSpockAvailable` swallowed errors, causing callers to silently fall back to
native PG mode on detection failures.
- Native PG subscription matching used LIKE substring patterns that could
collide on similar node names (e.g., `n1` matching `n10`); now uses regex
word boundaries.

## [v1.9.0] - 2026-04-17

### Added
Expand Down
14 changes: 14 additions & 0 deletions tests/integration/docker-compose-native.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -41,3 +41,17 @@ services:
- "wal_level=logical"
ports:
- "5432"
native-n3:
image: postgres:17
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: password
POSTGRES_DB: testdb
command:
- "postgres"
- "-c"
- "track_commit_timestamp=on"
- "-c"
- "wal_level=logical"
ports:
- "5432"
Loading
Loading