@prisma-next/extension-postgis 0.0.1
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 +283 -0
- package/dist/codec-types-DODPC0GY.d.mts +59 -0
- package/dist/codec-types-DODPC0GY.d.mts.map +1 -0
- package/dist/codec-types.d.mts +2 -0
- package/dist/codec-types.mjs +1 -0
- package/dist/column-types.d.mts +26 -0
- package/dist/column-types.d.mts.map +1 -0
- package/dist/column-types.mjs +28 -0
- package/dist/column-types.mjs.map +1 -0
- package/dist/constants-dLvIWSgv.mjs +6 -0
- package/dist/constants-dLvIWSgv.mjs.map +1 -0
- package/dist/control.d.mts +7 -0
- package/dist/control.d.mts.map +1 -0
- package/dist/control.mjs +189 -0
- package/dist/control.mjs.map +1 -0
- package/dist/descriptor-meta-DUKzIH9c.mjs +516 -0
- package/dist/descriptor-meta-DUKzIH9c.mjs.map +1 -0
- package/dist/geojson-Cj4ldHQ0.d.mts +61 -0
- package/dist/geojson-Cj4ldHQ0.d.mts.map +1 -0
- package/dist/geojson.d.mts +2 -0
- package/dist/geojson.mjs +60 -0
- package/dist/geojson.mjs.map +1 -0
- package/dist/operation-types-C2s9tY0P.d.mts +123 -0
- package/dist/operation-types-C2s9tY0P.d.mts.map +1 -0
- package/dist/operation-types.d.mts +2 -0
- package/dist/operation-types.mjs +1 -0
- package/dist/pack.d.mts +75 -0
- package/dist/pack.d.mts.map +1 -0
- package/dist/pack.mjs +2 -0
- package/dist/runtime.d.mts +19 -0
- package/dist/runtime.d.mts.map +1 -0
- package/dist/runtime.mjs +22 -0
- package/dist/runtime.mjs.map +1 -0
- package/package.json +64 -0
- package/src/contract.d.ts +91 -0
- package/src/contract.json +40 -0
- package/src/contract.ts +61 -0
- package/src/core/authoring.ts +18 -0
- package/src/core/codecs.ts +193 -0
- package/src/core/constants.ts +3 -0
- package/src/core/contract-space-constants.ts +30 -0
- package/src/core/descriptor-meta.ts +186 -0
- package/src/core/ewkb.ts +284 -0
- package/src/core/geojson.ts +131 -0
- package/src/core/registry.ts +14 -0
- package/src/exports/codec-types.ts +7 -0
- package/src/exports/column-types.ts +38 -0
- package/src/exports/control.ts +101 -0
- package/src/exports/geojson.ts +19 -0
- package/src/exports/operation-types.ts +7 -0
- package/src/exports/pack.ts +1 -0
- package/src/exports/runtime.ts +34 -0
- package/src/types/codec-types.ts +16 -0
- package/src/types/operation-types.ts +81 -0
package/README.md
ADDED
|
@@ -0,0 +1,283 @@
|
|
|
1
|
+
# @prisma-next/extension-postgis
|
|
2
|
+
|
|
3
|
+
Geospatial data for Prisma Next on PostgreSQL, powered by [PostGIS](https://postgis.net).
|
|
4
|
+
|
|
5
|
+
Model points, lines, and polygons as first-class columns, query them with a type-safe DSL (`distance`, `containment`, `intersection`, `bounding-box`), and let the framework handle the wire format, SRID metadata, and `CREATE EXTENSION postgis` for you.
|
|
6
|
+
|
|
7
|
+
## What you get
|
|
8
|
+
|
|
9
|
+
- **`Geometry` column type** — store Points, LineStrings, Polygons, and their Multi-\* variants as a single `geometry` column. Optional SRID parameter (e.g. `Geometry(4326)` for WGS84 lng/lat) flows through to `contract.d.ts` and DDL.
|
|
10
|
+
- **GeoJSON-shaped runtime values** — read and write geometries as plain `{ type, coordinates }` objects. No PostGIS-specific client APIs to learn.
|
|
11
|
+
- **Seven query operations** on geometry columns: `distance`, `distanceSphere`, `dwithin`, `contains`, `within`, `intersects`, `intersectsBbox`.
|
|
12
|
+
- **Automatic `CREATE EXTENSION`** — the control descriptor declares `postgis` as a database dependency, so `prisma-next db init` ensures the server has it enabled before the first migration runs.
|
|
13
|
+
- **Both authoring paths** — works with PSL schemas and the TypeScript contract builder.
|
|
14
|
+
|
|
15
|
+
## Prerequisites
|
|
16
|
+
|
|
17
|
+
The PostGIS extension must be installable on your PostgreSQL server. Most managed providers (RDS, Cloud SQL, Supabase, Neon, …) include it; for local development the easiest route is the `postgis/postgis` Docker image, or a multi-arch fork like `imresamu/postgis` on Apple Silicon hosts.
|
|
18
|
+
|
|
19
|
+
## Installation
|
|
20
|
+
|
|
21
|
+
```bash
|
|
22
|
+
pnpm add @prisma-next/extension-postgis
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## Quick start
|
|
26
|
+
|
|
27
|
+
A complete five-step example — see [`examples/prisma-next-postgis-demo`](../../../examples/prisma-next-postgis-demo) for the full version with a seeded database, a Next.js UI, and e2e tests.
|
|
28
|
+
|
|
29
|
+
**1. Register the extension in `prisma-next.config.ts`:**
|
|
30
|
+
|
|
31
|
+
```typescript
|
|
32
|
+
import { defineConfig } from '@prisma-next/cli/config-types';
|
|
33
|
+
import postgresAdapter from '@prisma-next/adapter-postgres/control';
|
|
34
|
+
import sql from '@prisma-next/family-sql/control';
|
|
35
|
+
import postgres from '@prisma-next/target-postgres/control';
|
|
36
|
+
import postgis from '@prisma-next/extension-postgis/control';
|
|
37
|
+
|
|
38
|
+
export default defineConfig({
|
|
39
|
+
family: sql,
|
|
40
|
+
target: postgres,
|
|
41
|
+
adapter: postgresAdapter,
|
|
42
|
+
extensionPacks: [postgis],
|
|
43
|
+
});
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
**2. Declare a geometry column in your schema (PSL):**
|
|
47
|
+
|
|
48
|
+
```prisma
|
|
49
|
+
// use prisma-next
|
|
50
|
+
|
|
51
|
+
types {
|
|
52
|
+
WgsGeometry = postgis.Geometry(4326)
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
model Cafe {
|
|
56
|
+
id String @id @default(uuid())
|
|
57
|
+
name String
|
|
58
|
+
location WgsGeometry
|
|
59
|
+
@@map("cafe")
|
|
60
|
+
}
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
**3. Emit the contract and apply the migration:**
|
|
64
|
+
|
|
65
|
+
```bash
|
|
66
|
+
pnpm prisma-next contract emit # generates contract.json + contract.d.ts
|
|
67
|
+
pnpm prisma-next db init # CREATE EXTENSION postgis + CREATE TABLE
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
**4. Wire the extension into the runtime:**
|
|
71
|
+
|
|
72
|
+
```typescript
|
|
73
|
+
// src/prisma/db.ts
|
|
74
|
+
import postgres from '@prisma-next/postgres/runtime';
|
|
75
|
+
import postgis from '@prisma-next/extension-postgis/runtime';
|
|
76
|
+
import type { Contract } from './contract.d';
|
|
77
|
+
import contractJson from './contract.json' with { type: 'json' };
|
|
78
|
+
|
|
79
|
+
export const db = postgres<Contract>({
|
|
80
|
+
contractJson,
|
|
81
|
+
extensions: [postgis],
|
|
82
|
+
url: process.env['DATABASE_URL']!,
|
|
83
|
+
});
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
**5. Query:**
|
|
87
|
+
|
|
88
|
+
```typescript
|
|
89
|
+
import { point } from '@prisma-next/extension-postgis/geojson';
|
|
90
|
+
import { db } from './prisma/db';
|
|
91
|
+
|
|
92
|
+
const ferryBuilding = point(-122.3937, 37.7955, 4326);
|
|
93
|
+
|
|
94
|
+
// Five nearest cafes, with their distance in metres.
|
|
95
|
+
const closest = await db.runtime().execute(
|
|
96
|
+
db.sql.cafe
|
|
97
|
+
.select('id', 'name')
|
|
98
|
+
.select('meters', (f, fns) => fns.distanceSphere(f.location, ferryBuilding))
|
|
99
|
+
.orderBy((f, fns) => fns.distanceSphere(f.location, ferryBuilding), { direction: 'asc' })
|
|
100
|
+
.limit(5)
|
|
101
|
+
.build(),
|
|
102
|
+
);
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
## Authoring schemas
|
|
106
|
+
|
|
107
|
+
### PSL
|
|
108
|
+
|
|
109
|
+
`postgis.Geometry(srid)` declares an SRID-constrained `geometry` column. Aliasing it via a `types {}` block keeps the SRID in one place when you have several geometry fields.
|
|
110
|
+
|
|
111
|
+
```prisma
|
|
112
|
+
types {
|
|
113
|
+
WgsGeometry = postgis.Geometry(4326)
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
model Route {
|
|
117
|
+
id String @id @default(uuid())
|
|
118
|
+
name String
|
|
119
|
+
path WgsGeometry // LineStrings, polygons, points — all valid runtime values
|
|
120
|
+
@@map("route")
|
|
121
|
+
}
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
`Geometry` without an SRID (`postgis.Geometry()`) is also valid for schemas that mix SRIDs at the row level.
|
|
125
|
+
|
|
126
|
+
### TypeScript contract builder
|
|
127
|
+
|
|
128
|
+
```typescript
|
|
129
|
+
import { textColumn, varcharColumn } from '@prisma-next/adapter-postgres/column-types';
|
|
130
|
+
import sqlFamily from '@prisma-next/family-sql/pack';
|
|
131
|
+
import { defineContract, field, model } from '@prisma-next/sql-contract-ts/contract-builder';
|
|
132
|
+
import { geometry, geometryColumn } from '@prisma-next/extension-postgis/column-types';
|
|
133
|
+
import postgis from '@prisma-next/extension-postgis/pack';
|
|
134
|
+
import postgres from '@prisma-next/target-postgres/pack';
|
|
135
|
+
|
|
136
|
+
export const contract = defineContract({
|
|
137
|
+
family: sqlFamily,
|
|
138
|
+
target: postgres,
|
|
139
|
+
extensionPacks: { postgis },
|
|
140
|
+
models: {
|
|
141
|
+
Cafe: model('Cafe', {
|
|
142
|
+
fields: {
|
|
143
|
+
id: field.column(varcharColumn).id(),
|
|
144
|
+
name: field.column(textColumn),
|
|
145
|
+
location: field.column(geometry({ srid: 4326 })), // SRID-constrained
|
|
146
|
+
},
|
|
147
|
+
}).sql({ table: 'cafe' }),
|
|
148
|
+
},
|
|
149
|
+
});
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
`geometry({ srid })` is the dimensioned form (emits `geometry(Geometry, 4326)` in DDL). `geometryColumn` is the unconstrained form for schemas that need flexibility.
|
|
153
|
+
|
|
154
|
+
## Geometry values
|
|
155
|
+
|
|
156
|
+
Runtime geometries are GeoJSON-shaped objects: `{ type, coordinates, srid? }`. Build them with the constructors from `@prisma-next/extension-postgis/geojson` rather than constructing the literals by hand — the constructors keep the coordinate ordering straight (`[lng, lat]`) and attach SRID metadata in one place.
|
|
157
|
+
|
|
158
|
+
```typescript
|
|
159
|
+
import { bboxPolygon, point, polygon } from '@prisma-next/extension-postgis/geojson';
|
|
160
|
+
|
|
161
|
+
// Point — note: longitude first, latitude second.
|
|
162
|
+
const sightglass = point(-122.4106, 37.7765, 4326);
|
|
163
|
+
|
|
164
|
+
// Polygon — outer ring, optionally followed by holes. First point must equal last.
|
|
165
|
+
const soma = polygon(
|
|
166
|
+
[
|
|
167
|
+
[-122.418, 37.77],
|
|
168
|
+
[-122.4, 37.77],
|
|
169
|
+
[-122.4, 37.785],
|
|
170
|
+
[-122.418, 37.785],
|
|
171
|
+
[-122.418, 37.77],
|
|
172
|
+
],
|
|
173
|
+
4326,
|
|
174
|
+
);
|
|
175
|
+
|
|
176
|
+
// Axis-aligned bbox polygon — handy for "what's in this map viewport?" queries.
|
|
177
|
+
const downtownViewport = bboxPolygon([-122.425, 37.775, -122.4, 37.8], 4326);
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
For `LineString`, `MultiPoint`, `MultiLineString`, and `MultiPolygon`, build the object literally:
|
|
181
|
+
|
|
182
|
+
```typescript
|
|
183
|
+
const route: Geometry = {
|
|
184
|
+
type: 'LineString',
|
|
185
|
+
coordinates: [[-122.4194, 37.7749], [-122.4106, 37.7765]],
|
|
186
|
+
srid: 4326,
|
|
187
|
+
};
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
## Querying
|
|
191
|
+
|
|
192
|
+
All seven operations are available on any `geometry` column inside the SQL DSL's `.where()`, `.select()`, and `.orderBy()` callbacks via the `fns` argument:
|
|
193
|
+
|
|
194
|
+
```typescript
|
|
195
|
+
// Within radius — uses ST_DistanceSphere for sphere-accurate metres.
|
|
196
|
+
db.sql.cafe
|
|
197
|
+
.select('id', 'name')
|
|
198
|
+
.where((f, fns) => fns.distanceSphere(f.location, ferryBuilding) <= 2_000)
|
|
199
|
+
.build();
|
|
200
|
+
|
|
201
|
+
// Point-in-polygon — "which neighborhood contains this point?"
|
|
202
|
+
db.sql.neighborhood
|
|
203
|
+
.select('id', 'name')
|
|
204
|
+
.where((f, fns) => fns.contains(f.boundary, sightglass))
|
|
205
|
+
.build();
|
|
206
|
+
|
|
207
|
+
// Index-friendly bounding-box filter for map viewport queries.
|
|
208
|
+
db.sql.cafe
|
|
209
|
+
.select('id', 'name')
|
|
210
|
+
.where((f, fns) => fns.intersectsBbox(f.location, downtownViewport))
|
|
211
|
+
.build();
|
|
212
|
+
|
|
213
|
+
// Routes that cross an arbitrary geometry (e.g. a road-closure polygon).
|
|
214
|
+
db.sql.route
|
|
215
|
+
.select('id', 'name')
|
|
216
|
+
.where((f, fns) => fns.intersects(f.path, closurePolygon))
|
|
217
|
+
.build();
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
User-supplied geometries (the second argument to each operation) are bound as parameters, not interpolated. The codec encodes them as EWKT on the wire — see [Wire format](#wire-format) below.
|
|
221
|
+
|
|
222
|
+
## Operations reference
|
|
223
|
+
|
|
224
|
+
| Method | SQL | Returns | Use when |
|
|
225
|
+
| --- | --- | --- | --- |
|
|
226
|
+
| `distance(other)` | `ST_Distance(self, other)` | `float8` | Cartesian distance in the geometry's native units (degrees for SRID 4326). |
|
|
227
|
+
| `distanceSphere(other)` | `ST_DistanceSphere(self, other)` | `float8` | Sphere-accurate metres between two lng/lat geometries. |
|
|
228
|
+
| `dwithin(other, distance)` | `ST_DWithin(self, other, distance)` | `boolean` | Index-friendly "are these within X of each other?" — `distance` is in the geometry's native units. |
|
|
229
|
+
| `contains(other)` | `ST_Contains(self, other)` | `boolean` | Point-in-polygon and polygon-contains-polygon checks. |
|
|
230
|
+
| `within(other)` | `ST_Within(self, other)` | `boolean` | The inverse of `contains` — `A within B` ⇔ `B contains A`. |
|
|
231
|
+
| `intersects(other)` | `ST_Intersects(self, other)` | `boolean` | Any kind of overlap between two geometries. |
|
|
232
|
+
| `intersectsBbox(other)` | `self && other` | `boolean` | Cheap 2-D bounding-box overlap — fast viewport filtering. |
|
|
233
|
+
|
|
234
|
+
### Picking the right distance op
|
|
235
|
+
|
|
236
|
+
For SRID 4326 (WGS84) lng/lat data, `distance` returns **degrees**, which is rarely what you want. Use `distanceSphere` for human-friendly metres, or cast to `geography` upstream if you need ellipsoidal accuracy. `dwithin` interprets its `distance` argument in whatever units the inputs use — pair it with a projected SRS (or use `geography`) if you want metres directly.
|
|
237
|
+
|
|
238
|
+
## SRID and units
|
|
239
|
+
|
|
240
|
+
- Declare an SRID at the column level (`postgis.Geometry(4326)` / `geometry({ srid: 4326 })`) to constrain the column and have the runtime preserve the SRID through writes.
|
|
241
|
+
- `point(lng, lat, srid)`, `polygon(rings, srid)`, and `bboxPolygon(box, srid)` attach the SRID to the value; the codec emits it as `SRID=4326;…` on the wire.
|
|
242
|
+
- `distance` and `dwithin` are not unit-aware — they return whatever the SRS uses. If you need metres on WGS84 data, prefer `distanceSphere`.
|
|
243
|
+
|
|
244
|
+
## Wire format
|
|
245
|
+
|
|
246
|
+
- **JS → SQL**: values are emitted as EWKT (`SRID=4326;POINT(-122.39 37.79)`) and cast to `::geometry`. SRID is preserved through the `SRID=…;` prefix.
|
|
247
|
+
- **SQL → JS**: `node-postgres` returns `geometry` columns as hex-encoded EWKB. The codec parses Point, LineString, Polygon, MultiPoint, MultiLineString, and MultiPolygon. Z and M coordinates are **not** supported in this release; if a column carries them, decoding throws so the mismatch is visible rather than silent.
|
|
248
|
+
|
|
249
|
+
## Capabilities
|
|
250
|
+
|
|
251
|
+
The extension declares a single capability flag:
|
|
252
|
+
|
|
253
|
+
- `postgis.geometry` — gating signal for the `geometry` codec and the seven operations above.
|
|
254
|
+
|
|
255
|
+
Features that require it should declare a `requires: ['postgis.geometry']` constraint in their capability gate.
|
|
256
|
+
|
|
257
|
+
## Types
|
|
258
|
+
|
|
259
|
+
For consumers that need to reference the value or operation shapes directly:
|
|
260
|
+
|
|
261
|
+
```typescript
|
|
262
|
+
import type { CodecTypes, Geometry } from '@prisma-next/extension-postgis/codec-types';
|
|
263
|
+
import type { OperationTypes, QueryOperationTypes } from '@prisma-next/extension-postgis/operation-types';
|
|
264
|
+
|
|
265
|
+
// CodecTypes['pg/geometry@1']['output'] = Geometry (the GeoJSON union)
|
|
266
|
+
// Geometry<4326> is the SRID-branded form rendered into contract.d.ts.
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
## Demo
|
|
270
|
+
|
|
271
|
+
The end-to-end demo in [`examples/prisma-next-postgis-demo`](../../../examples/prisma-next-postgis-demo) walks through:
|
|
272
|
+
|
|
273
|
+
- Schema with three geometry shapes (`Point`, `LineString`, `Polygon`).
|
|
274
|
+
- Seeded data (five SF cafes, two delivery routes, three neighborhood polygons).
|
|
275
|
+
- One query file per operation — distance, radius, point-in-polygon, intersection, and bbox.
|
|
276
|
+
- A Next.js App Router UI that runs the queries as server components and renders the results on a Leaflet map.
|
|
277
|
+
- Vitest e2e tests that exercise the full pipeline against a local PostGIS container.
|
|
278
|
+
|
|
279
|
+
## References
|
|
280
|
+
|
|
281
|
+
- [PostGIS documentation](https://postgis.net/docs/)
|
|
282
|
+
- [Prisma Next Architecture Overview](../../../docs/Architecture%20Overview.md)
|
|
283
|
+
- [Extension Packs Guide](../../../docs/reference/Extension-Packs-Naming-and-Layout.md)
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { t as Geometry$1 } from "./geojson-Cj4ldHQ0.mjs";
|
|
2
|
+
import { AnyCodecDescriptor, CodecCallContext, CodecDescriptorImpl, CodecImpl, CodecInstanceContext } from "@prisma-next/framework-components/codec";
|
|
3
|
+
import { JsonValue } from "@prisma-next/contract/types";
|
|
4
|
+
import { ExtractCodecTypes } from "@prisma-next/sql-relational-core/ast";
|
|
5
|
+
import { StandardSchemaV1 } from "@standard-schema/spec";
|
|
6
|
+
|
|
7
|
+
//#region src/core/constants.d.ts
|
|
8
|
+
declare const POSTGIS_GEOMETRY_CODEC_ID: "pg/geometry@1";
|
|
9
|
+
//#endregion
|
|
10
|
+
//#region src/core/codecs.d.ts
|
|
11
|
+
type GeometryParams = {
|
|
12
|
+
readonly srid: number;
|
|
13
|
+
};
|
|
14
|
+
declare class PostgisGeometryCodec extends CodecImpl<typeof POSTGIS_GEOMETRY_CODEC_ID, readonly ['equality'], string, Geometry$1> {
|
|
15
|
+
constructor(descriptor: AnyCodecDescriptor);
|
|
16
|
+
encode(value: Geometry$1, _ctx: CodecCallContext): Promise<string>;
|
|
17
|
+
decode(wire: string, _ctx: CodecCallContext): Promise<Geometry$1>;
|
|
18
|
+
encodeJson(value: Geometry$1): JsonValue;
|
|
19
|
+
decodeJson(json: JsonValue): Geometry$1;
|
|
20
|
+
}
|
|
21
|
+
declare class PostgisGeometryDescriptor extends CodecDescriptorImpl<GeometryParams> {
|
|
22
|
+
readonly codecId: "pg/geometry@1";
|
|
23
|
+
readonly traits: readonly ["equality"];
|
|
24
|
+
readonly targetTypes: readonly ["geometry"];
|
|
25
|
+
readonly meta: {
|
|
26
|
+
readonly db: {
|
|
27
|
+
readonly sql: {
|
|
28
|
+
readonly postgres: {
|
|
29
|
+
readonly nativeType: "geometry";
|
|
30
|
+
};
|
|
31
|
+
};
|
|
32
|
+
};
|
|
33
|
+
};
|
|
34
|
+
readonly paramsSchema: StandardSchemaV1<GeometryParams>;
|
|
35
|
+
renderOutputType(params: GeometryParams): string;
|
|
36
|
+
/**
|
|
37
|
+
* The runtime calls `factory(undefined)(ctx)` to materialize a
|
|
38
|
+
* representative codec for parameterised descriptors that ship a
|
|
39
|
+
* no-params column variant (here, `geometryColumn` vs `geometry({ srid })`).
|
|
40
|
+
* The runtime cast widens `params` to `unknown`, so guarding with an
|
|
41
|
+
* optional read keeps the typed call site (`factory({ srid })`)
|
|
42
|
+
* strict while still producing an SRID-agnostic codec for
|
|
43
|
+
* representative use. Encode/decode for an unparameterised column
|
|
44
|
+
* runs through this representative; the wire format already carries
|
|
45
|
+
* SRID inside the EWKT/EWKB payload, so it's dimension-independent.
|
|
46
|
+
*/
|
|
47
|
+
factory(_params: GeometryParams): (ctx: CodecInstanceContext) => PostgisGeometryCodec;
|
|
48
|
+
}
|
|
49
|
+
declare const codecDescriptorMap: {
|
|
50
|
+
readonly geometry: PostgisGeometryDescriptor;
|
|
51
|
+
};
|
|
52
|
+
type CodecTypes$1 = ExtractCodecTypes<typeof codecDescriptorMap>;
|
|
53
|
+
//#endregion
|
|
54
|
+
//#region src/types/codec-types.d.ts
|
|
55
|
+
type Geometry<_Srid extends number = number> = Geometry$1;
|
|
56
|
+
type CodecTypes = CodecTypes$1;
|
|
57
|
+
//#endregion
|
|
58
|
+
export { Geometry as n, CodecTypes as t };
|
|
59
|
+
//# sourceMappingURL=codec-types-DODPC0GY.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"codec-types-DODPC0GY.d.mts","names":[],"sources":["../src/core/constants.ts","../src/core/codecs.ts","../src/types/codec-types.ts"],"mappings":";;;;;;;cAAa,yBAAA;;;KCmDR,cAAA;EAAA,SAA4B,IAAA;AAAA;AAAA,cA2CpB,oBAAA,SAA6B,SAAA,QACjC,yBAAA,iCAGP,UAAA;cAEY,UAAA,EAAY,kBAAA;EAIlB,MAAA,CAAO,KAAA,EAAO,UAAA,EAAU,IAAA,EAAM,gBAAA,GAAmB,OAAA;EAKjD,MAAA,CAAO,IAAA,UAAc,IAAA,EAAM,gBAAA,GAAmB,OAAA,CAAQ,UAAA;EAO5D,UAAA,CAAW,KAAA,EAAO,UAAA,GAAW,SAAA;EAK7B,UAAA,CAAW,IAAA,EAAM,SAAA,GAAY,UAAA;AAAA;AAAA,cAMlB,yBAAA,SAAkC,mBAAA,CAAoB,cAAA;EAAA,SAC/C,OAAA;EAAA,SACA,MAAA;EAAA,SACA,WAAA;EAAA,SACA,IAAA;IAAA;;;;;;;;WACA,YAAA,EAAc,gBAAA,CAAiB,cAAA;EACxC,gBAAA,CAAiB,MAAA,EAAQ,cAAA;EAZvB;;;;AAMb;;;;;;;EAsBW,OAAA,CAAQ,OAAA,EAAS,cAAA,IAAkB,GAAA,EAAK,oBAAA,KAAyB,oBAAA;AAAA;AAAA,cAqCtE,kBAAA;EAAA,mBAEI,yBAAA;AAAA;AAAA,KAEE,YAAA,GAAa,iBAAA,QAAyB,kBAAA;;;KCjLtC,QAAA,kCAA0C,UAAA;AAAA,KAE1C,UAAA,GAAa,YAAA"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { ColumnTypeDescriptor } from "@prisma-next/framework-components/codec";
|
|
2
|
+
|
|
3
|
+
//#region src/exports/column-types.d.ts
|
|
4
|
+
declare const geometryColumn: {
|
|
5
|
+
readonly codecId: "pg/geometry@1";
|
|
6
|
+
readonly nativeType: "geometry";
|
|
7
|
+
};
|
|
8
|
+
/**
|
|
9
|
+
* Build an SRID-constrained geometry column descriptor.
|
|
10
|
+
*
|
|
11
|
+
* @example
|
|
12
|
+
* .column('location', { type: geometry({ srid: 4326 }), nullable: false })
|
|
13
|
+
* // Produces: nativeType: 'geometry', typeParams: { srid: 4326 }
|
|
14
|
+
*
|
|
15
|
+
* @throws {RangeError} If `srid` is not a non-negative integer.
|
|
16
|
+
*/
|
|
17
|
+
declare function geometry<S extends number>(options: {
|
|
18
|
+
readonly srid: S;
|
|
19
|
+
}): ColumnTypeDescriptor & {
|
|
20
|
+
readonly typeParams: {
|
|
21
|
+
readonly srid: S;
|
|
22
|
+
};
|
|
23
|
+
};
|
|
24
|
+
//#endregion
|
|
25
|
+
export { geometry, geometryColumn };
|
|
26
|
+
//# sourceMappingURL=column-types.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"column-types.d.mts","names":[],"sources":["../src/exports/column-types.ts"],"mappings":";;;cAWa,cAAA;EAAA,SAG4B,OAAA;EAAA,SAAA,UAAA;AAAA;;;;;;;;;;iBAWzB,QAAA,kBAAA,CAA2B,OAAA;EAAA,SAChC,IAAA,EAAM,CAAA;AAAA,IACb,oBAAA;EAAA,SAAkC,UAAA;IAAA,SAAuB,IAAA,EAAM,CAAA;EAAA;AAAA"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { t as POSTGIS_GEOMETRY_CODEC_ID } from "./constants-dLvIWSgv.mjs";
|
|
2
|
+
//#region src/exports/column-types.ts
|
|
3
|
+
const geometryColumn = {
|
|
4
|
+
codecId: POSTGIS_GEOMETRY_CODEC_ID,
|
|
5
|
+
nativeType: "geometry"
|
|
6
|
+
};
|
|
7
|
+
/**
|
|
8
|
+
* Build an SRID-constrained geometry column descriptor.
|
|
9
|
+
*
|
|
10
|
+
* @example
|
|
11
|
+
* .column('location', { type: geometry({ srid: 4326 }), nullable: false })
|
|
12
|
+
* // Produces: nativeType: 'geometry', typeParams: { srid: 4326 }
|
|
13
|
+
*
|
|
14
|
+
* @throws {RangeError} If `srid` is not a non-negative integer.
|
|
15
|
+
*/
|
|
16
|
+
function geometry(options) {
|
|
17
|
+
const { srid } = options;
|
|
18
|
+
if (!Number.isInteger(srid) || srid < 0) throw new RangeError(`postgis: srid must be a non-negative integer, got ${srid}`);
|
|
19
|
+
return {
|
|
20
|
+
codecId: POSTGIS_GEOMETRY_CODEC_ID,
|
|
21
|
+
nativeType: "geometry",
|
|
22
|
+
typeParams: { srid }
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
//#endregion
|
|
26
|
+
export { geometry, geometryColumn };
|
|
27
|
+
|
|
28
|
+
//# sourceMappingURL=column-types.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"column-types.mjs","names":[],"sources":["../src/exports/column-types.ts"],"sourcesContent":["/**\n * Column type descriptors for the PostGIS extension.\n *\n * Use `geometryColumn` for an untyped `geometry` column, or\n * `geometry({ srid })` to declare an SRID-constrained column whose DDL\n * comes out as `geometry(Geometry, <srid>)`.\n */\n\nimport type { ColumnTypeDescriptor } from '@prisma-next/framework-components/codec';\nimport { POSTGIS_GEOMETRY_CODEC_ID } from '../core/constants';\n\nexport const geometryColumn = {\n codecId: POSTGIS_GEOMETRY_CODEC_ID,\n nativeType: 'geometry',\n} as const satisfies ColumnTypeDescriptor;\n\n/**\n * Build an SRID-constrained geometry column descriptor.\n *\n * @example\n * .column('location', { type: geometry({ srid: 4326 }), nullable: false })\n * // Produces: nativeType: 'geometry', typeParams: { srid: 4326 }\n *\n * @throws {RangeError} If `srid` is not a non-negative integer.\n */\nexport function geometry<S extends number>(options: {\n readonly srid: S;\n}): ColumnTypeDescriptor & { readonly typeParams: { readonly srid: S } } {\n const { srid } = options;\n if (!Number.isInteger(srid) || srid < 0) {\n throw new RangeError(`postgis: srid must be a non-negative integer, got ${srid}`);\n }\n return {\n codecId: POSTGIS_GEOMETRY_CODEC_ID,\n nativeType: 'geometry',\n typeParams: { srid },\n } as const;\n}\n"],"mappings":";;AAWA,MAAa,iBAAiB;CAC5B,SAAS;CACT,YAAY;CACb;;;;;;;;;;AAWD,SAAgB,SAA2B,SAE8B;CACvE,MAAM,EAAE,SAAS;CACjB,IAAI,CAAC,OAAO,UAAU,KAAK,IAAI,OAAO,GACpC,MAAM,IAAI,WAAW,qDAAqD,OAAO;CAEnF,OAAO;EACL,SAAS;EACT,YAAY;EACZ,YAAY,EAAE,MAAM;EACrB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants-dLvIWSgv.mjs","names":[],"sources":["../src/core/constants.ts"],"sourcesContent":["export const POSTGIS_GEOMETRY_CODEC_ID = 'pg/geometry@1' as const;\n\nexport const SRID_WGS84 = 4326 as const;\n"],"mappings":";AAAA,MAAa,4BAA4B"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { SqlControlExtensionDescriptor } from "@prisma-next/family-sql/control";
|
|
2
|
+
|
|
3
|
+
//#region src/exports/control.d.ts
|
|
4
|
+
declare const postgisExtensionDescriptor: SqlControlExtensionDescriptor<'postgres'>;
|
|
5
|
+
//#endregion
|
|
6
|
+
export { postgisExtensionDescriptor as default, postgisExtensionDescriptor };
|
|
7
|
+
//# sourceMappingURL=control.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"control.d.mts","names":[],"sources":["../src/exports/control.ts"],"mappings":";;;cA+EM,0BAAA,EAA4B,6BAAA"}
|
package/dist/control.mjs
ADDED
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
import { t as POSTGIS_GEOMETRY_CODEC_ID } from "./constants-dLvIWSgv.mjs";
|
|
2
|
+
import { n as postgisQueryOperations, t as postgisPackMeta } from "./descriptor-meta-DUKzIH9c.mjs";
|
|
3
|
+
import { contractSpaceFromJson } from "@prisma-next/migration-tools/spaces";
|
|
4
|
+
//#region migrations/20260601T0000_install_postgis_extension/migration.json
|
|
5
|
+
var migration_default = {
|
|
6
|
+
from: null,
|
|
7
|
+
to: "sha256:01622b3970e0ee2a582cc4c857bca7f6ed970f21b23f44e3f2781eea0be7d5eb",
|
|
8
|
+
labels: [],
|
|
9
|
+
providedInvariants: ["postgis:install-postgis-v1"],
|
|
10
|
+
createdAt: "2026-06-01T00:00:00.000Z",
|
|
11
|
+
fromContract: null,
|
|
12
|
+
toContract: {
|
|
13
|
+
"schemaVersion": "1",
|
|
14
|
+
"targetFamily": "sql",
|
|
15
|
+
"target": "postgres",
|
|
16
|
+
"profileHash": "sha256:1a8dbe044289f30a1de958fe800cc5a8378b285d2e126a8c44b58864bac2c18e",
|
|
17
|
+
"roots": {},
|
|
18
|
+
"models": {},
|
|
19
|
+
"storage": {
|
|
20
|
+
"storageHash": "sha256:01622b3970e0ee2a582cc4c857bca7f6ed970f21b23f44e3f2781eea0be7d5eb",
|
|
21
|
+
"tables": {},
|
|
22
|
+
"types": { "geometry": {
|
|
23
|
+
"codecId": "pg/geometry@1",
|
|
24
|
+
"nativeType": "geometry",
|
|
25
|
+
"typeParams": {}
|
|
26
|
+
} }
|
|
27
|
+
},
|
|
28
|
+
"capabilities": {
|
|
29
|
+
"postgres": {
|
|
30
|
+
"jsonAgg": true,
|
|
31
|
+
"lateral": true,
|
|
32
|
+
"limit": true,
|
|
33
|
+
"orderBy": true,
|
|
34
|
+
"returning": true
|
|
35
|
+
},
|
|
36
|
+
"sql": {
|
|
37
|
+
"defaultInInsert": true,
|
|
38
|
+
"enums": true,
|
|
39
|
+
"returning": true
|
|
40
|
+
}
|
|
41
|
+
},
|
|
42
|
+
"extensionPacks": {},
|
|
43
|
+
"meta": {},
|
|
44
|
+
"_generated": {
|
|
45
|
+
"warning": "⚠️ GENERATED FILE - DO NOT EDIT",
|
|
46
|
+
"message": "This file is automatically generated by \"prisma-next contract emit\".",
|
|
47
|
+
"regenerate": "To regenerate, run: prisma-next contract emit"
|
|
48
|
+
}
|
|
49
|
+
},
|
|
50
|
+
hints: {
|
|
51
|
+
"used": [],
|
|
52
|
+
"applied": [],
|
|
53
|
+
"plannerVersion": "2.0.0"
|
|
54
|
+
},
|
|
55
|
+
migrationHash: "sha256:87029e185c726572b12a1383e3687dd9e3b19261f70bf75bbb3b76f884608597"
|
|
56
|
+
};
|
|
57
|
+
//#endregion
|
|
58
|
+
//#region migrations/20260601T0000_install_postgis_extension/ops.json
|
|
59
|
+
var ops_default = [{
|
|
60
|
+
"id": "postgis.install-postgis-extension",
|
|
61
|
+
"label": "Enable extension \"postgis\"",
|
|
62
|
+
"operationClass": "additive",
|
|
63
|
+
"invariantId": "postgis:install-postgis-v1",
|
|
64
|
+
"target": {
|
|
65
|
+
"id": "postgres",
|
|
66
|
+
"details": {
|
|
67
|
+
"schema": "public",
|
|
68
|
+
"objectType": "dependency",
|
|
69
|
+
"name": "postgis"
|
|
70
|
+
}
|
|
71
|
+
},
|
|
72
|
+
"precheck": [{
|
|
73
|
+
"description": "verify extension \"postgis\" is not already enabled",
|
|
74
|
+
"sql": "SELECT NOT EXISTS (SELECT 1 FROM pg_extension WHERE extname = 'postgis')"
|
|
75
|
+
}],
|
|
76
|
+
"execute": [{
|
|
77
|
+
"description": "create extension \"postgis\"",
|
|
78
|
+
"sql": "CREATE EXTENSION IF NOT EXISTS postgis"
|
|
79
|
+
}],
|
|
80
|
+
"postcheck": [{
|
|
81
|
+
"description": "confirm extension \"postgis\" is enabled",
|
|
82
|
+
"sql": "SELECT EXISTS (SELECT 1 FROM pg_extension WHERE extname = 'postgis')"
|
|
83
|
+
}]
|
|
84
|
+
}];
|
|
85
|
+
//#endregion
|
|
86
|
+
//#region migrations/refs/head.json
|
|
87
|
+
var head_default = {
|
|
88
|
+
hash: "sha256:01622b3970e0ee2a582cc4c857bca7f6ed970f21b23f44e3f2781eea0be7d5eb",
|
|
89
|
+
invariants: ["postgis:install-postgis-v1"]
|
|
90
|
+
};
|
|
91
|
+
//#endregion
|
|
92
|
+
//#region src/contract.json
|
|
93
|
+
var contract_default = {
|
|
94
|
+
schemaVersion: "1",
|
|
95
|
+
targetFamily: "sql",
|
|
96
|
+
target: "postgres",
|
|
97
|
+
profileHash: "sha256:1a8dbe044289f30a1de958fe800cc5a8378b285d2e126a8c44b58864bac2c18e",
|
|
98
|
+
roots: {},
|
|
99
|
+
models: {},
|
|
100
|
+
storage: {
|
|
101
|
+
"storageHash": "sha256:01622b3970e0ee2a582cc4c857bca7f6ed970f21b23f44e3f2781eea0be7d5eb",
|
|
102
|
+
"tables": {},
|
|
103
|
+
"types": { "geometry": {
|
|
104
|
+
"codecId": "pg/geometry@1",
|
|
105
|
+
"nativeType": "geometry",
|
|
106
|
+
"typeParams": {}
|
|
107
|
+
} }
|
|
108
|
+
},
|
|
109
|
+
capabilities: {
|
|
110
|
+
"postgres": {
|
|
111
|
+
"jsonAgg": true,
|
|
112
|
+
"lateral": true,
|
|
113
|
+
"limit": true,
|
|
114
|
+
"orderBy": true,
|
|
115
|
+
"returning": true
|
|
116
|
+
},
|
|
117
|
+
"sql": {
|
|
118
|
+
"defaultInInsert": true,
|
|
119
|
+
"enums": true,
|
|
120
|
+
"returning": true
|
|
121
|
+
}
|
|
122
|
+
},
|
|
123
|
+
extensionPacks: {},
|
|
124
|
+
meta: {},
|
|
125
|
+
_generated: {
|
|
126
|
+
"warning": "⚠️ GENERATED FILE - DO NOT EDIT",
|
|
127
|
+
"message": "This file is automatically generated by \"prisma-next contract emit\".",
|
|
128
|
+
"regenerate": "To regenerate, run: prisma-next contract emit"
|
|
129
|
+
}
|
|
130
|
+
};
|
|
131
|
+
//#endregion
|
|
132
|
+
//#region src/core/contract-space-constants.ts
|
|
133
|
+
/**
|
|
134
|
+
* Static names and identifiers used across postgis's contract space.
|
|
135
|
+
*
|
|
136
|
+
* Centralised here so the contract IR (`./contract`), the baseline
|
|
137
|
+
* migration ops (`./migrations`), the head ref, and the descriptor
|
|
138
|
+
* (`../exports/control`) all reference the same values without typos.
|
|
139
|
+
*
|
|
140
|
+
* The space identifier `'postgis'` is what the framework writes to
|
|
141
|
+
* `migrations/` in the user's repo and what the marker table's
|
|
142
|
+
* `space` column carries for postgis-owned rows.
|
|
143
|
+
*
|
|
144
|
+
* The `postgis:*` invariantId namespace is locked here — once
|
|
145
|
+
* published, an invariantId is immutable so downstream consumers can
|
|
146
|
+
* reference it by literal string match.
|
|
147
|
+
*/
|
|
148
|
+
const POSTGIS_SPACE_ID = "postgis";
|
|
149
|
+
const POSTGIS_BASELINE_MIGRATION_NAME = "20260601T0000_install_postgis_extension";
|
|
150
|
+
//#endregion
|
|
151
|
+
//#region src/exports/control.ts
|
|
152
|
+
const geometryControlPlaneHooks = {
|
|
153
|
+
expandNativeType: ({ nativeType, typeParams }) => {
|
|
154
|
+
const srid = typeParams?.["srid"];
|
|
155
|
+
if (typeof srid === "number" && Number.isInteger(srid) && srid >= 0) return `${nativeType}(Geometry,${srid})`;
|
|
156
|
+
return nativeType;
|
|
157
|
+
},
|
|
158
|
+
resolveIdentityValue: () => null
|
|
159
|
+
};
|
|
160
|
+
const postgisContractSpace = contractSpaceFromJson({
|
|
161
|
+
contractJson: contract_default,
|
|
162
|
+
migrations: [{
|
|
163
|
+
dirName: POSTGIS_BASELINE_MIGRATION_NAME,
|
|
164
|
+
metadata: migration_default,
|
|
165
|
+
ops: ops_default
|
|
166
|
+
}],
|
|
167
|
+
headRef: head_default
|
|
168
|
+
});
|
|
169
|
+
const postgisExtensionDescriptor = {
|
|
170
|
+
...postgisPackMeta,
|
|
171
|
+
id: POSTGIS_SPACE_ID,
|
|
172
|
+
contractSpace: postgisContractSpace,
|
|
173
|
+
types: {
|
|
174
|
+
...postgisPackMeta.types,
|
|
175
|
+
codecTypes: {
|
|
176
|
+
...postgisPackMeta.types.codecTypes,
|
|
177
|
+
controlPlaneHooks: { [POSTGIS_GEOMETRY_CODEC_ID]: geometryControlPlaneHooks }
|
|
178
|
+
}
|
|
179
|
+
},
|
|
180
|
+
queryOperations: () => postgisQueryOperations(),
|
|
181
|
+
create: () => ({
|
|
182
|
+
familyId: "sql",
|
|
183
|
+
targetId: "postgres"
|
|
184
|
+
})
|
|
185
|
+
};
|
|
186
|
+
//#endregion
|
|
187
|
+
export { postgisExtensionDescriptor as default, postgisExtensionDescriptor };
|
|
188
|
+
|
|
189
|
+
//# sourceMappingURL=control.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"control.mjs","names":["baselineMetadata","baselineOps"],"sources":["../migrations/20260601T0000_install_postgis_extension/migration.json","../migrations/20260601T0000_install_postgis_extension/ops.json","../migrations/refs/head.json","../src/contract.json","../src/core/contract-space-constants.ts","../src/exports/control.ts"],"sourcesContent":["","","","","/**\n * Static names and identifiers used across postgis's contract space.\n *\n * Centralised here so the contract IR (`./contract`), the baseline\n * migration ops (`./migrations`), the head ref, and the descriptor\n * (`../exports/control`) all reference the same values without typos.\n *\n * The space identifier `'postgis'` is what the framework writes to\n * `migrations/` in the user's repo and what the marker table's\n * `space` column carries for postgis-owned rows.\n *\n * The `postgis:*` invariantId namespace is locked here — once\n * published, an invariantId is immutable so downstream consumers can\n * reference it by literal string match.\n */\n\nexport const POSTGIS_SPACE_ID = 'postgis' as const;\n\nexport const POSTGIS_NATIVE_TYPE = 'geometry' as const;\n\nexport const POSTGIS_BASELINE_MIGRATION_NAME = '20260601T0000_install_postgis_extension' as const;\n\n/**\n * `postgis:*` invariantIds emitted by the baseline migration. Each id,\n * once published, is immutable: downstream consumers (other extensions,\n * the marker table) reference them by literal string match.\n */\nexport const POSTGIS_INVARIANTS = {\n installPostgis: 'postgis:install-postgis-v1',\n} as const;\n","/**\n * Control-plane descriptor for the postgis extension.\n *\n * **Contract-space package layout.** The extension's contract\n * + migrations are emitted by the same pipeline application authors use:\n *\n * `prisma-next contract emit` → `<package>/src/contract.{json,d.ts}`\n * `prisma-next migration plan` → `<package>/migrations/<dir>/...`\n *\n * The descriptor wires those JSON artefacts via JSON-import declarations\n * so they flow through the consuming application's module resolver\n * without filesystem assumptions, and synthesises the canonical\n * `MigrationPackage` shape for the framework's runner / verifier to\n * consume.\n *\n * Wired surfaces:\n *\n * - `contractSpace.{contractJson,migrations,headRef}` — sourced from\n * the on-disk artefacts emitted by `build:contract-space`.\n * - `types.codecTypes.controlPlaneHooks[POSTGIS_GEOMETRY_CODEC_ID]` —\n * codec control hooks (`expandNativeType`, `resolveIdentityValue`)\n * the SQL planner extracts via `extractCodecControlHooks` and uses\n * to render `geometry(Geometry,${srid})` column types.\n *\n * @see docs/architecture docs/adrs/ADR 212 - Contract spaces.md\n * (contract-space package layout convention).\n */\n\nimport type { Contract } from '@prisma-next/contract/types';\nimport type {\n CodecControlHooks,\n SqlControlExtensionDescriptor,\n} from '@prisma-next/family-sql/control';\nimport { contractSpaceFromJson } from '@prisma-next/migration-tools/spaces';\nimport type { SqlStorage } from '@prisma-next/sql-contract/types';\nimport baselineMetadata from '../../migrations/20260601T0000_install_postgis_extension/migration.json' with {\n type: 'json',\n};\nimport baselineOps from '../../migrations/20260601T0000_install_postgis_extension/ops.json' with {\n type: 'json',\n};\nimport headRef from '../../migrations/refs/head.json' with { type: 'json' };\nimport contractJson from '../contract.json' with { type: 'json' };\nimport { POSTGIS_GEOMETRY_CODEC_ID } from '../core/constants';\nimport {\n POSTGIS_BASELINE_MIGRATION_NAME,\n POSTGIS_SPACE_ID,\n} from '../core/contract-space-constants';\nimport { postgisPackMeta, postgisQueryOperations } from '../core/descriptor-meta';\n\nconst geometryControlPlaneHooks: CodecControlHooks = {\n expandNativeType: ({ nativeType, typeParams }) => {\n const srid = typeParams?.['srid'];\n if (typeof srid === 'number' && Number.isInteger(srid) && srid >= 0) {\n // PostGIS prints the type-modifier list without a space — match\n // it here so the verifier doesn't see `geometry(Geometry, 4326)`\n // (DDL) mismatch `geometry(Geometry,4326)` (introspected).\n return `${nativeType}(Geometry,${srid})`;\n }\n return nativeType;\n },\n // PostGIS has no canonical \"identity\" geometry; backfilling a\n // non-null column requires the user to supply a valid value, so we\n // don't synthesise one here.\n resolveIdentityValue: () => null,\n};\n\nconst postgisContractSpace = contractSpaceFromJson<Contract<SqlStorage>>({\n contractJson,\n migrations: [\n {\n dirName: POSTGIS_BASELINE_MIGRATION_NAME,\n metadata: baselineMetadata,\n ops: baselineOps,\n },\n ],\n headRef,\n});\n\nconst postgisExtensionDescriptor: SqlControlExtensionDescriptor<'postgres'> = {\n ...postgisPackMeta,\n id: POSTGIS_SPACE_ID,\n contractSpace: postgisContractSpace,\n types: {\n ...postgisPackMeta.types,\n codecTypes: {\n ...postgisPackMeta.types.codecTypes,\n controlPlaneHooks: {\n [POSTGIS_GEOMETRY_CODEC_ID]: geometryControlPlaneHooks,\n },\n },\n },\n queryOperations: () => postgisQueryOperations(),\n create: () => ({\n familyId: 'sql' as const,\n targetId: 'postgres' as const,\n }),\n};\n\nexport { postgisExtensionDescriptor };\nexport default postgisExtensionDescriptor;\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AIgBA,MAAa,mBAAmB;AAIhC,MAAa,kCAAkC;;;AC8B/C,MAAM,4BAA+C;CACnD,mBAAmB,EAAE,YAAY,iBAAiB;EAChD,MAAM,OAAO,aAAa;EAC1B,IAAI,OAAO,SAAS,YAAY,OAAO,UAAU,KAAK,IAAI,QAAQ,GAIhE,OAAO,GAAG,WAAW,YAAY,KAAK;EAExC,OAAO;;CAKT,4BAA4B;CAC7B;AAED,MAAM,uBAAuB,sBAA4C;CACvE,cAAA;CACA,YAAY,CACV;EACE,SAAS;EACT,UAAUA;EACV,KAAKC;EACN,CACF;CACD,SAAA;CACD,CAAC;AAEF,MAAM,6BAAwE;CAC5E,GAAG;CACH,IAAI;CACJ,eAAe;CACf,OAAO;EACL,GAAG,gBAAgB;EACnB,YAAY;GACV,GAAG,gBAAgB,MAAM;GACzB,mBAAmB,GAChB,4BAA4B,2BAC9B;GACF;EACF;CACD,uBAAuB,wBAAwB;CAC/C,eAAe;EACb,UAAU;EACV,UAAU;EACX;CACF"}
|