WARNING: THIS SITE IS A MIRROR OF GITHUB.COM / IT CANNOT LOGIN OR REGISTER ACCOUNTS / THE CONTENTS ARE PROVIDED AS-IS / THIS SITE ASSUMES NO RESPONSIBILITY FOR ANY DISPLAYED CONTENT OR LINKS / IF YOU FOUND SOMETHING MAY NOT GOOD FOR EVERYONE, CONTACT ADMIN AT ilovescratch@foxmail.com
Skip to content

Conversation

@KyleAMathews
Copy link
Contributor

When using columnMapper with ShapeStream, the columns parameter was not being encoded from app column names to database column names. This fix ensures that when a user specifies columns using app format (e.g., camelCase like userId), they are properly converted to the database format (e.g., snake_case like user_id) before being sent to the server.

This makes columnMapper work correctly with column subsets.

When using columnMapper with ShapeStream, the columns parameter
was not being encoded from app column names to database column names.
This fix ensures that when a user specifies columns using app format
(e.g., camelCase like `userId`), they are properly converted to the
database format (e.g., snake_case like `user_id`) before being sent
to the server.

This makes columnMapper work correctly with column subsets.
@codecov
Copy link

codecov bot commented Dec 8, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 61.64%. Comparing base (e90e24e) to head (e225ba5).
⚠️ Report is 12 commits behind head on main.
✅ All tests successful. No failed tests found.

Additional details and impacted files
@@           Coverage Diff           @@
##             main    #3564   +/-   ##
=======================================
  Coverage   61.64%   61.64%           
=======================================
  Files          40       40           
  Lines        1559     1559           
  Branches      106      107    +1     
=======================================
  Hits          961      961           
  Misses        597      597           
  Partials        1        1           
Flag Coverage Δ
electric-telemetry 22.71% <ø> (ø)
elixir 57.38% <ø> (ø)
elixir-client 73.94% <ø> (ø)
packages/experimental 87.73% <ø> (ø)
packages/react-hooks 86.48% <ø> (ø)
packages/y-electric 55.12% <ø> (ø)
typescript 72.39% <ø> (ø)
unit-tests 61.64% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Adds a test to verify that when data comes back from the server with
database column names (e.g., snake_case like user_id), the columnMapper
properly decodes them to app column names (e.g., camelCase like userId).

This complements the encoding test and verifies the full round-trip
works correctly with columnMapper and column subsets.
After toInternalParams converts the columns array to a comma-separated
string, we need to split it back to encode each column name, then join
them back together. Also added type guard for TypeScript safety.
- Add encodeColumns helper function in column-mapper.ts that follows
  the same pattern as encodeWhereClause
- Update client.ts to use encodeColumns for consistent encoding
- Add unit tests for encodeColumns function
@pkg-pr-new
Copy link

pkg-pr-new bot commented Dec 8, 2025

Open in StackBlitz

npm i https://pkg.pr.new/@electric-sql/react@3564
npm i https://pkg.pr.new/@electric-sql/client@3564
npm i https://pkg.pr.new/@electric-sql/y-electric@3564

commit: e225ba5

Copy link
Contributor

@kevin-dp kevin-dp left a comment

Choose a reason for hiding this comment

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

I'm worried about the corner case where a column name contains commas. The encodeColumns function won't handle this properly. I'm fine getting this out as a quick fix but we should then make an issue to fix this corner case in a follow up PR.

encode?: (columnName: string) => string
): string {
if (!columns || !encode) return columns ?? ``
return columns.split(`,`).map(encode).join(`,`)
Copy link
Contributor

Choose a reason for hiding this comment

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

What if a column name contains a comma? Postgres allows quoted names to contain special characters like commas.

- Rewrite encodeColumns to parse columns respecting quoted identifiers
- Quoted identifiers (double-quoted) are preserved as-is without encoding
- Handle escaped quotes ("") inside quoted identifiers
- Add tests for quoted column names with commas and special characters
Instead of parsing the comma-separated string to handle quoted column
names, access the original columns array directly from options and
encode each column before joining. This avoids the complexity of
parsing quoted identifiers with commas.

- Remove encodeColumns helper function
- Encode columns directly in #constructUrl from original array
- Remove encodeColumns unit tests (covered by stream integration tests)
@KyleAMathews
Copy link
Contributor Author

@kevin-dp I realized we were doing this wrong — we have access to the original column data so don't need to bother with parsing issues.

@KyleAMathews KyleAMathews requested a review from kevin-dp December 9, 2025 17:26
// Get original columns array from options (before toInternalParams converted to string)
const originalColumns = await resolveValue(this.options.params?.columns)
if (Array.isArray(originalColumns)) {
const encodedColumns = this.options.columnMapper
Copy link
Contributor

Choose a reason for hiding this comment

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

nit: the ternary is a bit harder to read than:

let encodedColumns = originalColumns
if (this.options.columnMapper) {
  encodedColumns = originalColumns.map((col) =>
    this.options.columnMapper!.encode(String(col))
  )
}

this.options.columnMapper!.encode(String(col))
)
: originalColumns
setQueryParam(fetchUrl, COLUMNS_QUERY_PARAM, encodedColumns.join(`,`))
Copy link
Contributor

Choose a reason for hiding this comment

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

Similar concern to before, what if the columns contain a comma. Imagine a column named "foo,bar" and a column "baz". After this encodedColumns.join(',') it will send "foo,bar,baz" to the server which will incorrectly interpret it as 3 columns.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

as it turns out we've always had this looming edge case —

Array.isArray(resolvedValue) ? resolvedValue.join(`,`) : resolvedValue,
— but yes, we should fix it — lemme consolidate the logic & then have it fix it

Add quoteIdentifier helper function that properly quotes PostgreSQL
identifiers by wrapping in double quotes and escaping internal quotes.

This ensures column names with special characters (commas, spaces,
quotes) are serialized correctly and won't be misinterpreted by the
server when parsing the columns parameter.

- Add quoteIdentifier function in column-mapper.ts
- Use quoteIdentifier when serializing column names
- Add tests for quoteIdentifier and columns with special characters
- Update existing tests to expect quoted column names
@netlify
Copy link

netlify bot commented Dec 10, 2025

Deploy Preview for electric-next ready!

Name Link
🔨 Latest commit 471a8c2
🔍 Latest deploy log https://app.netlify.com/projects/electric-next/deploys/693984b8dbc04600086ae5f5
😎 Deploy Preview https://deploy-preview-3564--electric-next.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

Add integration test that verifies column names with commas, quotes,
and spaces are correctly handled when selecting specific columns.

- Add testWithSpecialColumnsTable fixture that creates a table with
  columns named "normal", "has,comma", "has\"quote", "has space"
- Add integration test that selects a subset of these columns and
  verifies the data is returned correctly
@KyleAMathews
Copy link
Contributor Author

@kevin-dp ok I think we're actually handling things now

Copy link
Contributor

@kevin-dp kevin-dp left a comment

Choose a reason for hiding this comment

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

Thanks for fixing this Kyle. All looks good now!

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.

4 participants