Skip to content

Give the circular buffer, network point, pose and rigid geometry temporal types their classes - #88

Merged
estebanzimanyi merged 1 commit into
masterfrom
feat/extended-temporal-types
Oct 31, 2026
Merged

estebanzimanyi merged 1 commit into
masterfrom
feat/extended-temporal-types

Conversation

@estebanzimanyi

@estebanzimanyi estebanzimanyi commented May 18, 2026 •

Copy link
Copy Markdown
Member

PyMEOS binds the four temporal types of the MEOS 1.4 families as it binds
the temporal points: TCbuffer, TNpoint, TPose and TRgeometry, each with
its instant, sequence and sequence set classes, and the base values
Cbuffer, Npoint, Nsegment and Pose with the sets CbufferSet, NpointSet
and PoseSet. The value of a temporal rigid geometry is a shapely
geometry, its reference geometry placed by the pose. The factory and the
package exports name every class.

Each temporal class implements the methods the Temporal base declares
through the typed MEOS functions of its family: from_base_time and
from_base_temporal, from_mfjson, start_value, end_value, value_set and
value_at_timestamp. TRgeometry also carries the segments, the deletion
of a time value, the restriction before or after a timestamp, to_instant
and the sequence accessors of its own trgeometry functions. The pose
accessors are yaw and quaternion, the MEOS 1.4 names.

TCbuffer and TRgeometry carry the ever and always spatial relationships
MEOS defines for them, with the names TCbuffer and TPoint use:
is_ever_contains, is_ever_covers, is_ever_disjoint,
is_ever_within_distance, ever_intersects and ever_touches with their
always twins, each against the geometries, base values and temporal
values of the same type MEOS defines it for. For a geometry or a base
value containing or covering self they carry is_ever_contained_in and
is_ever_coveredby with their always twins; coveredby is the covers
relationship with the container first, named and computed as PostGIS's
coveredby and geography_coveredby. TCbuffer carries the temporal
relationships as well. MEOS defines no spatial relationship for the
network point or the pose.

A base value is built from its text or by keyword, as
Npoint(route=1, position=0.5), Cbuffer(point=..., radius=...) and
Pose(point=..., theta=...). Its WKB output is the bytes PyMEOS-CFFI
returns, its WKB input and a set's elements are a bytes object and a
Python list whose length is their own, and a network point set takes
each element as the Npoint struct npointset_make reads. The text of a
value is its asText, as in MobilityDB: str of a pose, a circular buffer,
a network point and their sets is pose_as_text, cbuffer_as_text,
npoint_as_text and spatialset_as_text, Pose(POINT(1 1),0.5), the sets
gaining as_text, as_wkt and as_ewkt as GeoSet has them, and a temporal
rigid geometry reads its text through trgeometry_in and writes it
through trgeometry_as_text and trgeometry_as_ewkt, the reference
geometry before the poses; repr of a temporal value is the class name
around its text.

The tests cover every class: construction from text, from the base
values and from MF-JSON, the outputs, the accessors, the comparisons and
the transformations of each family.

@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch 2 times, most recently from 4757f90 to 98f5065 Compare May 18, 2026 21:28
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from 98f5065 to a5a558f Compare May 19, 2026 07:24
@estebanzimanyi
estebanzimanyi force-pushed the bump/meos-1.4 branch 2 times, most recently from 6c7b804 to ecca684 Compare May 23, 2026 07:17
estebanzimanyi added a commit to estebanzimanyi/PyMEOS that referenced this pull request Jun 25, 2026
master predates the meos-idl.json OO codegen, which lives in the open stack.
Add tools/pin/compose-order.txt (the canonical fold manifest with the
disposition of every open PR; MobilityDB#95 is the verified OO-codegen frontier
containing MobilityDB#88/MobilityDB#89 and the family-switch stack) and GENERATION.md (the
per-binding generator policy: PyMEOS is two layers — PyMEOS-CFFI low-level +
the PyMEOS OO layer generated by tools/oo_codegen/codegen.py; the regular
families switch to generated mixins generate-then-retire).
@estebanzimanyi
estebanzimanyi force-pushed the bump/meos-1.4 branch 4 times, most recently from 011bea4 to 39f5fdd Compare October 22, 2026 11:46
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from a5a558f to 201a0c1 Compare October 22, 2026 11:54
estebanzimanyi added a commit that referenced this pull request Oct 22, 2026
Promotes the meos-idl.json-driven OO codegen from Draft preview to a
wired-in solution for the TCbuffer vertical slice.

- Generator (tools/oo_codegen/codegen.py): adds a behaviourally-faithful
  emitter (--mixin) that reproduces the hand-written isinstance ladder,
  argument transforms, result post-processing and super()/raise fallback
  exactly; only modelled families are wired (one family per PR). The
  Draft _preview/ path and the #89 coverage gate are unchanged.
- pymeos/main/_generated/tcbuffer_methods.py: generated TCbufferRegularMixin
  (30 regular methods: comparison, spatial relationship, distance,
  restriction), each dispatching to the exact pymeos_cffi backing the
  hand-written method used.
- pymeos/main/tcbuffer.py: inherits TCbufferRegularMixin; the 30
  now-generated regular methods are removed (never_* and the irregular
  hand-written core are kept).
- Provenance: regen-from-meos-api.sh + README document that the catalog
  is byte-schema-identical to MEOS-API run.py output and the generator
  runs unchanged on it.

Behavioural equivalence is proven by the existing suite: the full
tests/main/tcbuffer_test.py is byte-identical before and after the
switch -- 26 passed, 1 failed, where the single failure is a pre-existing
unrelated pymeos_cffi cbuffer_as_hexwkb out-parameter bug in the base
Cbuffer class (not temporal, not codegen). Static check: 30/30 generated
methods are backing-and-fallback identical to the hand-written oracle.

Stacked on #89; relies on #88's TCbuffer being instantiable.
estebanzimanyi added a commit that referenced this pull request Oct 22, 2026
Fans the meos-idl.json faithful codegen out to TPose (second family
after TCbuffer #90).

- codegen.py: add the `pose` FAMILY_MODEL entry (+ the `point` arg
  token — tpose distance spells its geometry overload
  `tdistance_tpose_point`). The Draft _preview path and #89 coverage
  gate are unchanged.
- pymeos/main/_generated/tpose_methods.py: generated TPoseRegularMixin
  (12 regular methods — comparison, temporal comparison, restriction,
  distance; pose has no spatial-relationship API). Each dispatches to the
  exact pymeos_cffi backing the hand-written method used.
- pymeos/main/tpose.py: inherits TPoseRegularMixin; the 12 now-generated
  regular methods removed. never_*/the irregular core and the
  already-real MEOS-backed value accessors (start_value/end_value/
  value_set/value_at_timestamp/value_n) are kept. Adds documented
  NotImplementedError stubs for from_base_time (MobilityDB#1084) and
  from_mfjson (MobilityDB#1085) so TPose/Inst/Seq/SeqSet are concrete.

Proof: tests/main/tpose_test.py is byte-identical hand-written vs wired
(A/B with the 2 stubs held constant) — 31 passed, 4 failed in BOTH; the
4 failures are pre-existing #88 defects OUTSIDE the codegen-switch domain
(TestTPoseOutputs/Pose test_str, TestTPoseAccessors test_value_at_timestamp,
TestPose test_from_as_hexwkb — hand-written accessors / base Pose, not
the regular families). Static check: 12/12 generated methods are
backing-and-fallback identical to the hand-written oracle. All
switch-domain tests (comparison/distance/restriction) pass. Stacked on
estebanzimanyi added a commit that referenced this pull request Oct 22, 2026
Third family in the codegen-switch fan-out (after TCbuffer #90, TPose

- codegen.py: add the `npoint` FAMILY_MODEL (+ `npointset` and `point`
  arg tokens; tnpoint distance spells `tdistance_tnpoint_point`). Make
  shortest_line's precision per-family (npoint: `precision: int = 15`;
  tcbuffer/tpose hardcode 10 with no param and omit the key, so #90/#91
  regenerate byte-identical -- verified). Draft _preview path and #89
  gate untouched.
- pymeos/main/_generated/tnpoint_methods.py: generated TNpointRegularMixin
  (12 regular methods -- comparison, temporal comparison, restriction,
  distance; npoint has no spatial-relationship API). Static check: 12/12
  backing-and-fallback identical to the hand-written oracle.
- pymeos/main/tnpoint.py: inherits the mixin; 12 now-generated regular
  methods removed; never_*/irregular core kept. Adds documented
  NotImplementedError stubs (value accessors -> MobilityDB#1082,
  from_base_time -> #1084, from_mfjson -> #1086) so TNpoint*/Inst/Seq/
  SeqSet are concrete.
- pymeos/collections/npoint/npointset.py: NpointSet shipped abstract in
  #88 (pre-existing base-collection defect, unrelated to the switch);
  add the 5 missing Set ops as thin super() delegations to the generic
  base Set (the established GeoSet.contains pattern), making NpointSet
  concrete.

Proof: tests/main/tnpoint_test.py is byte-identical hand-written vs
wired (A/B, stubs+NpointSet-fix held constant) -- both error IDENTICALLY
at the same pre-existing point (`tnpoint_test.py:211` TestNpointSet,
MeosTextInputError 'Missing delimiter'), so the switch delta is provably
zero. That collection error is a pre-existing #88/MEOS npointset
test-fixture/parser issue OUTSIDE the codegen-switch domain (base
NpointSet, not the temporal regular families), unrelated to and
unaffected by this change -- a separate follow-up. Static 12/12
identical is the positive proof. Stacked on #91.
estebanzimanyi added a commit that referenced this pull request Oct 22, 2026
Fourth family in the codegen-switch fan-out (after TCbuffer #90, TPose

- codegen.py: add the `rgeo` FAMILY_MODEL (temporal_token `trgeo`; geo
  token uses `geometry_to_gserialized($o)` -- single-arg, unlike the
  geo_to_gserialized(g, False) of the other spatial families; tokens
  geo/trgeo/tpoint/stbox) + `tpoint`/`trgeo` to _ORDER. Additive:
  #90/#91/#92 mixins regenerate byte-identical (regression-guarded).
- pymeos/main/_generated/trgeometry_methods.py: generated
  TRgeometryRegularMixin -- 10 methods (comparison, temporal comparison,
  distance/nad/nai/shortest_line). Static: 10/10 backing-and-fallback
  identical to the hand-written oracle.
- pymeos/main/trgeometry.py: inherits the mixin; the 10 now-generated
  regular methods removed. at/minus stay hand-written (rgeo restriction
  is the irregular `trgeo_restrict_<timetype>`+direction-bool pattern,
  not `trgeometry_at_*`, so the generator never collects them);
  never_*/irregular core kept. Adds documented NotImplementedError stubs
  for from_base_time and from_mfjson (pending upstream MEOS) so
  TRgeometry/Inst/Seq/SeqSet are concrete.

Proof: tests/main/trgeometry_test.py is byte-identical hand-written vs
wired (A/B, 2 stubs constant) -- both 6 failed / 23 passed, the SAME 6
pre-existing #88 hand-written-core defects OUTSIDE the switch domain
(TestTRgeometryConstructors/Accessors/GapMethods -- constructors,
accessors, known-gap methods; not comparison/distance), unrelated to and
unaffected by this change. Every switch-domain test passes. Static 10/10
identical is the positive proof. Stacked on #92.
@estebanzimanyi
estebanzimanyi force-pushed the bump/meos-1.4 branch 3 times, most recently from 3429b49 to d600b5c Compare October 22, 2026 21:35
@estebanzimanyi
estebanzimanyi force-pushed the bump/meos-1.4 branch 3 times, most recently from 62e6033 to 54316b4 Compare October 31, 2026 11:02
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from 201a0c1 to 3b845a9 Compare October 31, 2026 12:20
@estebanzimanyi
estebanzimanyi changed the base branch from bump/meos-1.4 to master October 31, 2026 12:22
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from 3b845a9 to a6a6569 Compare October 31, 2026 12:24
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from a6a6569 to fc53ce2 Compare October 31, 2026 15:00
@estebanzimanyi estebanzimanyi changed the title feat: OO support for the cbuffer, npoint, pose and rgeometry temporal types Give the circular buffer, network point, pose and rigid geometry temporal types their classes Oct 31, 2026
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from fc53ce2 to e3597a1 Compare October 31, 2026 15:12
…oral types their classes

PyMEOS binds the four temporal types of the MEOS 1.4 families as it binds
the temporal points: TCbuffer, TNpoint, TPose and TRgeometry, each with
its instant, sequence and sequence set classes, and the base values
Cbuffer, Npoint, Nsegment and Pose with the sets CbufferSet, NpointSet
and PoseSet. The value of a temporal rigid geometry is a shapely
geometry, its reference geometry placed by the pose. The factory and the
package exports name every class.

Each temporal class implements the methods the Temporal base declares
through the typed MEOS functions of its family: from_base_time and
from_base_temporal, from_mfjson, start_value, end_value, value_set and
value_at_timestamp. TRgeometry also carries the segments, the deletion
of a time value, the restriction before or after a timestamp, to_instant
and the sequence accessors of its own trgeometry functions. The pose
accessors are yaw and quaternion, the MEOS 1.4 names.

TCbuffer and TRgeometry carry the ever and always spatial relationships
MEOS defines for them, with the names TCbuffer and TPoint use:
is_ever_contains, is_ever_covers, is_ever_disjoint,
is_ever_within_distance, ever_intersects and ever_touches with their
always twins, each against the geometries, base values and temporal
values of the same type MEOS defines it for. For a geometry or a base
value containing or covering self they carry is_ever_contained_in and
is_ever_coveredby with their always twins; coveredby is the covers
relationship with the container first, named and computed as PostGIS's
coveredby and geography_coveredby. TCbuffer carries the temporal
relationships as well. MEOS defines no spatial relationship for the
network point or the pose.

A base value is built from its text or by keyword, as
Npoint(route=1, position=0.5), Cbuffer(point=..., radius=...) and
Pose(point=..., theta=...). Its WKB output is the bytes PyMEOS-CFFI
returns, its WKB input and a set's elements are a bytes object and a
Python list whose length is their own, and a network point set takes
each element as the Npoint struct npointset_make reads. The text of a
value is its asText, as in MobilityDB: str of a pose, a circular buffer,
a network point and their sets is pose_as_text, cbuffer_as_text,
npoint_as_text and spatialset_as_text, Pose(POINT(1 1),0.5), the sets
gaining as_text, as_wkt and as_ewkt as GeoSet has them, and a temporal
rigid geometry reads its text through trgeometry_in and writes it
through trgeometry_as_text and trgeometry_as_ewkt, the reference
geometry before the poses; repr of a temporal value is the class name
around its text.

The tests cover every class: construction from text, from the base
values and from MF-JSON, the outputs, the accessors, the comparisons and
the transformations of each family.
@estebanzimanyi
estebanzimanyi force-pushed the feat/extended-temporal-types branch from e3597a1 to 407ec84 Compare October 31, 2026 19:56
@estebanzimanyi
estebanzimanyi merged commit 59191dd into master Oct 31, 2026
9 of 15 checks passed
@estebanzimanyi
estebanzimanyi deleted the feat/extended-temporal-types branch October 31, 2026 21:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant