orange-orm 5.0.0-beta.0 → 5.0.0-beta.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 CHANGED
@@ -51,7 +51,7 @@ Watch the [tutorial video on YouTube](https://youtu.be/1IwwjPr2lMs)
51
51
  ![Relations diagram](./docs/diagram.svg)
52
52
 
53
53
  <sub>📄 map.ts</sub>
54
- ```ts
54
+ ```javascript
55
55
  import orange from 'orange-orm';
56
56
 
57
57
  const map = orange.map(x => ({
@@ -88,7 +88,7 @@ const map = orange.map(x => ({
88
88
  street: column('street').string(),
89
89
  postalCode: column('postalCode').string(),
90
90
  postalPlace: column('postalPlace').string(),
91
- countryCode: column('countryCode').string().enum(['NO', 'SE', 'DK', 'FI', 'IS', 'DE', 'FR', 'NL', 'ES', 'IT']),
91
+ countryCode: column('countryCode').string(),
92
92
  }))
93
93
 
94
94
  })).map(x => ({
@@ -106,7 +106,7 @@ export default map;
106
106
  ```
107
107
  <sub>📄 update.ts</sub>
108
108
 
109
- ```ts
109
+ ```javascript
110
110
  import map from './map';
111
111
  const db = map.sqlite('demo.db');
112
112
 
@@ -127,7 +127,7 @@ async function updateRow() {
127
127
  ```
128
128
  <sub>📄 filter.ts</sub>
129
129
 
130
- ```ts
130
+ ```javascript
131
131
  import map from './map';
132
132
  const db = map.sqlite('demo.db');
133
133
 
@@ -157,8 +157,7 @@ Each column within your database table is designated by using the <strong><i>col
157
157
  Relationships between tables can also be outlined. By using methods like <strong><i>hasOne</i></strong>, <strong><i>hasMany</i></strong>, and <strong><i>references</i></strong>, you can establish connections that reflect the relationships in your data schema. In the example below, an 'order' is linked to a 'customer' reference, a 'deliveryAddress', and multiple 'lines'. The hasMany and hasOne relations represents ownership - the tables 'deliveryAddress' and 'orderLine' are owned by the 'order' table, and therefore, they contain the 'orderId' column referring to their parent table, which is 'order'. The similar relationship exists between orderLine and package - hence the packages are owned by the orderLine. Conversely, the customer table is independent and can exist without any knowledge of the 'order' table. Therefore we say that the order table <i>references</i> the customer table - necessitating the existence of a 'customerId' column in the 'order' table.</p>
158
158
 
159
159
  <sub>📄 map.ts</sub>
160
-
161
- ```ts
160
+ ```javascript
162
161
  import orange from 'orange-orm';
163
162
 
164
163
  const map = orange.map(x => ({
@@ -194,7 +193,7 @@ const map = orange.map(x => ({
194
193
  street: column('street').string(),
195
194
  postalCode: column('postalCode').string(),
196
195
  postalPlace: column('postalPlace').string(),
197
- countryCode: column('countryCode').string().enum(['NO', 'SE', 'DK', 'FI', 'IS', 'DE', 'FR', 'NL', 'ES', 'IT']),
196
+ countryCode: column('countryCode').string(),
198
197
  }))
199
198
 
200
199
  })).map(x => ({
@@ -219,8 +218,7 @@ Then, we define a SQL string. This string outlines the structure of our SQLite d
219
218
  Because of a peculiarity in SQLite, which only allows one statement execution at a time, we split this SQL string into separate statements. We do this using the split() method, which breaks up the string at every semicolon.
220
219
 
221
220
  <sub>📄 init.ts</sub>
222
-
223
- ```ts
221
+ ```javascript
224
222
  import map from './map';
225
223
  const db = map.sqlite('demo.db');
226
224
 
@@ -339,7 +337,7 @@ await db.transaction(async (db) => {
339
337
  __From the browser__
340
338
  You can securely use Orange from the browser by utilizing the Express plugin, which serves to safeguard sensitive database credentials from exposure at the client level. This technique bypasses the need to transmit raw SQL queries directly from the client to the server. Instead, it logs method calls initiated by the client, which are later replayed and authenticated on the server. This not only reinforces security by preventing the disclosure of raw SQL queries on the client side but also facilitates a smoother operation. Essentially, this method mirrors a traditional REST API, augmented with advanced TypeScript tooling for enhanced functionality. You can read more about it in the section called [In the browser](#user-content-in-the-browser)
341
339
  <sub>📄 server.ts</sub>
342
- ```ts
340
+ ```javascript
343
341
  import map from './map';
344
342
  import { json } from 'body-parser';
345
343
  import express from 'express';
@@ -356,7 +354,7 @@ express().disable('x-powered-by')
356
354
  ```
357
355
 
358
356
  <sub>📄 browser.ts</sub>
359
- ```ts
357
+ ```javascript
360
358
  import map from './map';
361
359
 
362
360
  const db = map.http('http://localhost:3000/orange');
@@ -434,7 +432,7 @@ database_id = "<your-guid-for-the-database>"
434
432
  ```
435
433
 
436
434
  <sub>📄 src/index.ts</sub>
437
- ```ts
435
+ ```javascript
438
436
  import map from './map';
439
437
 
440
438
  export interface Env {
@@ -1176,7 +1174,7 @@ Raw sql queries, raw sql filters and transactions are disabled at the http clien
1176
1174
 
1177
1175
  <sub>📄 server.ts</sub>
1178
1176
 
1179
- ```ts
1177
+ ```javascript
1180
1178
  import map from './map';
1181
1179
  import { json } from 'body-parser';
1182
1180
  import express from 'express';
@@ -1193,7 +1191,7 @@ express().disable('x-powered-by')
1193
1191
  ```
1194
1192
 
1195
1193
  <sub>📄 browser.ts</sub>
1196
- ```ts
1194
+ ```javascript
1197
1195
  import map from './map';
1198
1196
 
1199
1197
  const db = map.http('http://localhost:3000/orange');
@@ -1224,7 +1222,7 @@ One notable side effect compared to the previous example, is that only the order
1224
1222
 
1225
1223
  <sub>📄 server.ts</sub>
1226
1224
 
1227
- ```ts
1225
+ ```javascript
1228
1226
  import map from './map';
1229
1227
  import { json } from 'body-parser';
1230
1228
  import express from 'express';
@@ -1259,7 +1257,7 @@ function validateToken(req, res, next) {
1259
1257
 
1260
1258
  <sub>📄 browser.ts</sub>
1261
1259
 
1262
- ```ts
1260
+ ```javascript
1263
1261
  import map from './map';
1264
1262
 
1265
1263
  const db = map.http('http://localhost:3000/orange');
@@ -1303,8 +1301,9 @@ async function updateRows() {
1303
1301
 
1304
1302
  ```
1305
1303
 
1306
- __Row Level Security__
1304
+ __Row Level Security (Postgres)__
1307
1305
  You can enforce tenant isolation at the database level by combining Postgres RLS with Express hooks. The example below mirrors the “Interceptors and base filter” style by putting the tenant id in a (fake) token on the client, then extracting it on the server and setting it inside the transaction. This is convenient for a demo because we can seed data and prove rows are filtered. In a real application you must validate signatures and derive tenant id from a trusted identity source, not from arbitrary client input.
1306
+ Available transaction hooks are `beforeBegin`, `afterBegin`, `beforeCommit`, `afterCommit`, and `afterRollback`.
1308
1307
 
1309
1308
  <sub>📄 setup.sql</sub>
1310
1309
 
@@ -1331,7 +1330,7 @@ insert into tenant_data (tenant_id, value) values
1331
1330
 
1332
1331
  <sub>📄 server.ts</sub>
1333
1332
 
1334
- ```ts
1333
+ ```javascript
1335
1334
  import map from './map';
1336
1335
  import { json } from 'body-parser';
1337
1336
  import express from 'express';
@@ -1346,7 +1345,6 @@ express().disable('x-powered-by')
1346
1345
  .use('/orange', db.express({
1347
1346
  hooks: {
1348
1347
  transaction: {
1349
- //beforeBegin: async (db, req) => ...,
1350
1348
  afterBegin: async (db, req) => {
1351
1349
  const tenantId = Number.parseInt(String(req.user?.tenantId ?? ''), 10);
1352
1350
  if (!Number.isFinite(tenantId)) throw new Error('Missing tenant id');
@@ -1355,12 +1353,7 @@ express().disable('x-powered-by')
1355
1353
  sql: 'select set_config(\'app.tenant_id\', ?, true)',
1356
1354
  parameters: [String(tenantId)]
1357
1355
  });
1358
- },
1359
- //beforeCommit: async (db, req) => ...,
1360
- //afterCommit: async (db, req) => ...,
1361
- // afterRollback: async (db, req, error) => {
1362
- // console.dir(error);
1363
- // }
1356
+ }
1364
1357
  }
1365
1358
  }
1366
1359
  }))
@@ -1389,7 +1382,7 @@ function decodeFakeJwt(token) {
1389
1382
 
1390
1383
  <sub>📄 browser.ts</sub>
1391
1384
 
1392
- ```ts
1385
+ ```javascript
1393
1386
  import map from './map';
1394
1387
 
1395
1388
  const db = map.http('http://localhost:3000/orange');
@@ -1802,8 +1795,7 @@ async function execute() {
1802
1795
  - **`json`** and **`jsonOf<T>`** are represented as an object or array in javascript and maps to JSON, JSONB, NVARCHAR(max) or TEXT (sqlite) in sql.
1803
1796
 
1804
1797
  <sub>📄 map.ts</sub>
1805
-
1806
- ```ts
1798
+ ```javascript
1807
1799
  import orange from 'orange-orm';
1808
1800
 
1809
1801
  interface Pet {
@@ -1826,8 +1818,7 @@ const map = orange.map(x => ({
1826
1818
  }));
1827
1819
  ```
1828
1820
  <sub>📄 map.js</sub>
1829
-
1830
- ```js
1821
+ ```javascript
1831
1822
  import orange from 'orange-orm';
1832
1823
 
1833
1824
  /**
@@ -1854,138 +1845,6 @@ const map = orange.map(x => ({
1854
1845
  ```
1855
1846
  </details>
1856
1847
 
1857
- <details id="enums"><summary><strong>Enums</strong></summary>
1858
- <p>Enums can be defined using object literals, arrays, or TypeScript enums. The <strong><i>enum(...)</i></strong> method uses literal types when possible, so prefer patterns that keep literals (inline objects, <code>as const</code>, or <code>Object.freeze</code> in JS).</p>
1859
-
1860
- <sub>📄 map.ts (TypeScript enum)</sub>
1861
-
1862
- ```ts
1863
- enum CountryCode {
1864
- NORWAY = 'NO',
1865
- SWEDEN = 'SE',
1866
- DENMARK = 'DK',
1867
- FINLAND = 'FI',
1868
- ICELAND = 'IS',
1869
- GERMANY = 'DE',
1870
- FRANCE = 'FR',
1871
- NETHERLANDS = 'NL',
1872
- SPAIN = 'ES',
1873
- ITALY = 'IT',
1874
- }
1875
-
1876
- const map = orange.map(x => ({
1877
- deliveryAddress: x.table('deliveryAddress').map(({ column }) => ({
1878
- id: column('id').numeric().primary(),
1879
- name: column('name').string(),
1880
- street: column('street').string(),
1881
- postalCode: column('postalCode').string(),
1882
- postalPlace: column('postalPlace').string(),
1883
- countryCode: column('countryCode').string().enum(CountryCode),
1884
- }))
1885
- }));
1886
- ```
1887
-
1888
-
1889
- <sub>📄 map.ts (as const)</sub>
1890
-
1891
- ```ts
1892
- const Countries = {
1893
- NORWAY: 'NO',
1894
- SWEDEN: 'SE',
1895
- DENMARK: 'DK',
1896
- FINLAND: 'FI',
1897
- ICELAND: 'IS',
1898
- GERMANY: 'DE',
1899
- FRANCE: 'FR',
1900
- NETHERLANDS: 'NL',
1901
- SPAIN: 'ES',
1902
- ITALY: 'IT',
1903
- } as const;
1904
-
1905
- const map = orange.map(x => ({
1906
- deliveryAddress: x.table('deliveryAddress').map(({ column }) => ({
1907
- id: column('id').numeric().primary(),
1908
- name: column('name').string(),
1909
- street: column('street').string(),
1910
- postalCode: column('postalCode').string(),
1911
- postalPlace: column('postalPlace').string(),
1912
- countryCode: column('countryCode').string().enum(Countries),
1913
- }))
1914
- }));
1915
- ```
1916
-
1917
- <sub>📄 map.ts (array)</sub>
1918
-
1919
- ```ts
1920
- const map = orange.map(x => ({
1921
- deliveryAddress: x.table('deliveryAddress').map(({ column }) => ({
1922
- id: column('id').numeric().primary(),
1923
- name: column('name').string(),
1924
- street: column('street').string(),
1925
- postalCode: column('postalCode').string(),
1926
- postalPlace: column('postalPlace').string(),
1927
- countryCode: column('countryCode').string().enum(
1928
- ['NO', 'SE', 'DK', 'FI', 'IS', 'DE', 'FR', 'NL', 'ES', 'IT']
1929
- ),
1930
- }))
1931
- }));
1932
- ```
1933
-
1934
- <sub>📄 map.ts (literal object)</sub>
1935
-
1936
- ```ts
1937
- const map = orange.map(x => ({
1938
- deliveryAddress: x.table('deliveryAddress').map(({ column }) => ({
1939
- id: column('id').numeric().primary(),
1940
- name: column('name').string(),
1941
- street: column('street').string(),
1942
- postalCode: column('postalCode').string(),
1943
- postalPlace: column('postalPlace').string(),
1944
- countryCode: column('countryCode').string().enum({
1945
- NORWAY: 'NO',
1946
- SWEDEN: 'SE',
1947
- DENMARK: 'DK',
1948
- FINLAND: 'FI',
1949
- ICELAND: 'IS',
1950
- GERMANY: 'DE',
1951
- FRANCE: 'FR',
1952
- NETHERLANDS: 'NL',
1953
- SPAIN: 'ES',
1954
- ITALY: 'IT',
1955
- }),
1956
- }))
1957
- }));
1958
- ```
1959
-
1960
- <sub>📄 map.js (Object.freeze)</sub>
1961
-
1962
- ```js
1963
- const Countries = Object.freeze({
1964
- NORWAY: 'NO',
1965
- SWEDEN: 'SE',
1966
- DENMARK: 'DK',
1967
- FINLAND: 'FI',
1968
- ICELAND: 'IS',
1969
- GERMANY: 'DE',
1970
- FRANCE: 'FR',
1971
- NETHERLANDS: 'NL',
1972
- SPAIN: 'ES',
1973
- ITALY: 'IT',
1974
- });
1975
-
1976
- const map = orange.map(x => ({
1977
- deliveryAddress: x.table('deliveryAddress').map(({ column }) => ({
1978
- id: column('id').numeric().primary(),
1979
- name: column('name').string(),
1980
- street: column('street').string(),
1981
- postalCode: column('postalCode').string(),
1982
- postalPlace: column('postalPlace').string(),
1983
- countryCode: column('countryCode').string().enum(Countries),
1984
- }))
1985
- }));
1986
- ```
1987
- </details>
1988
-
1989
1848
  <details id="default-values"><summary><strong>Default values</strong></summary>
1990
1849
  <p>Utilizing default values can be especially useful for automatically populating these fields when the underlying database doesn't offer native support for default value generation.
1991
1850
 
@@ -2012,7 +1871,7 @@ export default map;
2012
1871
  <p>In the previous sections you have already seen the <strong><i>notNull()</i></strong> validator being used on some columns. This will not only generate correct typescript mapping, but also throw an error if value is set to null or undefined. However, sometimes we do not want the notNull-validator to be run on inserts. Typically, when we have an autoincremental key or server generated uuid, it does not make sense to check for null on insert. This is where <strong><i>notNullExceptInsert()</strong></i> comes to rescue. You can also create your own custom validator as shown below. The last kind of validator, is the <a href="https://ajv.js.org/json-schema.html">ajv JSON schema validator</a>. This can be used on json columns as well as any other column type.</p>
2013
1872
 
2014
1873
  <sub>📄 map.ts</sub>
2015
- ```ts
1874
+ ```javascript
2016
1875
  import orange from 'orange-orm';
2017
1876
 
2018
1877
  interface Pet {
@@ -2043,7 +1902,7 @@ const map = orange.map(x => ({
2043
1902
  export default map;
2044
1903
  ```
2045
1904
  <sub>📄 map.js</sub>
2046
- ```js
1905
+ ```javascript
2047
1906
  import orange from 'orange-orm';
2048
1907
 
2049
1908
  /**
@@ -2253,7 +2112,7 @@ async function getCount() {
2253
2112
 
2254
2113
  <sub>📄 map.ts</sub>
2255
2114
 
2256
- ```ts
2115
+ ```javascript
2257
2116
  import orange from 'orange-orm';
2258
2117
 
2259
2118
  const map = orange.map(x => ({
@@ -2269,7 +2128,7 @@ export default map;
2269
2128
  ```
2270
2129
  <sub>📄 sensitive.ts</sub>
2271
2130
 
2272
- ```ts
2131
+ ```javascript
2273
2132
  import map from './map';
2274
2133
  const db = map.sqlite('demo.db');
2275
2134
 
@@ -5886,37 +5886,6 @@ function requireColumn () {
5886
5886
  return c;
5887
5887
  };
5888
5888
 
5889
- c.enum = function(values) {
5890
- let list = values;
5891
- if (Array.isArray(values))
5892
- list = values;
5893
- else if (values && typeof values === 'object') {
5894
- const keys = Object.keys(values);
5895
- const nonNumericKeys = keys.filter((key) => !/^-?\d+$/.test(key));
5896
- list = (nonNumericKeys.length ? nonNumericKeys : keys).map((key) => values[key]);
5897
- }
5898
- else
5899
- throw new Error('enum values must be an array');
5900
- const allowed = new Set(list);
5901
- column.enum = list;
5902
- function validate(value) {
5903
- if (value === undefined || value === null)
5904
- return;
5905
- if (!allowed.has(value)) {
5906
- const formatted = list.map((v) => JSON.stringify(v)).join(', ');
5907
- throw new Error(`Column ${column.alias} must be one of: ${formatted}`);
5908
- }
5909
- }
5910
- return c.validate(validate);
5911
- };
5912
-
5913
- c.enum2 = function(...values) {
5914
- const list = values.length === 1 && Array.isArray(values[0])
5915
- ? values[0]
5916
- : values;
5917
- return c.enum(list);
5918
- };
5919
-
5920
5889
  c.default = function(value) {
5921
5890
  column.default = value;
5922
5891
  return c;
@@ -5932,6 +5901,7 @@ function requireColumn () {
5932
5901
  var oldAlias = column.alias;
5933
5902
  table._aliases.delete(oldAlias);
5934
5903
  table._aliases.add(alias);
5904
+ delete table[oldAlias];
5935
5905
  table[alias] = column;
5936
5906
  column.alias = alias;
5937
5907
  return c;
package/dist/index.mjs CHANGED
@@ -5887,37 +5887,6 @@ function requireColumn () {
5887
5887
  return c;
5888
5888
  };
5889
5889
 
5890
- c.enum = function(values) {
5891
- let list = values;
5892
- if (Array.isArray(values))
5893
- list = values;
5894
- else if (values && typeof values === 'object') {
5895
- const keys = Object.keys(values);
5896
- const nonNumericKeys = keys.filter((key) => !/^-?\d+$/.test(key));
5897
- list = (nonNumericKeys.length ? nonNumericKeys : keys).map((key) => values[key]);
5898
- }
5899
- else
5900
- throw new Error('enum values must be an array');
5901
- const allowed = new Set(list);
5902
- column.enum = list;
5903
- function validate(value) {
5904
- if (value === undefined || value === null)
5905
- return;
5906
- if (!allowed.has(value)) {
5907
- const formatted = list.map((v) => JSON.stringify(v)).join(', ');
5908
- throw new Error(`Column ${column.alias} must be one of: ${formatted}`);
5909
- }
5910
- }
5911
- return c.validate(validate);
5912
- };
5913
-
5914
- c.enum2 = function(...values) {
5915
- const list = values.length === 1 && Array.isArray(values[0])
5916
- ? values[0]
5917
- : values;
5918
- return c.enum(list);
5919
- };
5920
-
5921
5890
  c.default = function(value) {
5922
5891
  column.default = value;
5923
5892
  return c;
@@ -5933,6 +5902,7 @@ function requireColumn () {
5933
5902
  var oldAlias = column.alias;
5934
5903
  table._aliases.delete(oldAlias);
5935
5904
  table._aliases.add(alias);
5905
+ delete table[oldAlias];
5936
5906
  table[alias] = column;
5937
5907
  column.alias = alias;
5938
5908
  return c;
@@ -19655,7 +19625,7 @@ function requireOutputInsertedSql () {
19655
19625
 
19656
19626
  function formatColumn(column) {
19657
19627
  if (column.formatOut)
19658
- return column.formatOut(context, 'INSERTED');
19628
+ return `${column.formatOut(context, 'INSERTED')} AS [${column._dbName}]`;
19659
19629
  else
19660
19630
  return `INSERTED.[${column._dbName}]`;
19661
19631
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "orange-orm",
3
- "version": "5.0.0-beta.0",
3
+ "version": "5.0.0-beta.2",
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
package/src/map.d.ts CHANGED
@@ -96,9 +96,7 @@ type ReturnArrayOrObj<W, V1, V2> =
96
96
  V1;
97
97
 
98
98
 
99
- type ColumnToType<T> = T extends EnumOf<infer E>
100
- ? E
101
- : T extends UuidColumnSymbol
99
+ type ColumnToType<T> = T extends UuidColumnSymbol
102
100
  ? string
103
101
  : T extends StringColumnSymbol
104
102
  ? string
@@ -627,10 +625,6 @@ type NotNullExceptInsert = {
627
625
  [' notNullExceptInsert']: boolean;
628
626
  };
629
627
 
630
- type EnumOf<T> = {
631
- [' enum']: T;
632
- };
633
-
634
628
  type JsonOf<T> = {
635
629
  [' isjsonOf']: boolean;
636
630
  type: T;
@@ -740,11 +734,6 @@ type DateWithTimeZoneValidator<M> = M extends NotNull
740
734
  };
741
735
 
742
736
  type StringColumnTypeDef<M> = StringValidator<M> & {
743
- enum<const V extends readonly string[]>(values: V): StringColumnTypeDef<M & EnumOf<V[number]>> & EnumOf<V[number]>;
744
- enum<const V extends Record<string, string>>(values: V): StringColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
745
- enum<TEnum>(values: Record<string, TEnum>): StringColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
746
- enum<E extends string>(values: readonly E[]): StringColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
747
- enum<E, V extends Record<string, E>>(values: V): StringColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
748
737
  primary(): StringColumnTypeDef<M & IsPrimary> & IsPrimary;
749
738
  notNull(): StringColumnTypeDef<M & NotNull> & NotNull;
750
739
  notNullExceptInsert(): StringColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -756,10 +745,6 @@ type StringColumnTypeDef<M> = StringValidator<M> & {
756
745
  M;
757
746
 
758
747
  type NumericColumnTypeDef<M> = NumericValidator<M> & {
759
- enum<const V extends Record<string, number>>(values: V): NumericColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
760
- enum<TEnum>(values: Record<string, TEnum>): NumericColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
761
- enum<E extends number>(values: readonly E[]): NumericColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
762
- enum<E, V extends Record<string, E>>(values: V): NumericColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
763
748
  primary(): NumericColumnTypeDef<M & IsPrimary> & IsPrimary;
764
749
  notNull(): NumericColumnTypeDef<M & NotNull> & NotNull;
765
750
  notNullExceptInsert(): NumericColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -771,10 +756,6 @@ type NumericColumnTypeDef<M> = NumericValidator<M> & {
771
756
  M;
772
757
 
773
758
  type BigIntColumnTypeDef<M> = BigIntValidator<M> & {
774
- enum<const V extends Record<string, bigint>>(values: V): BigIntColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
775
- enum<TEnum>(values: Record<string, TEnum>): BigIntColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
776
- enum<E extends bigint>(values: readonly E[]): BigIntColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
777
- enum<E, V extends Record<string, E>>(values: V): BigIntColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
778
759
  primary(): BigIntColumnTypeDef<M & IsPrimary> & IsPrimary;
779
760
  notNull(): BigIntColumnTypeDef<M & NotNull> & NotNull;
780
761
  notNullExceptInsert(): BigIntColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -786,10 +767,6 @@ type BigIntColumnTypeDef<M> = BigIntValidator<M> & {
786
767
  M;
787
768
 
788
769
  type UuidColumnTypeDef<M> = UuidValidator<M> & {
789
- enum<const V extends Record<string, string>>(values: V): UuidColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
790
- enum<TEnum>(values: Record<string, TEnum>): UuidColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
791
- enum<E extends string>(values: readonly E[]): UuidColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
792
- enum<E, V extends Record<string, E>>(values: V): UuidColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
793
770
  primary(): UuidColumnTypeDef<M & IsPrimary> & IsPrimary;
794
771
  notNull(): UuidColumnTypeDef<M & NotNull> & NotNull;
795
772
  notNullExceptInsert(): UuidColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -812,10 +789,6 @@ type JSONColumnTypeDef<M> = JSONValidator<M> & {
812
789
  M;
813
790
 
814
791
  type BinaryColumnTypeDef<M> = BinaryValidator<M> & {
815
- enum<const V extends Record<string, string>>(values: V): BinaryColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
816
- enum<TEnum>(values: Record<string, TEnum>): BinaryColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
817
- enum<E extends string>(values: readonly E[]): BinaryColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
818
- enum<E, V extends Record<string, E>>(values: V): BinaryColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
819
792
  primary(): BinaryColumnTypeDef<M & IsPrimary> & IsPrimary;
820
793
  notNull(): BinaryColumnTypeDef<M & NotNull> & NotNull;
821
794
  notNullExceptInsert(): BinaryColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -827,10 +800,6 @@ type BinaryColumnTypeDef<M> = BinaryValidator<M> & {
827
800
  M;
828
801
 
829
802
  type BooleanColumnTypeDef<M> = BooleanValidator<M> & {
830
- enum<const V extends Record<string, boolean>>(values: V): BooleanColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
831
- enum<TEnum>(values: Record<string, TEnum>): BooleanColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
832
- enum<E extends boolean>(values: readonly E[]): BooleanColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
833
- enum<E, V extends Record<string, E>>(values: V): BooleanColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
834
803
  primary(): BooleanColumnTypeDef<M & IsPrimary> & IsPrimary;
835
804
  notNull(): BooleanColumnTypeDef<M & NotNull> & NotNull;
836
805
  notNullExceptInsert(): BooleanColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -842,10 +811,6 @@ type BooleanColumnTypeDef<M> = BooleanValidator<M> & {
842
811
  M;
843
812
 
844
813
  type DateColumnTypeDef<M> = DateValidator<M> & {
845
- enum<const V extends Record<string, string | Date>>(values: V): DateColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
846
- enum<TEnum>(values: Record<string, TEnum>): DateColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
847
- enum<E extends string | Date>(values: readonly E[]): DateColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
848
- enum<E, V extends Record<string, E>>(values: V): DateColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
849
814
  primary(): DateColumnTypeDef<M & IsPrimary> & IsPrimary;
850
815
  notNull(): DateColumnTypeDef<M & NotNull> & NotNull;
851
816
  notNullExceptInsert(): DateColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -857,10 +822,6 @@ type DateColumnTypeDef<M> = DateValidator<M> & {
857
822
  M;
858
823
 
859
824
  type DateWithTimeZoneColumnTypeDef<M> = DateValidator<M> & {
860
- enum<const V extends Record<string, string | Date>>(values: V): DateWithTimeZoneColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
861
- enum<TEnum>(values: Record<string, TEnum>): DateWithTimeZoneColumnTypeDef<M & EnumOf<TEnum>> & EnumOf<TEnum>;
862
- enum<E extends string | Date>(values: readonly E[]): DateWithTimeZoneColumnTypeDef<M & EnumOf<E>> & EnumOf<E>;
863
- enum<E, V extends Record<string, E>>(values: V): DateWithTimeZoneColumnTypeDef<M & EnumOf<V[keyof V]>> & EnumOf<V[keyof V]>;
864
825
  primary(): DateWithTimeZoneColumnTypeDef<M & IsPrimary> & IsPrimary;
865
826
  notNull(): DateWithTimeZoneColumnTypeDef<M & NotNull> & NotNull;
866
827
  notNullExceptInsert(): DateWithTimeZoneColumnTypeDef<M & NotNull & NotNullExceptInsert> & NotNull & NotNullExceptInsert;
@@ -1039,9 +1000,7 @@ type ExtractPrimaryKeyNames<T> =
1039
1000
  type RelationTarget<T> =
1040
1001
  T extends { __tableAlias: infer S } ? Extract<S, string> : string;
1041
1002
 
1042
- type EnumSchema<T> = T extends EnumOf<infer E> ? { ' enum': readonly E[] } : {};
1043
-
1044
- type ColumnToSchemaType<T> = (
1003
+ type ColumnToSchemaType<T> =
1045
1004
  T extends JsonOf<infer U>
1046
1005
  ? { ' type': 'json'; ' tsType': U }
1047
1006
  & (T extends NotNullExceptInsert ? { ' notNull': true; ' notNullExceptInsert': true }
@@ -1087,8 +1046,7 @@ type ColumnToSchemaType<T> = (
1087
1046
  & (T extends NotNullExceptInsert ? { ' notNull': true; ' notNullExceptInsert': true }
1088
1047
  : T extends NotNull ? { ' notNull': true }
1089
1048
  : {}) :
1090
- never
1091
- ) & EnumSchema<T>;
1049
+ never;
1092
1050
 
1093
1051
  export type MappedDbDef<T> = {
1094
1052
  map<V extends AllowedDbMap<V>>(
@@ -1101,4 +1059,4 @@ export type MappedDbDef<T> = {
1101
1059
  * Usage: type Schema = ReturnType<typeof db.toSchema>
1102
1060
  */
1103
1061
  toSchema: <U = T>() => SchemaFromMappedDb<U>;
1104
- } & T & DbConnectable<T>;
1062
+ } & T & DbConnectable<T>;
package/src/map2.d.ts CHANGED
@@ -10,7 +10,6 @@ export type ORMColumnType = 'string' | 'bigint' | 'uuid' | 'date' | 'numeric' |
10
10
  // Base column definition with space-prefixed required properties
11
11
  export type ORMColumnDefinition = {
12
12
  ' type': ORMColumnType;
13
- ' enum'?: readonly (string | number | boolean | Date)[] | Record<string, string | number | boolean | Date>;
14
13
  ' notNull'?: boolean;
15
14
  ' notNullExceptInsert'?: boolean;
16
15
  };
@@ -25,7 +24,7 @@ export type ORMJsonColumnDefinition<T = any> = {
25
24
 
26
25
  type NormalizeColumn<T> =
27
26
  T extends ORMColumnType
28
- ? { ' type': T; ' enum'?: readonly (string | number | boolean | Date)[] | Record<string, string | number | boolean | Date>; ' notNull'?: boolean; ' notNullExceptInsert'?: boolean }
27
+ ? { ' type': T; ' notNull'?: boolean; ' notNullExceptInsert'?: boolean }
29
28
  : T extends { ' type': ORMColumnType }
30
29
  ? { ' notNull'?: boolean; ' notNullExceptInsert'?: boolean } & T
31
30
  : T extends { ' type': 'json'; ' tsType': any }
@@ -42,8 +41,6 @@ type IsRequiredInsert<CT> =
42
41
  : false; // Otherwise, it's optional
43
42
 
44
43
  type ColumnTypeToTS<CT> =
45
- NormalizeColumn<CT> extends { ' enum': readonly (infer E)[] } ? E :
46
- NormalizeColumn<CT> extends { ' enum': Record<string, infer E> } ? E :
47
44
  NormalizeColumn<CT>[' type'] extends 'numeric' ? number :
48
45
  NormalizeColumn<CT>[' type'] extends 'boolean' ? boolean :
49
46
  NormalizeColumn<CT>[' type'] extends 'json'
@@ -677,7 +674,7 @@ type AggregateCustomSelectorProperties<M extends Record<string, TableDefinition<
677
674
 
678
675
  export type TableClient<M extends Record<string, TableDefinition<M>>, K extends keyof M> = {
679
676
  // Array methods - return arrays with array-level active record methods, but individual items are plain
680
- getMany<strategy extends FetchStrategy<M, K>>(strategy?: strategy): Promise<WithArrayActiveRecord<Array<DeepExpand<Selection<M, K, strategy>>>, M, K>>;
677
+ getMany<strategy extends FetchStrategy<M, K> = {}>(strategy: strategy): Promise<WithArrayActiveRecord<Array<DeepExpand<Selection<M, K, strategy>>>, M, K>>;
681
678
 
682
679
  // Aggregate methods - return plain objects (no active record methods)
683
680
  aggregate<strategy extends AggregateStrategy<M, K>>(strategy: strategy): Promise<Array<DeepExpand<AggregateCustomSelectorProperties<M, K, strategy>>>>;
@@ -54,37 +54,6 @@ function defineColumn(column, table) {
54
54
  return c;
55
55
  };
56
56
 
57
- c.enum = function(values) {
58
- let list = values;
59
- if (Array.isArray(values))
60
- list = values;
61
- else if (values && typeof values === 'object') {
62
- const keys = Object.keys(values);
63
- const nonNumericKeys = keys.filter((key) => !/^-?\d+$/.test(key));
64
- list = (nonNumericKeys.length ? nonNumericKeys : keys).map((key) => values[key]);
65
- }
66
- else
67
- throw new Error('enum values must be an array');
68
- const allowed = new Set(list);
69
- column.enum = list;
70
- function validate(value) {
71
- if (value === undefined || value === null)
72
- return;
73
- if (!allowed.has(value)) {
74
- const formatted = list.map((v) => JSON.stringify(v)).join(', ');
75
- throw new Error(`Column ${column.alias} must be one of: ${formatted}`);
76
- }
77
- }
78
- return c.validate(validate);
79
- };
80
-
81
- c.enum2 = function(...values) {
82
- const list = values.length === 1 && Array.isArray(values[0])
83
- ? values[0]
84
- : values;
85
- return c.enum(list);
86
- };
87
-
88
57
  c.default = function(value) {
89
58
  column.default = value;
90
59
  return c;
@@ -100,6 +69,7 @@ function defineColumn(column, table) {
100
69
  var oldAlias = column.alias;
101
70
  table._aliases.delete(oldAlias);
102
71
  table._aliases.add(alias);
72
+ delete table[oldAlias];
103
73
  table[alias] = column;
104
74
  column.alias = alias;
105
75
  return c;
@@ -190,4 +160,4 @@ function inspect(obj) {
190
160
  }
191
161
 
192
162
 
193
- module.exports = defineColumn;
163
+ module.exports = defineColumn;
@@ -9,7 +9,7 @@ function outputInsertedSql(context, table) {
9
9
 
10
10
  function formatColumn(column) {
11
11
  if (column.formatOut)
12
- return column.formatOut(context, 'INSERTED');
12
+ return `${column.formatOut(context, 'INSERTED')} AS [${column._dbName}]`;
13
13
  else
14
14
  return `INSERTED.[${column._dbName}]`;
15
15
  }
@@ -17,4 +17,4 @@ function outputInsertedSql(context, table) {
17
17
 
18
18
 
19
19
 
20
- module.exports = outputInsertedSql;
20
+ module.exports = outputInsertedSql;
package/deno.lock DELETED
@@ -1,76 +0,0 @@
1
- {
2
- "version": "5",
3
- "specifiers": {
4
- "jsr:@std/assert@*": "1.0.17",
5
- "jsr:@std/assert@^1.0.17": "1.0.17",
6
- "jsr:@std/internal@^1.0.12": "1.0.12",
7
- "jsr:@std/path@*": "1.1.4",
8
- "jsr:@std/testing@*": "1.0.17"
9
- },
10
- "jsr": {
11
- "@std/assert@1.0.17": {
12
- "integrity": "df5ebfffe77c03b3fa1401e11c762cc8f603d51021c56c4d15a8c7ab45e90dbe",
13
- "dependencies": [
14
- "jsr:@std/internal"
15
- ]
16
- },
17
- "@std/internal@1.0.12": {
18
- "integrity": "972a634fd5bc34b242024402972cd5143eac68d8dffaca5eaa4dba30ce17b027"
19
- },
20
- "@std/path@1.1.4": {
21
- "integrity": "1d2d43f39efb1b42f0b1882a25486647cb851481862dc7313390b2bb044314b5",
22
- "dependencies": [
23
- "jsr:@std/internal"
24
- ]
25
- },
26
- "@std/testing@1.0.17": {
27
- "integrity": "87bdc2700fa98249d48a17cd72413352d3d3680dcfbdb64947fd0982d6bbf681",
28
- "dependencies": [
29
- "jsr:@std/assert@^1.0.17",
30
- "jsr:@std/internal"
31
- ]
32
- }
33
- },
34
- "workspace": {
35
- "packageJson": {
36
- "dependencies": [
37
- "npm:@cloudflare/workers-types@^4.20241106.0",
38
- "npm:@electric-sql/pglite@0.3",
39
- "npm:@lroal/on-change@^4.0.2",
40
- "npm:@rollup/plugin-commonjs@^28.0.2",
41
- "npm:@rollup/plugin-json@^6.1.0",
42
- "npm:@rollup/plugin-node-resolve@13",
43
- "npm:@tediousjs/connection-string@~0.4.1",
44
- "npm:@types/express@^4.17.13",
45
- "npm:@types/oracledb@^6.0.4",
46
- "npm:@types/tedious@^4.0.14",
47
- "npm:@typescript-eslint/eslint-plugin@6",
48
- "npm:@typescript-eslint/parser@6",
49
- "npm:@vitest/coverage-v8@^3.2.4",
50
- "npm:ajv@^8.17.1",
51
- "npm:axios@^1.6.2",
52
- "npm:better-sqlite3@^11.8.1",
53
- "npm:cors@^2.8.5",
54
- "npm:eslint-plugin-jest@^27.1.7",
55
- "npm:eslint@^8.57.0",
56
- "npm:express@^4.18.2",
57
- "npm:fast-json-patch@^3.1.1",
58
- "npm:findup-sync@5",
59
- "npm:glob@^10.3.4 || ^11.0.2",
60
- "npm:module-definition@4 || 5 || * || 6",
61
- "npm:msnodesqlv8@^4.1.0",
62
- "npm:mysql2@^3.9.4",
63
- "npm:oracledb@^6.3.0",
64
- "npm:owasp-dependency-check@^0.0.21",
65
- "npm:pg-query-stream@^3.3.2",
66
- "npm:pg@^8.5.1",
67
- "npm:rfdc@^1.2.0",
68
- "npm:rollup@^2.52.7",
69
- "npm:tedious@19",
70
- "npm:typescript@^5.4.5",
71
- "npm:uuid@^8.3.2 || 9 || 10 || ^11.1.0",
72
- "npm:vitest@^3.2.4"
73
- ]
74
- }
75
- }
76
- }
package/other.db DELETED
Binary file