sovereign 0.32.0__tar.gz → 1.0.0a3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {sovereign-0.32.0 → sovereign-1.0.0a3}/PKG-INFO +43 -45
- {sovereign-0.32.0 → sovereign-1.0.0a3}/README.md +5 -4
- sovereign-1.0.0a3/pyproject.toml +161 -0
- sovereign-1.0.0a3/src/sovereign/__init__.py +32 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/app.py +53 -42
- sovereign-1.0.0a3/src/sovereign/cache/__init__.py +245 -0
- sovereign-1.0.0a3/src/sovereign/cache/backends/__init__.py +110 -0
- sovereign-1.0.0a3/src/sovereign/cache/backends/s3.py +161 -0
- sovereign-1.0.0a3/src/sovereign/cache/filesystem.py +74 -0
- sovereign-1.0.0a3/src/sovereign/cache/types.py +17 -0
- sovereign-1.0.0a3/src/sovereign/configuration.py +607 -0
- sovereign-1.0.0a3/src/sovereign/context.py +285 -0
- sovereign-1.0.0a3/src/sovereign/dynamic_config/__init__.py +112 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/error_info.py +2 -3
- sovereign-1.0.0a3/src/sovereign/events.py +49 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/logging/access_logger.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/logging/application_logger.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/logging/bootstrapper.py +3 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/middlewares.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/modifiers/lib.py +1 -1
- sovereign-1.0.0a3/src/sovereign/rendering.py +124 -0
- sovereign-1.0.0a3/src/sovereign/rendering_common.py +91 -0
- sovereign-1.0.0a3/src/sovereign/server.py +127 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/statistics.py +19 -21
- sovereign-1.0.0a3/src/sovereign/templates/base.html +77 -0
- sovereign-1.0.0a3/src/sovereign/templates/resources.html +260 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/testing/loaders.py +1 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/testing/modifiers.py +0 -2
- sovereign-1.0.0a3/src/sovereign/tracing.py +103 -0
- sovereign-1.0.0a3/src/sovereign/types.py +304 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/auth.py +21 -6
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/crypto.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/suites/disabled_cipher.py +2 -2
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/eds.py +5 -3
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/entry_point_loader.py +2 -2
- sovereign-1.0.0a3/src/sovereign/utils/mock.py +75 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/templates.py +4 -2
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/timer.py +5 -3
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/version_info.py +8 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/weighted_clusters.py +2 -1
- sovereign-1.0.0a3/src/sovereign/v2/data/data_store.py +621 -0
- sovereign-1.0.0a3/src/sovereign/v2/data/render_discovery_response.py +24 -0
- sovereign-1.0.0a3/src/sovereign/v2/data/repositories.py +90 -0
- sovereign-1.0.0a3/src/sovereign/v2/data/utils.py +33 -0
- sovereign-1.0.0a3/src/sovereign/v2/data/worker_queue.py +273 -0
- sovereign-1.0.0a3/src/sovereign/v2/jobs/refresh_context.py +117 -0
- sovereign-1.0.0a3/src/sovereign/v2/jobs/render_discovery_job.py +145 -0
- sovereign-1.0.0a3/src/sovereign/v2/logging.py +81 -0
- sovereign-1.0.0a3/src/sovereign/v2/types.py +41 -0
- sovereign-1.0.0a3/src/sovereign/v2/web.py +101 -0
- sovereign-1.0.0a3/src/sovereign/v2/worker.py +199 -0
- sovereign-1.0.0a3/src/sovereign/views/__init__.py +7 -0
- sovereign-1.0.0a3/src/sovereign/views/api.py +82 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/views/crypto.py +1 -1
- sovereign-1.0.0a3/src/sovereign/views/discovery.py +92 -0
- sovereign-1.0.0a3/src/sovereign/views/healthchecks.py +127 -0
- sovereign-1.0.0a3/src/sovereign/views/interface.py +261 -0
- sovereign-1.0.0a3/src/sovereign/worker.py +193 -0
- sovereign-1.0.0a3/src/sovereign_files/__init__.py +0 -0
- sovereign-1.0.0a3/src/sovereign_files/static/darkmode.js +51 -0
- sovereign-1.0.0a3/src/sovereign_files/static/node_expression.js +42 -0
- sovereign-1.0.0a3/src/sovereign_files/static/panel.js +76 -0
- sovereign-1.0.0a3/src/sovereign_files/static/resources.css +246 -0
- sovereign-1.0.0a3/src/sovereign_files/static/resources.js +642 -0
- sovereign-1.0.0a3/src/sovereign_files/static/sass/style.scss +33 -0
- sovereign-1.0.0a3/src/sovereign_files/static/style.css +16143 -0
- sovereign-1.0.0a3/src/sovereign_files/static/style.css.map +1 -0
- sovereign-0.32.0/LICENSE.txt +0 -13
- sovereign-0.32.0/pyproject.toml +0 -138
- sovereign-0.32.0/src/sovereign/__init__.py +0 -93
- sovereign-0.32.0/src/sovereign/context.py +0 -194
- sovereign-0.32.0/src/sovereign/discovery.py +0 -193
- sovereign-0.32.0/src/sovereign/dynamic_config/__init__.py +0 -88
- sovereign-0.32.0/src/sovereign/schemas.py +0 -918
- sovereign-0.32.0/src/sovereign/server.py +0 -50
- sovereign-0.32.0/src/sovereign/sources/__init__.py +0 -3
- sovereign-0.32.0/src/sovereign/sources/file.py +0 -21
- sovereign-0.32.0/src/sovereign/sources/inline.py +0 -39
- sovereign-0.32.0/src/sovereign/sources/lib.py +0 -41
- sovereign-0.32.0/src/sovereign/sources/poller.py +0 -296
- sovereign-0.32.0/src/sovereign/static/panel.js +0 -56
- sovereign-0.32.0/src/sovereign/static/sass/style.scss +0 -27
- sovereign-0.32.0/src/sovereign/static/search_filter.js +0 -20
- sovereign-0.32.0/src/sovereign/static/style.css +0 -13553
- sovereign-0.32.0/src/sovereign/templates/base.html +0 -64
- sovereign-0.32.0/src/sovereign/templates/resources.html +0 -200
- sovereign-0.32.0/src/sovereign/tracing.py +0 -85
- sovereign-0.32.0/src/sovereign/utils/mock.py +0 -34
- sovereign-0.32.0/src/sovereign/views/admin.py +0 -138
- sovereign-0.32.0/src/sovereign/views/discovery.py +0 -165
- sovereign-0.32.0/src/sovereign/views/healthchecks.py +0 -41
- sovereign-0.32.0/src/sovereign/views/interface.py +0 -223
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/constants.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/dynamic_config/deser.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/dynamic_config/loaders.py +3 -3
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/logging/base_logger.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/logging/types.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/modifiers/__init__.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/response_class.py +2 -2
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/templates/err.html +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/__init__.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/__init__.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/suites/__init__.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/suites/aes_gcm_cipher.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/suites/base_cipher.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/crypto/suites/fernet_cipher.py +0 -0
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/dictupdate.py +1 -1
- {sovereign-0.32.0 → sovereign-1.0.0a3}/src/sovereign/utils/resources.py +1 -1
- {sovereign-0.32.0/src/sovereign/views → sovereign-1.0.0a3/src/sovereign/v2}/__init__.py +0 -0
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: sovereign
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 1.0.0a3
|
|
4
4
|
Summary: Envoy Proxy control-plane written in Python
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
Author: Vasili Syrakis
|
|
9
|
-
|
|
10
|
-
|
|
5
|
+
Project-URL: Homepage, https://pypi.org/project/sovereign/
|
|
6
|
+
Project-URL: Repository, https://bitbucket.org/atlassian/sovereign/src/master/
|
|
7
|
+
Project-URL: Documentation, https://developer.atlassian.com/platform/sovereign/
|
|
8
|
+
Author-email: Vasili Syrakis <vsyrakis@atlassian.com>
|
|
9
|
+
License-Expression: Apache-2.0
|
|
10
|
+
Keywords: control-plane,envoy,envoyproxy,management,server
|
|
11
11
|
Classifier: Development Status :: 5 - Production/Stable
|
|
12
12
|
Classifier: Environment :: No Input/Output (Daemon)
|
|
13
13
|
Classifier: Intended Audience :: Developers
|
|
@@ -16,48 +16,46 @@ Classifier: Intended Audience :: System Administrators
|
|
|
16
16
|
Classifier: License :: OSI Approved :: Apache Software License
|
|
17
17
|
Classifier: Natural Language :: English
|
|
18
18
|
Classifier: Operating System :: POSIX :: Linux
|
|
19
|
-
Classifier: Programming Language :: Python :: 3
|
|
20
|
-
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
-
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
-
Classifier: Programming Language :: Python :: 3.13
|
|
23
|
-
Classifier: Programming Language :: Python :: 3.10
|
|
24
19
|
Classifier: Programming Language :: Python :: 3.8
|
|
25
20
|
Classifier: Programming Language :: Python :: 3.9
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
26
23
|
Classifier: Topic :: Internet :: Proxy Servers
|
|
24
|
+
Requires-Python: <4.0,>=3.11.0
|
|
25
|
+
Requires-Dist: aiofiles<24,>=23.2.1
|
|
26
|
+
Requires-Dist: cachelib<0.11,>=0.10.2
|
|
27
|
+
Requires-Dist: cachetools<6,>=5.3.2
|
|
28
|
+
Requires-Dist: croniter<2,>=1.4.1
|
|
29
|
+
Requires-Dist: cryptography>=45.0.2
|
|
30
|
+
Requires-Dist: fastapi<0.129,>=0.128.0
|
|
31
|
+
Requires-Dist: glom<24,>=23.3.0
|
|
32
|
+
Requires-Dist: h11<0.17,>=0.16.0
|
|
33
|
+
Requires-Dist: jinja2<4,>=3.1.2
|
|
34
|
+
Requires-Dist: jmespath<2,>=1.0.1
|
|
35
|
+
Requires-Dist: pydantic-settings<2.6.0
|
|
36
|
+
Requires-Dist: pydantic<3,>=2.7.2
|
|
37
|
+
Requires-Dist: pyyaml<7,>=6.0.1
|
|
38
|
+
Requires-Dist: requests<3,>=2.32.4
|
|
39
|
+
Requires-Dist: rich>=14.2.0
|
|
40
|
+
Requires-Dist: starlette-context<0.4,>=0.3.6
|
|
41
|
+
Requires-Dist: starlette<0.50,>=0.49.1
|
|
42
|
+
Requires-Dist: structlog<24,>=23.1.0
|
|
43
|
+
Requires-Dist: supervisor<5,>=4.2.5
|
|
44
|
+
Requires-Dist: uvicorn<0.24,>=0.23.2
|
|
45
|
+
Requires-Dist: uvloop<1.0,>0.19.0
|
|
27
46
|
Provides-Extra: boto
|
|
47
|
+
Requires-Dist: boto3<2,>=1.28.62; extra == 'boto'
|
|
28
48
|
Provides-Extra: caching
|
|
29
49
|
Provides-Extra: httptools
|
|
50
|
+
Requires-Dist: httptools<0.7,>=0.6.0; extra == 'httptools'
|
|
30
51
|
Provides-Extra: orjson
|
|
52
|
+
Requires-Dist: orjson<4,>=3.9.15; extra == 'orjson'
|
|
31
53
|
Provides-Extra: sentry
|
|
54
|
+
Requires-Dist: sentry-sdk<3,>=2.14.0; extra == 'sentry'
|
|
32
55
|
Provides-Extra: statsd
|
|
56
|
+
Requires-Dist: datadog>=0.50.1; extra == 'statsd'
|
|
33
57
|
Provides-Extra: ujson
|
|
34
|
-
Requires-Dist:
|
|
35
|
-
Requires-Dist: PyYAML (>=6.0.1,<7.0.0)
|
|
36
|
-
Requires-Dist: aiofiles (>=23.2.1,<24.0.0)
|
|
37
|
-
Requires-Dist: boto3 (>=1.28.62,<2.0.0) ; extra == "boto"
|
|
38
|
-
Requires-Dist: cachelib (>=0.10.2,<0.11.0)
|
|
39
|
-
Requires-Dist: cachetools (>=5.3.2,<6.0.0)
|
|
40
|
-
Requires-Dist: cashews[redis] (>=6.3.0,<7.0.0) ; extra == "caching"
|
|
41
|
-
Requires-Dist: croniter (>=1.4.1,<2.0.0)
|
|
42
|
-
Requires-Dist: cryptography (>=42.0.0,<43.0.0)
|
|
43
|
-
Requires-Dist: datadog (>=0.47.0,<0.48.0) ; extra == "statsd"
|
|
44
|
-
Requires-Dist: fastapi (>=0.115.2,<0.116.0)
|
|
45
|
-
Requires-Dist: glom (>=23.3.0,<24.0.0)
|
|
46
|
-
Requires-Dist: gunicorn (>=23.0.0,<24.0.0)
|
|
47
|
-
Requires-Dist: httptools (>=0.6.0,<0.7.0) ; extra == "httptools"
|
|
48
|
-
Requires-Dist: orjson (>=3.9.15,<4.0.0) ; extra == "orjson"
|
|
49
|
-
Requires-Dist: pydantic (>=2.7.2,<3.0.0)
|
|
50
|
-
Requires-Dist: pydantic-settings (<2.6.0)
|
|
51
|
-
Requires-Dist: redis (<=5.0.0)
|
|
52
|
-
Requires-Dist: requests (>=2.31.0,<3.0.0)
|
|
53
|
-
Requires-Dist: sentry-sdk (>=2.14.0,<3.0.0) ; extra == "sentry"
|
|
54
|
-
Requires-Dist: starlette-context (>=0.3.6,<0.4.0)
|
|
55
|
-
Requires-Dist: structlog (>=23.1.0,<24.0.0)
|
|
56
|
-
Requires-Dist: ujson (>=5.8.0,<6.0.0) ; extra == "ujson"
|
|
57
|
-
Requires-Dist: uvicorn (>=0.23.2,<0.24.0)
|
|
58
|
-
Requires-Dist: uvloop (>=0.19.0,<0.20.0)
|
|
59
|
-
Project-URL: Documentation, https://developer.atlassian.com/platform/sovereign/
|
|
60
|
-
Project-URL: Repository, https://bitbucket.org/atlassian/sovereign/src/master/
|
|
58
|
+
Requires-Dist: ujson<6,>=5.8.0; extra == 'ujson'
|
|
61
59
|
Description-Content-Type: text/markdown
|
|
62
60
|
|
|
63
61
|
sovereign
|
|
@@ -133,17 +131,18 @@ Local development
|
|
|
133
131
|
|
|
134
132
|
Requirements
|
|
135
133
|
------------
|
|
136
|
-
*
|
|
134
|
+
* uv
|
|
137
135
|
* Docker
|
|
138
136
|
* Docker-compose
|
|
139
137
|
|
|
140
138
|
|
|
141
139
|
Installing dependencies for dev
|
|
142
140
|
-------------------------------
|
|
143
|
-
Dependencies and creation of virtualenv is handled by
|
|
141
|
+
Dependencies and creation of virtualenv is handled by uv
|
|
144
142
|
```
|
|
145
|
-
|
|
146
|
-
|
|
143
|
+
uv sync
|
|
144
|
+
uv venv activate
|
|
145
|
+
uv run <command>
|
|
147
146
|
```
|
|
148
147
|
|
|
149
148
|
Running locally
|
|
@@ -208,4 +207,3 @@ Copyright (c) 2018 Atlassian and others.
|
|
|
208
207
|
Apache 2.0 licensed, see [LICENSE.txt](LICENSE.txt) file.
|
|
209
208
|
|
|
210
209
|
|
|
211
|
-
|
|
@@ -71,17 +71,18 @@ Local development
|
|
|
71
71
|
|
|
72
72
|
Requirements
|
|
73
73
|
------------
|
|
74
|
-
*
|
|
74
|
+
* uv
|
|
75
75
|
* Docker
|
|
76
76
|
* Docker-compose
|
|
77
77
|
|
|
78
78
|
|
|
79
79
|
Installing dependencies for dev
|
|
80
80
|
-------------------------------
|
|
81
|
-
Dependencies and creation of virtualenv is handled by
|
|
81
|
+
Dependencies and creation of virtualenv is handled by uv
|
|
82
82
|
```
|
|
83
|
-
|
|
84
|
-
|
|
83
|
+
uv sync
|
|
84
|
+
uv venv activate
|
|
85
|
+
uv run <command>
|
|
85
86
|
```
|
|
86
87
|
|
|
87
88
|
Running locally
|
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
[project]
|
|
2
|
+
name = "sovereign"
|
|
3
|
+
version = "1.0.0a3"
|
|
4
|
+
description = "Envoy Proxy control-plane written in Python"
|
|
5
|
+
authors = [{ name = "Vasili Syrakis", email = "vsyrakis@atlassian.com" }]
|
|
6
|
+
requires-python = ">=3.11.0, <4.0"
|
|
7
|
+
readme = "README.md"
|
|
8
|
+
license = "Apache-2.0"
|
|
9
|
+
keywords = [
|
|
10
|
+
"envoy",
|
|
11
|
+
"envoyproxy",
|
|
12
|
+
"control-plane",
|
|
13
|
+
"management",
|
|
14
|
+
"server",
|
|
15
|
+
]
|
|
16
|
+
classifiers = [
|
|
17
|
+
"Development Status :: 5 - Production/Stable",
|
|
18
|
+
"Environment :: No Input/Output (Daemon)",
|
|
19
|
+
"Intended Audience :: Developers",
|
|
20
|
+
"Intended Audience :: Information Technology",
|
|
21
|
+
"Intended Audience :: System Administrators",
|
|
22
|
+
"License :: OSI Approved :: Apache Software License",
|
|
23
|
+
"Natural Language :: English",
|
|
24
|
+
"Operating System :: POSIX :: Linux",
|
|
25
|
+
"Programming Language :: Python :: 3.8",
|
|
26
|
+
"Programming Language :: Python :: 3.9",
|
|
27
|
+
"Programming Language :: Python :: 3.10",
|
|
28
|
+
"Programming Language :: Python :: 3.11",
|
|
29
|
+
"Topic :: Internet :: Proxy Servers",
|
|
30
|
+
]
|
|
31
|
+
dependencies = [
|
|
32
|
+
"uvicorn>=0.23.2,<0.24",
|
|
33
|
+
"aiofiles>=23.2.1,<24",
|
|
34
|
+
"requests>=2.32.4,<3",
|
|
35
|
+
"PyYAML>=6.0.1,<7",
|
|
36
|
+
"Jinja2>=3.1.2,<4",
|
|
37
|
+
"structlog>=23.1.0,<24",
|
|
38
|
+
"cachelib>=0.10.2,<0.11",
|
|
39
|
+
"glom>=23.3.0,<24",
|
|
40
|
+
"cryptography>=45.0.2",
|
|
41
|
+
"fastapi>=0.128.0,<0.129",
|
|
42
|
+
"uvloop>0.19.0,<1.0",
|
|
43
|
+
"croniter>=1.4.1,<2",
|
|
44
|
+
"cachetools>=5.3.2,<6",
|
|
45
|
+
"pydantic>=2.7.2,<3",
|
|
46
|
+
"pydantic-settings<2.6.0",
|
|
47
|
+
"starlette-context>=0.3.6,<0.4",
|
|
48
|
+
"starlette>=0.49.1,<0.50",
|
|
49
|
+
"h11>=0.16.0,<0.17",
|
|
50
|
+
"supervisor>=4.2.5,<5",
|
|
51
|
+
"jmespath>=1.0.1,<2",
|
|
52
|
+
"rich>=14.2.0",
|
|
53
|
+
]
|
|
54
|
+
|
|
55
|
+
[project.optional-dependencies]
|
|
56
|
+
sentry = ["sentry-sdk>=2.14.0,<3"]
|
|
57
|
+
boto = ["boto3>=1.28.62,<2"]
|
|
58
|
+
statsd = ["datadog>=0.50.1"]
|
|
59
|
+
ujson = ["ujson>=5.8.0,<6"]
|
|
60
|
+
orjson = ["orjson>=3.9.15,<4"]
|
|
61
|
+
caching = []
|
|
62
|
+
httptools = ["httptools>=0.6.0,<0.7"]
|
|
63
|
+
|
|
64
|
+
[project.urls]
|
|
65
|
+
Homepage = "https://pypi.org/project/sovereign/"
|
|
66
|
+
Repository = "https://bitbucket.org/atlassian/sovereign/src/master/"
|
|
67
|
+
Documentation = "https://developer.atlassian.com/platform/sovereign/"
|
|
68
|
+
|
|
69
|
+
[project.scripts]
|
|
70
|
+
sovereign = "sovereign.server:main"
|
|
71
|
+
sovereign-web = "sovereign.server:web"
|
|
72
|
+
sovereign-worker = "sovereign.server:worker"
|
|
73
|
+
|
|
74
|
+
[project.entry-points."sovereign.sources"]
|
|
75
|
+
file = "sovereign.sources.file:File"
|
|
76
|
+
inline = "sovereign.sources.inline:Inline"
|
|
77
|
+
|
|
78
|
+
[project.entry-points."sovereign.modifiers"]
|
|
79
|
+
sovereign_3rd_party_test = "sovereign.testing.modifiers:Test"
|
|
80
|
+
|
|
81
|
+
[project.entry-points."sovereign.loaders"]
|
|
82
|
+
example = "sovereign.testing.loaders:Multiply"
|
|
83
|
+
file = "sovereign.dynamic_config.loaders:File"
|
|
84
|
+
pkgdata = "sovereign.dynamic_config.loaders:PackageData"
|
|
85
|
+
http = "sovereign.dynamic_config.loaders:Web"
|
|
86
|
+
https = "sovereign.dynamic_config.loaders:Web"
|
|
87
|
+
env = "sovereign.dynamic_config.loaders:EnvironmentVariable"
|
|
88
|
+
module = "sovereign.dynamic_config.loaders:PythonModule"
|
|
89
|
+
s3 = "sovereign.dynamic_config.loaders:S3Bucket"
|
|
90
|
+
python = "sovereign.dynamic_config.loaders:PythonInlineCode"
|
|
91
|
+
inline = "sovereign.dynamic_config.loaders:Inline"
|
|
92
|
+
|
|
93
|
+
[project.entry-points."sovereign.deserializers"]
|
|
94
|
+
yaml = "sovereign.dynamic_config.deser:YamlDeserializer"
|
|
95
|
+
json = "sovereign.dynamic_config.deser:JsonDeserializer"
|
|
96
|
+
jinja = "sovereign.dynamic_config.deser:JinjaDeserializer"
|
|
97
|
+
jinja2 = "sovereign.dynamic_config.deser:JinjaDeserializer"
|
|
98
|
+
string = "sovereign.dynamic_config.deser:StringDeserializer"
|
|
99
|
+
raw = "sovereign.dynamic_config.deser:PassthroughDeserializer"
|
|
100
|
+
none = "sovereign.dynamic_config.deser:PassthroughDeserializer"
|
|
101
|
+
passthrough = "sovereign.dynamic_config.deser:PassthroughDeserializer"
|
|
102
|
+
ujson = "sovereign.dynamic_config.deser:UjsonDeserializer"
|
|
103
|
+
orjson = "sovereign.dynamic_config.deser:OrjsonDeserializer"
|
|
104
|
+
|
|
105
|
+
[project.entry-points."sovereign.cache.backends"]
|
|
106
|
+
s3 = "sovereign.cache.backends.s3:S3Backend"
|
|
107
|
+
|
|
108
|
+
[project.entry-points."sovereign.data_stores"]
|
|
109
|
+
memory = "sovereign.v2.data.data_store:InMemoryDataStore"
|
|
110
|
+
sqlite = "sovereign.v2.data.data_store:SqliteDataStore"
|
|
111
|
+
|
|
112
|
+
[project.entry-points."sovereign.queues"]
|
|
113
|
+
memory = "sovereign.v2.data.worker_queue:InMemoryQueue"
|
|
114
|
+
sqlite = "sovereign.v2.data.worker_queue:SqliteQueue"
|
|
115
|
+
|
|
116
|
+
[dependency-groups]
|
|
117
|
+
dev = [
|
|
118
|
+
"freezegun",
|
|
119
|
+
"httpx",
|
|
120
|
+
"moto>=5.0.0",
|
|
121
|
+
"pytest-asyncio",
|
|
122
|
+
"pytest-mock",
|
|
123
|
+
"ruff",
|
|
124
|
+
"tavern",
|
|
125
|
+
"toml",
|
|
126
|
+
"ty",
|
|
127
|
+
"ty==0.0.1a26",
|
|
128
|
+
"types-PyYAML",
|
|
129
|
+
"types-cachetools",
|
|
130
|
+
"types-croniter",
|
|
131
|
+
"types-mock>=5.2.0.20250306,<6",
|
|
132
|
+
"types-requests",
|
|
133
|
+
"types-setuptools",
|
|
134
|
+
"types-ujson",
|
|
135
|
+
]
|
|
136
|
+
|
|
137
|
+
[tool.hatch.build.targets.sdist]
|
|
138
|
+
include = [
|
|
139
|
+
"src/sovereign",
|
|
140
|
+
"src/sovereign_files",
|
|
141
|
+
"src/sovereign_files/**/*",
|
|
142
|
+
]
|
|
143
|
+
|
|
144
|
+
[tool.hatch.build.targets.wheel]
|
|
145
|
+
include = [
|
|
146
|
+
"src/sovereign",
|
|
147
|
+
"src/sovereign_files",
|
|
148
|
+
"src/sovereign_files/**/*",
|
|
149
|
+
]
|
|
150
|
+
|
|
151
|
+
[tool.hatch.build.targets.wheel.sources]
|
|
152
|
+
"src/sovereign" = "sovereign"
|
|
153
|
+
"src/sovereign_files" = "sovereign_files"
|
|
154
|
+
|
|
155
|
+
[[tool.uv.index]]
|
|
156
|
+
url = "https://pypi.org/simple"
|
|
157
|
+
default = true
|
|
158
|
+
|
|
159
|
+
[build-system]
|
|
160
|
+
requires = ["hatchling"]
|
|
161
|
+
build-backend = "hatchling.build"
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
from contextvars import ContextVar
|
|
2
|
+
from importlib.metadata import version
|
|
3
|
+
|
|
4
|
+
from sovereign.configuration import EncryptionConfig, config
|
|
5
|
+
from sovereign.logging.bootstrapper import LoggerBootstrapper
|
|
6
|
+
from sovereign.statistics import configure_statsd
|
|
7
|
+
from sovereign.utils.crypto.crypto import CipherContainer
|
|
8
|
+
from sovereign.utils.crypto.suites import EncryptionType
|
|
9
|
+
|
|
10
|
+
_request_id_ctx_var: ContextVar[str] = ContextVar("request_id", default="")
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
def get_request_id() -> str:
|
|
14
|
+
return _request_id_ctx_var.get()
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
WORKER_URL = "http://localhost:9080"
|
|
18
|
+
DIST_NAME = "sovereign"
|
|
19
|
+
__version__ = version(DIST_NAME)
|
|
20
|
+
|
|
21
|
+
stats = configure_statsd()
|
|
22
|
+
logs = LoggerBootstrapper(config)
|
|
23
|
+
application_logger = logs.application_logger.logger
|
|
24
|
+
|
|
25
|
+
encryption_configs = config.authentication.encryption_configs
|
|
26
|
+
server_cipher_container = CipherContainer.from_encryption_configs(
|
|
27
|
+
encryption_configs, logger=application_logger
|
|
28
|
+
)
|
|
29
|
+
disabled_ciphersuite = CipherContainer.from_encryption_configs(
|
|
30
|
+
encryption_configs=[EncryptionConfig("", EncryptionType.DISABLED)],
|
|
31
|
+
logger=application_logger,
|
|
32
|
+
)
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import asyncio
|
|
2
1
|
import traceback
|
|
3
2
|
from collections import namedtuple
|
|
4
3
|
|
|
@@ -7,32 +6,17 @@ from fastapi import FastAPI, Request
|
|
|
7
6
|
from fastapi.responses import FileResponse, JSONResponse, RedirectResponse, Response
|
|
8
7
|
from starlette_context.middleware import RawContextMiddleware
|
|
9
8
|
|
|
10
|
-
from sovereign import
|
|
11
|
-
|
|
12
|
-
asgi_config,
|
|
13
|
-
config,
|
|
14
|
-
logs,
|
|
15
|
-
poller,
|
|
16
|
-
template_context,
|
|
17
|
-
)
|
|
18
|
-
from sovereign.response_class import json_response_class
|
|
9
|
+
from sovereign import __version__, logs
|
|
10
|
+
from sovereign.configuration import ConfiguredResourceTypes, config
|
|
19
11
|
from sovereign.error_info import ErrorInfo
|
|
20
12
|
from sovereign.middlewares import LoggingMiddleware, RequestContextLogMiddleware
|
|
13
|
+
from sovereign.response_class import json_response_class
|
|
21
14
|
from sovereign.utils.resources import get_package_file
|
|
22
|
-
from sovereign.views import
|
|
15
|
+
from sovereign.views import api, crypto, discovery, healthchecks, interface
|
|
23
16
|
|
|
24
17
|
Router = namedtuple("Router", "module tags prefix")
|
|
25
18
|
|
|
26
19
|
DEBUG = config.debug
|
|
27
|
-
SENTRY_DSN = config.sentry_dsn.get_secret_value()
|
|
28
|
-
|
|
29
|
-
try:
|
|
30
|
-
import sentry_sdk
|
|
31
|
-
from sentry_sdk.integrations.asgi import SentryAsgiMiddleware
|
|
32
|
-
|
|
33
|
-
SENTRY_INSTALLED = True
|
|
34
|
-
except ImportError: # pragma: no cover
|
|
35
|
-
SENTRY_INSTALLED = False
|
|
36
20
|
|
|
37
21
|
|
|
38
22
|
def generic_error_response(e: Exception) -> JSONResponse:
|
|
@@ -69,25 +53,35 @@ def init_app() -> FastAPI:
|
|
|
69
53
|
|
|
70
54
|
routers = (
|
|
71
55
|
Router(discovery.router, ["Configuration Discovery"], ""),
|
|
72
|
-
Router(
|
|
73
|
-
Router(admin.router, ["Debugging Endpoints"], "/admin"),
|
|
74
|
-
Router(interface.router, ["User Interface"], "/ui"),
|
|
56
|
+
Router(api.router, ["API"], "/api"),
|
|
75
57
|
Router(healthchecks.router, ["Healthchecks"], ""),
|
|
58
|
+
Router(interface.router, ["User Interface"], "/ui"),
|
|
59
|
+
Router(crypto.router, ["Cryptographic Utilities"], "/crypto"),
|
|
76
60
|
)
|
|
77
61
|
for router in routers:
|
|
78
62
|
application.include_router(
|
|
79
63
|
router.module, tags=router.tags, prefix=router.prefix
|
|
80
64
|
)
|
|
81
65
|
|
|
82
|
-
application.add_middleware(RequestContextLogMiddleware)
|
|
83
|
-
application.add_middleware(LoggingMiddleware)
|
|
66
|
+
application.add_middleware(RequestContextLogMiddleware) # type: ignore
|
|
67
|
+
application.add_middleware(LoggingMiddleware) # type: ignore
|
|
84
68
|
|
|
85
|
-
if
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
69
|
+
if dsn := config.sentry_dsn.get_secret_value():
|
|
70
|
+
try:
|
|
71
|
+
# noinspection PyUnusedImports
|
|
72
|
+
import sentry_sdk
|
|
89
73
|
|
|
90
|
-
|
|
74
|
+
# noinspection PyUnusedImports
|
|
75
|
+
from sentry_sdk.integrations.asgi import SentryAsgiMiddleware
|
|
76
|
+
|
|
77
|
+
sentry_sdk.init(dsn)
|
|
78
|
+
application.add_middleware(SentryAsgiMiddleware) # type: ignore
|
|
79
|
+
except ImportError:
|
|
80
|
+
logs.application_logger.logger.error(
|
|
81
|
+
"Sentry DSN configured but failed to attach to webserver"
|
|
82
|
+
)
|
|
83
|
+
|
|
84
|
+
application.add_middleware(RawContextMiddleware) # type: ignore
|
|
91
85
|
|
|
92
86
|
@application.exception_handler(500)
|
|
93
87
|
async def exception_handler(_: Request, exc: Exception) -> JSONResponse:
|
|
@@ -105,24 +99,41 @@ def init_app() -> FastAPI:
|
|
|
105
99
|
|
|
106
100
|
@application.get("/static/{filename}", summary="Return a static asset")
|
|
107
101
|
async def static(filename: str) -> Response:
|
|
108
|
-
return FileResponse(get_package_file("
|
|
102
|
+
return FileResponse(get_package_file("sovereign_files", f"static/{filename}")) # type: ignore[arg-type]
|
|
109
103
|
|
|
110
|
-
@application.
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
104
|
+
@application.get(
|
|
105
|
+
"/admin/xds_dump",
|
|
106
|
+
summary="Deprecated API, please use /api/resources/{resource_type}",
|
|
107
|
+
)
|
|
108
|
+
async def dump_resources(request: Request) -> Response:
|
|
109
|
+
resource_type = ConfiguredResourceTypes(
|
|
110
|
+
request.query_params.get("xds_type", "cluster")
|
|
111
|
+
)
|
|
112
|
+
resource_name = request.query_params.get("name")
|
|
113
|
+
api_version = request.query_params.get("api_version", "v3")
|
|
114
|
+
service_cluster = request.query_params.get("service_cluster", "*")
|
|
115
|
+
region = request.query_params.get("region")
|
|
116
|
+
version = request.query_params.get("version")
|
|
117
|
+
response = await api.resource(
|
|
118
|
+
resource_type=resource_type,
|
|
119
|
+
resource_name=resource_name,
|
|
120
|
+
api_version=api_version,
|
|
121
|
+
service_cluster=service_cluster,
|
|
122
|
+
region=region,
|
|
123
|
+
version=version,
|
|
124
|
+
)
|
|
125
|
+
response.headers["Deprecation"] = "true"
|
|
126
|
+
response.headers["Link"] = f'</api/resources/{resource_type}>; rel="alternate"'
|
|
127
|
+
response.headers["Warning"] = (
|
|
128
|
+
f'299 - "Deprecated API: please use /api/resources/{resource_type}"'
|
|
129
|
+
)
|
|
130
|
+
response.status_code = 299
|
|
131
|
+
return response
|
|
118
132
|
|
|
119
133
|
return application
|
|
120
134
|
|
|
121
135
|
|
|
122
136
|
app = init_app()
|
|
123
|
-
logs.application_logger.logger.info(
|
|
124
|
-
f"Sovereign started and listening on {asgi_config.host}:{asgi_config.port}"
|
|
125
|
-
)
|
|
126
137
|
|
|
127
138
|
|
|
128
139
|
if __name__ == "__main__": # pragma: no cover
|