thestage 0.6.1__py3-none-any.whl → 0.6.3__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.
Files changed (177) hide show
  1. thestage/.env +4 -5
  2. thestage/__init__.py +3 -3
  3. thestage/__main__.py +9 -9
  4. thestage/cli_command.py +56 -56
  5. thestage/cli_command_helper.py +51 -51
  6. thestage/color_scheme/color_scheme.py +7 -7
  7. thestage/config/__init__.py +18 -18
  8. thestage/config/config_storage.py +5 -5
  9. thestage/config/env_base.py +7 -7
  10. thestage/controllers/__init__.py +0 -0
  11. thestage/controllers/base_controller.py +67 -67
  12. thestage/controllers/config_controller.py +137 -137
  13. thestage/controllers/container_controller.py +389 -389
  14. thestage/controllers/instance_controller.py +183 -183
  15. thestage/controllers/project_controller.py +810 -802
  16. thestage/controllers/utils_controller.py +32 -32
  17. thestage/debug_main.dist.py +28 -28
  18. thestage/entities/__init__.py +0 -0
  19. thestage/entities/container.py +17 -17
  20. thestage/entities/enums/__init__.py +0 -0
  21. thestage/entities/enums/order_direction_type.py +6 -6
  22. thestage/entities/enums/shell_type.py +7 -7
  23. thestage/entities/enums/tail_output_type.py +6 -6
  24. thestage/entities/enums/yes_no_response.py +7 -7
  25. thestage/entities/file_item.py +27 -27
  26. thestage/entities/project_inference_simulator.py +18 -18
  27. thestage/entities/project_inference_simulator_model.py +16 -16
  28. thestage/entities/project_task.py +19 -19
  29. thestage/entities/rented_instance.py +19 -19
  30. thestage/entities/self_hosted_instance.py +18 -18
  31. thestage/exceptions/__init__.py +0 -0
  32. thestage/exceptions/auth_exception.py +6 -6
  33. thestage/exceptions/base_exception.py +13 -13
  34. thestage/exceptions/business_logic_exception.py +6 -6
  35. thestage/exceptions/config_exception.py +6 -6
  36. thestage/exceptions/file_system_exception.py +6 -6
  37. thestage/exceptions/git_access_exception.py +17 -17
  38. thestage/exceptions/remote_server_exception.py +24 -24
  39. thestage/git/ProgressPrinter.py +22 -22
  40. thestage/helpers/__init__.py +0 -0
  41. thestage/helpers/error_handler.py +115 -115
  42. thestage/helpers/exception_hook.py +14 -14
  43. thestage/helpers/logger/__init__.py +0 -0
  44. thestage/helpers/logger/app_logger.py +50 -50
  45. thestage/helpers/ssh_util.py +38 -38
  46. thestage/i18n/en_GB/messages.po +947 -947
  47. thestage/i18n/translation.py +9 -9
  48. thestage/main.py +36 -36
  49. thestage/services/.env +6 -6
  50. thestage/services/__init__.py +0 -0
  51. thestage/services/abstract_mapper.py +9 -9
  52. thestage/services/abstract_service.py +87 -87
  53. thestage/services/app_config_service.py +52 -52
  54. thestage/services/clients/__init__.py +0 -0
  55. thestage/services/clients/git/__init__.py +0 -0
  56. thestage/services/clients/git/git_client.py +436 -433
  57. thestage/services/clients/thestage_api/__init__.py +0 -0
  58. thestage/services/clients/thestage_api/api_client.py +718 -718
  59. thestage/services/clients/thestage_api/core/api_client_core.py +108 -108
  60. thestage/services/clients/thestage_api/core/http_client_exception.py +12 -12
  61. thestage/services/clients/thestage_api/dtos/__init__.py +0 -0
  62. thestage/services/clients/thestage_api/dtos/base_response.py +13 -13
  63. thestage/services/clients/thestage_api/dtos/cloud_provider_region.py +19 -19
  64. thestage/services/clients/thestage_api/dtos/container_param_request.py +11 -11
  65. thestage/services/clients/thestage_api/dtos/container_response.py +67 -67
  66. thestage/services/clients/thestage_api/dtos/docker_container_assigned_device.py +10 -10
  67. thestage/services/clients/thestage_api/dtos/docker_container_controller/docker_container_list_request.py +13 -13
  68. thestage/services/clients/thestage_api/dtos/docker_container_controller/docker_container_list_response.py +13 -13
  69. thestage/services/clients/thestage_api/dtos/docker_container_mapping.py +10 -10
  70. thestage/services/clients/thestage_api/dtos/entity_filter_request.py +14 -14
  71. thestage/services/clients/thestage_api/dtos/enums/__init__.py +0 -0
  72. thestage/services/clients/thestage_api/dtos/enums/container_pending_action.py +10 -10
  73. thestage/services/clients/thestage_api/dtos/enums/container_status.py +17 -17
  74. thestage/services/clients/thestage_api/dtos/enums/cpu_type.py +8 -8
  75. thestage/services/clients/thestage_api/dtos/enums/currency_type.py +10 -10
  76. thestage/services/clients/thestage_api/dtos/enums/daemon_status.py +9 -9
  77. thestage/services/clients/thestage_api/dtos/enums/disk_type.py +7 -7
  78. thestage/services/clients/thestage_api/dtos/enums/drive_type.py +7 -7
  79. thestage/services/clients/thestage_api/dtos/enums/gpu_name.py +8 -8
  80. thestage/services/clients/thestage_api/dtos/enums/inference_model_status.py +9 -9
  81. thestage/services/clients/thestage_api/dtos/enums/inference_simulator_status.py +15 -15
  82. thestage/services/clients/thestage_api/dtos/enums/instance_rented_status.py +17 -17
  83. thestage/services/clients/thestage_api/dtos/enums/instance_type.py +7 -7
  84. thestage/services/clients/thestage_api/dtos/enums/location_region.py +11 -11
  85. thestage/services/clients/thestage_api/dtos/enums/power_status.py +10 -10
  86. thestage/services/clients/thestage_api/dtos/enums/provider_name.py +11 -11
  87. thestage/services/clients/thestage_api/dtos/enums/selfhosted_status.py +10 -10
  88. thestage/services/clients/thestage_api/dtos/enums/task_execution_status.py +12 -12
  89. thestage/services/clients/thestage_api/dtos/enums/task_status.py +12 -12
  90. thestage/services/clients/thestage_api/dtos/frontend_status.py +10 -10
  91. thestage/services/clients/thestage_api/dtos/inference_controller/deploy_inference_model_to_instance_request.py +13 -13
  92. thestage/services/clients/thestage_api/dtos/inference_controller/deploy_inference_model_to_instance_response.py +13 -13
  93. thestage/services/clients/thestage_api/dtos/inference_controller/deploy_inference_model_to_sagemaker_request.py +12 -12
  94. thestage/services/clients/thestage_api/dtos/inference_controller/deploy_inference_model_to_sagemaker_response.py +12 -12
  95. thestage/services/clients/thestage_api/dtos/inference_controller/get_inference_simulator_request.py +10 -10
  96. thestage/services/clients/thestage_api/dtos/inference_controller/get_inference_simulator_response.py +13 -13
  97. thestage/services/clients/thestage_api/dtos/inference_controller/inference_simulator_list_for_project_request.py +14 -14
  98. thestage/services/clients/thestage_api/dtos/inference_controller/inference_simulator_list_for_project_response.py +12 -12
  99. thestage/services/clients/thestage_api/dtos/inference_controller/inference_simulator_model_list_for_project_request.py +12 -12
  100. thestage/services/clients/thestage_api/dtos/inference_controller/inference_simulator_model_list_for_project_response.py +13 -13
  101. thestage/services/clients/thestage_api/dtos/inference_simulator_model_response.py +11 -11
  102. thestage/services/clients/thestage_api/dtos/inference_simulator_response.py +11 -11
  103. thestage/services/clients/thestage_api/dtos/installed_service.py +17 -17
  104. thestage/services/clients/thestage_api/dtos/instance_detected_gpus.py +20 -20
  105. thestage/services/clients/thestage_api/dtos/instance_rented_response.py +71 -71
  106. thestage/services/clients/thestage_api/dtos/logging_controller/docker_container_log_stream_request.py +7 -7
  107. thestage/services/clients/thestage_api/dtos/logging_controller/log_polling_request.py +13 -13
  108. thestage/services/clients/thestage_api/dtos/logging_controller/log_polling_response.py +14 -14
  109. thestage/services/clients/thestage_api/dtos/logging_controller/task_log_stream_request.py +7 -7
  110. thestage/services/clients/thestage_api/dtos/logging_controller/user_logs_query_request.py +21 -21
  111. thestage/services/clients/thestage_api/dtos/logging_controller/user_logs_query_response.py +14 -14
  112. thestage/services/clients/thestage_api/dtos/paginated_entity_list.py +11 -11
  113. thestage/services/clients/thestage_api/dtos/pagination_data.py +10 -10
  114. thestage/services/clients/thestage_api/dtos/price_definition.py +14 -14
  115. thestage/services/clients/thestage_api/dtos/project_controller/project_get_deploy_ssh_key_request.py +7 -7
  116. thestage/services/clients/thestage_api/dtos/project_controller/project_get_deploy_ssh_key_response.py +10 -10
  117. thestage/services/clients/thestage_api/dtos/project_controller/project_push_inference_simulator_model_request.py +8 -8
  118. thestage/services/clients/thestage_api/dtos/project_controller/project_push_inference_simulator_model_response.py +6 -6
  119. thestage/services/clients/thestage_api/dtos/project_controller/project_run_task_request.py +15 -15
  120. thestage/services/clients/thestage_api/dtos/project_controller/project_run_task_response.py +10 -10
  121. thestage/services/clients/thestage_api/dtos/project_controller/project_start_inference_simulator_request.py +13 -13
  122. thestage/services/clients/thestage_api/dtos/project_controller/project_start_inference_simulator_response.py +10 -10
  123. thestage/services/clients/thestage_api/dtos/project_response.py +32 -32
  124. thestage/services/clients/thestage_api/dtos/selfhosted_instance_response.py +56 -56
  125. thestage/services/clients/thestage_api/dtos/sftp_path_helper.py +13 -13
  126. thestage/services/clients/thestage_api/dtos/ssh_key_controller/add_ssh_key_to_user_request.py +8 -8
  127. thestage/services/clients/thestage_api/dtos/ssh_key_controller/add_ssh_key_to_user_response.py +11 -11
  128. thestage/services/clients/thestage_api/dtos/ssh_key_controller/add_ssh_public_key_to_instance_request.py +8 -8
  129. thestage/services/clients/thestage_api/dtos/ssh_key_controller/add_ssh_public_key_to_instance_response.py +11 -11
  130. thestage/services/clients/thestage_api/dtos/ssh_key_controller/is_user_has_public_ssh_key_request.py +7 -7
  131. thestage/services/clients/thestage_api/dtos/ssh_key_controller/is_user_has_public_ssh_key_response.py +12 -12
  132. thestage/services/clients/thestage_api/dtos/task_controller/task_list_for_project_request.py +10 -10
  133. thestage/services/clients/thestage_api/dtos/task_controller/task_list_for_project_response.py +12 -12
  134. thestage/services/clients/thestage_api/dtos/task_controller/task_status_localized_map_response.py +9 -9
  135. thestage/services/clients/thestage_api/dtos/task_controller/task_view_response.py +12 -12
  136. thestage/services/clients/thestage_api/dtos/user_controller/user_profile.py +12 -12
  137. thestage/services/clients/thestage_api/dtos/validate_token_response.py +11 -11
  138. thestage/services/config_provider/__init__.py +0 -0
  139. thestage/services/config_provider/config_provider.py +237 -237
  140. thestage/services/connect/connect_service.py +193 -196
  141. thestage/services/connect/dto/remote_server_config.py +9 -9
  142. thestage/services/container/__init__.py +0 -0
  143. thestage/services/container/container_service.py +374 -374
  144. thestage/services/container/mapper/__init__.py +0 -0
  145. thestage/services/container/mapper/container_mapper.py +30 -30
  146. thestage/services/core_files/config_entity.py +26 -26
  147. thestage/services/filesystem_service.py +133 -133
  148. thestage/services/instance/__init__.py +0 -0
  149. thestage/services/instance/instance_service.py +303 -303
  150. thestage/services/instance/mapper/__init__.py +0 -0
  151. thestage/services/instance/mapper/instance_mapper.py +24 -24
  152. thestage/services/instance/mapper/selfhosted_mapper.py +33 -33
  153. thestage/services/logging/byte_print_style.py +5 -5
  154. thestage/services/logging/dto/log_message.py +15 -15
  155. thestage/services/logging/dto/log_type.py +6 -6
  156. thestage/services/logging/exception/log_polling_exception.py +6 -6
  157. thestage/services/logging/logging_constants.py +3 -3
  158. thestage/services/logging/logging_service.py +367 -367
  159. thestage/services/project/__init__.py +0 -0
  160. thestage/services/project/dto/inference_simulator_dto.py +22 -22
  161. thestage/services/project/dto/inference_simulator_model_dto.py +20 -20
  162. thestage/services/project/dto/project_config.py +14 -14
  163. thestage/services/project/mapper/__init__.py +0 -0
  164. thestage/services/project/mapper/project_inference_simulator_mapper.py +21 -21
  165. thestage/services/project/mapper/project_inference_simulator_model_mapper.py +21 -21
  166. thestage/services/project/mapper/project_task_mapper.py +22 -22
  167. thestage/services/project/project_service.py +1253 -1260
  168. thestage/services/remote_server_service.py +609 -609
  169. thestage/services/service_factory.py +97 -97
  170. thestage/services/task/dto/task_dto.py +40 -40
  171. thestage/services/validation_service.py +61 -61
  172. {thestage-0.6.1.dist-info → thestage-0.6.3.dist-info}/LICENSE.txt +12 -12
  173. {thestage-0.6.1.dist-info → thestage-0.6.3.dist-info}/METADATA +3 -2
  174. thestage-0.6.3.dist-info/RECORD +176 -0
  175. {thestage-0.6.1.dist-info → thestage-0.6.3.dist-info}/WHEEL +1 -1
  176. thestage-0.6.1.dist-info/RECORD +0 -176
  177. {thestage-0.6.1.dist-info → thestage-0.6.3.dist-info}/entry_points.txt +0 -0
@@ -1,183 +1,183 @@
1
- from pathlib import Path
2
- from typing import Optional, List
3
-
4
- from thestage.cli_command import CliCommand
5
- from thestage.cli_command_helper import get_command_group_help_panel, get_command_metadata, check_command_permission
6
- from thestage.helpers.logger.app_logger import app_logger
7
- from thestage.services.instance.instance_service import InstanceService
8
- from thestage.i18n.translation import __
9
- from thestage.controllers.utils_controller import \
10
- validate_config_and_get_service_factory, get_current_directory
11
-
12
- import typer
13
-
14
-
15
- app = typer.Typer(no_args_is_help=True, help=__("Manage server instances"))
16
-
17
- rented = typer.Typer(no_args_is_help=True, help=__("Manage rented server instances"))
18
- self_hosted = typer.Typer(no_args_is_help=True, help=__("Manage self-hosted instances"))
19
-
20
- app.add_typer(rented, name="rented", rich_help_panel=get_command_group_help_panel())
21
- app.add_typer(self_hosted, name="self-hosted", rich_help_panel=get_command_group_help_panel())
22
-
23
-
24
- @rented.command(name="ls", help=__("List rented server instances"), **get_command_metadata(CliCommand.INSTANCE_RENTED_LS))
25
- def rented_list(
26
- row: int = typer.Option(
27
- 5,
28
- '--row',
29
- '-r',
30
- help=__("Set number of rows displayed per page"),
31
- is_eager=False,
32
- ),
33
- page: int = typer.Option(
34
- 1,
35
- '--page',
36
- '-p',
37
- help=__("Set starting page for displaying output"),
38
- is_eager=False,
39
- ),
40
- statuses: List[str] = typer.Option(
41
- None,
42
- '--status',
43
- '-s',
44
- help=__("Filter by status, use --status all to list all rented server instances"),
45
- is_eager=False,
46
- ),
47
- ):
48
- command_name = CliCommand.INSTANCE_RENTED_LS
49
- app_logger.info(f'Running {command_name} from {get_current_directory()}')
50
- check_command_permission(command_name)
51
-
52
- service_factory = validate_config_and_get_service_factory()
53
- instance_service: InstanceService = service_factory.get_instance_service()
54
-
55
- instance_service.print_rented_instance_list(
56
- statuses=statuses,
57
- row=row,
58
- page=page
59
- )
60
-
61
- typer.echo(__("Rented server instances listing complete"))
62
- raise typer.Exit(0)
63
-
64
-
65
- @rented.command(name="connect", no_args_is_help=True, help=__("Connect to rented server instance"), **get_command_metadata(CliCommand.INSTANCE_RENTED_CONNECT))
66
- def instance_connect(
67
- instance_uid: Optional[str] = typer.Argument(
68
- help=__("Rented server instance unique ID"),
69
- ),
70
- private_ssh_key_path: str = typer.Option(
71
- None,
72
- "--private-key-path",
73
- "-pk",
74
- help=__("Path to private key that will be accepted by remote server (optional)"),
75
- is_eager=False,
76
- )
77
- ):
78
- command_name = CliCommand.INSTANCE_RENTED_CONNECT
79
- app_logger.info(f'Running {command_name} from {get_current_directory()}')
80
- check_command_permission(command_name)
81
-
82
- if not instance_uid:
83
- typer.echo(__('Rented server instance unique ID is required'))
84
- raise typer.Exit(1)
85
-
86
- if private_ssh_key_path and not Path(private_ssh_key_path).is_file():
87
- typer.echo(f'No file found at provided path {private_ssh_key_path}')
88
- raise typer.Exit(1)
89
-
90
- service_factory = validate_config_and_get_service_factory()
91
- instance_service: InstanceService = service_factory.get_instance_service()
92
-
93
- instance_service.connect_to_rented_instance(
94
- instance_rented_slug=instance_uid,
95
- input_ssh_key_path=private_ssh_key_path
96
- )
97
-
98
- app_logger.info(f'Stop connecting to rented server instance')
99
- raise typer.Exit(0)
100
-
101
-
102
- @self_hosted.command(name="ls", help=__("List self-hosted instances"), **get_command_metadata(CliCommand.INSTANCE_SELF_HOSTED_LS))
103
- def self_hosted_list(
104
- row: int = typer.Option(
105
- 5,
106
- '--row',
107
- '-r',
108
- help=__("Set number of rows displayed per page"),
109
- is_eager=False,
110
- ),
111
- page: int = typer.Option(
112
- 1,
113
- '--page',
114
- '-p',
115
- help=__("Set starting page for displaying output"),
116
- is_eager=False,
117
- ),
118
- statuses: List[str] = typer.Option(
119
- None,
120
- '--status',
121
- '-s',
122
- help=__("Filter by status, use --status all to list all self-hosted server instances"),
123
- is_eager=False,
124
- ),
125
- ):
126
- command_name = CliCommand.INSTANCE_SELF_HOSTED_LS
127
- app_logger.info(f'Running {command_name} from {get_current_directory()}')
128
- check_command_permission(command_name)
129
-
130
- service_factory = validate_config_and_get_service_factory()
131
- instance_service: InstanceService = service_factory.get_instance_service()
132
-
133
- instance_service.print_self_hosted_instance_list(
134
- statuses=statuses,
135
- row=row,
136
- page=page
137
- )
138
-
139
- typer.echo(__("Self-hosted instances listing complete"))
140
- raise typer.Exit(0)
141
-
142
-
143
- @self_hosted.command(name="connect", no_args_is_help=True, help=__("Connect to self-hosted instance"), **get_command_metadata(CliCommand.INSTANCE_SELF_HOSTED_CONNECT))
144
- def self_hosted_connect(
145
- instance_slug: Optional[str] = typer.Argument(help=__("Self-hosted instance unique ID"),),
146
- username: Optional[str] = typer.Option(
147
- None,
148
- '--username',
149
- '-u',
150
- help=__("Username for server instance (required when connecting to self-hosted instance)"),
151
- is_eager=False,
152
- ),
153
- private_ssh_key_path: str = typer.Option(
154
- None,
155
- "--private-key-path",
156
- "-pk",
157
- help=__("Path to private key that will be accepted by remote server (optional)"),
158
- is_eager=False,
159
- ),
160
- ):
161
- command_name = CliCommand.INSTANCE_SELF_HOSTED_CONNECT
162
- app_logger.info(f'Running {command_name} from {get_current_directory()}')
163
- check_command_permission(command_name)
164
-
165
- if not instance_slug:
166
- typer.echo(__('Self-hosted instance unique ID is required'))
167
- raise typer.Exit(1)
168
-
169
- if private_ssh_key_path and not Path(private_ssh_key_path).is_file():
170
- typer.echo(f'No file found at provided path {private_ssh_key_path}')
171
- raise typer.Exit(1)
172
-
173
- service_factory = validate_config_and_get_service_factory()
174
- instance_service: InstanceService = service_factory.get_instance_service()
175
-
176
- instance_service.connect_to_selfhosted_instance(
177
- selfhosted_instance_slug=instance_slug,
178
- username=username,
179
- input_ssh_key_path=private_ssh_key_path
180
- )
181
-
182
- app_logger.info(f'Stop connecting to self-hosted instance')
183
- raise typer.Exit(0)
1
+ from pathlib import Path
2
+ from typing import Optional, List
3
+
4
+ from thestage.cli_command import CliCommand
5
+ from thestage.cli_command_helper import get_command_group_help_panel, get_command_metadata, check_command_permission
6
+ from thestage.helpers.logger.app_logger import app_logger
7
+ from thestage.services.instance.instance_service import InstanceService
8
+ from thestage.i18n.translation import __
9
+ from thestage.controllers.utils_controller import \
10
+ validate_config_and_get_service_factory, get_current_directory
11
+
12
+ import typer
13
+
14
+
15
+ app = typer.Typer(no_args_is_help=True, help=__("Manage server instances"))
16
+
17
+ rented = typer.Typer(no_args_is_help=True, help=__("Manage rented server instances"))
18
+ self_hosted = typer.Typer(no_args_is_help=True, help=__("Manage self-hosted instances"))
19
+
20
+ app.add_typer(rented, name="rented", rich_help_panel=get_command_group_help_panel())
21
+ app.add_typer(self_hosted, name="self-hosted", rich_help_panel=get_command_group_help_panel())
22
+
23
+
24
+ @rented.command(name="ls", help=__("List rented server instances"), **get_command_metadata(CliCommand.INSTANCE_RENTED_LS))
25
+ def rented_list(
26
+ row: int = typer.Option(
27
+ 5,
28
+ '--row',
29
+ '-r',
30
+ help=__("Set number of rows displayed per page"),
31
+ is_eager=False,
32
+ ),
33
+ page: int = typer.Option(
34
+ 1,
35
+ '--page',
36
+ '-p',
37
+ help=__("Set starting page for displaying output"),
38
+ is_eager=False,
39
+ ),
40
+ statuses: List[str] = typer.Option(
41
+ None,
42
+ '--status',
43
+ '-s',
44
+ help=__("Filter by status, use --status all to list all rented server instances"),
45
+ is_eager=False,
46
+ ),
47
+ ):
48
+ command_name = CliCommand.INSTANCE_RENTED_LS
49
+ app_logger.info(f'Running {command_name} from {get_current_directory()}')
50
+ check_command_permission(command_name)
51
+
52
+ service_factory = validate_config_and_get_service_factory()
53
+ instance_service: InstanceService = service_factory.get_instance_service()
54
+
55
+ instance_service.print_rented_instance_list(
56
+ statuses=statuses,
57
+ row=row,
58
+ page=page
59
+ )
60
+
61
+ typer.echo(__("Rented server instances listing complete"))
62
+ raise typer.Exit(0)
63
+
64
+
65
+ @rented.command(name="connect", no_args_is_help=True, help=__("Connect to rented server instance"), **get_command_metadata(CliCommand.INSTANCE_RENTED_CONNECT))
66
+ def instance_connect(
67
+ instance_uid: Optional[str] = typer.Argument(
68
+ help=__("Rented server instance unique ID"),
69
+ ),
70
+ private_ssh_key_path: str = typer.Option(
71
+ None,
72
+ "--private-key-path",
73
+ "-pk",
74
+ help=__("Path to private key that will be accepted by remote server (optional)"),
75
+ is_eager=False,
76
+ )
77
+ ):
78
+ command_name = CliCommand.INSTANCE_RENTED_CONNECT
79
+ app_logger.info(f'Running {command_name} from {get_current_directory()}')
80
+ check_command_permission(command_name)
81
+
82
+ if not instance_uid:
83
+ typer.echo(__('Rented server instance unique ID is required'))
84
+ raise typer.Exit(1)
85
+
86
+ if private_ssh_key_path and not Path(private_ssh_key_path).is_file():
87
+ typer.echo(f'No file found at provided path {private_ssh_key_path}')
88
+ raise typer.Exit(1)
89
+
90
+ service_factory = validate_config_and_get_service_factory()
91
+ instance_service: InstanceService = service_factory.get_instance_service()
92
+
93
+ instance_service.connect_to_rented_instance(
94
+ instance_rented_slug=instance_uid,
95
+ input_ssh_key_path=private_ssh_key_path
96
+ )
97
+
98
+ app_logger.info(f'Stop connecting to rented server instance')
99
+ raise typer.Exit(0)
100
+
101
+
102
+ @self_hosted.command(name="ls", help=__("List self-hosted instances"), **get_command_metadata(CliCommand.INSTANCE_SELF_HOSTED_LS))
103
+ def self_hosted_list(
104
+ row: int = typer.Option(
105
+ 5,
106
+ '--row',
107
+ '-r',
108
+ help=__("Set number of rows displayed per page"),
109
+ is_eager=False,
110
+ ),
111
+ page: int = typer.Option(
112
+ 1,
113
+ '--page',
114
+ '-p',
115
+ help=__("Set starting page for displaying output"),
116
+ is_eager=False,
117
+ ),
118
+ statuses: List[str] = typer.Option(
119
+ None,
120
+ '--status',
121
+ '-s',
122
+ help=__("Filter by status, use --status all to list all self-hosted server instances"),
123
+ is_eager=False,
124
+ ),
125
+ ):
126
+ command_name = CliCommand.INSTANCE_SELF_HOSTED_LS
127
+ app_logger.info(f'Running {command_name} from {get_current_directory()}')
128
+ check_command_permission(command_name)
129
+
130
+ service_factory = validate_config_and_get_service_factory()
131
+ instance_service: InstanceService = service_factory.get_instance_service()
132
+
133
+ instance_service.print_self_hosted_instance_list(
134
+ statuses=statuses,
135
+ row=row,
136
+ page=page
137
+ )
138
+
139
+ typer.echo(__("Self-hosted instances listing complete"))
140
+ raise typer.Exit(0)
141
+
142
+
143
+ @self_hosted.command(name="connect", no_args_is_help=True, help=__("Connect to self-hosted instance"), **get_command_metadata(CliCommand.INSTANCE_SELF_HOSTED_CONNECT))
144
+ def self_hosted_connect(
145
+ instance_slug: Optional[str] = typer.Argument(help=__("Self-hosted instance unique ID"),),
146
+ username: Optional[str] = typer.Option(
147
+ None,
148
+ '--username',
149
+ '-u',
150
+ help=__("Username for server instance (required when connecting to self-hosted instance)"),
151
+ is_eager=False,
152
+ ),
153
+ private_ssh_key_path: str = typer.Option(
154
+ None,
155
+ "--private-key-path",
156
+ "-pk",
157
+ help=__("Path to private key that will be accepted by remote server (optional)"),
158
+ is_eager=False,
159
+ ),
160
+ ):
161
+ command_name = CliCommand.INSTANCE_SELF_HOSTED_CONNECT
162
+ app_logger.info(f'Running {command_name} from {get_current_directory()}')
163
+ check_command_permission(command_name)
164
+
165
+ if not instance_slug:
166
+ typer.echo(__('Self-hosted instance unique ID is required'))
167
+ raise typer.Exit(1)
168
+
169
+ if private_ssh_key_path and not Path(private_ssh_key_path).is_file():
170
+ typer.echo(f'No file found at provided path {private_ssh_key_path}')
171
+ raise typer.Exit(1)
172
+
173
+ service_factory = validate_config_and_get_service_factory()
174
+ instance_service: InstanceService = service_factory.get_instance_service()
175
+
176
+ instance_service.connect_to_selfhosted_instance(
177
+ selfhosted_instance_slug=instance_slug,
178
+ username=username,
179
+ input_ssh_key_path=private_ssh_key_path
180
+ )
181
+
182
+ app_logger.info(f'Stop connecting to self-hosted instance')
183
+ raise typer.Exit(0)