Skip to content
Merged
Changes from 1 commit
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
7 changes: 5 additions & 2 deletions pgpm/core/src/export/export-meta.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { Parser } from 'csv-to-pg';
import { getPgPool } from 'pg-cache';
import type { Pool } from 'pg';

type FieldType = 'uuid' | 'uuid[]' | 'text' | 'text[]' | 'boolean' | 'image' | 'upload' | 'url' | 'jsonb' | 'int' | 'interval' | 'timestamptz';
type FieldType = 'uuid' | 'uuid[]' | 'text' | 'text[]' | 'boolean' | 'image' | 'upload' | 'url' | 'jsonb' | 'jsonb[]' | 'int' | 'interval' | 'timestamptz';

interface TableConfig {
schema: string;
Expand Down Expand Up @@ -35,6 +35,8 @@ const mapPgTypeToFieldType = (udtName: string): FieldType => {
case 'jsonb':
case 'json':
return 'jsonb';
case '_jsonb':
return 'jsonb[]';
case 'int4':
case 'int8':
case 'int2':
Expand Down Expand Up @@ -855,7 +857,8 @@ const config: Record<string, TableConfig> = {
use_rls: 'boolean',
node_data: 'jsonb',
grant_roles: 'text[]',
grant_privileges: 'jsonb',
fields: 'jsonb[]',
grant_privileges: 'jsonb[]',
Comment on lines +860 to +861
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🔴 jsonb[] field type has no coercion handler in csv-to-pg parser, producing corrupted SQL output

The PR adds jsonb[] as a valid FieldType and uses it for secure_table_provision.fields and secure_table_provision.grant_privileges, but the downstream csv-to-pg parser (packages/csv-to-pg/src/parse.ts:461-472) has no 'jsonb[]' case in its getCoercionFunc switch statement. This causes jsonb[] values to fall through to the default handler, which calls String(value) on the raw value. Since node-postgres returns jsonb[] columns as JavaScript arrays of parsed objects, String([{"a":1},{"b":2}]) produces "[object Object],[object Object]" — corrupted, unrecoverable data in the generated SQL INSERT statements.

Prompt for agents
The csv-to-pg parser at packages/csv-to-pg/src/parse.ts needs a new case for 'jsonb[]' in the getCoercionFunc function (around line 460, before the default case). The handler should:
1. Get the rawValue from the record
2. Check for null tokens
3. Verify the value is an array
4. JSON.stringify each element of the array
5. Format as a PostgreSQL array literal string, e.g. using the psqlArray helper but with JSON-stringified elements, or a custom approach like: '{' + array.map(el => '"' + JSON.stringify(el).replace(/\\/g, '\\\\').replace(/"/g, '\\"') + '"').join(',') + '}'
6. Return it as a string constant node

Example case to add in packages/csv-to-pg/src/parse.ts after the 'jsonb' case (around line 460):

    case 'jsonb[]':
      return (record) => {
        const rawValue = record[from[0]];
        if (isNullToken(rawValue)) {
          return makeNullOrThrow(fieldName, rawValue, type, required, 'value is empty or null');
        }
        if (Array.isArray(rawValue)) {
          if (rawValue.length === 0) {
            return makeNullOrThrow(fieldName, rawValue, type, required, 'array is empty');
          }
          const elements = rawValue.map(el => JSON.stringify(el));
          const arrayLiteral = psqlArray(elements);
          if (isEmpty(arrayLiteral)) {
            return makeNullOrThrow(fieldName, rawValue, type, required, 'failed to format array');
          }
          const val = nodes.aConst({ sval: ast.string({ sval: String(arrayLiteral) }) });
          return wrapValue(val, opts);
        }
        return makeNullOrThrow(fieldName, rawValue, type, required, 'value is not an array');
      };
Open in Devin Review

Was this helpful? React with 👍 or 👎 to provide feedback.

policy_type: 'text',
policy_privileges: 'text[]',
policy_role: 'text',
Expand Down
Loading