Skip to main content

OGC API Common structure and support for OGC Xpublish plugins

Project description

XPublish OGC Core

Enable Xpublish plugins that support various OGC standards to serve via fully OGC compliant routes.

This works by creating an app_router that restructures the Xpublish API around OGC API - Common conventions, and registering new hookspecs that other OGC plugins (for example xpublish-edr) implement to contribute their conformance classes, collection metadata, and data queries.

Endpoints

Path Description
/ Landing page with self, service-desc (/openapi.json), service-doc (/docs), conformance, and data links (including the http://www.opengis.net/def/rel/ogc/1.0/... link relations)
/conformance OGC API - Common conformance classes, plus every class declared by plugins via the ogc_conformance_classes hook
/collections One collection per published dataset, built from dataset attributes plus plugin contributions
/collections/{collection_id} A single collection, with data_queries aggregated from the ogc_collection_dataqueries hook. Unknown ids return an OGC exception shaped 404

If xpublish-ogc-core is installed it is loaded automatically through the xpublish.plugin entry point. The landing page title and description are configurable on the plugin, by instantiating it explicitly (note that passing plugins to xpublish.Rest disables entry point auto-loading, so list every plugin you want):

import xpublish
from xpublish_edr import CfEdrPlugin
from xpublish_ogc_core import OgcCorePlugin

rest = xpublish.Rest(
    datasets,
    plugins={
        "ogc-core": OgcCorePlugin(title="My data server", description="..."),
        "edr": CfEdrPlugin(),
    },
)

Hookspecs

Other OGC plugins implement these hookspecs (declared on OgcPluginSpec):

  • ogc_router(deps) — return an APIRouter mounted at the application root, for OGC routes like /collections/{collection_id}/position.
  • ogc_conformance_classes() — return a list of conformance class URIs (http://www.opengis.net/spec/...) to aggregate into /conformance.
  • ogc_collection_metadata(collection_id, ds) — return a dict of collection members (extent, parameter_names, crs, output_formats, ...) merged into the collection objects served at /collections and /collections/{collection_id}.
  • ogc_collection_dataqueries(collection_id, ds) — return a dict of data query descriptions (position, area, cube, ...) merged into the collection's data_queries.

Schema-driven development

Development on this plugin, and for other OGC plugins is driven by the official OGC schemas and test suites:

  • The official OGC schemas are vendored under src/xpublish_ogc_core/schemas/ so tests run offline (refresh with uv run scripts/update_schemas.py): the OGC API - Common Part 1 building blocks plus the collections shapes from OGC API - Features Part 1 (the "common" document, which core's own responses validate against), and the bundled OpenAPI documents published by the OGC API - EDR and OGC API - Tiles standards for the plugins implementing them.

  • xpublish_ogc_core.testing is shipped with the package so downstream plugins can validate their own responses against the official component schemas (the document argument picks the schema set, defaulting to "edr"):

    from xpublish_ogc_core.testing import validate_response
    
    validate_response("landingPage", client.get("/").json(), document="common")
    validate_response("collection", client.get("/collections/air").json())
    validate_response(
        "tileSet",
        client.get("/datasets/air/tiles/WebMercatorQuad").json(),
        document="tiles",
    )
    

    Validation failures raise with the jsonschema error messages, pointing at the exact spec violation.

  • Plugins are also suggested to use Schemathesis for hypothesis testing their advertised endpoints. xpublish_ogc_core.testing.bundled_schema() helps with loading the schema and then hypothesis testing against the spec. The tests can be run in coordination with those generated by the plguins themselves.

    plugin_schema = schemathesis.openapi.from_asgi("/openapi.json", build_app())
    
    
    ogc_schema = (
        testing.bundled_schema(with_app=build_app())
        .exclude(path_regex=r"^/collections/\{collectionId\}/items")
        .exclude(path_regex=r"^/collections/\{collectionId\}/instances")
        .exclude(path_regex=r"^/collections/\{collectionId\}/locations")
        .exclude(path_regex=r"^/collections/\{collectionId\}/radius")
        .exclude(path_regex=r"^/collections/\{collectionId\}/trajectory")
        .exclude(path_regex=r"^/collections/\{collectionId\}/corridor")
    )
    
    
    @schemathesis.pytest.parametrize(
        plugin=plugin_schema,
        ogc=ogc_schema,
    )
    def test_schema(case):
        # the EDR query parameters (WKT coords, comma separated bbox) are looser
        # than their OpenAPI parameter schemas can express, so 422 rejections of
        # schema-compliant inputs are expected
        case.call_and_validate(excluded_checks=[positive_data_acceptance])
    
  • xpublish_ogc_core.teamengine is also shipped to help facilitate other plugins testing with the OGC CITE test suites running in Docker.

    from xpublish_ogc_core import teamengine
    
    with (
        teamengine.serve_app(rest.app) as app_url,
        teamengine.teamengine_container(
            "ogccite/ets-ogcapi-edr10:1.3-teamengine-6.0.0-RC2"
        ) as engine_url,
    ):
        result = teamengine.run_suite(
            engine_url,
            "ogcapi-edr10",
            {"iut": app_url, "apiDefinition": f"{app_url}/openapi.json"},
        )
    
    assert not result.failure_names(), result.summary()
    

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

xpublish_ogc_core-0.1.0.tar.gz (67.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

xpublish_ogc_core-0.1.0-py3-none-any.whl (61.7 kB view details)

Uploaded Python 3

File details

Details for the file xpublish_ogc_core-0.1.0.tar.gz.

File metadata

  • Download URL: xpublish_ogc_core-0.1.0.tar.gz
  • Upload date:
  • Size: 67.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for xpublish_ogc_core-0.1.0.tar.gz
Algorithm Hash digest
SHA256 7b83272dc4b60b44c33a4558361ba3d9349d990a6111cea9d4f6d2c5e1453323
MD5 bea37eacf2fb87aeed9abb5318b8f8f8
BLAKE2b-256 08b0d07d507047ab9395c4d8d5e81a15fc084b9e8ef2635ebd1839e3050c448c

See more details on using hashes here.

Provenance

The following attestation bundles were made for xpublish_ogc_core-0.1.0.tar.gz:

Publisher: pypi-publish.yml on xpublish-community/xpublish-ogc-core

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file xpublish_ogc_core-0.1.0-py3-none-any.whl.

File metadata

File hashes

Hashes for xpublish_ogc_core-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 a9c2a66d67e14d8c8cbc1a85c4ff12fcddf98bad42dffdba093e74f43ce723ee
MD5 a4c3f0144b061b8dd5aa7af807b2846f
BLAKE2b-256 fd66b9ae464af5414d768ca3f236aab212c3b007e796c2617a2df8023a2b5ff7

See more details on using hashes here.

Provenance

The following attestation bundles were made for xpublish_ogc_core-0.1.0-py3-none-any.whl:

Publisher: pypi-publish.yml on xpublish-community/xpublish-ogc-core

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page