Skip to content

Commit 649bdd9

Browse files
authored
feat: initial implementation (#1)
1 parent 445ccc7 commit 649bdd9

31 files changed

Lines changed: 8185 additions & 0 deletions

.github/FUNDING.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
---
2+
github: [yaal-coop]

.github/workflows/tests.yaml

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
---
2+
name: tests
3+
on:
4+
push:
5+
branches:
6+
- main
7+
- '*.*.*'
8+
pull_request:
9+
branches:
10+
- main
11+
- '*.*.*'
12+
13+
jobs:
14+
tests:
15+
name: ${{ matrix.python }}
16+
runs-on: ubuntu-latest
17+
strategy:
18+
fail-fast: false
19+
matrix:
20+
python:
21+
- '3.12'
22+
- '3.11'
23+
steps:
24+
- uses: actions/checkout@v4
25+
- name: Install Poetry
26+
uses: snok/install-poetry@v1
27+
- uses: actions/setup-python@v5
28+
with:
29+
python-version: ${{ matrix.python }}
30+
cache: 'poetry'
31+
- name: Use scim2-models from repository
32+
run: |
33+
sed -i 's|scim2-models = { path = "../../", develop = true }|scim2-models = { git = "https://github.com/yaal-coop/scim2-models" }|g' pyproject.toml
34+
poetry lock --no-update
35+
- name: Install dependencies and run tests
36+
run: |
37+
poetry --version
38+
poetry install
39+
poetry run pytest --showlocals --cov --cov-fail-under=100 --cov-report term:skip-covered
40+
41+
style:
42+
runs-on: ubuntu-latest
43+
steps:
44+
- uses: actions/checkout@v4
45+
- uses: pre-commit/action@v3.0.1

.gitignore

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
.env
2+
*.sqlite
3+
*.pyc
4+
*.mo
5+
*.prof
6+
.python_history
7+
.tox
8+
.coverage
9+
.coverage.*
10+
htmlcov
11+
*.egg-info
12+
build
13+
dist
14+
.vscode
15+
.idea
16+
.directory

.pre-commit-config.yaml

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
---
2+
repos:
3+
- repo: https://github.com/astral-sh/ruff-pre-commit
4+
rev: 'v0.5.4'
5+
hooks:
6+
- id: ruff
7+
args: [--fix, --exit-non-zero-on-fix]
8+
- id: ruff-format
9+
- repo: https://github.com/pre-commit/pre-commit-hooks
10+
rev: v4.6.0
11+
hooks:
12+
- id: fix-byte-order-marker
13+
- id: trailing-whitespace
14+
exclude: "\\.svg$|\\.map$|\\.min\\.css$|\\.min\\.js$|\\.po$|\\.pot$"
15+
- id: end-of-file-fixer
16+
exclude: "\\.svg$|\\.map$|\\.min\\.css$|\\.min\\.js$|\\.po$|\\.pot$"
17+
- id: check-toml
18+
- repo: https://github.com/PyCQA/docformatter
19+
rev: v1.7.5
20+
hooks:
21+
- id: docformatter

README.md

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
# scim2-server
2+
3+
This is an example WSGI-SCIM server using [scim2-models](https://github.com/yaal-coop/scim2-models).
4+
It utilizes [werkzeug](https://werkzeug.palletsprojects.com/) and [scim2-filter-parser](https://github.com/15five/scim2-filter-parser) and keeps all resources in-memory,
5+
they are lost once the process exits.
6+
7+
## Features
8+
9+
- [x] Discovery endpoints (`/v2/ServiceProviderConfig`, `/v2/ResourceTypes`, `/v2/Schemas`)
10+
- [x] Create/Read/Update/Delete resources (`POST`, `GET`, `PUT`, `DELETE`)
11+
- [x] Searching & Filtering
12+
- [x] Support for ETags
13+
- [x] Unique Constraints
14+
- [x] HTTP PATCH (Add/Remove/Replace)
15+
- [x] Sorting
16+
17+
The only optional feature currently missing is support for Bulk operations ([RFC 7644, Section 3.7](https://datatracker.ietf.org/doc/html/rfc7644#section-3.7)).
18+
19+
## Usage
20+
21+
This repository functions as a submodule of the parent [scim2-models](https://github.com/yaal-coop/scim2-models). To use it in stand-alone
22+
mode, apply this diff to `pyproject.toml`:
23+
24+
```diff
25+
-scim2-models = { path = "../../", develop = true }
26+
+scim2-models = { git = "https://github.com/yaal-coop/scim2-models" }
27+
```
28+
29+
```shell
30+
$ scim2-server [-h] [--schema SCHEMA] [--resource-type RESOURCE_TYPE] [--bearer-token BEARER_TOKEN] [--hostname HOSTNAME] [--port PORT] [--reverse-proxy] [--dump-resources DUMP_RESOURCES]
31+
```
32+
33+
- `-h`/`--help`: Show help message
34+
- `--reverse-proxy`: Allow using the provider behind a Reverse Proxy (required for URL rewriting).
35+
- `--schema`: Register schemas from specified JSON file. If not provided, loads the default schemas from RFC 7643.
36+
- `--resource-type`: Register resource types from specified JSON file. If not provided, loads the default resource types from RFC 7643.
37+
- `--bearer-token`: Registers a bearer token that can be used for accessing the service. If no tokens are provided, anonymous access without authentication is allowed.
38+
- `--hostname`: The hostname to listen on. Defaults to `127.0.0.1`.
39+
- `--port`: The port to listen on. Defaults to `8080`.
40+
- `--dump-resources`: Dump a JSON document containing all resources when the provider exits normally.
41+
42+
## Notes
43+
44+
This provider can be used as a starting point if you want to implement a SCIM provider. You should probably change the following things, if you want to use it in production:
45+
46+
- Use a proper production WSGI server instead of the one provided by Werkzeug
47+
- Implement your own Backend as a subclass of `scim2_server.backend.Backend`
48+
- Implement proper authorization with OAuth instead of public access or static bearer tokens
49+
- Support the `/Me` endpoint, if it applies in your use case
50+
- Add support for using either a static URL prefix or improve the support for usage behind a reverse proxy
51+
52+
The provider in its current state has been tested successfully against a live Microsoft Entra system.

0 commit comments

Comments
 (0)