@quereus/quereus 4.20.0 → 4.20.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -0
- package/dist/src/common/types.d.ts +4 -4
- package/dist/src/index.d.ts +1 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +3 -2
- package/dist/src/index.js.map +1 -1
- package/dist/src/schema/catalog-rendering.js +13 -1
- package/dist/src/schema/catalog-rendering.js.map +1 -1
- package/dist/src/schema/catalog.d.ts +35 -2
- package/dist/src/schema/catalog.d.ts.map +1 -1
- package/dist/src/schema/catalog.js +42 -33
- package/dist/src/schema/catalog.js.map +1 -1
- package/dist/src/schema/schema-differ.d.ts +1 -1
- package/dist/src/schema/schema-differ.d.ts.map +1 -1
- package/dist/src/schema/schema-differ.js +195 -33
- package/dist/src/schema/schema-differ.js.map +1 -1
- package/dist/src/schema/unique-enforcement.d.ts +23 -1
- package/dist/src/schema/unique-enforcement.d.ts.map +1 -1
- package/dist/src/schema/unique-enforcement.js +43 -1
- package/dist/src/schema/unique-enforcement.js.map +1 -1
- package/dist/src/vtab/memory/layer/manager.d.ts +15 -12
- package/dist/src/vtab/memory/layer/manager.d.ts.map +1 -1
- package/dist/src/vtab/memory/layer/manager.js +87 -100
- package/dist/src/vtab/memory/layer/manager.js.map +1 -1
- package/package.json +7 -4
- package/test/README.md +173 -0
- package/test/logic/01-basic.sqllogic +39 -0
- package/test/logic/01.1-select-projection-extras.sqllogic +130 -0
- package/test/logic/01.2-strings.sqllogic +43 -0
- package/test/logic/01.5-insert-select.sqllogic +237 -0
- package/test/logic/01.6-update-extras.sqllogic +118 -0
- package/test/logic/01.7-update-from.sqllogic +67 -0
- package/test/logic/01.8-delete-extras.sqllogic +122 -0
- package/test/logic/01.8.1-delete-range-cow.sqllogic +115 -0
- package/test/logic/01.9-query-expr-dml-gates.sqllogic +32 -0
- package/test/logic/01.9-query-expr-dml.sqllogic +171 -0
- package/test/logic/01.9-query-expr-values.sqllogic +111 -0
- package/test/logic/01.9.1-limit-over-dml-subquery.sqllogic +119 -0
- package/test/logic/02-filters.sqllogic +54 -0
- package/test/logic/02-smoke.sqllogic +62 -0
- package/test/logic/02.1-bind-parameters.sqllogic +223 -0
- package/test/logic/03-expressions.sqllogic +190 -0
- package/test/logic/03.1-quoted-identifiers.sqllogic +55 -0
- package/test/logic/03.4-defaults.sqllogic +554 -0
- package/test/logic/03.4.1-default-edge-cases.sqllogic +99 -0
- package/test/logic/03.5-tvf.sqllogic +61 -0
- package/test/logic/03.6-type-system.sqllogic +544 -0
- package/test/logic/03.6.1-numeric-text-comparison-coercion.sqllogic +244 -0
- package/test/logic/03.6.2-value-to-text.sqllogic +224 -0
- package/test/logic/03.7-bigint-mixed-arithmetic.sqllogic +65 -0
- package/test/logic/03.8-not-precedence.sqllogic +255 -0
- package/test/logic/03.9-is-bool-predicate.sqllogic +150 -0
- package/test/logic/03.9.1-is-bool-predicate-partial-index.sqllogic +34 -0
- package/test/logic/04-order-by.sqllogic +38 -0
- package/test/logic/04-transactions.sqllogic +239 -0
- package/test/logic/04a-savepoint-lazy-attach.sqllogic +122 -0
- package/test/logic/05-vtab_memory.sqllogic +50 -0
- package/test/logic/05.0.1-vtab-memory-unique-index-collation.sqllogic +34 -0
- package/test/logic/05.1-composite-pk-range-scan.sqllogic +147 -0
- package/test/logic/05.1.1-secondary-index-range-scan.sqllogic +56 -0
- package/test/logic/05.2-cast-seek-correctness.sqllogic +124 -0
- package/test/logic/06-builtin_functions.sqllogic +149 -0
- package/test/logic/06.1-string-functions.sqllogic +92 -0
- package/test/logic/06.1.3-like-glob-edges.sqllogic +53 -0
- package/test/logic/06.2-math-functions.sqllogic +82 -0
- package/test/logic/06.3-schema.sqllogic +48 -0
- package/test/logic/06.3.1-schema-all-schemas.sqllogic +39 -0
- package/test/logic/06.3.2-schema-foreign-keys.sqllogic +208 -0
- package/test/logic/06.3.3-introspection-tags.sqllogic +202 -0
- package/test/logic/06.3.3.1-introspection-tags-index.sqllogic +74 -0
- package/test/logic/06.3.4-view-info.sqllogic +378 -0
- package/test/logic/06.3.5-column-info.sqllogic +347 -0
- package/test/logic/06.3.6-schema-views.sqllogic +29 -0
- package/test/logic/06.4-schema-search-path.sqllogic +354 -0
- package/test/logic/06.4.1-schema-case-insensitive.sqllogic +83 -0
- package/test/logic/06.4.2-collation-extras.sqllogic +472 -0
- package/test/logic/06.4.2.1-collation-index-access-paths.sqllogic +140 -0
- package/test/logic/06.4.3-write-path-collation.sqllogic +99 -0
- package/test/logic/06.4.4-comparison-collation-precedence.sqllogic +342 -0
- package/test/logic/06.4.5-any-collate-declared-keys.sqllogic +92 -0
- package/test/logic/06.5-polymorphic-types.sqllogic +169 -0
- package/test/logic/06.5.1-conversion-functions.sqllogic +173 -0
- package/test/logic/06.5.2-scalar-minmax.sqllogic +16 -0
- package/test/logic/06.5.3-undeclared-return-type-comparison.sqllogic +244 -0
- package/test/logic/06.5.4-declared-return-type-builtins.sqllogic +288 -0
- package/test/logic/06.6-aggregate-extended.sqllogic +78 -0
- package/test/logic/06.7-json-extended.sqllogic +53 -0
- package/test/logic/06.8-json-path-operators.sqllogic +99 -0
- package/test/logic/06.9-json-canonical-key.sqllogic +65 -0
- package/test/logic/06.9.1-json-coerce-once.sqllogic +417 -0
- package/test/logic/06.9.1.1-json-coerce-once-index.sqllogic +39 -0
- package/test/logic/06.9.2-json-structural-equality.sqllogic +382 -0
- package/test/logic/06.9.2.1-json-structural-equality-index.sqllogic +76 -0
- package/test/logic/06.9.3-json-index-range-seek.sqllogic +205 -0
- package/test/logic/07-aggregates.sqllogic +193 -0
- package/test/logic/07.1-aggregate-filter-clause.sqllogic +12 -0
- package/test/logic/07.2-aggregate-order-by.sqllogic +11 -0
- package/test/logic/07.3-group-by-extras.sqllogic +602 -0
- package/test/logic/07.3.1-group-by-order-by-key.sqllogic +164 -0
- package/test/logic/07.3.2-grouped-select-list-shape.sqllogic +231 -0
- package/test/logic/07.4-group-by-filter-composite-pk.sqllogic +120 -0
- package/test/logic/07.5-sum-mixed-exact-and-float.sqllogic +151 -0
- package/test/logic/07.5-window.sqllogic +1941 -0
- package/test/logic/07.5.1-window-named.sqllogic +13 -0
- package/test/logic/07.5.2-window-nth-value.sqllogic +13 -0
- package/test/logic/07.6-subqueries.sqllogic +78 -0
- package/test/logic/07.6.1-subquery-extras.sqllogic +93 -0
- package/test/logic/07.7-and-or-short-circuit.sqllogic +58 -0
- package/test/logic/07.7-in-subquery-caching.sqllogic +174 -0
- package/test/logic/07.7-scalar-agg-decorrelation.sqllogic +197 -0
- package/test/logic/07.7.1-in-extras.sqllogic +158 -0
- package/test/logic/07.7.1-scalar-agg-decorrelation-filter.sqllogic +105 -0
- package/test/logic/07.7.2-scalar-agg-decorrelation-nested.sqllogic +115 -0
- package/test/logic/07.7.3-exists-in-select-decorrelation.sqllogic +107 -0
- package/test/logic/07.7.4-where-conjunct-ordering.sqllogic +121 -0
- package/test/logic/07.7.5-filter-lost-under-index-order.sqllogic +134 -0
- package/test/logic/07.7.6-correlated-predicate-scope.sqllogic +178 -0
- package/test/logic/07.7.7-join-source-scope-shadowing.sqllogic +137 -0
- package/test/logic/07.7.8-correlated-ref-to-computed-column.sqllogic +165 -0
- package/test/logic/07.7.9-conjunct-monotonicity.sqllogic +200 -0
- package/test/logic/07.8-correlated-subquery-edges.sqllogic +71 -0
- package/test/logic/07.8.1-correlated-in-decorrelation-gates.sqllogic +156 -0
- package/test/logic/07.9-in-value-list.sqllogic +154 -0
- package/test/logic/07.9.1-in-value-list-composite-index.sqllogic +38 -0
- package/test/logic/08-views.sqllogic +64 -0
- package/test/logic/08.1-semi-anti-join.sqllogic +191 -0
- package/test/logic/08.1-view-edge-cases.sqllogic +118 -0
- package/test/logic/08.1.1-uncorrelated-in-semijoin.sqllogic +251 -0
- package/test/logic/08.2-existence-flag-semijoin-recovery.sqllogic +197 -0
- package/test/logic/08.3-existence-flag-inner-recovery.sqllogic +102 -0
- package/test/logic/08.4-key-set-semi-join.sqllogic +447 -0
- package/test/logic/09-set_operations.sqllogic +244 -0
- package/test/logic/09.1-set-op-cross-collation.sqllogic +230 -0
- package/test/logic/10-distinct_datatypes.sqllogic +127 -0
- package/test/logic/10.1-ddl-lifecycle.sqllogic +203 -0
- package/test/logic/10.1.1-create-table-syntax-edges.sqllogic +47 -0
- package/test/logic/10.1.2-ddl-in-transaction.sqllogic +143 -0
- package/test/logic/10.1.2.1-add-constraint-in-transaction.sqllogic +59 -0
- package/test/logic/10.1.3-ddl-drop-in-transaction.sqllogic +187 -0
- package/test/logic/10.1.3.1-drop-constraint-in-transaction.sqllogic +45 -0
- package/test/logic/10.1.4-create-table-duplicate-constraint-names.sqllogic +149 -0
- package/test/logic/10.1.4-ddl-transaction-policy.sqllogic +314 -0
- package/test/logic/10.1.5-alter-add-constraint-minted-name-disambiguation.sqllogic +219 -0
- package/test/logic/10.1.5-create-index-lifecycle.sqllogic +72 -0
- package/test/logic/10.1.6-ddl-transaction-policy-index.sqllogic +143 -0
- package/test/logic/10.1.7-create-table-default-type-check.sqllogic +119 -0
- package/test/logic/10.1.8-alter-add-check-existing-rows.sqllogic +117 -0
- package/test/logic/10.2-column-features.sqllogic +365 -0
- package/test/logic/10.2.1-table-options-rejection.sqllogic +63 -0
- package/test/logic/10.2.2-default-collation-memory.sqllogic +30 -0
- package/test/logic/10.3-function-features.sqllogic +247 -0
- package/test/logic/10.4-schema-scale.sqllogic +168 -0
- package/test/logic/10.4.1-schema-scale-indexes.sqllogic +121 -0
- package/test/logic/10.5-indexes.sqllogic +164 -0
- package/test/logic/10.5.1-partial-indexes.sqllogic +526 -0
- package/test/logic/10.5.2-expression-indexes.sqllogic +34 -0
- package/test/logic/10.5.3-desc-index-ordering.sqllogic +130 -0
- package/test/logic/10.5.4-composite-pk-index-update-phantom.sqllogic +55 -0
- package/test/logic/10.5.5-index-name-uniqueness.sqllogic +76 -0
- package/test/logic/10.5.6-minmax-index-boundary.sqllogic +204 -0
- package/test/logic/10.5.7-implicit-unique-index-lifecycle.sqllogic +1216 -0
- package/test/logic/10.6-distinct-edge-cases.sqllogic +119 -0
- package/test/logic/100-predicate-normalization-edge-cases.sqllogic +238 -0
- package/test/logic/100.1-where-extras.sqllogic +163 -0
- package/test/logic/100.1.1-where-join-on-order-indexed.sqllogic +35 -0
- package/test/logic/101-builtin-mutation-kills.sqllogic +974 -0
- package/test/logic/101-transaction-edge-cases.sqllogic +395 -0
- package/test/logic/102-schema-catalog-edge-cases.sqllogic +252 -0
- package/test/logic/102-unique-constraints.sqllogic +145 -0
- package/test/logic/102.0.1-schema-catalog-indexed-table.sqllogic +32 -0
- package/test/logic/102.1-unique-edge-cases.sqllogic +111 -0
- package/test/logic/102.1.1-unique-index-creation-edge-cases.sqllogic +75 -0
- package/test/logic/102.2-unique-collation.sqllogic +181 -0
- package/test/logic/102.2.1-unique-collation-index-derived.sqllogic +305 -0
- package/test/logic/103-database-options-edge-cases.sqllogic +108 -0
- package/test/logic/103.1-pragma-boolean-values.sqllogic +126 -0
- package/test/logic/104-emit-mutation-kills.sqllogic +236 -0
- package/test/logic/105-vtab-memory-mutation-kills.sqllogic +754 -0
- package/test/logic/105.1-vtab-memory-index-mutation-kills.sqllogic +540 -0
- package/test/logic/106-constraint-extractor-mutation-kills.sqllogic +350 -0
- package/test/logic/107-temporal-arithmetic-mutation-kills.sqllogic +833 -0
- package/test/logic/108-cardinality-estimation.sqllogic +146 -0
- package/test/logic/108.1-analyze-name-resolution.sqllogic +102 -0
- package/test/logic/109-aggregate-physical-selection.sqllogic +103 -0
- package/test/logic/11-joins.sqllogic +86 -0
- package/test/logic/11.1-join-using.sqllogic +267 -0
- package/test/logic/11.2-comma-join.sqllogic +35 -0
- package/test/logic/11.3-index-nested-loop-join.sqllogic +305 -0
- package/test/logic/11.3-mismatched-collation-join.sqllogic +74 -0
- package/test/logic/11.4-hash-join-side-swap.sqllogic +118 -0
- package/test/logic/110-scan-emitter-mutation-kills.sqllogic +121 -0
- package/test/logic/110.1-scan-emitter-index-scan-kills.sqllogic +47 -0
- package/test/logic/12-empty-primary-key.sqllogic +124 -0
- package/test/logic/12-join_padding_order.sqllogic +58 -0
- package/test/logic/12.1-orderby-index-consumption.sqllogic +40 -0
- package/test/logic/13-cte.sqllogic +137 -0
- package/test/logic/13.1-cte-multiple-recursive.sqllogic +104 -0
- package/test/logic/13.10-cte-qualified-name.sqllogic +136 -0
- package/test/logic/13.11-unreferenced-dml-cte.sqllogic +414 -0
- package/test/logic/13.12-nested-dml-cte-rejected.sqllogic +280 -0
- package/test/logic/13.2-cte-bind-params.sqllogic +98 -0
- package/test/logic/13.3-cte-edge-cases.sqllogic +120 -0
- package/test/logic/13.4-cte-extras.sqllogic +98 -0
- package/test/logic/13.5-cte-join-order.sqllogic +166 -0
- package/test/logic/13.6-cte-dml-runs-once.sqllogic +318 -0
- package/test/logic/13.7-cte-sibling-visibility.sqllogic +227 -0
- package/test/logic/13.8-insert-with-clause-visibility.sqllogic +254 -0
- package/test/logic/13.9-schema-authored-cte-isolation.sqllogic +328 -0
- package/test/logic/13.9.1-schema-authored-schema-path-isolation.sqllogic +408 -0
- package/test/logic/14-utilities.sqllogic +168 -0
- package/test/logic/15-timespan.sqllogic +279 -0
- package/test/logic/15.1-semantic-ordering.sqllogic +960 -0
- package/test/logic/15.1.1-json-check-coercion.sqllogic +178 -0
- package/test/logic/15.1.2-semantic-ordering-index.sqllogic +41 -0
- package/test/logic/15.1.3-declared-form-write-contract.sqllogic +519 -0
- package/test/logic/16-epoch.sqllogic +187 -0
- package/test/logic/17-weekday-modifier.sqllogic +78 -0
- package/test/logic/18-json-string-escapes.sqllogic +86 -0
- package/test/logic/18-strftime-extended-formats.sqllogic +68 -0
- package/test/logic/20-empty-single-row.sqllogic +261 -0
- package/test/logic/21-null-edge-cases.sqllogic +227 -0
- package/test/logic/21.1-where-null-comparisons.sqllogic +151 -0
- package/test/logic/21.1.1-where-null-comparisons-secondary-index.sqllogic +35 -0
- package/test/logic/21.2-between-edges.sqllogic +157 -0
- package/test/logic/22-boundary-values.sqllogic +175 -0
- package/test/logic/23-self-joins-duplicates.sqllogic +74 -0
- package/test/logic/24-builtin-branches.sqllogic +611 -0
- package/test/logic/24.1-substr-extras.sqllogic +75 -0
- package/test/logic/24.2-random-extras.sqllogic +39 -0
- package/test/logic/25-aggregate-edge-cases.sqllogic +289 -0
- package/test/logic/25.1-nested-aggregates.sqllogic +74 -0
- package/test/logic/25.2-having-edge-cases.sqllogic +318 -0
- package/test/logic/25.3-aggregate-isnull-empty.sqllogic +16 -0
- package/test/logic/25.4-groupby-fd-constant-empty.sqllogic +55 -0
- package/test/logic/25.5-ungrouped-aggregate-column-free-select-item.sqllogic +196 -0
- package/test/logic/26-join-edge-cases.sqllogic +333 -0
- package/test/logic/26.1-left-join-isnull-on-notnull.sqllogic +26 -0
- package/test/logic/26.2-left-join-on-vs-where.sqllogic +67 -0
- package/test/logic/26.3-join-on-constants.sqllogic +61 -0
- package/test/logic/26.4-join-on-is-null-nullable.sqllogic +44 -0
- package/test/logic/27-window-edge-cases.sqllogic +206 -0
- package/test/logic/27.1-window-groups-frame.sqllogic +13 -0
- package/test/logic/27.2-window-exclude.sqllogic +13 -0
- package/test/logic/27.3-window-json-aggregation.sqllogic +66 -0
- package/test/logic/28-set-ops-sort-edge-cases.sqllogic +444 -0
- package/test/logic/28.1-compound-limit-offset.sqllogic +143 -0
- package/test/logic/28.2-orderby-expression-extras.sqllogic +698 -0
- package/test/logic/28.2-set-op-branch-types.sqllogic +217 -0
- package/test/logic/29-constraint-edge-cases.sqllogic +442 -0
- package/test/logic/29.1-column-level-conflict-clause.sqllogic +171 -0
- package/test/logic/29.2-table-level-pk-conflict-clause.sqllogic +113 -0
- package/test/logic/40-constraints.sqllogic +418 -0
- package/test/logic/40.1-pk-desc-direction.sqllogic +76 -0
- package/test/logic/40.2-check-extras.sqllogic +683 -0
- package/test/logic/41-alter-table.sqllogic +191 -0
- package/test/logic/41-fk-cascade-conflict-and-self-ref.sqllogic +263 -0
- package/test/logic/41-fk-cross-schema.sqllogic +155 -0
- package/test/logic/41-fk-extended-targets.sqllogic +173 -0
- package/test/logic/41-foreign-keys.sqllogic +1001 -0
- package/test/logic/41-generated-column-errors.sqllogic +225 -0
- package/test/logic/41-generated-column-extras.sqllogic +598 -0
- package/test/logic/41-generated-column-scope.sqllogic +329 -0
- package/test/logic/41-generated-columns.sqllogic +361 -0
- package/test/logic/41.1-alter-pk.sqllogic +230 -0
- package/test/logic/41.1-fk-collation-conflict.sqllogic +277 -0
- package/test/logic/41.10-alter-drop-column-foreign-key.sqllogic +274 -0
- package/test/logic/41.10.1-alter-drop-column-unique-index.sqllogic +169 -0
- package/test/logic/41.10.2-alter-drop-column-check-and-assertion.sqllogic +1616 -0
- package/test/logic/41.10.3-alter-drop-column-referencing-fk.sqllogic +292 -0
- package/test/logic/41.10.4-drop-object-expression-dependents.sqllogic +602 -0
- package/test/logic/41.11-deferred-fk-with-rename.sqllogic +232 -0
- package/test/logic/41.12-alter-default-coercion.sqllogic +200 -0
- package/test/logic/41.13-alter-add-column-generated-backfill.sqllogic +566 -0
- package/test/logic/41.14-alter-add-column-subquery-backfill.sqllogic +129 -0
- package/test/logic/41.15-alter-column-default-type-check.sqllogic +178 -0
- package/test/logic/41.16-fk-unenforceable.sqllogic +364 -0
- package/test/logic/41.2-alter-column.sqllogic +382 -0
- package/test/logic/41.2.1-alter-column-retype-deleted-row-memory.sqllogic +32 -0
- package/test/logic/41.2.2-alter-column-retype-index-rebuild.sqllogic +77 -0
- package/test/logic/41.2.3-alter-column-set-not-null-pk-backfill.sqllogic +310 -0
- package/test/logic/41.2.3.1-alter-column-set-not-null-pk-backfill-secondary-index.sqllogic +37 -0
- package/test/logic/41.3-alter-add-column-unique.sqllogic +184 -0
- package/test/logic/41.3-alter-rename-propagation.sqllogic +2352 -0
- package/test/logic/41.3.1-alter-rename-index-propagation.sqllogic +94 -0
- package/test/logic/41.4-alter-add-column-constraints.sqllogic +855 -0
- package/test/logic/41.5-alter-misc.sqllogic +48 -0
- package/test/logic/41.5-cross-schema-foreign-keys.sqllogic +253 -0
- package/test/logic/41.6-alter-drop-rename-constraint.sqllogic +354 -0
- package/test/logic/41.6.1-alter-drop-constraint-index-derived.sqllogic +22 -0
- package/test/logic/41.7-alter-column-collate.sqllogic +105 -0
- package/test/logic/41.7.1-alter-column-collate-unique.sqllogic +45 -0
- package/test/logic/41.7.2-alter-column-collate-unique-store.sqllogic +208 -0
- package/test/logic/41.7.2.1-alter-column-collate-unique-index-store.sqllogic +114 -0
- package/test/logic/41.7.3-alter-column-retype-unique.sqllogic +293 -0
- package/test/logic/41.7.3.1-alter-column-retype-staged-rows-memory.sqllogic +41 -0
- package/test/logic/41.7.3.2-alter-column-retype-unique-index.sqllogic +72 -0
- package/test/logic/41.7.4-alter-column-retype-semantic-memory.sqllogic +445 -0
- package/test/logic/41.7.4.1-alter-column-retype-semantic-index-memory.sqllogic +91 -0
- package/test/logic/41.7.5-alter-column-collate-pk-staged-delete-memory.sqllogic +106 -0
- package/test/logic/41.8-alter-add-constraint-unique-fk.sqllogic +275 -0
- package/test/logic/41.8-alter-savepoint-staged-rows.sqllogic +443 -0
- package/test/logic/41.8.1-alter-rename-savepoint-staged-rows.sqllogic +408 -0
- package/test/logic/41.9-alter-constraint-body-change.sqllogic +180 -0
- package/test/logic/41.9-fk-restrict-batched.sqllogic +290 -0
- package/test/logic/42-committed-snapshot.sqllogic +254 -0
- package/test/logic/42-returning.sqllogic +159 -0
- package/test/logic/42.1-returning-extras.sqllogic +232 -0
- package/test/logic/42.2-returning-stored-row.sqllogic +165 -0
- package/test/logic/43-default-nullability.sqllogic +131 -0
- package/test/logic/43-transition-constraints.sqllogic +341 -0
- package/test/logic/43.1-default-collation.sqllogic +140 -0
- package/test/logic/43.1-notnull-or-conflict.sqllogic +79 -0
- package/test/logic/43.2-deferred-check-new-on-delete.sqllogic +95 -0
- package/test/logic/43.3-nullable-primary-key.sqllogic +587 -0
- package/test/logic/44-determinism-validation.sqllogic +164 -0
- package/test/logic/44-orthogonality.sqllogic +146 -0
- package/test/logic/44.1-nondeterministic-schema.sqllogic +316 -0
- package/test/logic/45-udf-determinism.sqllogic +39 -0
- package/test/logic/46-mutation-context.sqllogic +595 -0
- package/test/logic/47-upsert.sqllogic +255 -0
- package/test/logic/47.1-upsert-conflict-targets.sqllogic +169 -0
- package/test/logic/47.2-replace-and-or-clauses.sqllogic +164 -0
- package/test/logic/47.2.1-pk-replace-secondary-unique.sqllogic +374 -0
- package/test/logic/47.3-engine-or-fail.sqllogic +122 -0
- package/test/logic/47.3-upsert-conflict-target-collation.sqllogic +139 -0
- package/test/logic/47.3.1-upsert-conflict-index-derived-collation.sqllogic +25 -0
- package/test/logic/47.4-upsert-conflict-target-affinity.sqllogic +59 -0
- package/test/logic/47.5-upsert-do-update-constraints.sqllogic +440 -0
- package/test/logic/47.6-upsert-do-update-decomposed.sqllogic +100 -0
- package/test/logic/49-reference-graph.sqllogic +84 -0
- package/test/logic/50-declarative-schema.sqllogic +2550 -0
- package/test/logic/50-metadata-tags.sqllogic +1033 -0
- package/test/logic/50.0.1-metadata-tags-index.sqllogic +141 -0
- package/test/logic/50.1-declare-schema-pk.sqllogic +150 -0
- package/test/logic/50.2-declare-schema-renames.sqllogic +949 -0
- package/test/logic/50.2.1-declare-schema-index-renames.sqllogic +173 -0
- package/test/logic/50.3-declare-schema-duplicate-names.sqllogic +280 -0
- package/test/logic/50.4-declare-schema-apply-restore.sqllogic +192 -0
- package/test/logic/51-lens-foundation.sqllogic +147 -0
- package/test/logic/51-materialized-views.sqllogic +376 -0
- package/test/logic/51.5-materialized-views-coarsened-key.sqllogic +198 -0
- package/test/logic/51.7-maintained-table-attach-detach.sqllogic +468 -0
- package/test/logic/51.8-maintained-table-declared-constraints.sqllogic +440 -0
- package/test/logic/51.85-maintained-table-parent-fk.sqllogic +103 -0
- package/test/logic/51.9-maintained-table-secondary-unique.sqllogic +237 -0
- package/test/logic/51.9.1-maintained-table-partial-unique.sqllogic +36 -0
- package/test/logic/52-lens-overrides.sqllogic +566 -0
- package/test/logic/53-materialized-views-rowtime.sqllogic +1601 -0
- package/test/logic/53-reserved-tags.sqllogic +252 -0
- package/test/logic/53.1-materialized-view-write-through.sqllogic +329 -0
- package/test/logic/53.2-materialized-view-rename-propagation.sqllogic +483 -0
- package/test/logic/53.3-materialized-view-constraint-only-ddl.sqllogic +409 -0
- package/test/logic/53.3.1-materialized-view-index-ddl-irrelevance.sqllogic +29 -0
- package/test/logic/53.4-materialized-view-structural-alter-restore.sqllogic +436 -0
- package/test/logic/54-covering-mv-enforcement.sqllogic +314 -0
- package/test/logic/54.1-covering-mv-partial-enforcement.sqllogic +34 -0
- package/test/logic/55-internal-eviction-reporting.sqllogic +89 -0
- package/test/logic/55-lens-prover.sqllogic +202 -0
- package/test/logic/55.1-eviction-restrict-fk.sqllogic +148 -0
- package/test/logic/55.5-lens-authored-inverse.sqllogic +1468 -0
- package/test/logic/80-grow-retrieve-pass.sqllogic +79 -0
- package/test/logic/81-quickpick.sqllogic +24 -0
- package/test/logic/82-bloom-join.sqllogic +185 -0
- package/test/logic/83-merge-join.sqllogic +280 -0
- package/test/logic/84-asof-scan.sqllogic +238 -0
- package/test/logic/84-key-cardinality.sqllogic +50 -0
- package/test/logic/85-relational-const-folding.sqllogic +51 -0
- package/test/logic/86-scalar-cse.sqllogic +42 -0
- package/test/logic/90-error_paths.sqllogic +114 -0
- package/test/logic/90.1-parse-errors.sqllogic +77 -0
- package/test/logic/90.2-alter-table-errors.sqllogic +53 -0
- package/test/logic/90.2.1-alter-extra-errors.sqllogic +51 -0
- package/test/logic/90.3-expression-errors.sqllogic +43 -0
- package/test/logic/90.4-dml-errors.sqllogic +47 -0
- package/test/logic/90.5-unsupported-join-types.sqllogic +37 -0
- package/test/logic/90.5.1-right-full-join-read.sqllogic +157 -0
- package/test/logic/90.6-select-error-paths.sqllogic +57 -0
- package/test/logic/91-merge-join-edge-cases.sqllogic +159 -0
- package/test/logic/92-hash-aggregate-edge-cases.sqllogic +139 -0
- package/test/logic/93-ddl-view-edge-cases.sqllogic +104 -0
- package/test/logic/93.1-view-error-paths.sqllogic +74 -0
- package/test/logic/93.2-view-mutation-pending.sqllogic +108 -0
- package/test/logic/93.3-view-mutation-or-clause.sqllogic +60 -0
- package/test/logic/93.4-view-mutation.sqllogic +4881 -0
- package/test/logic/93.4.1-view-mutation-partial-unique-cardinality.sqllogic +31 -0
- package/test/logic/93.5-authored-inverse.sqllogic +415 -0
- package/test/logic/93.6-set-op-flagless-write.sqllogic +862 -0
- package/test/logic/94-tvf-edge-cases.sqllogic +58 -0
- package/test/logic/94.1-limit-offset-edge-cases.sqllogic +109 -0
- package/test/logic/94.2-limit-offset-extras.sqllogic +98 -0
- package/test/logic/95-assertions.sqllogic +1417 -0
- package/test/logic/96-subquery-edge-cases.sqllogic +276 -0
- package/test/logic/97-json-function-edge-cases.sqllogic +633 -0
- package/test/logic/97.1-json-blob-and-special-values.sqllogic +92 -0
- package/test/logic/98-temporal-edge-cases.sqllogic +515 -0
- package/test/logic/99-conversion-edge-cases.sqllogic +325 -0
- package/test/logic/99.0.1-schema-index-listing.sqllogic +21 -0
- package/test/logic/99.1-cast-syntax-extras.sqllogic +167 -0
- package/test/logic/drop-unique-index.sqllogic +88 -0
- package/test/logic/pushdown-test.sqllogic +36 -0
|
@@ -0,0 +1,633 @@
|
|
|
1
|
+
-- 97-json-function-edge-cases.sqllogic
|
|
2
|
+
-- Targeted coverage for uncovered branches in json.ts and json-helpers.ts:
|
|
3
|
+
-- json_valid Uint8Array, json_schema, json_type paths, json_extract fallback,
|
|
4
|
+
-- json_quote special types, json_object odd args, json_array_length non-string path,
|
|
5
|
+
-- json_patch error paths, json_insert/replace/set/remove edge cases,
|
|
6
|
+
-- json_group_array/object aggregation, coerceToJsonValue, prepareJsonValue,
|
|
7
|
+
-- resolveJsonPathForModify createParents, deepCopyJson, getJsonType, evaluateJsonPathBasic
|
|
8
|
+
|
|
9
|
+
-- ============================================================
|
|
10
|
+
-- json_valid: additional edge cases
|
|
11
|
+
-- ============================================================
|
|
12
|
+
|
|
13
|
+
-- Null input returns false
|
|
14
|
+
SELECT json_valid(null) as result;
|
|
15
|
+
→ [{"result":false}]
|
|
16
|
+
|
|
17
|
+
-- Numeric types are valid JSON
|
|
18
|
+
SELECT json_valid(0) as result;
|
|
19
|
+
→ [{"result":true}]
|
|
20
|
+
|
|
21
|
+
SELECT json_valid(3.14) as result;
|
|
22
|
+
→ [{"result":true}]
|
|
23
|
+
|
|
24
|
+
-- Boolean types are valid JSON
|
|
25
|
+
SELECT json_valid(true) as result;
|
|
26
|
+
→ [{"result":true}]
|
|
27
|
+
|
|
28
|
+
SELECT json_valid(false) as result;
|
|
29
|
+
→ [{"result":true}]
|
|
30
|
+
|
|
31
|
+
-- Native objects are valid
|
|
32
|
+
SELECT json_valid(json_object('a', 1)) as result;
|
|
33
|
+
→ [{"result":true}]
|
|
34
|
+
|
|
35
|
+
-- Malformed JSON strings
|
|
36
|
+
SELECT json_valid('{missing_quotes: 1}') as result;
|
|
37
|
+
→ [{"result":false}]
|
|
38
|
+
|
|
39
|
+
SELECT json_valid('{"truncated":') as result;
|
|
40
|
+
→ [{"result":false}]
|
|
41
|
+
|
|
42
|
+
SELECT json_valid('{]') as result;
|
|
43
|
+
→ [{"result":false}]
|
|
44
|
+
|
|
45
|
+
-- ============================================================
|
|
46
|
+
-- json_schema: validation
|
|
47
|
+
-- ============================================================
|
|
48
|
+
|
|
49
|
+
-- Valid schema matching (use comma-separated fields to avoid semicolons)
|
|
50
|
+
SELECT json_schema('{"name":"Alice","age":30}', '{ name: string, age: number }') as result;
|
|
51
|
+
→ [{"result":true}]
|
|
52
|
+
|
|
53
|
+
-- Schema mismatch
|
|
54
|
+
SELECT json_schema('{"name":"Alice","age":"thirty"}', '{ name: string, age: number }') as result;
|
|
55
|
+
→ [{"result":false}]
|
|
56
|
+
|
|
57
|
+
-- Non-string schema returns false
|
|
58
|
+
SELECT json_schema('{"a":1}', 42) as result;
|
|
59
|
+
→ [{"result":false}]
|
|
60
|
+
|
|
61
|
+
-- Invalid JSON input returns false
|
|
62
|
+
SELECT json_schema('not-json', '{ name: string }') as result;
|
|
63
|
+
→ [{"result":false}]
|
|
64
|
+
|
|
65
|
+
-- Invalid schema syntax returns false
|
|
66
|
+
SELECT json_schema('{"a":1}', '!!!invalid!!!') as result;
|
|
67
|
+
→ [{"result":false}]
|
|
68
|
+
|
|
69
|
+
-- Null input returns false
|
|
70
|
+
SELECT json_schema(null, '{ name: string }') as result;
|
|
71
|
+
→ [{"result":false}]
|
|
72
|
+
|
|
73
|
+
-- ============================================================
|
|
74
|
+
-- json_type: path and edge cases
|
|
75
|
+
-- ============================================================
|
|
76
|
+
|
|
77
|
+
-- json_type with path argument
|
|
78
|
+
SELECT json_type('{"a":42}', '$.a') as result;
|
|
79
|
+
→ [{"result":"integer"}]
|
|
80
|
+
|
|
81
|
+
SELECT json_type('{"a":3.14}', '$.a') as result;
|
|
82
|
+
→ [{"result":"real"}]
|
|
83
|
+
|
|
84
|
+
SELECT json_type('{"a":"hello"}', '$.a') as result;
|
|
85
|
+
→ [{"result":"text"}]
|
|
86
|
+
|
|
87
|
+
SELECT json_type('{"a":true}', '$.a') as result;
|
|
88
|
+
→ [{"result":"true"}]
|
|
89
|
+
|
|
90
|
+
SELECT json_type('{"a":false}', '$.a') as result;
|
|
91
|
+
→ [{"result":"false"}]
|
|
92
|
+
|
|
93
|
+
SELECT json_type('{"a":null}', '$.a') as result;
|
|
94
|
+
→ [{"result":"null"}]
|
|
95
|
+
|
|
96
|
+
SELECT json_type('{"a":[1,2]}', '$.a') as result;
|
|
97
|
+
→ [{"result":"array"}]
|
|
98
|
+
|
|
99
|
+
SELECT json_type('{"a":{"b":1}}', '$.a') as result;
|
|
100
|
+
→ [{"result":"object"}]
|
|
101
|
+
|
|
102
|
+
-- Non-existent path returns null
|
|
103
|
+
SELECT json_type('{"a":1}', '$.b') as result;
|
|
104
|
+
→ [{"result":null}]
|
|
105
|
+
|
|
106
|
+
-- Non-string path returns 'null'
|
|
107
|
+
SELECT json_type('{"a":1}', 42) as result;
|
|
108
|
+
→ [{"result":"null"}]
|
|
109
|
+
|
|
110
|
+
-- Invalid JSON returns null
|
|
111
|
+
SELECT json_type('not-json') as result;
|
|
112
|
+
→ [{"result":null}]
|
|
113
|
+
|
|
114
|
+
-- Null input: coerceToJsonValue(null) returns JSON null, getJsonType(null) returns 'null' string
|
|
115
|
+
SELECT json_type(null) as result;
|
|
116
|
+
→ [{"result":"null"}]
|
|
117
|
+
|
|
118
|
+
-- No-path call on each type
|
|
119
|
+
SELECT json_type('42') as result;
|
|
120
|
+
→ [{"result":"integer"}]
|
|
121
|
+
|
|
122
|
+
SELECT json_type('"hello"') as result;
|
|
123
|
+
→ [{"result":"text"}]
|
|
124
|
+
|
|
125
|
+
-- ============================================================
|
|
126
|
+
-- json_extract: edge cases
|
|
127
|
+
-- ============================================================
|
|
128
|
+
|
|
129
|
+
-- No paths returns null
|
|
130
|
+
SELECT json_extract('{"a":1}') as result;
|
|
131
|
+
→ [{"result":null}]
|
|
132
|
+
|
|
133
|
+
-- Non-string path returns null
|
|
134
|
+
SELECT json_extract('{"a":1}', 42) as result;
|
|
135
|
+
→ [{"result":null}]
|
|
136
|
+
|
|
137
|
+
-- Boolean value extraction
|
|
138
|
+
SELECT json_extract('{"a":true}', '$.a') as result;
|
|
139
|
+
→ [{"result":true}]
|
|
140
|
+
|
|
141
|
+
SELECT json_extract('{"a":false}', '$.a') as result;
|
|
142
|
+
→ [{"result":false}]
|
|
143
|
+
|
|
144
|
+
-- Nested object extraction (returns native object)
|
|
145
|
+
SELECT json_extract('{"a":{"b":{"c":42}}}', '$.a.b') as result;
|
|
146
|
+
→ [{"result":{"c":42}}]
|
|
147
|
+
|
|
148
|
+
-- Array extraction
|
|
149
|
+
SELECT json_extract('{"a":[10,20,30]}', '$.a') as result;
|
|
150
|
+
→ [{"result":[10,20,30]}]
|
|
151
|
+
|
|
152
|
+
-- Array index extraction
|
|
153
|
+
SELECT json_extract('[10,20,30]', '$[1]') as result;
|
|
154
|
+
→ [{"result":20}]
|
|
155
|
+
|
|
156
|
+
-- Deep nesting
|
|
157
|
+
SELECT json_extract('{"a":{"b":{"c":{"d":99}}}}', '$.a.b.c.d') as result;
|
|
158
|
+
→ [{"result":99}]
|
|
159
|
+
|
|
160
|
+
-- Multiple paths: first found wins
|
|
161
|
+
SELECT json_extract('{"a":1,"b":2}', '$.x', '$.y', '$.b') as result;
|
|
162
|
+
→ [{"result":2}]
|
|
163
|
+
|
|
164
|
+
-- All paths miss returns null
|
|
165
|
+
SELECT json_extract('{"a":1}', '$.x', '$.y', '$.z') as result;
|
|
166
|
+
→ [{"result":null}]
|
|
167
|
+
|
|
168
|
+
-- Root path extraction
|
|
169
|
+
SELECT json_extract('42', '$') as result;
|
|
170
|
+
→ [{"result":42}]
|
|
171
|
+
|
|
172
|
+
SELECT json_extract('"hello"', '$') as result;
|
|
173
|
+
→ [{"result":"hello"}]
|
|
174
|
+
|
|
175
|
+
-- ============================================================
|
|
176
|
+
-- json_quote: edge cases
|
|
177
|
+
-- ============================================================
|
|
178
|
+
|
|
179
|
+
-- Null returns 'null' string
|
|
180
|
+
SELECT json_quote(null) as result;
|
|
181
|
+
→ [{"result":"null"}]
|
|
182
|
+
|
|
183
|
+
-- Integer
|
|
184
|
+
SELECT json_quote(42) as result;
|
|
185
|
+
→ [{"result":"42"}]
|
|
186
|
+
|
|
187
|
+
-- Float
|
|
188
|
+
SELECT json_quote(3.14) as result;
|
|
189
|
+
→ [{"result":"3.14"}]
|
|
190
|
+
|
|
191
|
+
-- Boolean
|
|
192
|
+
SELECT json_quote(true) as result;
|
|
193
|
+
→ [{"result":"true"}]
|
|
194
|
+
|
|
195
|
+
SELECT json_quote(false) as result;
|
|
196
|
+
→ [{"result":"false"}]
|
|
197
|
+
|
|
198
|
+
-- String with special characters
|
|
199
|
+
SELECT json_quote('hello "world"') as result;
|
|
200
|
+
→ [{"result":"\"hello \\\"world\\\"\""}]
|
|
201
|
+
|
|
202
|
+
-- Native object
|
|
203
|
+
SELECT json_quote(json_object('a', 1)) as result;
|
|
204
|
+
→ [{"result":"{\"a\":1}"}]
|
|
205
|
+
|
|
206
|
+
-- ============================================================
|
|
207
|
+
-- json_object: edge cases
|
|
208
|
+
-- ============================================================
|
|
209
|
+
|
|
210
|
+
-- Odd number of args returns null
|
|
211
|
+
SELECT json_object('a') as result;
|
|
212
|
+
→ [{"result":null}]
|
|
213
|
+
|
|
214
|
+
-- Non-string key returns null
|
|
215
|
+
SELECT json_object(42, 'value') as result;
|
|
216
|
+
→ [{"result":null}]
|
|
217
|
+
|
|
218
|
+
-- Empty args returns empty object
|
|
219
|
+
SELECT json_object() as result;
|
|
220
|
+
→ [{"result":{}}]
|
|
221
|
+
|
|
222
|
+
-- Multiple key-value pairs
|
|
223
|
+
SELECT json_object('a', 1, 'b', 'two', 'c', true) as result;
|
|
224
|
+
→ [{"result":{"a":1,"b":"two","c":true}}]
|
|
225
|
+
|
|
226
|
+
-- ============================================================
|
|
227
|
+
-- json_array: edge cases
|
|
228
|
+
-- ============================================================
|
|
229
|
+
|
|
230
|
+
-- Empty args returns empty array
|
|
231
|
+
SELECT json_array() as result;
|
|
232
|
+
→ [{"result":[]}]
|
|
233
|
+
|
|
234
|
+
-- Mixed types
|
|
235
|
+
SELECT json_array(1, 'two', true, null) as result;
|
|
236
|
+
→ [{"result":[1,"two",true,null]}]
|
|
237
|
+
|
|
238
|
+
-- ============================================================
|
|
239
|
+
-- json_array_length: edge cases
|
|
240
|
+
-- ============================================================
|
|
241
|
+
|
|
242
|
+
-- Non-array returns 0
|
|
243
|
+
SELECT json_array_length('42') as result;
|
|
244
|
+
→ [{"result":0}]
|
|
245
|
+
|
|
246
|
+
SELECT json_array_length('{}') as result;
|
|
247
|
+
→ [{"result":0}]
|
|
248
|
+
|
|
249
|
+
-- Empty array
|
|
250
|
+
SELECT json_array_length('[]') as result;
|
|
251
|
+
→ [{"result":0}]
|
|
252
|
+
|
|
253
|
+
-- Normal array
|
|
254
|
+
SELECT json_array_length('[1,2,3]') as result;
|
|
255
|
+
→ [{"result":3}]
|
|
256
|
+
|
|
257
|
+
-- With path to array
|
|
258
|
+
SELECT json_array_length('{"a":[1,2,3,4]}', '$.a') as result;
|
|
259
|
+
→ [{"result":4}]
|
|
260
|
+
|
|
261
|
+
-- Path to non-array returns 0
|
|
262
|
+
SELECT json_array_length('{"a":42}', '$.a') as result;
|
|
263
|
+
→ [{"result":0}]
|
|
264
|
+
|
|
265
|
+
-- Non-string path returns 0
|
|
266
|
+
SELECT json_array_length('[1,2,3]', 42) as result;
|
|
267
|
+
→ [{"result":0}]
|
|
268
|
+
|
|
269
|
+
-- Missing path returns 0
|
|
270
|
+
SELECT json_array_length('{"a":[1]}', '$.b') as result;
|
|
271
|
+
→ [{"result":0}]
|
|
272
|
+
|
|
273
|
+
-- Null input: coerceToJsonValue(null) = JSON null, not undefined, so returns 0
|
|
274
|
+
SELECT json_array_length(null) as result;
|
|
275
|
+
→ [{"result":0}]
|
|
276
|
+
|
|
277
|
+
-- ============================================================
|
|
278
|
+
-- json_patch: edge cases
|
|
279
|
+
-- ============================================================
|
|
280
|
+
|
|
281
|
+
-- Valid add operation
|
|
282
|
+
SELECT json_patch('{"a":1}', '[{"op":"add","path":"/b","value":2}]') as result;
|
|
283
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
284
|
+
|
|
285
|
+
-- Valid replace operation
|
|
286
|
+
SELECT json_patch('{"a":1}', '[{"op":"replace","path":"/a","value":99}]') as result;
|
|
287
|
+
→ [{"result":{"a":99}}]
|
|
288
|
+
|
|
289
|
+
-- Valid remove operation
|
|
290
|
+
SELECT json_patch('{"a":1,"b":2}', '[{"op":"remove","path":"/b"}]') as result;
|
|
291
|
+
→ [{"result":{"a":1}}]
|
|
292
|
+
|
|
293
|
+
-- Invalid first arg returns null
|
|
294
|
+
SELECT json_patch('not-json', '[{"op":"add","path":"/a","value":1}]') as result;
|
|
295
|
+
→ [{"result":null}]
|
|
296
|
+
|
|
297
|
+
-- Invalid second arg returns null
|
|
298
|
+
SELECT json_patch('{"a":1}', 'not-json') as result;
|
|
299
|
+
→ [{"result":null}]
|
|
300
|
+
|
|
301
|
+
-- Null first arg returns null
|
|
302
|
+
SELECT json_patch(null, '[{"op":"add","path":"/a","value":1}]') as result;
|
|
303
|
+
→ [{"result":null}]
|
|
304
|
+
|
|
305
|
+
-- Patch with invalid path (triggers catch block)
|
|
306
|
+
SELECT json_patch('{"a":1}', '[{"op":"replace","path":"/nonexistent/deep/path","value":99}]') as result;
|
|
307
|
+
→ [{"result":null}]
|
|
308
|
+
|
|
309
|
+
-- Patch operation missing required fields returns null
|
|
310
|
+
SELECT json_patch('{"a":1}', '[{"value":1}]') as result;
|
|
311
|
+
→ [{"result":null}]
|
|
312
|
+
|
|
313
|
+
-- Multiple operations
|
|
314
|
+
SELECT json_patch('{"a":1}', '[{"op":"add","path":"/b","value":2},{"op":"remove","path":"/a"}]') as result;
|
|
315
|
+
→ [{"result":{"b":2}}]
|
|
316
|
+
|
|
317
|
+
-- ============================================================
|
|
318
|
+
-- json_insert: edge cases
|
|
319
|
+
-- ============================================================
|
|
320
|
+
|
|
321
|
+
-- No args (odd) returns null
|
|
322
|
+
SELECT json_insert('{"a":1}') as result;
|
|
323
|
+
→ [{"result":null}]
|
|
324
|
+
|
|
325
|
+
-- Non-string path returns null
|
|
326
|
+
SELECT json_insert('{"a":1}', 42, 'val') as result;
|
|
327
|
+
→ [{"result":null}]
|
|
328
|
+
|
|
329
|
+
-- Insert doesn't overwrite existing
|
|
330
|
+
SELECT json_insert('{"a":1}', '$.a', 99) as result;
|
|
331
|
+
→ [{"result":{"a":1}}]
|
|
332
|
+
|
|
333
|
+
-- Insert creates new key
|
|
334
|
+
SELECT json_insert('{"a":1}', '$.b', 2) as result;
|
|
335
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
336
|
+
|
|
337
|
+
-- Insert at array index within bounds (splice)
|
|
338
|
+
SELECT json_insert('[1,2,3]', '$[1]', 99) as result;
|
|
339
|
+
→ [{"result":[1,2,3]}]
|
|
340
|
+
|
|
341
|
+
-- Insert at array end (append)
|
|
342
|
+
SELECT json_insert('[1,2]', '$[2]', 3) as result;
|
|
343
|
+
→ [{"result":[1,2,3]}]
|
|
344
|
+
|
|
345
|
+
-- Invalid path syntax continues
|
|
346
|
+
SELECT json_insert('{"a":1}', '$invalid', 99) as result;
|
|
347
|
+
→ [{"result":{"a":1}}]
|
|
348
|
+
|
|
349
|
+
-- Multiple inserts
|
|
350
|
+
SELECT json_insert('{}', '$.a', 1, '$.b', 2) as result;
|
|
351
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
352
|
+
|
|
353
|
+
-- Invalid JSON input
|
|
354
|
+
SELECT json_insert('not-json', '$.a', 1) as result;
|
|
355
|
+
→ [{"result":null}]
|
|
356
|
+
|
|
357
|
+
-- Odd number of path/value args returns null
|
|
358
|
+
SELECT json_insert('{"a":1}', '$.b') as result;
|
|
359
|
+
→ [{"result":null}]
|
|
360
|
+
|
|
361
|
+
-- ============================================================
|
|
362
|
+
-- json_replace: edge cases
|
|
363
|
+
-- ============================================================
|
|
364
|
+
|
|
365
|
+
-- Replace existing key
|
|
366
|
+
SELECT json_replace('{"a":1,"b":2}', '$.a', 99) as result;
|
|
367
|
+
→ [{"result":{"a":99,"b":2}}]
|
|
368
|
+
|
|
369
|
+
-- Replace non-existing key does nothing
|
|
370
|
+
SELECT json_replace('{"a":1}', '$.b', 99) as result;
|
|
371
|
+
→ [{"result":{"a":1}}]
|
|
372
|
+
|
|
373
|
+
-- Replace root path
|
|
374
|
+
SELECT json_replace('{"a":1}', '$', 42) as result;
|
|
375
|
+
→ [{"result":42}]
|
|
376
|
+
|
|
377
|
+
-- Replace array element
|
|
378
|
+
SELECT json_replace('[10,20,30]', '$[1]', 99) as result;
|
|
379
|
+
→ [{"result":[10,99,30]}]
|
|
380
|
+
|
|
381
|
+
-- Replace array element out of bounds does nothing
|
|
382
|
+
SELECT json_replace('[10,20,30]', '$[5]', 99) as result;
|
|
383
|
+
→ [{"result":[10,20,30]}]
|
|
384
|
+
|
|
385
|
+
-- Invalid JSON
|
|
386
|
+
SELECT json_replace('not-json', '$.a', 1) as result;
|
|
387
|
+
→ [{"result":null}]
|
|
388
|
+
|
|
389
|
+
-- No args returns null
|
|
390
|
+
SELECT json_replace('{"a":1}') as result;
|
|
391
|
+
→ [{"result":null}]
|
|
392
|
+
|
|
393
|
+
-- Non-string path returns null
|
|
394
|
+
SELECT json_replace('{"a":1}', 42, 99) as result;
|
|
395
|
+
→ [{"result":null}]
|
|
396
|
+
|
|
397
|
+
-- Multiple replacements
|
|
398
|
+
SELECT json_replace('{"a":1,"b":2}', '$.a', 10, '$.b', 20) as result;
|
|
399
|
+
→ [{"result":{"a":10,"b":20}}]
|
|
400
|
+
|
|
401
|
+
-- ============================================================
|
|
402
|
+
-- json_set: edge cases
|
|
403
|
+
-- ============================================================
|
|
404
|
+
|
|
405
|
+
-- Set existing key (replace)
|
|
406
|
+
SELECT json_set('{"a":1}', '$.a', 99) as result;
|
|
407
|
+
→ [{"result":{"a":99}}]
|
|
408
|
+
|
|
409
|
+
-- Set new key (create)
|
|
410
|
+
SELECT json_set('{"a":1}', '$.b', 2) as result;
|
|
411
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
412
|
+
|
|
413
|
+
-- Set root path
|
|
414
|
+
SELECT json_set('{"a":1}', '$', 42) as result;
|
|
415
|
+
→ [{"result":42}]
|
|
416
|
+
|
|
417
|
+
-- Set array element in bounds
|
|
418
|
+
SELECT json_set('[10,20,30]', '$[1]', 99) as result;
|
|
419
|
+
→ [{"result":[10,99,30]}]
|
|
420
|
+
|
|
421
|
+
-- Set array element at end (append)
|
|
422
|
+
SELECT json_set('[10,20]', '$[2]', 30) as result;
|
|
423
|
+
→ [{"result":[10,20,30]}]
|
|
424
|
+
|
|
425
|
+
-- Set array element beyond end (gap-fill with nulls)
|
|
426
|
+
SELECT json_set('[1]', '$[4]', 'x') as result;
|
|
427
|
+
→ [{"result":[1,null,null,null,"x"]}]
|
|
428
|
+
|
|
429
|
+
-- Set on deeply nested missing path: pathInfo null means continue (no-op)
|
|
430
|
+
SELECT json_set('{}', '$.a.b', 42) as result;
|
|
431
|
+
→ [{"result":{}}]
|
|
432
|
+
|
|
433
|
+
-- Invalid JSON
|
|
434
|
+
SELECT json_set('not-json', '$.a', 1) as result;
|
|
435
|
+
→ [{"result":null}]
|
|
436
|
+
|
|
437
|
+
-- No args returns null
|
|
438
|
+
SELECT json_set('{}') as result;
|
|
439
|
+
→ [{"result":null}]
|
|
440
|
+
|
|
441
|
+
-- Non-string path returns null
|
|
442
|
+
SELECT json_set('{}', 42, 'val') as result;
|
|
443
|
+
→ [{"result":null}]
|
|
444
|
+
|
|
445
|
+
-- Multiple sets
|
|
446
|
+
SELECT json_set('{}', '$.a', 1, '$.b', 2, '$.c', 3) as result;
|
|
447
|
+
→ [{"result":{"a":1,"b":2,"c":3}}]
|
|
448
|
+
|
|
449
|
+
-- ============================================================
|
|
450
|
+
-- json_remove: edge cases
|
|
451
|
+
-- ============================================================
|
|
452
|
+
|
|
453
|
+
-- No paths returns original data
|
|
454
|
+
SELECT json_remove('{"a":1,"b":2}') as result;
|
|
455
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
456
|
+
|
|
457
|
+
-- Remove existing key
|
|
458
|
+
SELECT json_remove('{"a":1,"b":2}', '$.a') as result;
|
|
459
|
+
→ [{"result":{"b":2}}]
|
|
460
|
+
|
|
461
|
+
-- Remove non-existing key does nothing
|
|
462
|
+
SELECT json_remove('{"a":1}', '$.z') as result;
|
|
463
|
+
→ [{"result":{"a":1}}]
|
|
464
|
+
|
|
465
|
+
-- Remove array element
|
|
466
|
+
SELECT json_remove('[10,20,30]', '$[0]') as result;
|
|
467
|
+
→ [{"result":[20,30]}]
|
|
468
|
+
|
|
469
|
+
-- Remove array element out of bounds does nothing
|
|
470
|
+
SELECT json_remove('[10,20,30]', '$[5]') as result;
|
|
471
|
+
→ [{"result":[10,20,30]}]
|
|
472
|
+
|
|
473
|
+
-- Non-string path returns null
|
|
474
|
+
SELECT json_remove('{"a":1}', 42) as result;
|
|
475
|
+
→ [{"result":null}]
|
|
476
|
+
|
|
477
|
+
-- Invalid JSON
|
|
478
|
+
SELECT json_remove('not-json', '$.a') as result;
|
|
479
|
+
→ [{"result":null}]
|
|
480
|
+
|
|
481
|
+
-- Null JSON
|
|
482
|
+
SELECT json_remove(null, '$.a') as result;
|
|
483
|
+
→ [{"result":null}]
|
|
484
|
+
|
|
485
|
+
-- Multiple removals
|
|
486
|
+
SELECT json_remove('{"a":1,"b":2,"c":3}', '$.a', '$.c') as result;
|
|
487
|
+
→ [{"result":{"b":2}}]
|
|
488
|
+
|
|
489
|
+
-- Invalid path syntax continues silently
|
|
490
|
+
SELECT json_remove('{"a":1}', '$[invalid') as result;
|
|
491
|
+
→ [{"result":{"a":1}}]
|
|
492
|
+
|
|
493
|
+
-- ============================================================
|
|
494
|
+
-- json_group_array / json_group_object: aggregation
|
|
495
|
+
-- ============================================================
|
|
496
|
+
|
|
497
|
+
CREATE TABLE json_agg_t (id INTEGER PRIMARY KEY, name TEXT NULL, val INTEGER NULL);
|
|
498
|
+
INSERT INTO json_agg_t VALUES (1, 'a', 10), (2, 'b', 20), (3, null, 30);
|
|
499
|
+
-- run
|
|
500
|
+
|
|
501
|
+
-- json_group_array collects non-null and null values
|
|
502
|
+
SELECT json_group_array(val) as result FROM json_agg_t;
|
|
503
|
+
→ [{"result":[10,20,30]}]
|
|
504
|
+
|
|
505
|
+
-- json_group_object skips null keys
|
|
506
|
+
SELECT json_group_object(name, val) as result FROM json_agg_t;
|
|
507
|
+
→ [{"result":{"a":10,"b":20}}]
|
|
508
|
+
|
|
509
|
+
-- json_group_array with all nulls still collects them
|
|
510
|
+
CREATE TABLE json_agg_nulls (id INTEGER PRIMARY KEY, val INTEGER NULL);
|
|
511
|
+
INSERT INTO json_agg_nulls VALUES (1, null), (2, null);
|
|
512
|
+
-- run
|
|
513
|
+
|
|
514
|
+
SELECT json_group_array(val) as result FROM json_agg_nulls;
|
|
515
|
+
→ [{"result":[null,null]}]
|
|
516
|
+
|
|
517
|
+
-- json_group_object with empty table
|
|
518
|
+
CREATE TABLE json_agg_empty2 (id INTEGER PRIMARY KEY, name TEXT, val INTEGER);
|
|
519
|
+
SELECT json_group_object(name, val) as result FROM json_agg_empty2;
|
|
520
|
+
→ [{"result":null}]
|
|
521
|
+
|
|
522
|
+
DROP TABLE json_agg_t;
|
|
523
|
+
DROP TABLE json_agg_nulls;
|
|
524
|
+
DROP TABLE json_agg_empty2;
|
|
525
|
+
|
|
526
|
+
-- ============================================================
|
|
527
|
+
-- json path: quoted keys, bracket notation, edge cases
|
|
528
|
+
-- ============================================================
|
|
529
|
+
|
|
530
|
+
-- Quoted key with dot in name
|
|
531
|
+
SELECT json_extract('{"a.b":42}', '$."a.b"') as result;
|
|
532
|
+
→ [{"result":42}]
|
|
533
|
+
|
|
534
|
+
-- Bracket notation for arrays
|
|
535
|
+
SELECT json_extract('[[1,2],[3,4]]', '$[0][1]') as result;
|
|
536
|
+
→ [{"result":2}]
|
|
537
|
+
|
|
538
|
+
-- Deeply nested mixed paths
|
|
539
|
+
SELECT json_extract('{"a":[{"b":99}]}', '$.a[0].b') as result;
|
|
540
|
+
→ [{"result":99}]
|
|
541
|
+
|
|
542
|
+
-- Invalid path: unclosed bracket
|
|
543
|
+
SELECT json_extract('{"a":1}', '$[0') as result;
|
|
544
|
+
→ [{"result":null}]
|
|
545
|
+
|
|
546
|
+
-- Invalid path: negative index
|
|
547
|
+
SELECT json_extract('[1,2,3]', '$[-1]') as result;
|
|
548
|
+
→ [{"result":null}]
|
|
549
|
+
|
|
550
|
+
-- Invalid path: empty string
|
|
551
|
+
SELECT json_extract('{"a":1}', '') as result;
|
|
552
|
+
→ [{"result":null}]
|
|
553
|
+
|
|
554
|
+
-- Root path returns full value
|
|
555
|
+
SELECT json_extract('{"a":1,"b":2}', '$') as result;
|
|
556
|
+
→ [{"result":{"a":1,"b":2}}]
|
|
557
|
+
|
|
558
|
+
-- Path through null parent
|
|
559
|
+
SELECT json_extract('{"a":null}', '$.a.b') as result;
|
|
560
|
+
→ [{"result":null}]
|
|
561
|
+
|
|
562
|
+
-- ============================================================
|
|
563
|
+
-- json_insert into nested structures
|
|
564
|
+
-- ============================================================
|
|
565
|
+
|
|
566
|
+
-- Insert into nested object
|
|
567
|
+
SELECT json_insert('{"a":{"b":1}}', '$.a.c', 2) as result;
|
|
568
|
+
→ [{"result":{"a":{"b":1,"c":2}}}]
|
|
569
|
+
|
|
570
|
+
-- Insert into nested array
|
|
571
|
+
SELECT json_insert('{"a":[1,2]}', '$.a[2]', 3) as result;
|
|
572
|
+
→ [{"result":{"a":[1,2,3]}}]
|
|
573
|
+
|
|
574
|
+
-- ============================================================
|
|
575
|
+
-- json_set with createParents on deep paths
|
|
576
|
+
-- ============================================================
|
|
577
|
+
|
|
578
|
+
-- Deep path where intermediate doesn't exist: returns unchanged
|
|
579
|
+
SELECT json_set('{"a":{}}', '$.a.b[0]', 'first') as result;
|
|
580
|
+
→ [{"result":{"a":{}}}]
|
|
581
|
+
|
|
582
|
+
-- createParents: set new key on existing object
|
|
583
|
+
SELECT json_set('{"a":{"b":1}}', '$.a.c', 2) as result;
|
|
584
|
+
→ [{"result":{"a":{"b":1,"c":2}}}]
|
|
585
|
+
|
|
586
|
+
-- ============================================================
|
|
587
|
+
-- json type detection on native objects
|
|
588
|
+
-- ============================================================
|
|
589
|
+
|
|
590
|
+
SELECT json_type(json_array(1, 2, 3)) as result;
|
|
591
|
+
→ [{"result":"array"}]
|
|
592
|
+
|
|
593
|
+
SELECT json_type(json_object('a', 1)) as result;
|
|
594
|
+
→ [{"result":"object"}]
|
|
595
|
+
|
|
596
|
+
SELECT json_type(42) as result;
|
|
597
|
+
→ [{"result":"integer"}]
|
|
598
|
+
|
|
599
|
+
SELECT json_type(3.14) as result;
|
|
600
|
+
→ [{"result":"real"}]
|
|
601
|
+
|
|
602
|
+
SELECT json_type(true) as result;
|
|
603
|
+
→ [{"result":"true"}]
|
|
604
|
+
|
|
605
|
+
SELECT json_type(false) as result;
|
|
606
|
+
→ [{"result":"false"}]
|
|
607
|
+
|
|
608
|
+
SELECT json_type(null) as result;
|
|
609
|
+
→ [{"result":"null"}]
|
|
610
|
+
|
|
611
|
+
-- ============================================================
|
|
612
|
+
-- json_extract with string value
|
|
613
|
+
-- ============================================================
|
|
614
|
+
|
|
615
|
+
SELECT json_extract('{"a":"hello"}', '$.a') as result;
|
|
616
|
+
→ [{"result":"hello"}]
|
|
617
|
+
|
|
618
|
+
-- ============================================================
|
|
619
|
+
-- Mutation doesn't affect original (deep copy verification)
|
|
620
|
+
-- ============================================================
|
|
621
|
+
|
|
622
|
+
CREATE TABLE json_mut (id INTEGER PRIMARY KEY, data JSON);
|
|
623
|
+
INSERT INTO json_mut VALUES (1, '{"a":[1,2,3]}');
|
|
624
|
+
-- run
|
|
625
|
+
|
|
626
|
+
-- json_set returns new data, original should be unchanged
|
|
627
|
+
SELECT json_set(data, '$.a[0]', 99) as modified FROM json_mut WHERE id = 1;
|
|
628
|
+
→ [{"modified":{"a":[99,2,3]}}]
|
|
629
|
+
|
|
630
|
+
SELECT data FROM json_mut WHERE id = 1;
|
|
631
|
+
→ [{"data":{"a":[1,2,3]}}]
|
|
632
|
+
|
|
633
|
+
DROP TABLE json_mut;
|