stoobly-agent 1.2.3__py3-none-any.whl → 1.4.0__py3-none-any.whl
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.
- stoobly_agent/__init__.py +1 -1
- stoobly_agent/app/api/application_http_request_handler.py +3 -3
- stoobly_agent/app/api/proxy_controller.py +8 -7
- stoobly_agent/app/cli/config_cli.py +1 -1
- stoobly_agent/app/cli/helpers/certificate_authority.py +7 -6
- stoobly_agent/app/cli/helpers/print_service.py +17 -0
- stoobly_agent/app/cli/scaffold/app.py +16 -34
- stoobly_agent/app/cli/scaffold/app_command.py +4 -7
- stoobly_agent/app/cli/scaffold/app_config.py +15 -2
- stoobly_agent/app/cli/scaffold/app_create_command.py +18 -2
- stoobly_agent/app/cli/scaffold/command.py +1 -1
- stoobly_agent/app/cli/scaffold/constants.py +9 -5
- stoobly_agent/app/cli/scaffold/docker/app_builder.py +3 -7
- stoobly_agent/app/cli/scaffold/docker/constants.py +0 -1
- stoobly_agent/app/cli/scaffold/docker/service/builder.py +12 -11
- stoobly_agent/app/cli/scaffold/docker/workflow/builder.py +14 -31
- stoobly_agent/app/cli/scaffold/docker/workflow/mock_decorator.py +6 -2
- stoobly_agent/app/cli/scaffold/docker/workflow/reverse_proxy_decorator.py +6 -2
- stoobly_agent/app/cli/scaffold/hosts_file_manager.py +112 -0
- stoobly_agent/app/cli/scaffold/service.py +1 -2
- stoobly_agent/app/cli/scaffold/service_command.py +1 -1
- stoobly_agent/app/cli/scaffold/service_config.py +10 -14
- stoobly_agent/app/cli/scaffold/service_workflow_validate_command.py +9 -11
- stoobly_agent/app/cli/scaffold/templates/app/.Dockerfile.context +2 -4
- stoobly_agent/app/cli/scaffold/templates/app/.Makefile +108 -68
- stoobly_agent/app/cli/scaffold/templates/app/.docker-compose.base.yml +8 -13
- stoobly_agent/app/cli/scaffold/templates/app/Makefile +1 -1
- stoobly_agent/app/cli/scaffold/templates/app/build/.docker-compose.base.yml +8 -4
- stoobly_agent/app/cli/scaffold/templates/app/build/mock/.docker-compose.mock.yml +2 -6
- stoobly_agent/app/cli/scaffold/templates/app/build/mock/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/build/mock/bin/.init +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/build/record/.docker-compose.record.yml +2 -6
- stoobly_agent/app/cli/scaffold/templates/app/build/record/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/build/record/bin/.init +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/build/test/.docker-compose.test.yml +2 -6
- stoobly_agent/app/cli/scaffold/templates/app/build/test/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/build/test/bin/.init +3 -0
- stoobly_agent/app/cli/scaffold/templates/app/entrypoint/.docker-compose.base.yml +2 -0
- stoobly_agent/app/cli/scaffold/templates/app/entrypoint/mock/.docker-compose.mock.yml +2 -8
- stoobly_agent/app/cli/scaffold/templates/app/entrypoint/record/.docker-compose.record.yml +2 -8
- stoobly_agent/app/cli/scaffold/templates/app/entrypoint/test/.docker-compose.test.yml +2 -8
- stoobly_agent/app/cli/scaffold/templates/app/stoobly-ui/exec/.docker-compose.exec.yml +2 -3
- stoobly_agent/app/cli/scaffold/templates/app/stoobly-ui/exec/bin/.logs +1 -0
- stoobly_agent/app/cli/scaffold/templates/app/stoobly-ui/exec/bin/.services +9 -0
- stoobly_agent/app/cli/scaffold/templates/app/stoobly-ui/mock/.docker-compose.mock.yml +1 -2
- stoobly_agent/app/cli/scaffold/templates/app/stoobly-ui/record/.docker-compose.record.yml +1 -2
- stoobly_agent/app/cli/scaffold/templates/workflow/mock/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/workflow/mock/bin/.init +7 -1
- stoobly_agent/app/cli/scaffold/templates/workflow/record/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/workflow/record/bin/.init +7 -1
- stoobly_agent/app/cli/scaffold/templates/workflow/test/bin/.configure +3 -0
- stoobly_agent/app/cli/scaffold/templates/workflow/test/bin/.init +7 -1
- stoobly_agent/app/cli/scaffold/validate_command.py +2 -2
- stoobly_agent/app/cli/scaffold/workflow.py +5 -4
- stoobly_agent/app/cli/scaffold/workflow_command.py +3 -3
- stoobly_agent/app/cli/scaffold/workflow_create_command.py +0 -1
- stoobly_agent/app/cli/scaffold/workflow_run_command.py +78 -45
- stoobly_agent/app/cli/scaffold_cli.py +246 -109
- stoobly_agent/app/cli/snapshot_cli.py +7 -3
- stoobly_agent/app/models/adapters/joined_request_adapter.py +6 -0
- stoobly_agent/app/models/factories/resource/local_db/helpers/scenario_snapshot.py +3 -1
- stoobly_agent/app/models/helpers/apply.py +34 -17
- stoobly_agent/app/models/helpers/create_request_params_service.py +4 -0
- stoobly_agent/app/proxy/handle_mock_service.py +2 -0
- stoobly_agent/app/proxy/handle_replay_service.py +2 -0
- stoobly_agent/app/proxy/mitmproxy/request_facade.py +1 -1
- stoobly_agent/app/proxy/mitmproxy/response_body_facade.py +19 -0
- stoobly_agent/app/proxy/mitmproxy/response_facade.py +90 -18
- stoobly_agent/app/proxy/record/join_request_service.py +1 -1
- stoobly_agent/app/proxy/replay/body_parser_service.py +11 -3
- stoobly_agent/app/settings/constants/request_component.py +2 -1
- stoobly_agent/config/constants/custom_headers.py +13 -13
- stoobly_agent/config/constants/headers.py +0 -2
- stoobly_agent/config/data_dir.py +2 -1
- stoobly_agent/config/schema.yml +2 -2
- stoobly_agent/public/18-es2015.583f191cc7ad512ee262.js +1 -0
- stoobly_agent/public/18-es5.583f191cc7ad512ee262.js +1 -0
- stoobly_agent/public/35-es2015.8f79ff8748d4ff06ab03.js +1 -0
- stoobly_agent/public/35-es5.8f79ff8748d4ff06ab03.js +1 -0
- stoobly_agent/public/index.html +1 -1
- stoobly_agent/public/main-es2015.2cc16523aa3fcaba51e5.js +1 -0
- stoobly_agent/public/main-es5.2cc16523aa3fcaba51e5.js +1 -0
- stoobly_agent/public/{runtime-es2015.9addf49b79aca951b7e2.js → runtime-es2015.b914470164e4d6e75d96.js} +1 -1
- stoobly_agent/public/{runtime-es5.9addf49b79aca951b7e2.js → runtime-es5.b914470164e4d6e75d96.js} +1 -1
- stoobly_agent/test/app/cli/scaffold/cli_invoker.py +1 -2
- stoobly_agent/test/app/cli/scaffold/{hosts_file_reader_test.py → hosts_file_manager_test.py} +20 -20
- stoobly_agent/test/app/cli/snapshot/snapshot_apply_test.py +162 -1
- stoobly_agent/test/app/models/schemas/.stoobly/db/VERSION +1 -1
- stoobly_agent/test/mock_data/scaffold/docker-compose-assets-service.yml +1 -3
- {stoobly_agent-1.2.3.dist-info → stoobly_agent-1.4.0.dist-info}/METADATA +1 -1
- {stoobly_agent-1.2.3.dist-info → stoobly_agent-1.4.0.dist-info}/RECORD +94 -93
- stoobly_agent/app/cli/scaffold/hosts_file_reader.py +0 -65
- stoobly_agent/app/cli/scaffold/templates/app/.Dockerfile.proxy +0 -34
- stoobly_agent/public/18-es2015.d3b430636a4d6f544d92.js +0 -1
- stoobly_agent/public/18-es5.d3b430636a4d6f544d92.js +0 -1
- stoobly_agent/public/35-es2015.f741ebce0bfc25f0ec99.js +0 -1
- stoobly_agent/public/35-es5.f741ebce0bfc25f0ec99.js +0 -1
- stoobly_agent/public/main-es2015.ccd46ac1b6638ddf2066.js +0 -1
- stoobly_agent/public/main-es5.ccd46ac1b6638ddf2066.js +0 -1
- {stoobly_agent-1.2.3.dist-info → stoobly_agent-1.4.0.dist-info}/LICENSE +0 -0
- {stoobly_agent-1.2.3.dist-info → stoobly_agent-1.4.0.dist-info}/WHEEL +0 -0
- {stoobly_agent-1.2.3.dist-info → stoobly_agent-1.4.0.dist-info}/entry_points.txt +0 -0
@@ -1,22 +1,18 @@
|
|
1
1
|
services:
|
2
2
|
build.init:
|
3
|
-
build:
|
4
|
-
context: ./
|
5
|
-
dockerfile: ../../.Dockerfile.context
|
6
3
|
extends:
|
7
4
|
file: ../.docker-compose.base.yml
|
8
5
|
service: build.init_base
|
6
|
+
image: stoobly.${USER_ID}
|
9
7
|
profiles:
|
10
8
|
- test
|
11
9
|
build.configure:
|
12
|
-
build:
|
13
|
-
context: ./
|
14
|
-
dockerfile: ../../.Dockerfile.context
|
15
10
|
depends_on:
|
16
11
|
build.init:
|
17
12
|
condition: service_completed_successfully
|
18
13
|
extends:
|
19
14
|
file: ../.docker-compose.base.yml
|
20
15
|
service: build.configure_base
|
16
|
+
image: stoobly.${USER_ID}
|
21
17
|
profiles:
|
22
18
|
- test
|
@@ -7,6 +7,7 @@ services:
|
|
7
7
|
extends:
|
8
8
|
file: ../.docker-compose.base.yml
|
9
9
|
service: context_base
|
10
|
+
working_dir: /home/stoobly/.stoobly/docker/entrypoint/${WORKFLOW_NAME}
|
10
11
|
entrypoint.init_base:
|
11
12
|
command:
|
12
13
|
- bin/.init
|
@@ -14,3 +15,4 @@ services:
|
|
14
15
|
extends:
|
15
16
|
file: ../.docker-compose.base.yml
|
16
17
|
service: context_base
|
18
|
+
working_dir: /home/stoobly/.stoobly/docker/entrypoint/${WORKFLOW_NAME}
|
@@ -3,9 +3,6 @@ networks:
|
|
3
3
|
name: entrypoint
|
4
4
|
services:
|
5
5
|
entrypoint.configure:
|
6
|
-
build:
|
7
|
-
context: ./
|
8
|
-
dockerfile: ../../.Dockerfile.context
|
9
6
|
depends_on:
|
10
7
|
entrypoint.init:
|
11
8
|
condition: service_completed_successfully
|
@@ -13,19 +10,16 @@ services:
|
|
13
10
|
extends:
|
14
11
|
file: ../.docker-compose.base.yml
|
15
12
|
service: entrypoint.configure_base
|
13
|
+
image: stoobly.${USER_ID}
|
16
14
|
profiles:
|
17
15
|
- mock
|
18
16
|
volumes: []
|
19
17
|
entrypoint.init:
|
20
|
-
build:
|
21
|
-
context: ./
|
22
|
-
dockerfile: ../../.Dockerfile.context
|
23
18
|
environment: {}
|
24
19
|
extends:
|
25
20
|
file: ../.docker-compose.base.yml
|
26
21
|
service: entrypoint.init_base
|
22
|
+
image: stoobly.${USER_ID}
|
27
23
|
profiles:
|
28
24
|
- mock
|
29
|
-
volumes:
|
30
|
-
- ./dist:/home/stoobly/dist
|
31
25
|
volumes: {}
|
@@ -3,9 +3,6 @@ networks:
|
|
3
3
|
name: entrypoint
|
4
4
|
services:
|
5
5
|
entrypoint.configure:
|
6
|
-
build:
|
7
|
-
context: ./
|
8
|
-
dockerfile: ../../.Dockerfile.context
|
9
6
|
depends_on:
|
10
7
|
entrypoint.init:
|
11
8
|
condition: service_completed_successfully
|
@@ -13,19 +10,16 @@ services:
|
|
13
10
|
extends:
|
14
11
|
file: ../.docker-compose.base.yml
|
15
12
|
service: entrypoint.configure_base
|
13
|
+
image: stoobly.${USER_ID}
|
16
14
|
profiles:
|
17
15
|
- record
|
18
16
|
volumes: []
|
19
17
|
entrypoint.init:
|
20
|
-
build:
|
21
|
-
context: ./
|
22
|
-
dockerfile: ../../.Dockerfile.context
|
23
18
|
environment: {}
|
24
19
|
extends:
|
25
20
|
file: ../.docker-compose.base.yml
|
26
21
|
service: entrypoint.init_base
|
22
|
+
image: stoobly.${USER_ID}
|
27
23
|
profiles:
|
28
24
|
- record
|
29
|
-
volumes:
|
30
|
-
- ./dist:/home/stoobly/dist
|
31
25
|
volumes: {}
|
@@ -3,9 +3,6 @@ networks:
|
|
3
3
|
name: entrypoint
|
4
4
|
services:
|
5
5
|
entrypoint.configure:
|
6
|
-
build:
|
7
|
-
context: ./
|
8
|
-
dockerfile: ../../.Dockerfile.context
|
9
6
|
depends_on:
|
10
7
|
entrypoint.init:
|
11
8
|
condition: service_completed_successfully
|
@@ -13,19 +10,16 @@ services:
|
|
13
10
|
extends:
|
14
11
|
file: ../.docker-compose.base.yml
|
15
12
|
service: entrypoint.configure_base
|
13
|
+
image: stoobly.${USER_ID}
|
16
14
|
profiles:
|
17
15
|
- test
|
18
16
|
volumes: []
|
19
17
|
entrypoint.init:
|
20
|
-
build:
|
21
|
-
context: ./
|
22
|
-
dockerfile: ../../.Dockerfile.context
|
23
18
|
environment: {}
|
24
19
|
extends:
|
25
20
|
file: ../.docker-compose.base.yml
|
26
21
|
service: entrypoint.init_base
|
22
|
+
image: stoobly.${USER_ID}
|
27
23
|
profiles:
|
28
24
|
- test
|
29
|
-
volumes:
|
30
|
-
- ./dist:/home/stoobly/dist
|
31
25
|
volumes: {}
|
@@ -1,12 +1,11 @@
|
|
1
1
|
services:
|
2
2
|
stoobly_ui.command:
|
3
|
-
|
4
|
-
dockerfile: ../../.Dockerfile.context
|
5
|
-
command: ['${EXEC_COMMAND}', '${EXEC_ARGS}']
|
3
|
+
command: ['.stoobly/docker/stoobly-ui/exec/${EXEC_COMMAND}', '${EXEC_ARGS}']
|
6
4
|
environment:
|
7
5
|
EXEC_OPTIONS: ${EXEC_OPTIONS}
|
8
6
|
extends:
|
9
7
|
file: ../.docker-compose.base.yml
|
10
8
|
service: stoobly_ui.base
|
9
|
+
image: stoobly.${USER_ID}
|
11
10
|
profiles:
|
12
11
|
- exec
|
@@ -1,7 +1,13 @@
|
|
1
1
|
#!/bin/bash
|
2
2
|
|
3
|
-
|
3
|
+
# This file was automatically generated. DO NOT EDIT.
|
4
|
+
# Any changes made to this file will be overwritten.
|
5
|
+
|
6
|
+
if [ -n "$SERVICE_HOSTNAME" ] && [ "$SERVICE_SCHEME" = "https" ]; then
|
7
|
+
stoobly-agent ca-cert mkcert $SERVICE_HOSTNAME
|
8
|
+
fi
|
4
9
|
|
10
|
+
entrypoint=$(dirname -- "$0")/init
|
5
11
|
if [ -e "$entrypoint" ]; then
|
6
12
|
"$entrypoint"
|
7
13
|
fi
|
@@ -1,7 +1,13 @@
|
|
1
1
|
#!/bin/bash
|
2
2
|
|
3
|
-
|
3
|
+
# This file was automatically generated. DO NOT EDIT.
|
4
|
+
# Any changes made to this file will be overwritten.
|
5
|
+
|
6
|
+
if [ -n "$SERVICE_HOSTNAME" ] && [ "$SERVICE_SCHEME" = "https" ] ; then
|
7
|
+
stoobly-agent ca-cert mkcert $SERVICE_HOSTNAME
|
8
|
+
fi
|
4
9
|
|
10
|
+
entrypoint=$(dirname -- "$0")/init
|
5
11
|
if [ -e "$entrypoint" ]; then
|
6
12
|
"$entrypoint"
|
7
13
|
fi
|
@@ -1,7 +1,13 @@
|
|
1
1
|
#!/bin/bash
|
2
2
|
|
3
|
-
|
3
|
+
# This file was automatically generated. DO NOT EDIT.
|
4
|
+
# Any changes made to this file will be overwritten.
|
5
|
+
|
6
|
+
if [ -n "$SERVICE_HOSTNAME" ] && [ "$SERVICE_SCHEME" = "https" ]; then
|
7
|
+
stoobly-agent ca-cert mkcert $SERVICE_HOSTNAME
|
8
|
+
fi
|
4
9
|
|
10
|
+
entrypoint=$(dirname -- "$0")/init
|
5
11
|
if [ -e "$entrypoint" ]; then
|
6
12
|
"$entrypoint"
|
7
13
|
fi
|
@@ -35,7 +35,7 @@ class ValidateCommand():
|
|
35
35
|
if logs and re.search('error', str(logs), re.IGNORECASE):
|
36
36
|
raise ScaffoldValidateException(f"Error logs potentially detected in: {init_container_name}")
|
37
37
|
if init_container.status != 'exited' or init_container.attrs['State']['ExitCode'] != 0:
|
38
|
-
raise ScaffoldValidateException(f"init container
|
38
|
+
raise ScaffoldValidateException(f"init container {init_container_name} exited with: {init_container.attrs['State']['ExitCode']}")
|
39
39
|
|
40
40
|
configure_container = self.__get_container(configure_container_name)
|
41
41
|
|
@@ -43,7 +43,7 @@ class ValidateCommand():
|
|
43
43
|
if configure_container.status == 'exited' and configure_container.attrs['State']['ExitCode'] == 0:
|
44
44
|
configure_container_ran = True
|
45
45
|
if not configure_container_ran:
|
46
|
-
raise ScaffoldValidateException(f"
|
46
|
+
raise ScaffoldValidateException(f"configure container {configure_container_name} exited with: {configure_container.attrs['State']['ExitCode']}")
|
47
47
|
|
48
48
|
def validate_detached(self, container: Container) -> None:
|
49
49
|
print(f"Validating detached for: {container.name}")
|
@@ -33,14 +33,15 @@ class Workflow():
|
|
33
33
|
|
34
34
|
@property
|
35
35
|
def service_paths(self):
|
36
|
-
|
36
|
+
all_service_paths = self.app.service_paths
|
37
|
+
return list(filter(lambda path: os.path.exists(os.path.join(path, self.workflow_name)), all_service_paths))
|
37
38
|
|
38
39
|
# TODO: merge into 1 services property
|
39
40
|
|
40
41
|
# Returns services that run in this specific workflow
|
41
42
|
@property
|
42
43
|
def services_ran(self) -> List[str]:
|
43
|
-
services_dir = os.path.join(self.app.
|
44
|
+
services_dir = os.path.join(self.app.data_dir_path, self.app.scaffold_namespace)
|
44
45
|
|
45
46
|
services = []
|
46
47
|
for filename in os.listdir(services_dir):
|
@@ -56,5 +57,5 @@ class Workflow():
|
|
56
57
|
return services
|
57
58
|
|
58
59
|
def service_paths_from_services(self, services: List[str]):
|
59
|
-
|
60
|
-
return list(map(lambda service: os.path.join(
|
60
|
+
scaffold_namespace_path = self.app.scaffold_namespace_path
|
61
|
+
return list(map(lambda service: os.path.join(scaffold_namespace_path, service), services))
|
@@ -26,7 +26,7 @@ class WorkflowCommand(ServiceCommand):
|
|
26
26
|
@property
|
27
27
|
def compose_path(self):
|
28
28
|
return os.path.join(
|
29
|
-
self.
|
29
|
+
self.data_dir_path,
|
30
30
|
self.compose_relative_path
|
31
31
|
)
|
32
32
|
|
@@ -70,7 +70,7 @@ class WorkflowCommand(ServiceCommand):
|
|
70
70
|
@property
|
71
71
|
def custom_compose_path(self):
|
72
72
|
return os.path.join(
|
73
|
-
self.
|
73
|
+
self.data_dir_path,
|
74
74
|
self.custom_compose_relative_path
|
75
75
|
)
|
76
76
|
|
@@ -114,7 +114,7 @@ class WorkflowCommand(ServiceCommand):
|
|
114
114
|
@property
|
115
115
|
def workflow_path(self):
|
116
116
|
return os.path.join(
|
117
|
-
self.
|
117
|
+
self.data_dir_path,
|
118
118
|
self.workflow_relative_path
|
119
119
|
)
|
120
120
|
|
@@ -17,7 +17,6 @@ CORE_WORKFLOWS = [WORKFLOW_MOCK_TYPE, WORKFLOW_RECORD_TYPE, WORKFLOW_TEST_TYPE]
|
|
17
17
|
|
18
18
|
class BuildOptions(TypedDict):
|
19
19
|
builder_class: type
|
20
|
-
headless: bool
|
21
20
|
service_builder: ServiceBuilder
|
22
21
|
template: WORKFLOW_TEMPLATE
|
23
22
|
workflow_decorators: List[Union[MockDecorator, ReverseProxyDecorator]]
|
@@ -12,42 +12,47 @@ from stoobly_agent.lib.logger import Logger
|
|
12
12
|
from .app import App
|
13
13
|
from .constants import (
|
14
14
|
APP_NETWORK_ENV, CA_CERTS_DIR_ENV, CERTS_DIR_ENV, CONTEXT_DIR_ENV, NAMESERVERS_FILE,
|
15
|
-
SERVICE_DNS_ENV, SERVICE_NAME_ENV, USER_ID_ENV, WORKFLOW_NAME_ENV
|
15
|
+
SERVICE_DNS_ENV, SERVICE_NAME_ENV, USER_ID_ENV, WORKFLOW_NAME_ENV, WORKFLOW_NAMESPACE_ENV
|
16
16
|
)
|
17
|
+
from .docker.constants import DOCKERFILE_CONTEXT
|
17
18
|
from .workflow_command import WorkflowCommand
|
18
19
|
from .workflow_env import WorkflowEnv
|
19
20
|
|
20
21
|
LOG_ID = 'WorkflowRunCommand'
|
21
22
|
|
22
|
-
class
|
23
|
-
attached: bool
|
23
|
+
class ComposeOptions(TypedDict):
|
24
24
|
namespace: str
|
25
|
-
|
25
|
+
user_id: str
|
26
|
+
|
27
|
+
class BuildOptions(ComposeOptions):
|
28
|
+
user_id: str
|
26
29
|
verbose: bool
|
27
30
|
|
31
|
+
class DownOptions(ComposeOptions):
|
32
|
+
extra_compose_path: str
|
33
|
+
rmi: bool
|
34
|
+
|
35
|
+
class UpOptions(ComposeOptions):
|
36
|
+
attached: bool
|
37
|
+
extra_compose_path: str
|
38
|
+
pull: bool
|
39
|
+
|
28
40
|
class WorkflowRunCommand(WorkflowCommand):
|
29
41
|
def __init__(self, app: App, **kwargs):
|
30
42
|
super().__init__(app, **kwargs)
|
31
43
|
|
32
44
|
self.__current_working_dir = os.getcwd()
|
33
|
-
self.__ca_certs_dir_path = app.ca_certs_dir_path
|
34
|
-
self.__certs_dir_path = app.certs_dir_path
|
35
|
-
self.__context_dir_path = app.context_dir_path
|
36
|
-
self.__extra_compose_path = kwargs.get('extra_compose_path')
|
45
|
+
self.__ca_certs_dir_path = kwargs.get('ca_certs_dir_path') or app.ca_certs_dir_path
|
46
|
+
self.__certs_dir_path = kwargs.get('certs_dir_path') or app.certs_dir_path
|
47
|
+
self.__context_dir_path = kwargs.get('context_dir_path') or app.context_dir_path
|
37
48
|
self.__network = kwargs.get('network') or self.app_config.network
|
38
49
|
|
39
50
|
@property
|
40
51
|
def ca_certs_dir_path(self):
|
41
|
-
if not os.path.exists(self.__ca_certs_dir_path):
|
42
|
-
os.makedirs(self.__ca_certs_dir_path)
|
43
|
-
|
44
52
|
return self.__ca_certs_dir_path
|
45
53
|
|
46
54
|
@property
|
47
55
|
def certs_dir_path(self):
|
48
|
-
if not os.path.exists(self.__certs_dir_path):
|
49
|
-
os.makedirs(self.__certs_dir_path)
|
50
|
-
|
51
56
|
return self.__certs_dir_path
|
52
57
|
|
53
58
|
@property
|
@@ -66,10 +71,6 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
66
71
|
def current_working_dir(self, v):
|
67
72
|
self.__current_working_dir = v
|
68
73
|
|
69
|
-
@property
|
70
|
-
def extra_compose_path(self):
|
71
|
-
return self.__extra_compose_path
|
72
|
-
|
73
74
|
@property
|
74
75
|
def nameservers(self):
|
75
76
|
path = self.nameservers_path
|
@@ -88,17 +89,43 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
88
89
|
def network(self):
|
89
90
|
return self.__network
|
90
91
|
|
92
|
+
def create_image(self, **options: BuildOptions):
|
93
|
+
relative_namespace_path = os.path.relpath(self.scaffold_namespace_path, self.__current_working_dir)
|
94
|
+
dockerfile_path = os.path.join(relative_namespace_path, DOCKERFILE_CONTEXT)
|
95
|
+
user_id = options['user_id'] or os.getuid()
|
96
|
+
|
97
|
+
command = ['docker', 'build']
|
98
|
+
command.append(f"-f {dockerfile_path}")
|
99
|
+
command.append(f"-t stoobly.{user_id}")
|
100
|
+
command.append(f"--build-arg USER_ID={user_id}")
|
101
|
+
|
102
|
+
if not os.environ.get('STOOBLY_IMAGE_USE_LOCAL'):
|
103
|
+
command.append('--pull')
|
104
|
+
|
105
|
+
if not options.get('verbose'):
|
106
|
+
command.append('--quiet')
|
107
|
+
|
108
|
+
# To avoid large context transfer times, should be a folder with relatively low number of files
|
109
|
+
command.append(relative_namespace_path)
|
110
|
+
|
111
|
+
return ' '.join(command)
|
112
|
+
|
113
|
+
def remove_image(self, user_id: str = None):
|
114
|
+
user_id = user_id or os.getuid()
|
115
|
+
command = ['docker', 'rmi', f"stoobly.{user_id}", '&>', '/dev/null']
|
116
|
+
command.append('|| true')
|
117
|
+
return ' '.join(command)
|
118
|
+
|
91
119
|
def create_network(self):
|
92
|
-
return f"docker network create {self.network}
|
120
|
+
return f"docker network create {self.network} &> /dev/null"
|
93
121
|
|
94
122
|
def remove_network(self):
|
95
|
-
return f"docker network rm {self.network}
|
123
|
+
return f"docker network rm {self.network} &> /dev/null || true"
|
96
124
|
|
97
125
|
def up(self, **options: UpOptions):
|
98
126
|
if not os.path.exists(self.compose_path):
|
99
127
|
return ''
|
100
128
|
|
101
|
-
build_command = ['docker', 'compose']
|
102
129
|
command = ['COMPOSE_IGNORE_ORPHANS=true', 'docker', 'compose']
|
103
130
|
command_options = []
|
104
131
|
|
@@ -123,27 +150,24 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
123
150
|
|
124
151
|
command_options.append(f"-f {os.path.relpath(self.custom_compose_path, self.__current_working_dir)}")
|
125
152
|
|
126
|
-
if
|
127
|
-
command_options.append(f"-f {os.path.relpath(
|
153
|
+
if options.get('extra_compose_path'):
|
154
|
+
command_options.append(f"-f {os.path.relpath(options['extra_compose_path'], self.__current_working_dir)}")
|
128
155
|
|
129
156
|
command_options.append(f"--profile {self.workflow_name}")
|
130
157
|
|
131
|
-
if options.get('namespace'):
|
132
|
-
|
133
|
-
|
134
|
-
build_command += command_options
|
135
|
-
build_command.append('build')
|
136
|
-
build_command.append('--pull')
|
137
|
-
|
138
|
-
if not options.get('verbose'):
|
139
|
-
build_command.append('--quiet')
|
140
|
-
|
141
|
-
if options.get('no_cache'):
|
142
|
-
build_command.append('--no-cache')
|
158
|
+
if not options.get('namespace'):
|
159
|
+
options['namespace'] = self.workflow_name
|
160
|
+
command_options.append(f"-p {options['namespace']}")
|
143
161
|
|
144
162
|
command += command_options
|
145
163
|
command.append('up')
|
146
164
|
|
165
|
+
if options.get('build'):
|
166
|
+
command.append('--build')
|
167
|
+
|
168
|
+
if options.get('pull'):
|
169
|
+
command.append('--pull missing')
|
170
|
+
|
147
171
|
if not options.get('attached'):
|
148
172
|
command.append('-d')
|
149
173
|
else:
|
@@ -159,11 +183,11 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
159
183
|
# Otherwise, even if a service exits with a non-zero exit code, exit code 0 is returned
|
160
184
|
command.append(option)
|
161
185
|
|
162
|
-
self.write_env()
|
186
|
+
self.write_env(**options)
|
163
187
|
|
164
|
-
return '
|
188
|
+
return ' '.join(command)
|
165
189
|
|
166
|
-
def down(self, **options):
|
190
|
+
def down(self, **options: DownOptions):
|
167
191
|
if not os.path.exists(self.compose_path):
|
168
192
|
return ''
|
169
193
|
|
@@ -176,18 +200,21 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
176
200
|
if self.custom_services:
|
177
201
|
command.append(f"-f {os.path.relpath(self.custom_compose_path, self.__current_working_dir)}")
|
178
202
|
|
179
|
-
if
|
180
|
-
command.append(f"-f {os.path.relpath(
|
203
|
+
if options.get('extra_compose_path'):
|
204
|
+
command.append(f"-f {os.path.relpath(options['extra_compose_path'], self.__current_working_dir)}")
|
181
205
|
|
182
206
|
command.append(f"--profile {self.workflow_name}")
|
183
207
|
|
184
|
-
if options.get('namespace'):
|
185
|
-
|
208
|
+
if not options.get('namespace'):
|
209
|
+
options['namespace'] = self.workflow_name
|
210
|
+
command.append(f"-p {options['namespace']}")
|
186
211
|
|
187
212
|
command.append('down')
|
188
213
|
|
189
214
|
if options.get('rmi'):
|
190
|
-
command.append(
|
215
|
+
command.append('--rmi local')
|
216
|
+
|
217
|
+
self.write_env(**options)
|
191
218
|
|
192
219
|
return ' '.join(command)
|
193
220
|
|
@@ -212,14 +239,20 @@ class WorkflowRunCommand(WorkflowCommand):
|
|
212
239
|
if nameservers:
|
213
240
|
fp.write("\n".join(nameservers))
|
214
241
|
|
215
|
-
def write_env(self):
|
242
|
+
def write_env(self, **options: ComposeOptions):
|
243
|
+
namespace = options.get('namespace')
|
244
|
+
user_id = options.get('user_id')
|
245
|
+
|
216
246
|
_config = {}
|
217
247
|
_config[CA_CERTS_DIR_ENV] = self.ca_certs_dir_path
|
218
248
|
_config[CERTS_DIR_ENV] = self.certs_dir_path
|
219
249
|
_config[CONTEXT_DIR_ENV] = self.context_dir_path
|
220
250
|
_config[SERVICE_NAME_ENV] = self.service_name
|
221
|
-
_config[USER_ID_ENV] = os.getuid()
|
251
|
+
_config[USER_ID_ENV] = user_id or os.getuid()
|
222
252
|
_config[WORKFLOW_NAME_ENV] = self.workflow_name
|
253
|
+
|
254
|
+
if namespace:
|
255
|
+
_config[WORKFLOW_NAMESPACE_ENV] = namespace
|
223
256
|
|
224
257
|
if self.network:
|
225
258
|
_config[APP_NETWORK_ENV] = self.network
|