Skip to content

Fix boolean output of dolt system table columns - #3153

Open
zachmu wants to merge 1 commit into
mainfrom
zachmu/issue3116
Open

Fix boolean output of dolt system table columns#3153
zachmu wants to merge 1 commit into
mainfrom
zachmu/issue3116

Conversation

@zachmu

@zachmu zachmu commented Aug 20, 2026

Copy link
Copy Markdown
Member

Boolean columns of dolt system tables (e.g. dolt.branches.dirty) are now sent over the wire as booleans in text format.

Fixes #3116.

Boolean columns of dolt system tables (dolt.branches.dirty, dolt.status.staged,
dolt.diff.data_change, etc.) were sent over the wire as MySQL-style '0'/'1' in
text format whenever a filter or sort sat between the projection and the system
table (e.g. SELECT dirty FROM dolt.branches WHERE name = 'main'), while the
field description advertised the boolean OID. Clients that validate text output,
such as psycopg2, fail with "can't parse boolean: '0'".

Two fixes:

- TypeSanitizer's GetField handling only wrapped fields in a GMSCast when the
  system table was the node's direct child. It now searches the subtree for the
  relation the field names (respecting aliases and stopping at subquery
  aliases), so intermediate Filter/Sort/etc. nodes no longer defeat the
  GMS-to-Doltgres type translation.

- rowToBytes' text-format path serialized GMS-typed columns with the GMS type's
  SQL() even though schemaToFieldDescriptions advertises the equivalent Doltgres
  type's OID. It now converts such values through GMSCast and serializes with
  the Doltgres type, mirroring what the binary-format path already did.

Adds a ScriptTest and a simple-protocol MessageFlowTest (pgx negotiates binary
results, which took the working code path, so the wire-level test is the one
that reproduces the customer's failure).
@github-actions

Copy link
Copy Markdown
Contributor
Main PR
Total 42090 42090
Successful 18980 18981
Failures 23110 23109
Partial Successes1 5461 5461
Main PR
Successful 45.0938% 45.0962%
Failures 54.9062% 54.9038%

${\color{lightgreen}Progressions (1)}$

subselect

QUERY: select count(*) from tenk1 t
where (exists(select 1 from tenk1 k where k.unique1 = t.unique2) or ten < 0);

Footnotes

  1. These are tests that we're marking as Successful, however they do not match the expected output in some way. This is due to small differences, such as different wording on the error messages, or the column names being incorrect while the data itself is correct.

@itoqa

itoqa Bot commented Aug 20, 2026

Copy link
Copy Markdown

Ito QA test results
Commit: 93e350f: 13 test cases ran, 13 passed ✅.

Summary

Coverage focused on database result correctness across normal queries, filtered, sorted, grouped, aliased, and reordered reads, including system and user boolean values. It also exercised edge cases around NULL column alignment, empty results, binary and text formats, prepared-query follow-up behavior, and boolean state changes after a commit.

Safe to merge — the exercised query and result-handling behaviors remained correct across normal, edge-case, and format-sensitive scenarios, with no PR-attributable regressions or unresolved failures. Overall risk is low.

Tests run by Ito

View full run

Result Severity Type Description
General Filtered and sorted branch queries returned the same readable boolean value, and the value matched the advertised PostgreSQL boolean type.
General Queries kept each NULL marker in its own column while the boolean and integer values stayed in the expected positions. A follow-up query also returned the same column layout.
General The simple follow-up query still returned 42 and a NULL value. The prepared-query check could not run because this local endpoint does not support PREPARE or EXECUTE, and the available tools did not include a binary-capable client; source review and repository wire tests confirmed the result formatting paths remain correct.
General Direct, filtered, sorted, aliased, and grouped queries all returned a valid boolean value with the correct PostgreSQL type.
Boolean The filtered branch query returned a valid PostgreSQL boolean and advertised the matching boolean type.
Boolean Filtered and sorted status and diff queries returned valid PostgreSQL boolean values with matching boolean type metadata.
Result The query returned integer 42 and preserved the second SQL NULL as an empty protocol field.
Result Binary query results decoded correctly for an ordinary value and a system-table boolean. The first attempt was blocked by missing client libraries, but a local wire-protocol retest completed successfully.
Rev The user table query succeeded through an alias and returned true then false in the requested order. The column was reported as a PostgreSQL boolean.
Rev The branch query returned the branch name and hash as text, and the dirty value as a valid boolean.
Rev An empty branch search returned no rows but still described its column as a boolean. The next branch query on the same connection completed successfully and returned the correct value.
Serialize The filtered branch query returned the boolean value t, matching the advertised PostgreSQL boolean type.
Serialize The dirty value was returned as PostgreSQL text t before the commit and f after the commit.

Tip

Reply with @itoqa to send us feedback on this test run.

@coffeegoddd

Copy link
Copy Markdown
Contributor

@zachmu DOLT

read_tests from_latency_median to_latency_median is_faster
covering_index_scan_postgres 2.48 2.48 0
groupby_scan_postgres 77.19 77.19 0
index_join_postgres 2.22 2.22 0
index_join_scan_postgres 1.58 1.58 0
index_scan_postgres 493.24 484.44 0
oltp_point_select 0.37 0.36 0
oltp_read_only 6.32 6.43 0
select_random_points 0.7 0.7 0
select_random_ranges 1.03 1.03 0
table_scan_postgres 484.44 475.79 0
types_table_scan_postgres 1258.08 1213.57 0
write_tests from_latency_median to_latency_median is_faster
bulk_insert 0.001 0.001 0
oltp_delete_insert_postgres 6.67 6.67 0
oltp_insert 3.36 3.36 0
oltp_read_write 13.46 13.46 0
oltp_update_index 3.55 3.55 0
oltp_update_non_index 3.25 3.25 0
oltp_write_only 7.04 7.04 0
types_delete_insert_postgres 7.17 7.17 0

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

dolt.branches.dirty does not have boolean output

2 participants