orionis-installer 0.1.0__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.
- orionis_installer-0.1.0/.github/workflows/ci.yml +68 -0
- orionis_installer-0.1.0/.python-version +1 -0
- orionis_installer-0.1.0/LICENCE +21 -0
- orionis_installer-0.1.0/MANIFEST.in +8 -0
- orionis_installer-0.1.0/PKG-INFO +286 -0
- orionis_installer-0.1.0/README.md +266 -0
- orionis_installer-0.1.0/pyproject.toml +68 -0
- orionis_installer-0.1.0/scripts/verify_distribution.py +132 -0
- orionis_installer-0.1.0/setup.cfg +4 -0
- orionis_installer-0.1.0/src/orionis_installer/__init__.py +3 -0
- orionis_installer-0.1.0/src/orionis_installer/__main__.py +6 -0
- orionis_installer-0.1.0/src/orionis_installer/cli.py +343 -0
- orionis_installer-0.1.0/src/orionis_installer/configuration.py +397 -0
- orionis_installer-0.1.0/src/orionis_installer/exceptions.py +31 -0
- orionis_installer-0.1.0/src/orionis_installer/installer.py +391 -0
- orionis_installer-0.1.0/src/orionis_installer/messages.py +241 -0
- orionis_installer-0.1.0/src/orionis_installer/models.py +223 -0
- orionis_installer-0.1.0/src/orionis_installer/post_install.py +431 -0
- orionis_installer-0.1.0/src/orionis_installer/prerequisites.py +167 -0
- orionis_installer-0.1.0/src/orionis_installer/processes.py +767 -0
- orionis_installer-0.1.0/src/orionis_installer/py.typed +0 -0
- orionis_installer-0.1.0/src/orionis_installer/skeleton.py +282 -0
- orionis_installer-0.1.0/src/orionis_installer/ui/__init__.py +177 -0
- orionis_installer-0.1.0/src/orionis_installer/ui/messages.py +109 -0
- orionis_installer-0.1.0/src/orionis_installer/ui/output.py +228 -0
- orionis_installer-0.1.0/src/orionis_installer/ui/prompts.py +299 -0
- orionis_installer-0.1.0/src/orionis_installer/ui/theme.py +37 -0
- orionis_installer-0.1.0/src/orionis_installer/validation.py +151 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/PKG-INFO +286 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/SOURCES.txt +58 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/dependency_links.txt +1 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/entry_points.txt +2 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/requires.txt +6 -0
- orionis_installer-0.1.0/src/orionis_installer.egg-info/top_level.txt +1 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/.env.example +14 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/.gitignore +5 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/LICENCE +2 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/README.md +9 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/bootstrap/app.py +1 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/config/database.py +28 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/config/filesystems.py +19 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/database/.gitkeep +1 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/pyproject.toml +19 -0
- orionis_installer-0.1.0/tests/fixtures/skeleton/reactor +1 -0
- orionis_installer-0.1.0/tests/integration/test_offline.py +436 -0
- orionis_installer-0.1.0/tests/integration/test_real_smoke.py +76 -0
- orionis_installer-0.1.0/tests/unit/test_cli.py +703 -0
- orionis_installer-0.1.0/tests/unit/test_configuration.py +625 -0
- orionis_installer-0.1.0/tests/unit/test_contract_regressions.py +533 -0
- orionis_installer-0.1.0/tests/unit/test_documentation.py +43 -0
- orionis_installer-0.1.0/tests/unit/test_installer.py +555 -0
- orionis_installer-0.1.0/tests/unit/test_messages.py +61 -0
- orionis_installer-0.1.0/tests/unit/test_models.py +192 -0
- orionis_installer-0.1.0/tests/unit/test_post_install.py +647 -0
- orionis_installer-0.1.0/tests/unit/test_prerequisites.py +380 -0
- orionis_installer-0.1.0/tests/unit/test_processes.py +641 -0
- orionis_installer-0.1.0/tests/unit/test_skeleton.py +590 -0
- orionis_installer-0.1.0/tests/unit/test_ui.py +311 -0
- orionis_installer-0.1.0/tests/unit/test_validation.py +275 -0
- orionis_installer-0.1.0/uv.lock +576 -0
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
pull_request:
|
|
6
|
+
workflow_dispatch:
|
|
7
|
+
|
|
8
|
+
permissions:
|
|
9
|
+
contents: read
|
|
10
|
+
|
|
11
|
+
jobs:
|
|
12
|
+
checks:
|
|
13
|
+
name: Python 3.14 / ${{ matrix.os }}
|
|
14
|
+
runs-on: ${{ matrix.os }}
|
|
15
|
+
timeout-minutes: 20
|
|
16
|
+
strategy:
|
|
17
|
+
fail-fast: false
|
|
18
|
+
matrix:
|
|
19
|
+
os: [ubuntu-latest, windows-latest, macos-latest]
|
|
20
|
+
env:
|
|
21
|
+
NO_COLOR: "1"
|
|
22
|
+
UV_NO_PROGRESS: "1"
|
|
23
|
+
ORIONIS_REAL_SMOKE: "0"
|
|
24
|
+
steps:
|
|
25
|
+
# Official revisions in uv's GitHub guide, inspected 2026-10-06.
|
|
26
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
|
|
27
|
+
with:
|
|
28
|
+
persist-credentials: false
|
|
29
|
+
- uses: actions/setup-python@5fda3b95a4ea91299a34e894583c3862153e4b97 # v7.0.0
|
|
30
|
+
with:
|
|
31
|
+
python-version: "3.14"
|
|
32
|
+
- uses: astral-sh/setup-uv@c771a70e6277c0a99b617c7a806ffedaca235ff9 # v9.0.0
|
|
33
|
+
with:
|
|
34
|
+
version: "0.11.30"
|
|
35
|
+
enable-cache: true
|
|
36
|
+
- name: Sync development environment
|
|
37
|
+
run: uv sync --locked --python 3.14
|
|
38
|
+
- name: Ruff and format
|
|
39
|
+
run: |
|
|
40
|
+
uv run --no-sync ruff check .
|
|
41
|
+
uv run --no-sync ruff format --check .
|
|
42
|
+
- name: Static types
|
|
43
|
+
run: uv run --no-sync mypy
|
|
44
|
+
- name: Offline and unit tests
|
|
45
|
+
run: uv run --no-sync pytest --cov=orionis_installer --cov-report=term-missing --cov-report=xml
|
|
46
|
+
- name: Build wheel and source distribution
|
|
47
|
+
run: uv build
|
|
48
|
+
- name: Clean wheel environment and entry point
|
|
49
|
+
shell: bash
|
|
50
|
+
run: |
|
|
51
|
+
python - <<'PY'
|
|
52
|
+
import os
|
|
53
|
+
import pathlib
|
|
54
|
+
import subprocess
|
|
55
|
+
import tempfile
|
|
56
|
+
|
|
57
|
+
wheel, = pathlib.Path("dist").glob("*.whl")
|
|
58
|
+
with tempfile.TemporaryDirectory(prefix="orionis-wheel-") as temporary:
|
|
59
|
+
environment = pathlib.Path(temporary) / "clean"
|
|
60
|
+
subprocess.run(["uv", "venv", str(environment), "--python", "3.14"], check=True)
|
|
61
|
+
scripts = environment / ("Scripts" if os.name == "nt" else "bin")
|
|
62
|
+
python = scripts / ("python.exe" if os.name == "nt" else "python")
|
|
63
|
+
entry = scripts / ("orionis.exe" if os.name == "nt" else "orionis")
|
|
64
|
+
subprocess.run(["uv", "pip", "install", "--python", str(python), str(wheel.resolve())], check=True)
|
|
65
|
+
for arguments in (["--version"], ["--help"], ["new", "--help"]):
|
|
66
|
+
subprocess.run([str(entry), *arguments], cwd=temporary, check=True)
|
|
67
|
+
subprocess.run(["uvx", "--python", "3.14", "--from", str(wheel.resolve()), "orionis", "--version"], cwd=temporary, check=True)
|
|
68
|
+
PY
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
3.14
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2023 - 2025 RAÚL MAURICIO UÑATE CASTRO
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
include README.md LICENCE pyproject.toml uv.lock .python-version
|
|
2
|
+
recursive-include src *.py py.typed
|
|
3
|
+
recursive-include tests *.py *.toml *.md *.example .gitignore .gitkeep LICENCE reactor
|
|
4
|
+
recursive-include docs *.md *.patch
|
|
5
|
+
recursive-include scripts *.py
|
|
6
|
+
recursive-include .github *.yml
|
|
7
|
+
global-exclude *.py[cod]
|
|
8
|
+
global-exclude __pycache__
|
|
@@ -0,0 +1,286 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: orionis-installer
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Create Orionis applications with isolated Python environments.
|
|
5
|
+
License-Expression: MIT
|
|
6
|
+
Classifier: Environment :: Console
|
|
7
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
8
|
+
Classifier: Operating System :: OS Independent
|
|
9
|
+
Classifier: Typing :: Typed
|
|
10
|
+
Requires-Python: >=3.14
|
|
11
|
+
Description-Content-Type: text/markdown
|
|
12
|
+
License-File: LICENCE
|
|
13
|
+
Requires-Dist: typer<0.28,>=0.27.3
|
|
14
|
+
Requires-Dist: rich<16,>=15.0.0
|
|
15
|
+
Requires-Dist: prompt-toolkit<4,>=3.0.53
|
|
16
|
+
Requires-Dist: tomlkit<0.16,>=0.15.1
|
|
17
|
+
Requires-Dist: packaging<27,>=26.3
|
|
18
|
+
Requires-Dist: python-dotenv<2,>=1.2.4
|
|
19
|
+
Dynamic: license-file
|
|
20
|
+
|
|
21
|
+
# Orionis Installer
|
|
22
|
+
|
|
23
|
+
`orionis-installer` creates applications from the official Orionis skeleton on
|
|
24
|
+
`master`, with Python **3.14.x**, a project-local `.venv` and `uv.lock`. Its Python
|
|
25
|
+
module is `orionis_installer` and its executable is **`orionis`**.
|
|
26
|
+
|
|
27
|
+
The installer depends on CLI and configuration libraries. Orionis, database
|
|
28
|
+
drivers, cloud SDKs and Faker belong to the generated application's environment.
|
|
29
|
+
The English wizard supports arrow keys, Enter, visible defaults and immediate
|
|
30
|
+
validation. Its ASCII banner adapts to narrow terminals; `NO_COLOR` and
|
|
31
|
+
`--no-color` disable colors.
|
|
32
|
+
|
|
33
|
+
## Installation
|
|
34
|
+
|
|
35
|
+
Install [uv](https://docs.astral.sh/uv/getting-started/installation/) and
|
|
36
|
+
[Git](https://git-scm.com/downloads). Python 3.14 or newer runs the installer; uv
|
|
37
|
+
selects stable Python 3.14.x for the application and can obtain it according to
|
|
38
|
+
its download and network policies.
|
|
39
|
+
|
|
40
|
+
When this distribution is available on your package index:
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
uvx --from orionis-installer orionis new
|
|
44
|
+
uvx --from orionis-installer orionis new blog
|
|
45
|
+
uvx --python 3.14 --from orionis-installer orionis new
|
|
46
|
+
uv tool install --python 3.14 orionis-installer
|
|
47
|
+
orionis new blog
|
|
48
|
+
orionis --help
|
|
49
|
+
orionis --version
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
`uvx --python 3.14` selects the **installer's** interpreter. The application has an
|
|
53
|
+
independent environment. The framework can also provide an `orionis` executable;
|
|
54
|
+
invoke the installer through `uvx --from orionis-installer orionis ...` and use
|
|
55
|
+
Reactor through the application's Python. Do not overwrite existing executables
|
|
56
|
+
with force flags.
|
|
57
|
+
|
|
58
|
+
For a local build:
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
uv build
|
|
62
|
+
uvx --python 3.14 --from ./dist/orionis_installer-0.1.0-py3-none-any.whl orionis --version
|
|
63
|
+
uvx --python 3.14 --from ./dist/orionis_installer-0.1.0-py3-none-any.whl orionis new blog
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
## Interactive wizard
|
|
67
|
+
|
|
68
|
+
After checking prerequisites, the wizard requests:
|
|
69
|
+
|
|
70
|
+
1. Application name, defaulting to `orionis-app`; `new blog` supplies it directly.
|
|
71
|
+
2. Description, defaulting to `A modern application built with Orionis Framework.`
|
|
72
|
+
3. Optional author name and email.
|
|
73
|
+
4. File storage drivers and, for `all`, the default disk.
|
|
74
|
+
5. Database drivers and, for `all`, the default connection.
|
|
75
|
+
6. Confirmation of the absolute destination, Python target, extras and source.
|
|
76
|
+
|
|
77
|
+
Explicit options skip their corresponding questions. After installation, the
|
|
78
|
+
wizard asks about Git initialization (Yes), migrations and initial seeders (No),
|
|
79
|
+
and Visual Studio Code (Yes), in that order. Ctrl+C cancels with exit code 130.
|
|
80
|
+
Without a TTY, use `--no-interaction`; help and version remain available.
|
|
81
|
+
|
|
82
|
+
Names use 1–100 ASCII letters, digits, dots, hyphens and underscores, with
|
|
83
|
+
alphanumeric endpoints. Path separators, traversal, controls and reserved
|
|
84
|
+
Windows names are rejected. Author names and descriptions support Unicode;
|
|
85
|
+
`--path` supports spaces and Unicode. Invalid names are diagnosed without silent
|
|
86
|
+
normalization. An existing destination is always rejected, even when empty.
|
|
87
|
+
|
|
88
|
+
## Non-interactive use
|
|
89
|
+
|
|
90
|
+
```bash
|
|
91
|
+
orionis new blog --no-interaction
|
|
92
|
+
orionis new blog --no-interaction --git --no-migrate --no-open
|
|
93
|
+
orionis new analytics --no-interaction --storage s3 --database redshift
|
|
94
|
+
orionis new team --no-interaction --storage all --database all
|
|
95
|
+
orionis new blog --no-interaction --path "./Project with spaces" --author-name "Jane Doe" --author-email jane@example.com
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Defaults are `orionis-app`, the description above, no author, local storage and
|
|
99
|
+
SQLite. Aggregate driver selections default to local storage and SQLite unless
|
|
100
|
+
specified otherwise. Git, migrations and the editor are skipped unless their
|
|
101
|
+
positive flags are provided. This mode never requests credentials.
|
|
102
|
+
|
|
103
|
+
## CLI options
|
|
104
|
+
|
|
105
|
+
`--version`, `--no-color` and `--verbose` are global options. `--no-color` and
|
|
106
|
+
`--verbose` also work after `new`. Other options belong to `new`:
|
|
107
|
+
|
|
108
|
+
| Option | Behavior |
|
|
109
|
+
| --- | --- |
|
|
110
|
+
| `new [NAME]` | Application name and default folder name. |
|
|
111
|
+
| `--path PATH` | Final project location; its parent must exist. |
|
|
112
|
+
| `--description TEXT` | Application description. |
|
|
113
|
+
| `--author-name TEXT`, `--author-email TEXT` | Optional author metadata; empty values omit a field. |
|
|
114
|
+
| `--storage local\|s3\|azure\|gcs\|all` | File storage drivers to install. |
|
|
115
|
+
| `--default-storage local\|s3\|azure\|gcs` | Active disk with `all`; defaults to local. |
|
|
116
|
+
| `--database sqlite\|mysql\|pgsql\|oracle\|sqlserver\|redshift\|all` | Database drivers to install. |
|
|
117
|
+
| `--default-database sqlite\|mysql\|pgsql\|oracle\|sqlserver\|redshift` | Active connection with `all`; defaults to SQLite. |
|
|
118
|
+
| `--git / --no-git` | Initialize Git or skip it. |
|
|
119
|
+
| `--migrate / --no-migrate` | Request migrations and initial seeders or skip them. |
|
|
120
|
+
| `--open / --no-open` | Open Visual Studio Code or skip it. |
|
|
121
|
+
| `--no-interaction` | Apply safe defaults without reading input. |
|
|
122
|
+
| `--no-color` | Disable colors; also respects `NO_COLOR`, including an empty value. |
|
|
123
|
+
| `--verbose` | Show plan diagnostics without raw subprocess output or secrets. |
|
|
124
|
+
|
|
125
|
+
A default driver must be concrete. Without `all`, it can only repeat the selected
|
|
126
|
+
driver. There is no destructive `--force` option.
|
|
127
|
+
|
|
128
|
+
## Drivers and configuration
|
|
129
|
+
|
|
130
|
+
| Storage selection | Orionis extra |
|
|
131
|
+
| --- | --- |
|
|
132
|
+
| `local` | None |
|
|
133
|
+
| `s3` | `s3` |
|
|
134
|
+
| `azure` | `azure` |
|
|
135
|
+
| `gcs` | `gcs` |
|
|
136
|
+
| `all` | `storage` |
|
|
137
|
+
|
|
138
|
+
| Database selection | Orionis extra |
|
|
139
|
+
| --- | --- |
|
|
140
|
+
| `sqlite` | None |
|
|
141
|
+
| `mysql` | `mysql` |
|
|
142
|
+
| `pgsql` | `pgsql` |
|
|
143
|
+
| `oracle` | `oracle` |
|
|
144
|
+
| `sqlserver` | `sqlserver` |
|
|
145
|
+
| `redshift` | `redshift` |
|
|
146
|
+
| `all` | `database` |
|
|
147
|
+
|
|
148
|
+
Every application includes `factories`. Extras are sorted and deduplicated:
|
|
149
|
+
local + SQLite uses `factories`; S3 + Redshift uses `factories,redshift,s3`; both
|
|
150
|
+
aggregate selections use `database,factories,storage`. Aggregate extras install
|
|
151
|
+
drivers while migrations use one concrete connection. Installing an SDK creates
|
|
152
|
+
no buckets, accounts, permissions or infrastructure.
|
|
153
|
+
|
|
154
|
+
The installer preserves TOML comments, valid dependency groups, the application's
|
|
155
|
+
version and the skeleton's Orionis requirement. The application remains
|
|
156
|
+
unpackaged through `tool.uv.package = false`. `.env.example` is preferred;
|
|
157
|
+
`env.example` is supported. Only verified configuration keys are changed, and the
|
|
158
|
+
example remains intact. External connections and cloud storage require subsequent
|
|
159
|
+
credential configuration. See the [inspected contract](docs/sources.md).
|
|
160
|
+
|
|
161
|
+
APP_KEY is generated by the framework using the project interpreter, without
|
|
162
|
+
`--force`; existing keys are preserved. The official skeleton's administrative
|
|
163
|
+
seeder uses static example credentials, so automatic `--migrate` is blocked
|
|
164
|
+
before data changes. Review the [separate hardening patch](docs/seeder-hardening.patch)
|
|
165
|
+
and configure independent administrator credentials before manually running
|
|
166
|
+
Reactor. The installer does not automatically certify modified seeder code.
|
|
167
|
+
|
|
168
|
+
## Installation and recovery
|
|
169
|
+
|
|
170
|
+
The installer clones only the official `master` branch into a sibling staging
|
|
171
|
+
area, validates it, records its SHA and removes only that clone's `.git`. It
|
|
172
|
+
configures files before publication and then runs one main
|
|
173
|
+
`uv sync --python 3.14` at the final location. `.venv` is never moved from staging.
|
|
174
|
+
Python, the installed Orionis distribution, extras, lockfile, APP_KEY and effective
|
|
175
|
+
configuration are checked before reporting success.
|
|
176
|
+
|
|
177
|
+
Failures before publication clean only owned staging files. Failures after
|
|
178
|
+
publication preserve the project and report recovery steps. The operation is not
|
|
179
|
+
fully atomic across files, dependencies and database changes. An inherited uv
|
|
180
|
+
workspace or custom `UV_CONFIG_FILE` is rejected to protect isolation; use uv's
|
|
181
|
+
conventional configuration or documented environment variables for network,
|
|
182
|
+
index and download policies. See [security and isolation](docs/security.md).
|
|
183
|
+
|
|
184
|
+
| Exit code | Meaning |
|
|
185
|
+
| --- | --- |
|
|
186
|
+
| `0` | Application ready; requested operations completed or skipped, or confirmation declined. |
|
|
187
|
+
| `1` | Critical download, configuration, publication or installation failure. |
|
|
188
|
+
| `2` | Invalid arguments, missing prerequisites or an incompatible contract. |
|
|
189
|
+
| `3` | Project created, but a requested post-install operation failed. |
|
|
190
|
+
| `130` | User cancellation or end of input. |
|
|
191
|
+
|
|
192
|
+
Git runs only `git init`. It creates no commit, remote or push. Git and editor
|
|
193
|
+
failures preserve the project; independent post-install operations still run
|
|
194
|
+
unless cancelled. A failed migration may have changed data: inspect the database
|
|
195
|
+
before retrying. No automatic rollback or `migrate:fresh` is performed.
|
|
196
|
+
|
|
197
|
+
For a preserved project, review its configuration before recovering:
|
|
198
|
+
|
|
199
|
+
```bash
|
|
200
|
+
cd blog
|
|
201
|
+
uv sync --python 3.14
|
|
202
|
+
uv run python -B reactor key:generate
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
Start a ready application:
|
|
206
|
+
|
|
207
|
+
```bash
|
|
208
|
+
cd blog
|
|
209
|
+
uv run python -B reactor serve
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
After reviewing the connection and securing the seeders:
|
|
213
|
+
|
|
214
|
+
```bash
|
|
215
|
+
uv run python -B reactor migrate --seed
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
## Development
|
|
219
|
+
|
|
220
|
+
```bash
|
|
221
|
+
uv sync --locked --python 3.14
|
|
222
|
+
uv run --no-sync ruff check .
|
|
223
|
+
uv run --no-sync ruff format --check .
|
|
224
|
+
uv run --no-sync mypy
|
|
225
|
+
uv run --no-sync pytest --cov=orionis_installer --cov-report=term-missing
|
|
226
|
+
uv build
|
|
227
|
+
uv run --no-sync python scripts/verify_distribution.py
|
|
228
|
+
```
|
|
229
|
+
|
|
230
|
+
Normal tests use controlled terminal input, disposable processes and explicit
|
|
231
|
+
fixtures. Offline integration uses a local Git repository with simulated uv and
|
|
232
|
+
framework responses; it does not require Orionis or a network connection. The
|
|
233
|
+
distribution verification script installs the wheel into a clean temporary
|
|
234
|
+
environment and creates a disposable application through real uvx.
|
|
235
|
+
|
|
236
|
+
Enable the real smoke test explicitly. It uses the official skeleton, uv and a
|
|
237
|
+
disposable SQLite database, without running the example administrator seeder:
|
|
238
|
+
|
|
239
|
+
```bash
|
|
240
|
+
ORIONIS_REAL_SMOKE=1 uv run --no-sync pytest -m smoke -v
|
|
241
|
+
```
|
|
242
|
+
|
|
243
|
+
```powershell
|
|
244
|
+
$env:ORIONIS_REAL_SMOKE = '1'
|
|
245
|
+
uv run --no-sync pytest -m smoke -v
|
|
246
|
+
Remove-Item Env:ORIONIS_REAL_SMOKE
|
|
247
|
+
```
|
|
248
|
+
|
|
249
|
+
[CI](.github/workflows/ci.yml) checks Python 3.14 on Ubuntu, Windows and macOS,
|
|
250
|
+
including lint, formatting, types, tests, build and the clean-wheel entry point.
|
|
251
|
+
Runtime checks on an individual machine do not verify the other platforms or
|
|
252
|
+
external cloud/database services. CI does not publish the package.
|
|
253
|
+
|
|
254
|
+
Follow the English, typed documentation style of
|
|
255
|
+
[Orionis commands](https://github.com/orionis-framework/framework/blob/1.x/orionis/console/commands/support/key_generate.py)
|
|
256
|
+
and [configuration entities](https://github.com/orionis-framework/framework/blob/1.x/orionis/foundation/config/database/entities/connections.py).
|
|
257
|
+
Use concise triple-double-quoted NumPy docstrings for every function and method,
|
|
258
|
+
including private helpers and callbacks. Start with an imperative sentence;
|
|
259
|
+
include relevant Parameters, Returns, Yields and Raises sections, without an
|
|
260
|
+
Examples section. Ruff enforces the NumPy convention and D401; an AST-based test
|
|
261
|
+
checks documentation coverage for nested and private functions as well.
|
|
262
|
+
|
|
263
|
+
Source lives in `src/orionis_installer`; unit and integration tests live in
|
|
264
|
+
`tests`; technical contracts and policies live in `docs`; distribution verification
|
|
265
|
+
lives in `scripts`. Message catalogs remain centralized in `messages.py` and
|
|
266
|
+
`ui/messages.py`. Dependency constraints are declared in [pyproject.toml](pyproject.toml)
|
|
267
|
+
and development resolutions in [uv.lock](uv.lock). License: [MIT](LICENCE).
|
|
268
|
+
|
|
269
|
+
## Releasing to PyPI
|
|
270
|
+
|
|
271
|
+
Update the version in `pyproject.toml` and `src/orionis_installer/__init__.py`
|
|
272
|
+
together before a release. Configure PyPI authentication through
|
|
273
|
+
`UV_PUBLISH_TOKEN` or another [supported uv authentication method](https://docs.astral.sh/uv/guides/package/#publishing-your-package).
|
|
274
|
+
Run the root release script from PowerShell:
|
|
275
|
+
|
|
276
|
+
```powershell
|
|
277
|
+
.\release.ps1
|
|
278
|
+
```
|
|
279
|
+
|
|
280
|
+
The script requires `main` and an `origin` remote. It reads the manifest version,
|
|
281
|
+
cleans old builds, synchronizes Python 3.14, builds wheel/sdist, publishes to PyPI,
|
|
282
|
+
stages all changes, commits the release and pushes `main`. Versions with a major
|
|
283
|
+
component of at least 1 also create and push `v<version>` after checking for tag
|
|
284
|
+
conflicts. Successful releases clean generated builds. Failures stop the remaining
|
|
285
|
+
steps and retain artifacts for inspection or retry; completed uploads and Git
|
|
286
|
+
operations are not rolled back.
|
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
# Orionis Installer
|
|
2
|
+
|
|
3
|
+
`orionis-installer` creates applications from the official Orionis skeleton on
|
|
4
|
+
`master`, with Python **3.14.x**, a project-local `.venv` and `uv.lock`. Its Python
|
|
5
|
+
module is `orionis_installer` and its executable is **`orionis`**.
|
|
6
|
+
|
|
7
|
+
The installer depends on CLI and configuration libraries. Orionis, database
|
|
8
|
+
drivers, cloud SDKs and Faker belong to the generated application's environment.
|
|
9
|
+
The English wizard supports arrow keys, Enter, visible defaults and immediate
|
|
10
|
+
validation. Its ASCII banner adapts to narrow terminals; `NO_COLOR` and
|
|
11
|
+
`--no-color` disable colors.
|
|
12
|
+
|
|
13
|
+
## Installation
|
|
14
|
+
|
|
15
|
+
Install [uv](https://docs.astral.sh/uv/getting-started/installation/) and
|
|
16
|
+
[Git](https://git-scm.com/downloads). Python 3.14 or newer runs the installer; uv
|
|
17
|
+
selects stable Python 3.14.x for the application and can obtain it according to
|
|
18
|
+
its download and network policies.
|
|
19
|
+
|
|
20
|
+
When this distribution is available on your package index:
|
|
21
|
+
|
|
22
|
+
```bash
|
|
23
|
+
uvx --from orionis-installer orionis new
|
|
24
|
+
uvx --from orionis-installer orionis new blog
|
|
25
|
+
uvx --python 3.14 --from orionis-installer orionis new
|
|
26
|
+
uv tool install --python 3.14 orionis-installer
|
|
27
|
+
orionis new blog
|
|
28
|
+
orionis --help
|
|
29
|
+
orionis --version
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
`uvx --python 3.14` selects the **installer's** interpreter. The application has an
|
|
33
|
+
independent environment. The framework can also provide an `orionis` executable;
|
|
34
|
+
invoke the installer through `uvx --from orionis-installer orionis ...` and use
|
|
35
|
+
Reactor through the application's Python. Do not overwrite existing executables
|
|
36
|
+
with force flags.
|
|
37
|
+
|
|
38
|
+
For a local build:
|
|
39
|
+
|
|
40
|
+
```bash
|
|
41
|
+
uv build
|
|
42
|
+
uvx --python 3.14 --from ./dist/orionis_installer-0.1.0-py3-none-any.whl orionis --version
|
|
43
|
+
uvx --python 3.14 --from ./dist/orionis_installer-0.1.0-py3-none-any.whl orionis new blog
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
## Interactive wizard
|
|
47
|
+
|
|
48
|
+
After checking prerequisites, the wizard requests:
|
|
49
|
+
|
|
50
|
+
1. Application name, defaulting to `orionis-app`; `new blog` supplies it directly.
|
|
51
|
+
2. Description, defaulting to `A modern application built with Orionis Framework.`
|
|
52
|
+
3. Optional author name and email.
|
|
53
|
+
4. File storage drivers and, for `all`, the default disk.
|
|
54
|
+
5. Database drivers and, for `all`, the default connection.
|
|
55
|
+
6. Confirmation of the absolute destination, Python target, extras and source.
|
|
56
|
+
|
|
57
|
+
Explicit options skip their corresponding questions. After installation, the
|
|
58
|
+
wizard asks about Git initialization (Yes), migrations and initial seeders (No),
|
|
59
|
+
and Visual Studio Code (Yes), in that order. Ctrl+C cancels with exit code 130.
|
|
60
|
+
Without a TTY, use `--no-interaction`; help and version remain available.
|
|
61
|
+
|
|
62
|
+
Names use 1–100 ASCII letters, digits, dots, hyphens and underscores, with
|
|
63
|
+
alphanumeric endpoints. Path separators, traversal, controls and reserved
|
|
64
|
+
Windows names are rejected. Author names and descriptions support Unicode;
|
|
65
|
+
`--path` supports spaces and Unicode. Invalid names are diagnosed without silent
|
|
66
|
+
normalization. An existing destination is always rejected, even when empty.
|
|
67
|
+
|
|
68
|
+
## Non-interactive use
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
orionis new blog --no-interaction
|
|
72
|
+
orionis new blog --no-interaction --git --no-migrate --no-open
|
|
73
|
+
orionis new analytics --no-interaction --storage s3 --database redshift
|
|
74
|
+
orionis new team --no-interaction --storage all --database all
|
|
75
|
+
orionis new blog --no-interaction --path "./Project with spaces" --author-name "Jane Doe" --author-email jane@example.com
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
Defaults are `orionis-app`, the description above, no author, local storage and
|
|
79
|
+
SQLite. Aggregate driver selections default to local storage and SQLite unless
|
|
80
|
+
specified otherwise. Git, migrations and the editor are skipped unless their
|
|
81
|
+
positive flags are provided. This mode never requests credentials.
|
|
82
|
+
|
|
83
|
+
## CLI options
|
|
84
|
+
|
|
85
|
+
`--version`, `--no-color` and `--verbose` are global options. `--no-color` and
|
|
86
|
+
`--verbose` also work after `new`. Other options belong to `new`:
|
|
87
|
+
|
|
88
|
+
| Option | Behavior |
|
|
89
|
+
| --- | --- |
|
|
90
|
+
| `new [NAME]` | Application name and default folder name. |
|
|
91
|
+
| `--path PATH` | Final project location; its parent must exist. |
|
|
92
|
+
| `--description TEXT` | Application description. |
|
|
93
|
+
| `--author-name TEXT`, `--author-email TEXT` | Optional author metadata; empty values omit a field. |
|
|
94
|
+
| `--storage local\|s3\|azure\|gcs\|all` | File storage drivers to install. |
|
|
95
|
+
| `--default-storage local\|s3\|azure\|gcs` | Active disk with `all`; defaults to local. |
|
|
96
|
+
| `--database sqlite\|mysql\|pgsql\|oracle\|sqlserver\|redshift\|all` | Database drivers to install. |
|
|
97
|
+
| `--default-database sqlite\|mysql\|pgsql\|oracle\|sqlserver\|redshift` | Active connection with `all`; defaults to SQLite. |
|
|
98
|
+
| `--git / --no-git` | Initialize Git or skip it. |
|
|
99
|
+
| `--migrate / --no-migrate` | Request migrations and initial seeders or skip them. |
|
|
100
|
+
| `--open / --no-open` | Open Visual Studio Code or skip it. |
|
|
101
|
+
| `--no-interaction` | Apply safe defaults without reading input. |
|
|
102
|
+
| `--no-color` | Disable colors; also respects `NO_COLOR`, including an empty value. |
|
|
103
|
+
| `--verbose` | Show plan diagnostics without raw subprocess output or secrets. |
|
|
104
|
+
|
|
105
|
+
A default driver must be concrete. Without `all`, it can only repeat the selected
|
|
106
|
+
driver. There is no destructive `--force` option.
|
|
107
|
+
|
|
108
|
+
## Drivers and configuration
|
|
109
|
+
|
|
110
|
+
| Storage selection | Orionis extra |
|
|
111
|
+
| --- | --- |
|
|
112
|
+
| `local` | None |
|
|
113
|
+
| `s3` | `s3` |
|
|
114
|
+
| `azure` | `azure` |
|
|
115
|
+
| `gcs` | `gcs` |
|
|
116
|
+
| `all` | `storage` |
|
|
117
|
+
|
|
118
|
+
| Database selection | Orionis extra |
|
|
119
|
+
| --- | --- |
|
|
120
|
+
| `sqlite` | None |
|
|
121
|
+
| `mysql` | `mysql` |
|
|
122
|
+
| `pgsql` | `pgsql` |
|
|
123
|
+
| `oracle` | `oracle` |
|
|
124
|
+
| `sqlserver` | `sqlserver` |
|
|
125
|
+
| `redshift` | `redshift` |
|
|
126
|
+
| `all` | `database` |
|
|
127
|
+
|
|
128
|
+
Every application includes `factories`. Extras are sorted and deduplicated:
|
|
129
|
+
local + SQLite uses `factories`; S3 + Redshift uses `factories,redshift,s3`; both
|
|
130
|
+
aggregate selections use `database,factories,storage`. Aggregate extras install
|
|
131
|
+
drivers while migrations use one concrete connection. Installing an SDK creates
|
|
132
|
+
no buckets, accounts, permissions or infrastructure.
|
|
133
|
+
|
|
134
|
+
The installer preserves TOML comments, valid dependency groups, the application's
|
|
135
|
+
version and the skeleton's Orionis requirement. The application remains
|
|
136
|
+
unpackaged through `tool.uv.package = false`. `.env.example` is preferred;
|
|
137
|
+
`env.example` is supported. Only verified configuration keys are changed, and the
|
|
138
|
+
example remains intact. External connections and cloud storage require subsequent
|
|
139
|
+
credential configuration. See the [inspected contract](docs/sources.md).
|
|
140
|
+
|
|
141
|
+
APP_KEY is generated by the framework using the project interpreter, without
|
|
142
|
+
`--force`; existing keys are preserved. The official skeleton's administrative
|
|
143
|
+
seeder uses static example credentials, so automatic `--migrate` is blocked
|
|
144
|
+
before data changes. Review the [separate hardening patch](docs/seeder-hardening.patch)
|
|
145
|
+
and configure independent administrator credentials before manually running
|
|
146
|
+
Reactor. The installer does not automatically certify modified seeder code.
|
|
147
|
+
|
|
148
|
+
## Installation and recovery
|
|
149
|
+
|
|
150
|
+
The installer clones only the official `master` branch into a sibling staging
|
|
151
|
+
area, validates it, records its SHA and removes only that clone's `.git`. It
|
|
152
|
+
configures files before publication and then runs one main
|
|
153
|
+
`uv sync --python 3.14` at the final location. `.venv` is never moved from staging.
|
|
154
|
+
Python, the installed Orionis distribution, extras, lockfile, APP_KEY and effective
|
|
155
|
+
configuration are checked before reporting success.
|
|
156
|
+
|
|
157
|
+
Failures before publication clean only owned staging files. Failures after
|
|
158
|
+
publication preserve the project and report recovery steps. The operation is not
|
|
159
|
+
fully atomic across files, dependencies and database changes. An inherited uv
|
|
160
|
+
workspace or custom `UV_CONFIG_FILE` is rejected to protect isolation; use uv's
|
|
161
|
+
conventional configuration or documented environment variables for network,
|
|
162
|
+
index and download policies. See [security and isolation](docs/security.md).
|
|
163
|
+
|
|
164
|
+
| Exit code | Meaning |
|
|
165
|
+
| --- | --- |
|
|
166
|
+
| `0` | Application ready; requested operations completed or skipped, or confirmation declined. |
|
|
167
|
+
| `1` | Critical download, configuration, publication or installation failure. |
|
|
168
|
+
| `2` | Invalid arguments, missing prerequisites or an incompatible contract. |
|
|
169
|
+
| `3` | Project created, but a requested post-install operation failed. |
|
|
170
|
+
| `130` | User cancellation or end of input. |
|
|
171
|
+
|
|
172
|
+
Git runs only `git init`. It creates no commit, remote or push. Git and editor
|
|
173
|
+
failures preserve the project; independent post-install operations still run
|
|
174
|
+
unless cancelled. A failed migration may have changed data: inspect the database
|
|
175
|
+
before retrying. No automatic rollback or `migrate:fresh` is performed.
|
|
176
|
+
|
|
177
|
+
For a preserved project, review its configuration before recovering:
|
|
178
|
+
|
|
179
|
+
```bash
|
|
180
|
+
cd blog
|
|
181
|
+
uv sync --python 3.14
|
|
182
|
+
uv run python -B reactor key:generate
|
|
183
|
+
```
|
|
184
|
+
|
|
185
|
+
Start a ready application:
|
|
186
|
+
|
|
187
|
+
```bash
|
|
188
|
+
cd blog
|
|
189
|
+
uv run python -B reactor serve
|
|
190
|
+
```
|
|
191
|
+
|
|
192
|
+
After reviewing the connection and securing the seeders:
|
|
193
|
+
|
|
194
|
+
```bash
|
|
195
|
+
uv run python -B reactor migrate --seed
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
## Development
|
|
199
|
+
|
|
200
|
+
```bash
|
|
201
|
+
uv sync --locked --python 3.14
|
|
202
|
+
uv run --no-sync ruff check .
|
|
203
|
+
uv run --no-sync ruff format --check .
|
|
204
|
+
uv run --no-sync mypy
|
|
205
|
+
uv run --no-sync pytest --cov=orionis_installer --cov-report=term-missing
|
|
206
|
+
uv build
|
|
207
|
+
uv run --no-sync python scripts/verify_distribution.py
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
Normal tests use controlled terminal input, disposable processes and explicit
|
|
211
|
+
fixtures. Offline integration uses a local Git repository with simulated uv and
|
|
212
|
+
framework responses; it does not require Orionis or a network connection. The
|
|
213
|
+
distribution verification script installs the wheel into a clean temporary
|
|
214
|
+
environment and creates a disposable application through real uvx.
|
|
215
|
+
|
|
216
|
+
Enable the real smoke test explicitly. It uses the official skeleton, uv and a
|
|
217
|
+
disposable SQLite database, without running the example administrator seeder:
|
|
218
|
+
|
|
219
|
+
```bash
|
|
220
|
+
ORIONIS_REAL_SMOKE=1 uv run --no-sync pytest -m smoke -v
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
```powershell
|
|
224
|
+
$env:ORIONIS_REAL_SMOKE = '1'
|
|
225
|
+
uv run --no-sync pytest -m smoke -v
|
|
226
|
+
Remove-Item Env:ORIONIS_REAL_SMOKE
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
[CI](.github/workflows/ci.yml) checks Python 3.14 on Ubuntu, Windows and macOS,
|
|
230
|
+
including lint, formatting, types, tests, build and the clean-wheel entry point.
|
|
231
|
+
Runtime checks on an individual machine do not verify the other platforms or
|
|
232
|
+
external cloud/database services. CI does not publish the package.
|
|
233
|
+
|
|
234
|
+
Follow the English, typed documentation style of
|
|
235
|
+
[Orionis commands](https://github.com/orionis-framework/framework/blob/1.x/orionis/console/commands/support/key_generate.py)
|
|
236
|
+
and [configuration entities](https://github.com/orionis-framework/framework/blob/1.x/orionis/foundation/config/database/entities/connections.py).
|
|
237
|
+
Use concise triple-double-quoted NumPy docstrings for every function and method,
|
|
238
|
+
including private helpers and callbacks. Start with an imperative sentence;
|
|
239
|
+
include relevant Parameters, Returns, Yields and Raises sections, without an
|
|
240
|
+
Examples section. Ruff enforces the NumPy convention and D401; an AST-based test
|
|
241
|
+
checks documentation coverage for nested and private functions as well.
|
|
242
|
+
|
|
243
|
+
Source lives in `src/orionis_installer`; unit and integration tests live in
|
|
244
|
+
`tests`; technical contracts and policies live in `docs`; distribution verification
|
|
245
|
+
lives in `scripts`. Message catalogs remain centralized in `messages.py` and
|
|
246
|
+
`ui/messages.py`. Dependency constraints are declared in [pyproject.toml](pyproject.toml)
|
|
247
|
+
and development resolutions in [uv.lock](uv.lock). License: [MIT](LICENCE).
|
|
248
|
+
|
|
249
|
+
## Releasing to PyPI
|
|
250
|
+
|
|
251
|
+
Update the version in `pyproject.toml` and `src/orionis_installer/__init__.py`
|
|
252
|
+
together before a release. Configure PyPI authentication through
|
|
253
|
+
`UV_PUBLISH_TOKEN` or another [supported uv authentication method](https://docs.astral.sh/uv/guides/package/#publishing-your-package).
|
|
254
|
+
Run the root release script from PowerShell:
|
|
255
|
+
|
|
256
|
+
```powershell
|
|
257
|
+
.\release.ps1
|
|
258
|
+
```
|
|
259
|
+
|
|
260
|
+
The script requires `main` and an `origin` remote. It reads the manifest version,
|
|
261
|
+
cleans old builds, synchronizes Python 3.14, builds wheel/sdist, publishes to PyPI,
|
|
262
|
+
stages all changes, commits the release and pushes `main`. Versions with a major
|
|
263
|
+
component of at least 1 also create and push `v<version>` after checking for tag
|
|
264
|
+
conflicts. Successful releases clean generated builds. Failures stop the remaining
|
|
265
|
+
steps and retain artifacts for inspection or retry; completed uploads and Git
|
|
266
|
+
operations are not rolled back.
|