Skip to content

Commit 8c1e1e3

Browse files
Merge pull request #206 from developmentseed/feature/collection-base-class
add Collection Abstract BaseClass
2 parents 6832efa + a21862d commit 8c1e1e3

File tree

3 files changed

+63
-40
lines changed

3 files changed

+63
-40
lines changed

CHANGES.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,11 @@ Note: Minor version `0.X.0` update might break the API, It's recommended to pin
88

99
## [unreleased]
1010

11+
## [0.11.0] - TBD
12+
13+
* rename `tipg.collections.Collection -> tipg.collections.PgCollection`
14+
* add `tipg.collections.Collection` abstract base class
15+
1116
## [0.10.0] - 2025-02-20
1217

1318
* convert tile bbox into collection's CRS for `MVT` where selection (author @callsumzg, https://github.com/developmentseed/tipg/pull/205)

tipg/collections.py

Lines changed: 57 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
"""tipg.dbmodel: database events."""
22

3+
import abc
34
import datetime
45
import re
56
from functools import lru_cache
@@ -158,13 +159,12 @@ class Parameter(Column):
158159
default: Optional[str] = None
159160

160161

161-
class Collection(BaseModel):
162-
"""Model for DB Table and Function."""
162+
class Collection(BaseModel, metaclass=abc.ABCMeta):
163+
"""Collection Base Class."""
163164

164165
type: str
165166
id: str
166167
table: str
167-
dbschema: str = Field(alias="schema")
168168
title: Optional[str] = None
169169
description: Optional[str] = None
170170
table_columns: List[Column] = []
@@ -298,6 +298,57 @@ def get_column(self, property_name: str) -> Optional[Column]:
298298

299299
return None
300300

301+
@property
302+
def queryables(self) -> Dict:
303+
"""Return the queryables."""
304+
if self.geometry_columns:
305+
geoms = {
306+
col.name: {"$ref": geojson_schema.get(col.geometry_type.upper(), "")}
307+
for col in self.geometry_columns
308+
}
309+
else:
310+
geoms = {}
311+
312+
props = {
313+
col.name: {"name": col.name, "type": col.json_type}
314+
for col in self.properties
315+
if col.name not in geoms
316+
}
317+
318+
return {**geoms, **props}
319+
320+
@abc.abstractmethod
321+
async def features(self, *args, **kwargs) -> ItemList:
322+
"""Get Items."""
323+
...
324+
325+
@abc.abstractmethod
326+
async def get_tile(self, *args, **kwargs) -> bytes:
327+
"""Get MVT Tile."""
328+
...
329+
330+
331+
class CollectionList(TypedDict):
332+
"""Collections."""
333+
334+
collections: List[Collection]
335+
matched: Optional[int]
336+
next: Optional[int]
337+
prev: Optional[int]
338+
339+
340+
class Catalog(TypedDict):
341+
"""Internal Collection Catalog."""
342+
343+
collections: Dict[str, Collection]
344+
last_updated: datetime.datetime
345+
346+
347+
class PgCollection(Collection):
348+
"""Model for DB Table and Function."""
349+
350+
dbschema: str = Field(alias="schema")
351+
301352
def _select_no_geo(self, properties: Optional[List[str]], addid: bool = True):
302353
nocomma = False
303354
columns = self.columns(properties)
@@ -858,42 +909,9 @@ async def get_tile(
858909
debug_query(q, *p)
859910

860911
async with pool.acquire() as conn:
861-
return await conn.fetchval(q, *p)
862-
863-
@property
864-
def queryables(self) -> Dict:
865-
"""Return the queryables."""
866-
if self.geometry_columns:
867-
geoms = {
868-
col.name: {"$ref": geojson_schema.get(col.geometry_type.upper(), "")}
869-
for col in self.geometry_columns
870-
}
871-
else:
872-
geoms = {}
912+
tile = await conn.fetchval(q, *p)
873913

874-
props = {
875-
col.name: {"name": col.name, "type": col.json_type}
876-
for col in self.properties
877-
if col.name not in geoms
878-
}
879-
880-
return {**geoms, **props}
881-
882-
883-
class CollectionList(TypedDict):
884-
"""Collections."""
885-
886-
collections: List[Collection]
887-
matched: Optional[int]
888-
next: Optional[int]
889-
prev: Optional[int]
890-
891-
892-
class Catalog(TypedDict):
893-
"""Internal Collection Catalog."""
894-
895-
collections: Dict[str, Collection]
896-
last_updated: datetime.datetime
914+
return bytes(tile)
897915

898916

899917
async def get_collection_index( # noqa: C901
@@ -990,7 +1008,7 @@ async def get_collection_index( # noqa: C901
9901008
if table_conf.geomcol == c["name"] or geometry_column is None:
9911009
geometry_column = c
9921010

993-
catalog[table_id] = Collection(
1011+
catalog[table_id] = PgCollection(
9941012
type=table["entity"],
9951013
id=table_id,
9961014
table=table["name"],

tipg/factory.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1606,7 +1606,7 @@ async def collection_get_tile(
16061606
dt=datetime_column,
16071607
)
16081608

1609-
return Response(bytes(tile), media_type=MediaType.mvt.value)
1609+
return Response(tile, media_type=MediaType.mvt.value)
16101610

16111611
def _tilejson_routes(self):
16121612
############################################################################

0 commit comments

Comments
 (0)