Metadata-Version: 2.4
Name: fdpneo
Version: 0.13.1
Summary: FAIR Data Point v2 server — a FAIR-aligned metadata repository implementing the FDP specifications.
Project-URL: Homepage, https://github.com/FAIRDataTeam/fdp-server
Project-URL: Documentation, https://specs.fairdatapoint.org
Project-URL: Repository, https://github.com/FAIRDataTeam/fdp-server
Project-URL: Issues, https://github.com/FAIRDataTeam/fdp-server/issues
Author: FDP Contributors
License: MIT
License-File: LICENSE
License-File: NOTICE
Keywords: dcat,fair,fdp,ldp,metadata,rdf,shacl,sparql
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Science/Research
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3 :: Only
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Topic :: Scientific/Engineering
Requires-Python: >=3.12
Requires-Dist: aiohttp>=3.14.0
Requires-Dist: alembic>=1.13
Requires-Dist: asyncpg>=0.29
Requires-Dist: authlib>=1.3
Requires-Dist: cryptography>=48.0.1
Requires-Dist: fastapi[standard]>=0.115
Requires-Dist: geoip2>=4.8
Requires-Dist: httpx>=0.27
Requires-Dist: joserfc>=1.6.8
Requires-Dist: opentelemetry-api>=1.27
Requires-Dist: opentelemetry-instrumentation-fastapi>=0.48b0
Requires-Dist: opentelemetry-instrumentation-httpx>=0.48b0
Requires-Dist: opentelemetry-instrumentation-sqlalchemy>=0.48b0
Requires-Dist: opentelemetry-sdk>=1.27
Requires-Dist: pydantic-settings>=2.14.2
Requires-Dist: pydantic>=2.7
Requires-Dist: pyjwt[crypto]>=2.13.0
Requires-Dist: pyshacl>=0.26
Requires-Dist: python-multipart>=0.0.31
Requires-Dist: pyyaml>=6.0
Requires-Dist: rdflib>=7.0
Requires-Dist: rich>=13.7
Requires-Dist: sqlalchemy[asyncio]>=2.0
Requires-Dist: starlette>=1.3.1
Requires-Dist: structlog>=24.2
Requires-Dist: typer>=0.12
Requires-Dist: uvicorn[standard]>=0.30
Provides-Extra: dev
Requires-Dist: aiosqlite>=0.20; extra == 'dev'
Requires-Dist: httpx>=0.27; extra == 'dev'
Requires-Dist: pyright>=1.1.380; extra == 'dev'
Requires-Dist: pytest-asyncio>=0.24; extra == 'dev'
Requires-Dist: pytest-cov>=5.0; extra == 'dev'
Requires-Dist: pytest-mock>=3.14; extra == 'dev'
Requires-Dist: pytest>=8.3; extra == 'dev'
Requires-Dist: respx>=0.21; extra == 'dev'
Requires-Dist: ruff>=0.6; extra == 'dev'
Requires-Dist: testcontainers[postgres]>=4.8; extra == 'dev'
Description-Content-Type: text/markdown

# FAIR Data Point v2 — Server

> [!CAUTION]
This is NOT the reference implementation, just an experimentation. The initial development has been heavily based on AI code generation.

A FAIR-aligned metadata repository implementing the [FAIR Data Point specifications](https://specs.fairdatapoint.org), modelled on W3C DCAT with user-defined SHACL schemas, ODRL-based access control, and a full W3C Linked Data Platform API.

This repository contains the **server** implementation. The reference web client lives in a separate repository: `fdp-client` (URL to be set at repo creation).

> **Status: active development.** The core stack runs — you can bring up the full client + server + services with one command (see [Getting started](#getting-started)). This README still describes some target-state features that are in progress, and the bundled deployment is dev-credentialed, so it is not yet hardened for production. 


## What the FDP does

The FDP is a metadata repository. It serves descriptions of datasets, data services, organizations, biobanks, patient registries, scientific publications, methodologies, semantic artefacts — anything a community wishes to describe through its own SHACL schemas — over standard semantic-web protocols. Consumers can browse and search the metadata through a REST API (Linked Data Platform), run SPARQL queries against it, and access the underlying open-access data distributions where policy permits.

## Key design choices

- **Python + FastAPI** server, **Vue 3 + TypeScript** client, in **separate repositories**
- **External OIDC** for authentication — no internal user database
- **Modular monolith** with four bounded contexts: metadata provider, security enforcer, metrics gatherer, simple data provider
- **PostgreSQL** for operational state (metrics, auth cache, audit), **pluggable triple store** for RDF metadata
- **Full LDP** including `PATCH` for partial record updates
- **ODRL profile** (Permissions and Prohibitions) for access control; **versioned Offers**, **materialized Agreements** for audit
- **Anonymous-by-design metrics** — GDPR-safe by construction, not by policy
- **Deployment profiles** for community-specific schema and policy bundles

## Documentation

| Document | Purpose |
|---|---|
| [Architecture overview](docs/architecture/) | Full architecture design with diagrams |
| [Developer documentation](docs/dev-docs/) | Onboarding guide for contributors — code organization, request lifecycle, key processes, with UML/ArchiMate diagrams |
| [Architecture Decision Records](docs/adr/) | Rationale for major architectural choices |
| API reference | Generated OpenAPI spec (link forthcoming) |
| Operator guide | Deployment, configuration, profile management (link forthcoming) |

## Architecture at a glance

The server exposes two HTTP surfaces — a REST/LDP API and a SPARQL endpoint — both sharing authentication, authorization, and a common storage layer:

![Server components](docs/architecture/diagrams/03_server_components.svg)

See the [full architecture document](docs/architecture/README.md) for the data model, the SPARQL access-control flow, the ODRL policy lifecycle, and the deployment-profile mechanism.

## Repository layout

```
fdp-server/
├── README.md                       ← this file
├── docs/
│   ├── architecture/               ← architecture document and diagrams
│   │   ├── README.md
│   │   └── diagrams/
│   └── adr/                        ← architecture decision records
├── src/fdpneo_server/
│   ├── identity/                   ← OIDC integration, request context
│   ├── metadata/                   ← records, schemas, LDP server
│   ├── policy/                     ← ODRL evaluator, PDP, authorization cache
│   ├── access/                     ← SPARQL endpoint, query rewriting
│   ├── data/                       ← simple data provider
│   ├── metrics/                    ← anonymized event pipeline, dashboard API
│   ├── storage/                    ← triple store adapter, Postgres repository
│   ├── shared/                     ← RDF utilities, event bus, error types
│   └── main.py
├── tests/
│   ├── unit/
│   ├── integration/                ← testcontainers-backed triple store + Postgres
│   ├── contract/                   ← OpenAPI conformance
│   └── conformance/                ← FDP specs and LDP test suite
├── deploy/
│   ├── compose.yaml                ← dev stack: GraphDB + Postgres + Keycloak (server runs on host)
│   ├── stack/                      ← full stack: client + server + services, one command
│   └── helm/
└── pyproject.toml
```

## Technology stack

| Concern | Choice |
|---|---|
| Language | Python 3.12+ |
| Web framework | FastAPI |
| Validation at the edge | Pydantic v2 |
| RDF library | RDFLib (Oxigraph bindings considered for hot paths) |
| SHACL validation | pySHACL |
| OIDC | Authlib |
| ORM | SQLAlchemy 2.x (async) |
| Migrations | Alembic |
| Background jobs | arq (Postgres-backed) |
| Logging | structlog |
| Tracing | OpenTelemetry |
| Package management | uv |
| Testing | pytest, pytest-asyncio, testcontainers |

## Getting started

There are two ways to run the FDP, depending on whether you are developing the server or just want a running instance.

### Full stack, one command (client + server + services)

The `deploy/stack/` compose brings up everything — the Vue client, the FastAPI server, and the backing services (GraphDB, PostgreSQL, Keycloak) — with the GraphDB repository, database schema, and default metadata profile bootstrapped automatically on first boot.

```bash
cd server
cp deploy/stack/.env.example deploy/stack/.env      # then edit PUBLIC_HOST / secrets
docker compose -f deploy/stack/compose.yaml --env-file deploy/stack/.env up -d
```

Then open the UI at **http://localhost:5173**, the API at **http://localhost:8000**, and Keycloak at **http://localhost:8081**. Images are pulled from GHCR by default; add `--build` to build from source (the client builds from a sibling `../client` checkout). See [`deploy/stack/README.md`](deploy/stack/README.md) for details and production-hardening notes.

**API documentation.** The OpenAPI spec is always served at **http://localhost:8000/fdp-api/openapi.json** (in every environment — point client codegen and tooling here). The interactive docs UIs — Swagger at **/fdp-api/docs** and ReDoc at **/fdp-api/redoc** — are served only in `development` mode or when `EXPOSE_API_DOCS=true`; the full-stack `.env` enables them by default for evaluation.

**Agent access (MCP).** The full stack comes up **agent-ready**: an [`fdp-mcp`](../mcp) Model Context Protocol bridge (ADR-0018) runs at **http://localhost:8002/mcp**, exposing a read-only tool surface over the *public* FDP API only. Point any MCP client at it — see [`../mcp/docs/agent-quickstart.md`](../mcp/docs/agent-quickstart.md). Disable it with `--scale mcp=0`.

> [!WARNING]
> The bundled Keycloak realm and credentials are **development-only**. Rotate every secret and harden Keycloak before any real deployment.

### Development stack (backing services only)

For working on the server itself, run only the backing services in Docker and run the server on the host so you get hot-reload and a debugger:

```bash
# clone, then:
docker compose -f deploy/compose.yaml up -d       # GraphDB + PostgreSQL + Keycloak
uv sync
uv run fdp db migrate
uv run fdp profile apply   # bundled default profile
uv run fastapi dev src/fdpneo_server/main.py
```

This compose starts GraphDB, PostgreSQL, and a Keycloak instance pre-configured for local development, but not the server or client. The default profile bootstraps a minimal FDP/DCAT setup; replace it with a community profile to bootstrap a custom deployment.

## License

[MIT](./LICENSE), matching the FDP reference implementation. Contributions require a DCO sign-off — see [CONTRIBUTING.md](./CONTRIBUTING.md).

## See also

- FDP specifications: [specs.fairdatapoint.org](https://specs.fairdatapoint.org)
- Current reference implementation: [github.com/FAIRDataTeam/FAIRDataPoint](https://github.com/FAIRDataTeam/FAIRDataPoint)
- Reference client repository: `fdp-client` (URL to be set at repo creation)
