odoo-devops-tools 1.9.2__tar.gz → 1.10.2__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.
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/PKG-INFO +35 -7
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/README.md +34 -6
- odoo_devops_tools-1.10.2/odoo_devops_tools/__init__.py +1 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools/env.py +163 -8
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/PKG-INFO +35 -7
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/pyproject.toml +1 -1
- odoo_devops_tools-1.9.2/odoo_devops_tools/__init__.py +0 -1
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/LICENSE +0 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/SOURCES.txt +0 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/dependency_links.txt +0 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/entry_points.txt +0 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/top_level.txt +0 -0
- {odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/setup.cfg +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: odoo-devops-tools
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.10.2
|
|
4
4
|
Summary: A small set of utilities for local Odoo development and simple Odoo deployments.
|
|
5
5
|
Author: Roman Lacko
|
|
6
6
|
License-Expression: MIT
|
|
@@ -30,7 +30,18 @@ Dynamic: license-file
|
|
|
30
30
|
|
|
31
31
|
A small set of utilities for **local Odoo development** and **simple Odoo deployments**.
|
|
32
32
|
|
|
33
|
-
|
|
33
|
+
At the center of the toolkit is **`odt-env`**: a declarative CLI that turns one INI project file into a ready-to-use Odoo workspace for local development or simple deployment.
|
|
34
|
+
|
|
35
|
+
Why use `odt-env`?
|
|
36
|
+
|
|
37
|
+
- Keep the whole workspace definition in one project file: Odoo version, source repositories, addons, Python settings, Docker settings, and Odoo configuration.
|
|
38
|
+
- Recreate the same workspace consistently across machines by syncing Odoo and addons from Git, local paths, or pinned commits.
|
|
39
|
+
- Use fast shallow clones by default, with optional full-history clones when development workflows need them.
|
|
40
|
+
- Let `uv` provision the right Python virtual environment and resolve Odoo plus addon dependencies into a single lock file.
|
|
41
|
+
- Build a local wheelhouse once and recreate the virtual environment later using strict offline installs.
|
|
42
|
+
- Generate the Odoo configuration and helper scripts for running, testing, shell access, module updates, backups, and restores.
|
|
43
|
+
- Build a custom Docker image from the same project definition and generate a ready-to-review Docker Compose file.
|
|
44
|
+
- Load the project file from a local path, Git repository, or HTTP(S) URL, with CLI variable overrides for reusable project templates.
|
|
34
45
|
|
|
35
46
|
---
|
|
36
47
|
|
|
@@ -90,7 +101,7 @@ Run `odt-env` against the project file:
|
|
|
90
101
|
odt-env odoo-project.ini --sync-all --create-venv
|
|
91
102
|
```
|
|
92
103
|
|
|
93
|
-
#### 1.3. Optional: Load the project file from Git
|
|
104
|
+
#### 1.3. Optional: Load the project file from Git or URL
|
|
94
105
|
|
|
95
106
|
Instead of passing a local file, the `INI` argument can point to a file stored in a Git repository:
|
|
96
107
|
|
|
@@ -99,6 +110,20 @@ odt-env --sync-all --create-venv \
|
|
|
99
110
|
git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini
|
|
100
111
|
```
|
|
101
112
|
|
|
113
|
+
It can also point to an HTTP(S) URL that serves a raw INI file:
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
odt-env --sync-all --create-venv \
|
|
117
|
+
https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
GitHub `blob` URLs copied from the browser are accepted and converted to their raw file URL automatically:
|
|
121
|
+
|
|
122
|
+
```bash
|
|
123
|
+
odt-env --sync-all --create-venv \
|
|
124
|
+
https://github.com/lck/odoo-devops-tools/blob/main/examples/odoo18-minimal.ini
|
|
125
|
+
```
|
|
126
|
+
|
|
102
127
|
After provisioning, the workspace has the following structure:
|
|
103
128
|
|
|
104
129
|
```text
|
|
@@ -543,6 +568,7 @@ If no options are specified, `odt-env` only regenerates configuration files and
|
|
|
543
568
|
- `INI` — required project file. This can be either:
|
|
544
569
|
- a local filesystem path, for example `odoo-project.ini` or `/path/to/odoo-project.ini`
|
|
545
570
|
- a Git-backed INI source, for example `git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini?ref=main`
|
|
571
|
+
- an HTTP(S) URL pointing to a raw INI file, for example `https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini`
|
|
546
572
|
|
|
547
573
|
Git-backed INI sources use this syntax:
|
|
548
574
|
|
|
@@ -552,9 +578,13 @@ git::REPO_URL//PATH/TO/PROJECT.ini?ref=REF
|
|
|
552
578
|
|
|
553
579
|
The `?ref=REF` part is optional and can point to a branch, tag, or commit.
|
|
554
580
|
|
|
581
|
+
HTTP(S)-backed INI sources must point to raw INI content.
|
|
582
|
+
For GitHub files, prefer `raw.githubusercontent.com` URLs.
|
|
583
|
+
GitHub `blob` URLs are accepted and converted to raw URLs automatically.
|
|
584
|
+
|
|
555
585
|
### Paths and outputs
|
|
556
586
|
|
|
557
|
-
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed INI.
|
|
587
|
+
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed or URL-backed INI.
|
|
558
588
|
- `-e KEY=VALUE`, `--extra-var KEY=VALUE` — override or inject a value in the optional `[vars]` section; can be repeated
|
|
559
589
|
- `--no-configs` — do not generate config files
|
|
560
590
|
- `--no-scripts` — do not generate helper scripts under `ROOT/odoo-scripts/`
|
|
@@ -735,9 +765,7 @@ commit = abcdef1
|
|
|
735
765
|
|
|
736
766
|
This section is optional.
|
|
737
767
|
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
- `target_image` — Docker image name/tag to build. This value is also used in the generated Compose file. Required when `--build-docker-image` is used.
|
|
768
|
+
- `target_image` — Docker image name/tag to build. Required when `--build-docker-image` is used.
|
|
741
769
|
- `base_image` — Docker image used as the base image in the generated Dockerfile. Default: `odoo:${odoo:version}`.
|
|
742
770
|
- `compose_project_name` — optional top-level name written to `ROOT/compose.yml`.
|
|
743
771
|
- `odoo_service` — Docker Compose service name for Odoo. Default: `odoo`.
|
|
@@ -2,7 +2,18 @@
|
|
|
2
2
|
|
|
3
3
|
A small set of utilities for **local Odoo development** and **simple Odoo deployments**.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
At the center of the toolkit is **`odt-env`**: a declarative CLI that turns one INI project file into a ready-to-use Odoo workspace for local development or simple deployment.
|
|
6
|
+
|
|
7
|
+
Why use `odt-env`?
|
|
8
|
+
|
|
9
|
+
- Keep the whole workspace definition in one project file: Odoo version, source repositories, addons, Python settings, Docker settings, and Odoo configuration.
|
|
10
|
+
- Recreate the same workspace consistently across machines by syncing Odoo and addons from Git, local paths, or pinned commits.
|
|
11
|
+
- Use fast shallow clones by default, with optional full-history clones when development workflows need them.
|
|
12
|
+
- Let `uv` provision the right Python virtual environment and resolve Odoo plus addon dependencies into a single lock file.
|
|
13
|
+
- Build a local wheelhouse once and recreate the virtual environment later using strict offline installs.
|
|
14
|
+
- Generate the Odoo configuration and helper scripts for running, testing, shell access, module updates, backups, and restores.
|
|
15
|
+
- Build a custom Docker image from the same project definition and generate a ready-to-review Docker Compose file.
|
|
16
|
+
- Load the project file from a local path, Git repository, or HTTP(S) URL, with CLI variable overrides for reusable project templates.
|
|
6
17
|
|
|
7
18
|
---
|
|
8
19
|
|
|
@@ -62,7 +73,7 @@ Run `odt-env` against the project file:
|
|
|
62
73
|
odt-env odoo-project.ini --sync-all --create-venv
|
|
63
74
|
```
|
|
64
75
|
|
|
65
|
-
#### 1.3. Optional: Load the project file from Git
|
|
76
|
+
#### 1.3. Optional: Load the project file from Git or URL
|
|
66
77
|
|
|
67
78
|
Instead of passing a local file, the `INI` argument can point to a file stored in a Git repository:
|
|
68
79
|
|
|
@@ -71,6 +82,20 @@ odt-env --sync-all --create-venv \
|
|
|
71
82
|
git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini
|
|
72
83
|
```
|
|
73
84
|
|
|
85
|
+
It can also point to an HTTP(S) URL that serves a raw INI file:
|
|
86
|
+
|
|
87
|
+
```bash
|
|
88
|
+
odt-env --sync-all --create-venv \
|
|
89
|
+
https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
GitHub `blob` URLs copied from the browser are accepted and converted to their raw file URL automatically:
|
|
93
|
+
|
|
94
|
+
```bash
|
|
95
|
+
odt-env --sync-all --create-venv \
|
|
96
|
+
https://github.com/lck/odoo-devops-tools/blob/main/examples/odoo18-minimal.ini
|
|
97
|
+
```
|
|
98
|
+
|
|
74
99
|
After provisioning, the workspace has the following structure:
|
|
75
100
|
|
|
76
101
|
```text
|
|
@@ -515,6 +540,7 @@ If no options are specified, `odt-env` only regenerates configuration files and
|
|
|
515
540
|
- `INI` — required project file. This can be either:
|
|
516
541
|
- a local filesystem path, for example `odoo-project.ini` or `/path/to/odoo-project.ini`
|
|
517
542
|
- a Git-backed INI source, for example `git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini?ref=main`
|
|
543
|
+
- an HTTP(S) URL pointing to a raw INI file, for example `https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini`
|
|
518
544
|
|
|
519
545
|
Git-backed INI sources use this syntax:
|
|
520
546
|
|
|
@@ -524,9 +550,13 @@ git::REPO_URL//PATH/TO/PROJECT.ini?ref=REF
|
|
|
524
550
|
|
|
525
551
|
The `?ref=REF` part is optional and can point to a branch, tag, or commit.
|
|
526
552
|
|
|
553
|
+
HTTP(S)-backed INI sources must point to raw INI content.
|
|
554
|
+
For GitHub files, prefer `raw.githubusercontent.com` URLs.
|
|
555
|
+
GitHub `blob` URLs are accepted and converted to raw URLs automatically.
|
|
556
|
+
|
|
527
557
|
### Paths and outputs
|
|
528
558
|
|
|
529
|
-
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed INI.
|
|
559
|
+
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed or URL-backed INI.
|
|
530
560
|
- `-e KEY=VALUE`, `--extra-var KEY=VALUE` — override or inject a value in the optional `[vars]` section; can be repeated
|
|
531
561
|
- `--no-configs` — do not generate config files
|
|
532
562
|
- `--no-scripts` — do not generate helper scripts under `ROOT/odoo-scripts/`
|
|
@@ -707,9 +737,7 @@ commit = abcdef1
|
|
|
707
737
|
|
|
708
738
|
This section is optional.
|
|
709
739
|
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
- `target_image` — Docker image name/tag to build. This value is also used in the generated Compose file. Required when `--build-docker-image` is used.
|
|
740
|
+
- `target_image` — Docker image name/tag to build. Required when `--build-docker-image` is used.
|
|
713
741
|
- `base_image` — Docker image used as the base image in the generated Dockerfile. Default: `odoo:${odoo:version}`.
|
|
714
742
|
- `compose_project_name` — optional top-level name written to `ROOT/compose.yml`.
|
|
715
743
|
- `odoo_service` — Docker Compose service name for Odoo. Default: `odoo`.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "1.10.2"
|
|
@@ -21,13 +21,17 @@ import tempfile
|
|
|
21
21
|
from dataclasses import dataclass, replace
|
|
22
22
|
from pathlib import Path, PurePosixPath
|
|
23
23
|
from typing import Any, Dict, Optional
|
|
24
|
-
from urllib.
|
|
24
|
+
from urllib.error import HTTPError, URLError
|
|
25
|
+
from urllib.parse import parse_qs, unquote, urlparse, urlunparse
|
|
26
|
+
from urllib.request import Request, urlopen
|
|
25
27
|
|
|
26
28
|
from . import __version__
|
|
27
29
|
|
|
28
30
|
_logger = logging.getLogger("odt-env")
|
|
29
31
|
|
|
30
32
|
_GIT_INI_PREFIX = "git::"
|
|
33
|
+
_URL_INI_TIMEOUT_SECONDS = 30
|
|
34
|
+
_URL_INI_MAX_BYTES = 1024 * 1024
|
|
31
35
|
|
|
32
36
|
_DEFAULT_REQUIREMENTS = [
|
|
33
37
|
"pip",
|
|
@@ -102,6 +106,12 @@ class GitIniSource:
|
|
|
102
106
|
ref: Optional[str] = None
|
|
103
107
|
|
|
104
108
|
|
|
109
|
+
@dataclass(frozen=True)
|
|
110
|
+
class UrlIniSource:
|
|
111
|
+
url: str
|
|
112
|
+
original_url: str
|
|
113
|
+
|
|
114
|
+
|
|
105
115
|
@dataclass(frozen=True)
|
|
106
116
|
class VirtualenvConfig:
|
|
107
117
|
python_version: str
|
|
@@ -3230,6 +3240,142 @@ def _copy_git_ini_to_root(source: GitIniSource, root: Path) -> Path:
|
|
|
3230
3240
|
return copied_ini_path
|
|
3231
3241
|
|
|
3232
3242
|
|
|
3243
|
+
def _github_blob_url_to_raw(url: str) -> Optional[str]:
|
|
3244
|
+
"""Convert a GitHub web UI blob URL to a raw.githubusercontent.com URL."""
|
|
3245
|
+
parsed = urlparse(url)
|
|
3246
|
+
if parsed.scheme not in {"http", "https"}:
|
|
3247
|
+
return None
|
|
3248
|
+
if parsed.netloc.lower() != "github.com":
|
|
3249
|
+
return None
|
|
3250
|
+
|
|
3251
|
+
parts = [unquote(part) for part in parsed.path.split("/") if part]
|
|
3252
|
+
if len(parts) < 5 or parts[2] != "blob":
|
|
3253
|
+
return None
|
|
3254
|
+
|
|
3255
|
+
owner, repo, _blob, ref, *file_parts = parts
|
|
3256
|
+
if not owner or not repo or not ref or not file_parts:
|
|
3257
|
+
return None
|
|
3258
|
+
if any(part in (".", "..") for part in file_parts):
|
|
3259
|
+
raise Exception("Invalid GitHub blob URL: file path must not contain '.' or '..'.")
|
|
3260
|
+
|
|
3261
|
+
raw_path = "/" + "/".join([owner, repo, ref, *file_parts])
|
|
3262
|
+
return urlunparse(("https", "raw.githubusercontent.com", raw_path, "", "", ""))
|
|
3263
|
+
|
|
3264
|
+
|
|
3265
|
+
def _parse_url_ini_source(raw_ini: str) -> Optional[UrlIniSource]:
|
|
3266
|
+
"""Parse an HTTP(S)-backed INI source.
|
|
3267
|
+
|
|
3268
|
+
GitHub ``/blob/`` URLs are accepted as a convenience and normalized to
|
|
3269
|
+
raw.githubusercontent.com URLs before downloading.
|
|
3270
|
+
"""
|
|
3271
|
+
raw_value = (raw_ini or "").strip()
|
|
3272
|
+
parsed = urlparse(raw_value)
|
|
3273
|
+
if parsed.scheme not in {"http", "https"}:
|
|
3274
|
+
return None
|
|
3275
|
+
if not parsed.netloc:
|
|
3276
|
+
raise Exception("Invalid URL INI source: missing host.")
|
|
3277
|
+
|
|
3278
|
+
if parsed.scheme == "http":
|
|
3279
|
+
_logger.warning(
|
|
3280
|
+
"URL INI source uses plain HTTP; prefer HTTPS when possible: %s",
|
|
3281
|
+
raw_value,
|
|
3282
|
+
)
|
|
3283
|
+
|
|
3284
|
+
normalized = _github_blob_url_to_raw(raw_value)
|
|
3285
|
+
if normalized is not None:
|
|
3286
|
+
_logger.info(
|
|
3287
|
+
"Normalized GitHub blob URL to raw INI URL: %s -> %s",
|
|
3288
|
+
raw_value,
|
|
3289
|
+
normalized,
|
|
3290
|
+
)
|
|
3291
|
+
return UrlIniSource(url=normalized, original_url=raw_value)
|
|
3292
|
+
|
|
3293
|
+
return UrlIniSource(url=raw_value, original_url=raw_value)
|
|
3294
|
+
|
|
3295
|
+
|
|
3296
|
+
def _safe_url_ini_filename(source_url: str) -> str:
|
|
3297
|
+
"""Return a safe local filename for a downloaded URL INI."""
|
|
3298
|
+
parsed = urlparse(source_url)
|
|
3299
|
+
raw_name = PurePosixPath(unquote(parsed.path)).name.strip()
|
|
3300
|
+
if not raw_name or raw_name in {".", ".."}:
|
|
3301
|
+
return "odoo-project.ini"
|
|
3302
|
+
|
|
3303
|
+
# Keep the URL basename but strip path separators that could appear after
|
|
3304
|
+
# decoding percent-encoded input.
|
|
3305
|
+
safe_name = raw_name.replace("/", "_").replace("\\", "_")
|
|
3306
|
+
return safe_name or "odoo-project.ini"
|
|
3307
|
+
|
|
3308
|
+
|
|
3309
|
+
def _copy_url_ini_to_root(source: UrlIniSource, root: Path) -> Path:
|
|
3310
|
+
"""Download an HTTP(S)-backed INI into ``root`` and return that local copy."""
|
|
3311
|
+
request = Request(
|
|
3312
|
+
source.url,
|
|
3313
|
+
headers={"User-Agent": f"odt-env/{__version__}"},
|
|
3314
|
+
method="GET",
|
|
3315
|
+
)
|
|
3316
|
+
|
|
3317
|
+
try:
|
|
3318
|
+
with urlopen(request, timeout=_URL_INI_TIMEOUT_SECONDS) as response:
|
|
3319
|
+
content_type = response.headers.get("Content-Type", "")
|
|
3320
|
+
raw = response.read(_URL_INI_MAX_BYTES + 1)
|
|
3321
|
+
except HTTPError as e:
|
|
3322
|
+
raise Exception(f"Failed to download URL INI: HTTP {e.code} {e.reason} ({source.url})") from e
|
|
3323
|
+
except URLError as e:
|
|
3324
|
+
raise Exception(f"Failed to download URL INI: {e.reason} ({source.url})") from e
|
|
3325
|
+
except OSError as e:
|
|
3326
|
+
raise Exception(f"Failed to download URL INI: {e} ({source.url})") from e
|
|
3327
|
+
|
|
3328
|
+
if len(raw) > _URL_INI_MAX_BYTES:
|
|
3329
|
+
raise Exception(
|
|
3330
|
+
f"URL INI is too large: maximum supported size is {_URL_INI_MAX_BYTES} bytes ({source.url})"
|
|
3331
|
+
)
|
|
3332
|
+
|
|
3333
|
+
try:
|
|
3334
|
+
text = raw.decode("utf-8-sig")
|
|
3335
|
+
except UnicodeDecodeError as e:
|
|
3336
|
+
raise Exception(f"URL INI must be UTF-8 encoded: {source.url}") from e
|
|
3337
|
+
|
|
3338
|
+
if not text.strip():
|
|
3339
|
+
raise Exception(f"URL INI is empty: {source.url}")
|
|
3340
|
+
|
|
3341
|
+
# Fail early for common copy/paste mistakes where a web UI HTML page is
|
|
3342
|
+
# downloaded instead of the raw INI file.
|
|
3343
|
+
if re.search(r"<\s*!doctype\s+html|<\s*html[\s>]", text[:2048], flags=re.IGNORECASE):
|
|
3344
|
+
raise Exception(
|
|
3345
|
+
"Downloaded URL INI looks like an HTML page, not a raw INI file. "
|
|
3346
|
+
"Use a raw file URL instead."
|
|
3347
|
+
)
|
|
3348
|
+
|
|
3349
|
+
probe = configparser.ConfigParser(interpolation=configparser.ExtendedInterpolation())
|
|
3350
|
+
try:
|
|
3351
|
+
probe.read_string(text)
|
|
3352
|
+
except configparser.Error as e:
|
|
3353
|
+
raise Exception(f"Downloaded URL INI is not a valid INI file: {source.url} ({e})") from e
|
|
3354
|
+
if not probe.has_section("odoo"):
|
|
3355
|
+
raise Exception(f"Downloaded URL INI is missing required [odoo] section: {source.url}")
|
|
3356
|
+
|
|
3357
|
+
if content_type:
|
|
3358
|
+
_logger.info("Downloaded URL INI content type: %s", content_type)
|
|
3359
|
+
|
|
3360
|
+
copied_ini_path = root / _safe_url_ini_filename(source.url)
|
|
3361
|
+
try:
|
|
3362
|
+
copied_ini_path.write_text(text, encoding="utf-8")
|
|
3363
|
+
except OSError as e:
|
|
3364
|
+
raise Exception(f"Failed to write URL INI to workspace root: {copied_ini_path} ({e})") from e
|
|
3365
|
+
|
|
3366
|
+
try:
|
|
3367
|
+
copied_ini_path = copied_ini_path.resolve()
|
|
3368
|
+
except Exception:
|
|
3369
|
+
copied_ini_path = copied_ini_path.absolute()
|
|
3370
|
+
|
|
3371
|
+
_logger.info(
|
|
3372
|
+
"Downloaded URL INI into workspace root: %s (source=%s)",
|
|
3373
|
+
copied_ini_path,
|
|
3374
|
+
source.original_url,
|
|
3375
|
+
)
|
|
3376
|
+
return copied_ini_path
|
|
3377
|
+
|
|
3378
|
+
|
|
3233
3379
|
def build_parser() -> argparse.ArgumentParser:
|
|
3234
3380
|
epilog = """If no options are specified, odt-env only regenerates configs and helper scripts.
|
|
3235
3381
|
|
|
@@ -3237,6 +3383,7 @@ Examples:
|
|
|
3237
3383
|
odt-env /path/to/odoo-project.ini --sync-all --create-venv
|
|
3238
3384
|
odt-env /path/to/odoo-project.ini --sync-all --create-venv --root /full/path/to/workspace-root
|
|
3239
3385
|
odt-env git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini?ref=main --sync-all --create-venv
|
|
3386
|
+
odt-env https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini --sync-all --create-venv
|
|
3240
3387
|
odt-env /path/to/odoo-project.ini --create-venv-from-wheelhouse
|
|
3241
3388
|
odt-env /path/to/odoo-project.ini --sync-addons --build-docker-image
|
|
3242
3389
|
odt-env /path/to/odoo-project.ini --sync-all --create-venv -e odoo_version=19.0
|
|
@@ -3260,7 +3407,8 @@ Examples:
|
|
|
3260
3407
|
"ini",
|
|
3261
3408
|
metavar="INI",
|
|
3262
3409
|
help=(
|
|
3263
|
-
"Local path to odoo-project.ini,
|
|
3410
|
+
"Local path to odoo-project.ini, Git source git::REPO_URL//PATH/TO/PROJECT.ini?ref=REF, "
|
|
3411
|
+
"or HTTP(S) URL to a raw INI file."
|
|
3264
3412
|
),
|
|
3265
3413
|
)
|
|
3266
3414
|
|
|
@@ -3270,7 +3418,8 @@ Examples:
|
|
|
3270
3418
|
default=None,
|
|
3271
3419
|
help=(
|
|
3272
3420
|
"Override workspace ROOT directory. By default, local INI uses its containing directory; "
|
|
3273
|
-
"Git INI
|
|
3421
|
+
"Git and URL INI sources use the current working directory. "
|
|
3422
|
+
"Explicit ROOT is created automatically if needed."
|
|
3274
3423
|
),
|
|
3275
3424
|
)
|
|
3276
3425
|
|
|
@@ -3416,18 +3565,20 @@ def main() -> None:
|
|
|
3416
3565
|
|
|
3417
3566
|
try:
|
|
3418
3567
|
git_ini_source = _parse_git_ini_source(args.ini)
|
|
3568
|
+
url_ini_source = None if git_ini_source is not None else _parse_url_ini_source(args.ini)
|
|
3419
3569
|
except Exception as e:
|
|
3420
3570
|
parser.error(str(e))
|
|
3421
3571
|
|
|
3422
3572
|
root_override: Optional[Path] = None
|
|
3423
|
-
if git_ini_source is not None:
|
|
3573
|
+
if git_ini_source is not None or url_ini_source is not None:
|
|
3574
|
+
source_kind = "Git" if git_ini_source is not None else "URL"
|
|
3424
3575
|
if args.root:
|
|
3425
3576
|
root_override = _validate_root_override(parser, args.root)
|
|
3426
3577
|
else:
|
|
3427
3578
|
try:
|
|
3428
3579
|
cwd = Path.cwd()
|
|
3429
3580
|
except OSError as e:
|
|
3430
|
-
parser.error(f'Failed to resolve current working directory for
|
|
3581
|
+
parser.error(f'Failed to resolve current working directory for {source_kind} INI ROOT: {e}')
|
|
3431
3582
|
|
|
3432
3583
|
try:
|
|
3433
3584
|
root_override = cwd.resolve()
|
|
@@ -3435,15 +3586,19 @@ def main() -> None:
|
|
|
3435
3586
|
root_override = cwd.absolute()
|
|
3436
3587
|
|
|
3437
3588
|
if not root_override.is_dir():
|
|
3438
|
-
parser.error(f'Current working directory for
|
|
3589
|
+
parser.error(f'Current working directory for {source_kind} INI ROOT is not a directory: {root_override}')
|
|
3439
3590
|
|
|
3440
3591
|
_logger.info(
|
|
3441
|
-
'Workspace ROOT default for
|
|
3592
|
+
'Workspace ROOT default for %s INI (current working directory): %s',
|
|
3593
|
+
source_kind,
|
|
3442
3594
|
root_override,
|
|
3443
3595
|
)
|
|
3444
3596
|
|
|
3445
3597
|
try:
|
|
3446
|
-
|
|
3598
|
+
if git_ini_source is not None:
|
|
3599
|
+
ini_path = _copy_git_ini_to_root(git_ini_source, root_override)
|
|
3600
|
+
else:
|
|
3601
|
+
ini_path = _copy_url_ini_to_root(url_ini_source, root_override)
|
|
3447
3602
|
except Exception as e:
|
|
3448
3603
|
_logger.error('%s', e)
|
|
3449
3604
|
raise SystemExit(1)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: odoo-devops-tools
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.10.2
|
|
4
4
|
Summary: A small set of utilities for local Odoo development and simple Odoo deployments.
|
|
5
5
|
Author: Roman Lacko
|
|
6
6
|
License-Expression: MIT
|
|
@@ -30,7 +30,18 @@ Dynamic: license-file
|
|
|
30
30
|
|
|
31
31
|
A small set of utilities for **local Odoo development** and **simple Odoo deployments**.
|
|
32
32
|
|
|
33
|
-
|
|
33
|
+
At the center of the toolkit is **`odt-env`**: a declarative CLI that turns one INI project file into a ready-to-use Odoo workspace for local development or simple deployment.
|
|
34
|
+
|
|
35
|
+
Why use `odt-env`?
|
|
36
|
+
|
|
37
|
+
- Keep the whole workspace definition in one project file: Odoo version, source repositories, addons, Python settings, Docker settings, and Odoo configuration.
|
|
38
|
+
- Recreate the same workspace consistently across machines by syncing Odoo and addons from Git, local paths, or pinned commits.
|
|
39
|
+
- Use fast shallow clones by default, with optional full-history clones when development workflows need them.
|
|
40
|
+
- Let `uv` provision the right Python virtual environment and resolve Odoo plus addon dependencies into a single lock file.
|
|
41
|
+
- Build a local wheelhouse once and recreate the virtual environment later using strict offline installs.
|
|
42
|
+
- Generate the Odoo configuration and helper scripts for running, testing, shell access, module updates, backups, and restores.
|
|
43
|
+
- Build a custom Docker image from the same project definition and generate a ready-to-review Docker Compose file.
|
|
44
|
+
- Load the project file from a local path, Git repository, or HTTP(S) URL, with CLI variable overrides for reusable project templates.
|
|
34
45
|
|
|
35
46
|
---
|
|
36
47
|
|
|
@@ -90,7 +101,7 @@ Run `odt-env` against the project file:
|
|
|
90
101
|
odt-env odoo-project.ini --sync-all --create-venv
|
|
91
102
|
```
|
|
92
103
|
|
|
93
|
-
#### 1.3. Optional: Load the project file from Git
|
|
104
|
+
#### 1.3. Optional: Load the project file from Git or URL
|
|
94
105
|
|
|
95
106
|
Instead of passing a local file, the `INI` argument can point to a file stored in a Git repository:
|
|
96
107
|
|
|
@@ -99,6 +110,20 @@ odt-env --sync-all --create-venv \
|
|
|
99
110
|
git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini
|
|
100
111
|
```
|
|
101
112
|
|
|
113
|
+
It can also point to an HTTP(S) URL that serves a raw INI file:
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
odt-env --sync-all --create-venv \
|
|
117
|
+
https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
GitHub `blob` URLs copied from the browser are accepted and converted to their raw file URL automatically:
|
|
121
|
+
|
|
122
|
+
```bash
|
|
123
|
+
odt-env --sync-all --create-venv \
|
|
124
|
+
https://github.com/lck/odoo-devops-tools/blob/main/examples/odoo18-minimal.ini
|
|
125
|
+
```
|
|
126
|
+
|
|
102
127
|
After provisioning, the workspace has the following structure:
|
|
103
128
|
|
|
104
129
|
```text
|
|
@@ -543,6 +568,7 @@ If no options are specified, `odt-env` only regenerates configuration files and
|
|
|
543
568
|
- `INI` — required project file. This can be either:
|
|
544
569
|
- a local filesystem path, for example `odoo-project.ini` or `/path/to/odoo-project.ini`
|
|
545
570
|
- a Git-backed INI source, for example `git::https://github.com/lck/odoo-devops-tools.git//examples/odoo18-minimal.ini?ref=main`
|
|
571
|
+
- an HTTP(S) URL pointing to a raw INI file, for example `https://raw.githubusercontent.com/lck/odoo-devops-tools/main/examples/odoo18-minimal.ini`
|
|
546
572
|
|
|
547
573
|
Git-backed INI sources use this syntax:
|
|
548
574
|
|
|
@@ -552,9 +578,13 @@ git::REPO_URL//PATH/TO/PROJECT.ini?ref=REF
|
|
|
552
578
|
|
|
553
579
|
The `?ref=REF` part is optional and can point to a branch, tag, or commit.
|
|
554
580
|
|
|
581
|
+
HTTP(S)-backed INI sources must point to raw INI content.
|
|
582
|
+
For GitHub files, prefer `raw.githubusercontent.com` URLs.
|
|
583
|
+
GitHub `blob` URLs are accepted and converted to raw URLs automatically.
|
|
584
|
+
|
|
555
585
|
### Paths and outputs
|
|
556
586
|
|
|
557
|
-
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed INI.
|
|
587
|
+
- `--root ROOT` — workspace root directory. Default: the directory containing a local INI file, or the current working directory for a Git-backed or URL-backed INI.
|
|
558
588
|
- `-e KEY=VALUE`, `--extra-var KEY=VALUE` — override or inject a value in the optional `[vars]` section; can be repeated
|
|
559
589
|
- `--no-configs` — do not generate config files
|
|
560
590
|
- `--no-scripts` — do not generate helper scripts under `ROOT/odoo-scripts/`
|
|
@@ -735,9 +765,7 @@ commit = abcdef1
|
|
|
735
765
|
|
|
736
766
|
This section is optional.
|
|
737
767
|
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
- `target_image` — Docker image name/tag to build. This value is also used in the generated Compose file. Required when `--build-docker-image` is used.
|
|
768
|
+
- `target_image` — Docker image name/tag to build. Required when `--build-docker-image` is used.
|
|
741
769
|
- `base_image` — Docker image used as the base image in the generated Dockerfile. Default: `odoo:${odoo:version}`.
|
|
742
770
|
- `compose_project_name` — optional top-level name written to `ROOT/compose.yml`.
|
|
743
771
|
- `odoo_service` — Docker Compose service name for Odoo. Default: `odoo`.
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "1.9.2"
|
|
File without changes
|
|
File without changes
|
{odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
{odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/entry_points.txt
RENAMED
|
File without changes
|
{odoo_devops_tools-1.9.2 → odoo_devops_tools-1.10.2}/odoo_devops_tools.egg-info/top_level.txt
RENAMED
|
File without changes
|
|
File without changes
|