snowflake-cli-labs 3.0.0rc5__py3-none-any.whl → 3.0.2__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 (244) hide show
  1. README.md +21 -0
  2. {snowflake_cli_labs-3.0.0rc5.dist-info → snowflake_cli_labs-3.0.2.dist-info}/METADATA +6 -96
  3. snowflake_cli_labs-3.0.2.dist-info/RECORD +5 -0
  4. snowflake/cli/__about__.py +0 -17
  5. snowflake/cli/__init__.py +0 -13
  6. snowflake/cli/_app/__init__.py +0 -22
  7. snowflake/cli/_app/__main__.py +0 -31
  8. snowflake/cli/_app/api_impl/__init__.py +0 -13
  9. snowflake/cli/_app/api_impl/plugin/__init__.py +0 -13
  10. snowflake/cli/_app/api_impl/plugin/plugin_config_provider_impl.py +0 -66
  11. snowflake/cli/_app/cli_app.py +0 -252
  12. snowflake/cli/_app/commands_registration/__init__.py +0 -33
  13. snowflake/cli/_app/commands_registration/builtin_plugins.py +0 -50
  14. snowflake/cli/_app/commands_registration/command_plugins_loader.py +0 -169
  15. snowflake/cli/_app/commands_registration/commands_registration_with_callbacks.py +0 -105
  16. snowflake/cli/_app/commands_registration/exception_logging.py +0 -26
  17. snowflake/cli/_app/commands_registration/threadsafe.py +0 -48
  18. snowflake/cli/_app/commands_registration/typer_registration.py +0 -153
  19. snowflake/cli/_app/constants.py +0 -19
  20. snowflake/cli/_app/dev/__init__.py +0 -13
  21. snowflake/cli/_app/dev/commands_structure.py +0 -48
  22. snowflake/cli/_app/dev/docs/__init__.py +0 -13
  23. snowflake/cli/_app/dev/docs/commands_docs_generator.py +0 -118
  24. snowflake/cli/_app/dev/docs/generator.py +0 -35
  25. snowflake/cli/_app/dev/docs/project_definition_docs_generator.py +0 -58
  26. snowflake/cli/_app/dev/docs/project_definition_generate_json_schema.py +0 -227
  27. snowflake/cli/_app/dev/docs/template_utils.py +0 -23
  28. snowflake/cli/_app/dev/docs/templates/definition_description.rst.jinja2 +0 -38
  29. snowflake/cli/_app/dev/docs/templates/overview.rst.jinja2 +0 -9
  30. snowflake/cli/_app/dev/docs/templates/usage.rst.jinja2 +0 -67
  31. snowflake/cli/_app/dev/pycharm_remote_debug.py +0 -46
  32. snowflake/cli/_app/loggers.py +0 -199
  33. snowflake/cli/_app/main_typer.py +0 -62
  34. snowflake/cli/_app/printing.py +0 -181
  35. snowflake/cli/_app/secret.py +0 -9
  36. snowflake/cli/_app/snow_connector.py +0 -309
  37. snowflake/cli/_app/telemetry.py +0 -220
  38. snowflake/cli/_app/version_check.py +0 -74
  39. snowflake/cli/_plugins/__init__.py +0 -13
  40. snowflake/cli/_plugins/connection/__init__.py +0 -13
  41. snowflake/cli/_plugins/connection/commands.py +0 -353
  42. snowflake/cli/_plugins/connection/plugin_spec.py +0 -30
  43. snowflake/cli/_plugins/connection/util.py +0 -195
  44. snowflake/cli/_plugins/cortex/__init__.py +0 -13
  45. snowflake/cli/_plugins/cortex/commands.py +0 -332
  46. snowflake/cli/_plugins/cortex/constants.py +0 -17
  47. snowflake/cli/_plugins/cortex/manager.py +0 -189
  48. snowflake/cli/_plugins/cortex/plugin_spec.py +0 -30
  49. snowflake/cli/_plugins/cortex/types.py +0 -22
  50. snowflake/cli/_plugins/git/__init__.py +0 -13
  51. snowflake/cli/_plugins/git/commands.py +0 -358
  52. snowflake/cli/_plugins/git/manager.py +0 -151
  53. snowflake/cli/_plugins/git/plugin_spec.py +0 -30
  54. snowflake/cli/_plugins/helpers/__init__.py +0 -13
  55. snowflake/cli/_plugins/helpers/commands.py +0 -90
  56. snowflake/cli/_plugins/helpers/plugin_spec.py +0 -30
  57. snowflake/cli/_plugins/init/__init__.py +0 -13
  58. snowflake/cli/_plugins/init/commands.py +0 -248
  59. snowflake/cli/_plugins/init/plugin_spec.py +0 -30
  60. snowflake/cli/_plugins/nativeapp/__init__.py +0 -13
  61. snowflake/cli/_plugins/nativeapp/artifacts.py +0 -757
  62. snowflake/cli/_plugins/nativeapp/bundle_context.py +0 -31
  63. snowflake/cli/_plugins/nativeapp/codegen/__init__.py +0 -13
  64. snowflake/cli/_plugins/nativeapp/codegen/artifact_processor.py +0 -91
  65. snowflake/cli/_plugins/nativeapp/codegen/compiler.py +0 -149
  66. snowflake/cli/_plugins/nativeapp/codegen/sandbox.py +0 -306
  67. snowflake/cli/_plugins/nativeapp/codegen/setup/native_app_setup_processor.py +0 -249
  68. snowflake/cli/_plugins/nativeapp/codegen/setup/setup_driver.py.source +0 -59
  69. snowflake/cli/_plugins/nativeapp/codegen/snowpark/callback_source.py.jinja +0 -181
  70. snowflake/cli/_plugins/nativeapp/codegen/snowpark/extension_function_utils.py +0 -217
  71. snowflake/cli/_plugins/nativeapp/codegen/snowpark/models.py +0 -61
  72. snowflake/cli/_plugins/nativeapp/codegen/snowpark/python_processor.py +0 -523
  73. snowflake/cli/_plugins/nativeapp/codegen/templates/templates_processor.py +0 -114
  74. snowflake/cli/_plugins/nativeapp/commands.py +0 -559
  75. snowflake/cli/_plugins/nativeapp/common_flags.py +0 -44
  76. snowflake/cli/_plugins/nativeapp/constants.py +0 -27
  77. snowflake/cli/_plugins/nativeapp/entities/__init__.py +0 -0
  78. snowflake/cli/_plugins/nativeapp/entities/application.py +0 -878
  79. snowflake/cli/_plugins/nativeapp/entities/application_package.py +0 -1392
  80. snowflake/cli/_plugins/nativeapp/exceptions.py +0 -113
  81. snowflake/cli/_plugins/nativeapp/feature_flags.py +0 -24
  82. snowflake/cli/_plugins/nativeapp/manager.py +0 -415
  83. snowflake/cli/_plugins/nativeapp/plugin_spec.py +0 -30
  84. snowflake/cli/_plugins/nativeapp/policy.py +0 -53
  85. snowflake/cli/_plugins/nativeapp/project_model.py +0 -211
  86. snowflake/cli/_plugins/nativeapp/run_processor.py +0 -184
  87. snowflake/cli/_plugins/nativeapp/same_account_install_method.py +0 -70
  88. snowflake/cli/_plugins/nativeapp/teardown_processor.py +0 -70
  89. snowflake/cli/_plugins/nativeapp/utils.py +0 -98
  90. snowflake/cli/_plugins/nativeapp/v2_conversions/v2_to_v1_decorator.py +0 -262
  91. snowflake/cli/_plugins/nativeapp/version/__init__.py +0 -13
  92. snowflake/cli/_plugins/nativeapp/version/commands.py +0 -141
  93. snowflake/cli/_plugins/nativeapp/version/version_processor.py +0 -98
  94. snowflake/cli/_plugins/notebook/__init__.py +0 -13
  95. snowflake/cli/_plugins/notebook/commands.py +0 -86
  96. snowflake/cli/_plugins/notebook/exceptions.py +0 -20
  97. snowflake/cli/_plugins/notebook/manager.py +0 -71
  98. snowflake/cli/_plugins/notebook/plugin_spec.py +0 -30
  99. snowflake/cli/_plugins/notebook/types.py +0 -15
  100. snowflake/cli/_plugins/object/__init__.py +0 -13
  101. snowflake/cli/_plugins/object/command_aliases.py +0 -95
  102. snowflake/cli/_plugins/object/commands.py +0 -180
  103. snowflake/cli/_plugins/object/common.py +0 -85
  104. snowflake/cli/_plugins/object/manager.py +0 -118
  105. snowflake/cli/_plugins/object/plugin_spec.py +0 -30
  106. snowflake/cli/_plugins/snowpark/__init__.py +0 -13
  107. snowflake/cli/_plugins/snowpark/commands.py +0 -450
  108. snowflake/cli/_plugins/snowpark/common.py +0 -268
  109. snowflake/cli/_plugins/snowpark/models.py +0 -150
  110. snowflake/cli/_plugins/snowpark/package/__init__.py +0 -13
  111. snowflake/cli/_plugins/snowpark/package/anaconda_packages.py +0 -199
  112. snowflake/cli/_plugins/snowpark/package/commands.py +0 -195
  113. snowflake/cli/_plugins/snowpark/package/manager.py +0 -44
  114. snowflake/cli/_plugins/snowpark/package/utils.py +0 -26
  115. snowflake/cli/_plugins/snowpark/package_utils.py +0 -354
  116. snowflake/cli/_plugins/snowpark/plugin_spec.py +0 -30
  117. snowflake/cli/_plugins/snowpark/snowpark_entity.py +0 -29
  118. snowflake/cli/_plugins/snowpark/snowpark_entity_model.py +0 -173
  119. snowflake/cli/_plugins/snowpark/snowpark_project_paths.py +0 -109
  120. snowflake/cli/_plugins/snowpark/snowpark_shared.py +0 -59
  121. snowflake/cli/_plugins/snowpark/zipper.py +0 -89
  122. snowflake/cli/_plugins/spcs/__init__.py +0 -33
  123. snowflake/cli/_plugins/spcs/common.py +0 -99
  124. snowflake/cli/_plugins/spcs/compute_pool/__init__.py +0 -13
  125. snowflake/cli/_plugins/spcs/compute_pool/commands.py +0 -241
  126. snowflake/cli/_plugins/spcs/compute_pool/manager.py +0 -121
  127. snowflake/cli/_plugins/spcs/image_registry/__init__.py +0 -13
  128. snowflake/cli/_plugins/spcs/image_registry/commands.py +0 -65
  129. snowflake/cli/_plugins/spcs/image_registry/manager.py +0 -105
  130. snowflake/cli/_plugins/spcs/image_repository/__init__.py +0 -13
  131. snowflake/cli/_plugins/spcs/image_repository/commands.py +0 -202
  132. snowflake/cli/_plugins/spcs/image_repository/manager.py +0 -84
  133. snowflake/cli/_plugins/spcs/plugin_spec.py +0 -30
  134. snowflake/cli/_plugins/spcs/services/__init__.py +0 -13
  135. snowflake/cli/_plugins/spcs/services/commands.py +0 -345
  136. snowflake/cli/_plugins/spcs/services/manager.py +0 -208
  137. snowflake/cli/_plugins/sql/__init__.py +0 -13
  138. snowflake/cli/_plugins/sql/commands.py +0 -86
  139. snowflake/cli/_plugins/sql/manager.py +0 -92
  140. snowflake/cli/_plugins/sql/plugin_spec.py +0 -30
  141. snowflake/cli/_plugins/sql/snowsql_templating.py +0 -28
  142. snowflake/cli/_plugins/stage/__init__.py +0 -13
  143. snowflake/cli/_plugins/stage/commands.py +0 -264
  144. snowflake/cli/_plugins/stage/diff.py +0 -280
  145. snowflake/cli/_plugins/stage/manager.py +0 -582
  146. snowflake/cli/_plugins/stage/md5.py +0 -160
  147. snowflake/cli/_plugins/stage/plugin_spec.py +0 -30
  148. snowflake/cli/_plugins/stage/utils.py +0 -54
  149. snowflake/cli/_plugins/streamlit/__init__.py +0 -13
  150. snowflake/cli/_plugins/streamlit/commands.py +0 -195
  151. snowflake/cli/_plugins/streamlit/manager.py +0 -220
  152. snowflake/cli/_plugins/streamlit/plugin_spec.py +0 -30
  153. snowflake/cli/_plugins/streamlit/streamlit_entity.py +0 -12
  154. snowflake/cli/_plugins/streamlit/streamlit_entity_model.py +0 -66
  155. snowflake/cli/_plugins/workspace/__init__.py +0 -13
  156. snowflake/cli/_plugins/workspace/action_context.py +0 -18
  157. snowflake/cli/_plugins/workspace/commands.py +0 -306
  158. snowflake/cli/_plugins/workspace/manager.py +0 -74
  159. snowflake/cli/_plugins/workspace/plugin_spec.py +0 -30
  160. snowflake/cli/api/__init__.py +0 -48
  161. snowflake/cli/api/cli_global_context.py +0 -247
  162. snowflake/cli/api/commands/__init__.py +0 -13
  163. snowflake/cli/api/commands/alias.py +0 -23
  164. snowflake/cli/api/commands/common.py +0 -25
  165. snowflake/cli/api/commands/decorators.py +0 -369
  166. snowflake/cli/api/commands/execution_metadata.py +0 -40
  167. snowflake/cli/api/commands/experimental_behaviour.py +0 -18
  168. snowflake/cli/api/commands/flags.py +0 -561
  169. snowflake/cli/api/commands/overrideable_parameter.py +0 -143
  170. snowflake/cli/api/commands/snow_typer.py +0 -247
  171. snowflake/cli/api/commands/utils.py +0 -18
  172. snowflake/cli/api/config.py +0 -380
  173. snowflake/cli/api/connections.py +0 -216
  174. snowflake/cli/api/console/__init__.py +0 -17
  175. snowflake/cli/api/console/abc.py +0 -94
  176. snowflake/cli/api/console/console.py +0 -134
  177. snowflake/cli/api/console/enum.py +0 -17
  178. snowflake/cli/api/constants.py +0 -90
  179. snowflake/cli/api/entities/common.py +0 -56
  180. snowflake/cli/api/entities/utils.py +0 -370
  181. snowflake/cli/api/errno.py +0 -28
  182. snowflake/cli/api/exceptions.py +0 -190
  183. snowflake/cli/api/feature_flags.py +0 -54
  184. snowflake/cli/api/identifiers.py +0 -190
  185. snowflake/cli/api/metrics.py +0 -92
  186. snowflake/cli/api/output/__init__.py +0 -13
  187. snowflake/cli/api/output/formats.py +0 -20
  188. snowflake/cli/api/output/types.py +0 -118
  189. snowflake/cli/api/plugins/__init__.py +0 -13
  190. snowflake/cli/api/plugins/command/__init__.py +0 -72
  191. snowflake/cli/api/plugins/command/plugin_hook_specs.py +0 -21
  192. snowflake/cli/api/plugins/plugin_config.py +0 -32
  193. snowflake/cli/api/project/__init__.py +0 -13
  194. snowflake/cli/api/project/definition.py +0 -126
  195. snowflake/cli/api/project/definition_conversion.py +0 -400
  196. snowflake/cli/api/project/definition_manager.py +0 -145
  197. snowflake/cli/api/project/errors.py +0 -56
  198. snowflake/cli/api/project/project_verification.py +0 -23
  199. snowflake/cli/api/project/schemas/__init__.py +0 -13
  200. snowflake/cli/api/project/schemas/entities/__init__.py +0 -13
  201. snowflake/cli/api/project/schemas/entities/common.py +0 -153
  202. snowflake/cli/api/project/schemas/entities/entities.py +0 -61
  203. snowflake/cli/api/project/schemas/project_definition.py +0 -330
  204. snowflake/cli/api/project/schemas/template.py +0 -77
  205. snowflake/cli/api/project/schemas/updatable_model.py +0 -202
  206. snowflake/cli/api/project/schemas/v1/__init__.py +0 -0
  207. snowflake/cli/api/project/schemas/v1/identifier_model.py +0 -51
  208. snowflake/cli/api/project/schemas/v1/native_app/__init__.py +0 -0
  209. snowflake/cli/api/project/schemas/v1/native_app/application.py +0 -61
  210. snowflake/cli/api/project/schemas/v1/native_app/native_app.py +0 -93
  211. snowflake/cli/api/project/schemas/v1/native_app/package.py +0 -84
  212. snowflake/cli/api/project/schemas/v1/native_app/path_mapping.py +0 -65
  213. snowflake/cli/api/project/schemas/v1/snowpark/__init__.py +0 -0
  214. snowflake/cli/api/project/schemas/v1/snowpark/argument.py +0 -28
  215. snowflake/cli/api/project/schemas/v1/snowpark/callable.py +0 -69
  216. snowflake/cli/api/project/schemas/v1/snowpark/snowpark.py +0 -36
  217. snowflake/cli/api/project/schemas/v1/streamlit/__init__.py +0 -0
  218. snowflake/cli/api/project/schemas/v1/streamlit/streamlit.py +0 -47
  219. snowflake/cli/api/project/util.py +0 -278
  220. snowflake/cli/api/rendering/__init__.py +0 -13
  221. snowflake/cli/api/rendering/jinja.py +0 -118
  222. snowflake/cli/api/rendering/project_definition_templates.py +0 -43
  223. snowflake/cli/api/rendering/project_templates.py +0 -98
  224. snowflake/cli/api/rendering/sql_templates.py +0 -105
  225. snowflake/cli/api/rest_api.py +0 -178
  226. snowflake/cli/api/sanitizers.py +0 -43
  227. snowflake/cli/api/secure_path.py +0 -360
  228. snowflake/cli/api/secure_utils.py +0 -118
  229. snowflake/cli/api/sql_execution.py +0 -280
  230. snowflake/cli/api/utils/__init__.py +0 -13
  231. snowflake/cli/api/utils/cursor.py +0 -34
  232. snowflake/cli/api/utils/definition_rendering.py +0 -415
  233. snowflake/cli/api/utils/dict_utils.py +0 -73
  234. snowflake/cli/api/utils/error_handling.py +0 -23
  235. snowflake/cli/api/utils/graph.py +0 -97
  236. snowflake/cli/api/utils/models.py +0 -63
  237. snowflake/cli/api/utils/naming_utils.py +0 -13
  238. snowflake/cli/api/utils/path_utils.py +0 -36
  239. snowflake/cli/api/utils/templating_functions.py +0 -144
  240. snowflake/cli/api/utils/types.py +0 -35
  241. snowflake_cli_labs-3.0.0rc5.dist-info/RECORD +0 -242
  242. snowflake_cli_labs-3.0.0rc5.dist-info/entry_points.txt +0 -2
  243. {snowflake_cli_labs-3.0.0rc5.dist-info → snowflake_cli_labs-3.0.2.dist-info}/WHEEL +0 -0
  244. {snowflake_cli_labs-3.0.0rc5.dist-info → snowflake_cli_labs-3.0.2.dist-info}/licenses/LICENSE +0 -0
@@ -1,202 +0,0 @@
1
- # Copyright (c) 2024 Snowflake Inc.
2
- #
3
- # Licensed under the Apache License, Version 2.0 (the "License");
4
- # you may not use this file except in compliance with the License.
5
- # You may obtain a copy of the License at
6
- #
7
- # http://www.apache.org/licenses/LICENSE-2.0
8
- #
9
- # Unless required by applicable law or agreed to in writing, software
10
- # distributed under the License is distributed on an "AS IS" BASIS,
11
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
- # See the License for the specific language governing permissions and
13
- # limitations under the License.
14
-
15
- from __future__ import annotations
16
-
17
- import json
18
- from typing import Optional
19
-
20
- import requests
21
- import typer
22
- from click import ClickException
23
- from snowflake.cli._plugins.object.command_aliases import (
24
- add_object_command_aliases,
25
- scope_option,
26
- )
27
- from snowflake.cli._plugins.spcs.image_registry.manager import RegistryManager
28
- from snowflake.cli._plugins.spcs.image_repository.manager import ImageRepositoryManager
29
- from snowflake.cli.api.commands.flags import (
30
- IfNotExistsOption,
31
- ReplaceOption,
32
- identifier_argument,
33
- like_option,
34
- )
35
- from snowflake.cli.api.commands.snow_typer import SnowTyperFactory
36
- from snowflake.cli.api.console import cli_console
37
- from snowflake.cli.api.constants import ObjectType
38
- from snowflake.cli.api.identifiers import FQN
39
- from snowflake.cli.api.output.types import (
40
- CollectionResult,
41
- MessageResult,
42
- SingleQueryResult,
43
- )
44
- from snowflake.cli.api.project.util import is_valid_object_name
45
-
46
- app = SnowTyperFactory(
47
- name="image-repository",
48
- help="Manages Snowpark Container Services image repositories.",
49
- short_help="Manages image repositories.",
50
- )
51
-
52
-
53
- def _repo_name_callback(name: FQN):
54
- if not is_valid_object_name(name.identifier, max_depth=2, allow_quoted=False):
55
- raise ClickException(
56
- f"'{name}' is not a valid image repository name. Note that image repository names must be unquoted identifiers. The same constraint also applies to database and schema names where you create an image repository."
57
- )
58
- return name
59
-
60
-
61
- REPO_NAME_ARGUMENT = identifier_argument(
62
- sf_object="image repository",
63
- example="my_repository",
64
- callback=_repo_name_callback,
65
- )
66
-
67
- add_object_command_aliases(
68
- app=app,
69
- object_type=ObjectType.IMAGE_REPOSITORY,
70
- name_argument=REPO_NAME_ARGUMENT,
71
- like_option=like_option(
72
- help_example='`list --like "my%"` lists all image repositories that begin with “my”.'
73
- ),
74
- scope_option=scope_option(help_example="`list --in database my_db`"),
75
- ommit_commands=["describe"],
76
- )
77
-
78
-
79
- @app.command(requires_connection=True)
80
- def create(
81
- name: FQN = REPO_NAME_ARGUMENT,
82
- replace: bool = ReplaceOption(),
83
- if_not_exists: bool = IfNotExistsOption(),
84
- **options,
85
- ):
86
- """
87
- Creates a new image repository in the current schema.
88
- """
89
- return SingleQueryResult(
90
- ImageRepositoryManager().create(
91
- name=name.identifier, replace=replace, if_not_exists=if_not_exists
92
- )
93
- )
94
-
95
-
96
- @app.command("list-images", requires_connection=True)
97
- def list_images(
98
- name: FQN = REPO_NAME_ARGUMENT,
99
- **options,
100
- ) -> CollectionResult:
101
- """Lists images in the given repository."""
102
- repository_manager = ImageRepositoryManager()
103
- database = repository_manager.get_database()
104
- schema = repository_manager.get_schema()
105
- url = repository_manager.get_repository_url(name.identifier)
106
- api_url = repository_manager.get_repository_api_url(url)
107
- bearer_login = RegistryManager().login_to_registry(api_url)
108
- repos = []
109
- query: Optional[str] = f"{api_url}/_catalog?n=10"
110
-
111
- while query:
112
- # Make paginated catalog requests
113
- response = requests.get(
114
- query, headers={"Authorization": f"Bearer {bearer_login}"}
115
- )
116
-
117
- if response.status_code != 200:
118
- raise ClickException(f"Call to the registry failed {response.text}")
119
-
120
- data = json.loads(response.text)
121
- if "repositories" in data:
122
- repos.extend(data["repositories"])
123
-
124
- if "Link" in response.headers:
125
- # There are more results
126
- query = f"{api_url}/_catalog?n=10&last={repos[-1]}"
127
- else:
128
- query = None
129
-
130
- images = []
131
- for repo in repos:
132
- prefix = f"/{database}/{schema}/{name}/"
133
- repo = repo.replace("baserepo/", prefix)
134
- images.append({"image": repo})
135
-
136
- return CollectionResult(images)
137
-
138
-
139
- @app.command("list-tags", requires_connection=True)
140
- def list_tags(
141
- name: FQN = REPO_NAME_ARGUMENT,
142
- image_name: str = typer.Option(
143
- ...,
144
- "--image-name",
145
- "--image_name",
146
- "-i",
147
- help="Fully qualified name of the image as shown in the output of list-images",
148
- show_default=False,
149
- ),
150
- **options,
151
- ) -> CollectionResult:
152
- """Lists tags for the given image in a repository."""
153
-
154
- repository_manager = ImageRepositoryManager()
155
- url = repository_manager.get_repository_url(name.identifier)
156
- api_url = repository_manager.get_repository_api_url(url)
157
- bearer_login = RegistryManager().login_to_registry(api_url)
158
-
159
- image_realname = "/".join(image_name.split("/")[4:])
160
- tags = []
161
- query: Optional[str] = f"{api_url}/{image_realname}/tags/list?n=10"
162
-
163
- while query is not None:
164
- # Make paginated catalog requests
165
- response = requests.get(
166
- query, headers={"Authorization": f"Bearer {bearer_login}"}
167
- )
168
-
169
- if response.status_code != 200:
170
- cli_console.warning(f"Call to the registry failed {response.text}")
171
-
172
- data = json.loads(response.text)
173
- if "tags" in data:
174
- tags.extend(data["tags"])
175
-
176
- if "Link" in response.headers:
177
- # There are more results
178
- query = f"{api_url}/{image_realname}/tags/list?n=10&last={tags[-1]}"
179
- else:
180
- query = None
181
-
182
- tags_list = []
183
- for tag in tags:
184
- image_tag = f"{image_name}:{tag}"
185
- tags_list.append({"tag": image_tag})
186
-
187
- return CollectionResult(tags_list)
188
-
189
-
190
- @app.command("url", requires_connection=True)
191
- def repo_url(
192
- name: FQN = REPO_NAME_ARGUMENT,
193
- **options,
194
- ):
195
- """Returns the URL for the given repository."""
196
- return MessageResult(
197
- (
198
- ImageRepositoryManager().get_repository_url(
199
- repo_name=name.identifier, with_scheme=False
200
- )
201
- )
202
- )
@@ -1,84 +0,0 @@
1
- # Copyright (c) 2024 Snowflake Inc.
2
- #
3
- # Licensed under the Apache License, Version 2.0 (the "License");
4
- # you may not use this file except in compliance with the License.
5
- # You may obtain a copy of the License at
6
- #
7
- # http://www.apache.org/licenses/LICENSE-2.0
8
- #
9
- # Unless required by applicable law or agreed to in writing, software
10
- # distributed under the License is distributed on an "AS IS" BASIS,
11
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
- # See the License for the specific language governing permissions and
13
- # limitations under the License.
14
-
15
- from urllib.parse import urlparse
16
-
17
- from snowflake.cli._plugins.spcs.common import handle_object_already_exists
18
- from snowflake.cli.api.constants import ObjectType
19
- from snowflake.cli.api.identifiers import FQN
20
- from snowflake.cli.api.sql_execution import SqlExecutionMixin
21
- from snowflake.connector.errors import ProgrammingError
22
-
23
-
24
- class ImageRepositoryManager(SqlExecutionMixin):
25
- def get_database(self):
26
- return self._conn.database
27
-
28
- def get_schema(self):
29
- return self._conn.schema
30
-
31
- def get_role(self):
32
- return self._conn.role
33
-
34
- def get_repository_url(self, repo_name: str, with_scheme: bool = True):
35
-
36
- repo_row = self.show_specific_object(
37
- "image repositories", repo_name, check_schema=True
38
- )
39
- if repo_row is None:
40
- fqn = FQN.from_string(repo_name).using_connection(self._conn)
41
- raise ProgrammingError(
42
- f"Image repository '{fqn.identifier}' does not exist or not authorized."
43
- )
44
- if with_scheme:
45
- return f"https://{repo_row['repository_url']}"
46
- else:
47
- return repo_row["repository_url"]
48
-
49
- def get_repository_api_url(self, repo_url):
50
- """
51
- Converts a repo URL to a registry OCI API URL.
52
- https://reg.com/db/schema/repo becomes https://reg.com/v2/db/schema/repo
53
- """
54
- parsed_url = urlparse(repo_url)
55
-
56
- scheme = parsed_url.scheme
57
- host = parsed_url.netloc
58
- path = parsed_url.path
59
-
60
- return f"{scheme}://{host}/v2{path}"
61
-
62
- def create(
63
- self,
64
- name: str,
65
- if_not_exists: bool,
66
- replace: bool,
67
- ):
68
- if if_not_exists and replace:
69
- raise ValueError(
70
- "'replace' and 'if_not_exists' options are mutually exclusive for ImageRepositoryManager.create"
71
- )
72
- elif replace:
73
- create_statement = "create or replace image repository"
74
- elif if_not_exists:
75
- create_statement = "create image repository if not exists"
76
- else:
77
- create_statement = "create image repository"
78
-
79
- try:
80
- return self._execute_schema_query(f"{create_statement} {name}", name=name)
81
- except ProgrammingError as e:
82
- handle_object_already_exists(
83
- e, ObjectType.IMAGE_REPOSITORY, name, replace_available=True
84
- )
@@ -1,30 +0,0 @@
1
- # Copyright (c) 2024 Snowflake Inc.
2
- #
3
- # Licensed under the Apache License, Version 2.0 (the "License");
4
- # you may not use this file except in compliance with the License.
5
- # You may obtain a copy of the License at
6
- #
7
- # http://www.apache.org/licenses/LICENSE-2.0
8
- #
9
- # Unless required by applicable law or agreed to in writing, software
10
- # distributed under the License is distributed on an "AS IS" BASIS,
11
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
- # See the License for the specific language governing permissions and
13
- # limitations under the License.
14
-
15
- from snowflake.cli._plugins.spcs import app
16
- from snowflake.cli.api.plugins.command import (
17
- SNOWCLI_ROOT_COMMAND_PATH,
18
- CommandSpec,
19
- CommandType,
20
- plugin_hook_impl,
21
- )
22
-
23
-
24
- @plugin_hook_impl
25
- def command_spec():
26
- return CommandSpec(
27
- parent_command_path=SNOWCLI_ROOT_COMMAND_PATH,
28
- command_type=CommandType.COMMAND_GROUP,
29
- typer_instance=app.create_instance(),
30
- )
@@ -1,13 +0,0 @@
1
- # Copyright (c) 2024 Snowflake Inc.
2
- #
3
- # Licensed under the Apache License, Version 2.0 (the "License");
4
- # you may not use this file except in compliance with the License.
5
- # You may obtain a copy of the License at
6
- #
7
- # http://www.apache.org/licenses/LICENSE-2.0
8
- #
9
- # Unless required by applicable law or agreed to in writing, software
10
- # distributed under the License is distributed on an "AS IS" BASIS,
11
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
- # See the License for the specific language governing permissions and
13
- # limitations under the License.
@@ -1,345 +0,0 @@
1
- # Copyright (c) 2024 Snowflake Inc.
2
- #
3
- # Licensed under the Apache License, Version 2.0 (the "License");
4
- # you may not use this file except in compliance with the License.
5
- # You may obtain a copy of the License at
6
- #
7
- # http://www.apache.org/licenses/LICENSE-2.0
8
- #
9
- # Unless required by applicable law or agreed to in writing, software
10
- # distributed under the License is distributed on an "AS IS" BASIS,
11
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
- # See the License for the specific language governing permissions and
13
- # limitations under the License.
14
-
15
- from __future__ import annotations
16
-
17
- import sys
18
- from pathlib import Path
19
- from typing import List, Optional
20
-
21
- import typer
22
- from click import ClickException
23
- from snowflake.cli._plugins.object.command_aliases import (
24
- add_object_command_aliases,
25
- scope_option,
26
- )
27
- from snowflake.cli._plugins.object.common import CommentOption, Tag, TagOption
28
- from snowflake.cli._plugins.spcs.common import (
29
- print_log_lines,
30
- validate_and_set_instances,
31
- )
32
- from snowflake.cli._plugins.spcs.services.manager import ServiceManager
33
- from snowflake.cli.api.commands.flags import (
34
- IfNotExistsOption,
35
- OverrideableOption,
36
- identifier_argument,
37
- like_option,
38
- )
39
- from snowflake.cli.api.commands.snow_typer import SnowTyperFactory
40
- from snowflake.cli.api.constants import ObjectType
41
- from snowflake.cli.api.identifiers import FQN
42
- from snowflake.cli.api.output.types import (
43
- CommandResult,
44
- QueryJsonValueResult,
45
- QueryResult,
46
- SingleQueryResult,
47
- )
48
- from snowflake.cli.api.project.util import is_valid_object_name
49
-
50
- app = SnowTyperFactory(
51
- name="service",
52
- help="Manages Snowpark Container Services services.",
53
- short_help="Manages services.",
54
- )
55
-
56
-
57
- def _service_name_callback(name: FQN) -> FQN:
58
- if not is_valid_object_name(name.identifier, max_depth=2, allow_quoted=False):
59
- raise ClickException(
60
- f"'{name}' is not a valid service name. Note service names must be unquoted identifiers. The same constraint also applies to database and schema names where you create a service."
61
- )
62
- return name
63
-
64
-
65
- ServiceNameArgument = identifier_argument(
66
- sf_object="service",
67
- example="my_service",
68
- callback=_service_name_callback,
69
- )
70
-
71
- SpecPathOption = typer.Option(
72
- ...,
73
- "--spec-path",
74
- help="Path to service specification file.",
75
- file_okay=True,
76
- dir_okay=False,
77
- exists=True,
78
- show_default=False,
79
- )
80
-
81
- _MIN_INSTANCES_HELP = "Minimum number of service instances to run."
82
- MinInstancesOption = OverrideableOption(
83
- 1, "--min-instances", help=_MIN_INSTANCES_HELP, min=1
84
- )
85
-
86
- _MAX_INSTANCES_HELP = "Maximum number of service instances to run."
87
- MaxInstancesOption = OverrideableOption(
88
- None, "--max-instances", help=_MAX_INSTANCES_HELP, min=1
89
- )
90
-
91
- _QUERY_WAREHOUSE_HELP = "Warehouse to use if a service container connects to Snowflake to execute a query without explicitly specifying a warehouse to use."
92
- QueryWarehouseOption = OverrideableOption(
93
- None,
94
- "--query-warehouse",
95
- help=_QUERY_WAREHOUSE_HELP,
96
- )
97
-
98
- _AUTO_RESUME_HELP = "The service will automatically resume when a service function or ingress is called."
99
- AutoResumeOption = OverrideableOption(
100
- True,
101
- "--auto-resume/--no-auto-resume",
102
- help=_AUTO_RESUME_HELP,
103
- )
104
-
105
- _COMMENT_HELP = "Comment for the service."
106
-
107
- add_object_command_aliases(
108
- app=app,
109
- object_type=ObjectType.SERVICE,
110
- name_argument=ServiceNameArgument,
111
- like_option=like_option(
112
- help_example='`list --like "my%"` lists all services that begin with “my”.'
113
- ),
114
- scope_option=scope_option(help_example="`list --in compute-pool my_pool`"),
115
- )
116
-
117
-
118
- @app.command(requires_connection=True)
119
- def create(
120
- name: FQN = ServiceNameArgument,
121
- compute_pool: str = typer.Option(
122
- ...,
123
- "--compute-pool",
124
- help="Compute pool to run the service on.",
125
- show_default=False,
126
- ),
127
- spec_path: Path = SpecPathOption,
128
- min_instances: int = MinInstancesOption(),
129
- max_instances: Optional[int] = MaxInstancesOption(),
130
- auto_resume: bool = AutoResumeOption(),
131
- external_access_integrations: Optional[List[str]] = typer.Option(
132
- None,
133
- "--eai-name",
134
- help="Identifies External Access Integrations(EAI) that the service can access. This option may be specified multiple times for multiple EAIs.",
135
- ),
136
- query_warehouse: Optional[str] = QueryWarehouseOption(),
137
- tags: Optional[List[Tag]] = TagOption(help="Tag for the service."),
138
- comment: Optional[str] = CommentOption(help=_COMMENT_HELP),
139
- if_not_exists: bool = IfNotExistsOption(),
140
- **options,
141
- ) -> CommandResult:
142
- """
143
- Creates a new service in the current schema.
144
- """
145
- max_instances = validate_and_set_instances(
146
- min_instances, max_instances, "instances"
147
- )
148
- cursor = ServiceManager().create(
149
- service_name=name.identifier,
150
- min_instances=min_instances,
151
- max_instances=max_instances,
152
- compute_pool=compute_pool,
153
- spec_path=spec_path,
154
- external_access_integrations=external_access_integrations,
155
- auto_resume=auto_resume,
156
- query_warehouse=query_warehouse,
157
- tags=tags,
158
- comment=comment,
159
- if_not_exists=if_not_exists,
160
- )
161
- return SingleQueryResult(cursor)
162
-
163
-
164
- @app.command(requires_connection=True)
165
- def execute_job(
166
- name: FQN = ServiceNameArgument,
167
- compute_pool: str = typer.Option(
168
- ...,
169
- "--compute-pool",
170
- help="Compute pool to run the job service on.",
171
- show_default=False,
172
- ),
173
- spec_path: Path = SpecPathOption,
174
- external_access_integrations: Optional[List[str]] = typer.Option(
175
- None,
176
- "--eai-name",
177
- help="Identifies External Access Integrations(EAI) that the job service can access. This option may be specified multiple times for multiple EAIs.",
178
- ),
179
- query_warehouse: Optional[str] = QueryWarehouseOption(),
180
- comment: Optional[str] = CommentOption(help=_COMMENT_HELP),
181
- **options,
182
- ) -> CommandResult:
183
- """
184
- Creates and executes a job service in the current schema.
185
- """
186
- cursor = ServiceManager().execute_job(
187
- job_service_name=name.identifier,
188
- compute_pool=compute_pool,
189
- spec_path=spec_path,
190
- external_access_integrations=external_access_integrations,
191
- query_warehouse=query_warehouse,
192
- comment=comment,
193
- )
194
- return SingleQueryResult(cursor)
195
-
196
-
197
- @app.command(requires_connection=True)
198
- def status(name: FQN = ServiceNameArgument, **options) -> CommandResult:
199
- """
200
- Retrieves the status of a service.
201
- """
202
- cursor = ServiceManager().status(service_name=name.identifier)
203
- return QueryJsonValueResult(cursor)
204
-
205
-
206
- @app.command(requires_connection=True)
207
- def logs(
208
- name: FQN = ServiceNameArgument,
209
- container_name: str = typer.Option(
210
- ...,
211
- "--container-name",
212
- help="Name of the container.",
213
- show_default=False,
214
- ),
215
- instance_id: str = typer.Option(
216
- ...,
217
- "--instance-id",
218
- help="ID of the service instance, starting with 0.",
219
- show_default=False,
220
- ),
221
- num_lines: int = typer.Option(
222
- 500, "--num-lines", help="Number of lines to retrieve."
223
- ),
224
- **options,
225
- ):
226
- """
227
- Retrieves local logs from a service container.
228
- """
229
- results = ServiceManager().logs(
230
- service_name=name.identifier,
231
- instance_id=instance_id,
232
- container_name=container_name,
233
- num_lines=num_lines,
234
- )
235
- cursor = results.fetchone()
236
- logs = next(iter(cursor)).split("\n")
237
- print_log_lines(sys.stdout, name, "0", logs)
238
-
239
-
240
- @app.command(requires_connection=True)
241
- def upgrade(
242
- name: FQN = ServiceNameArgument,
243
- spec_path: Path = SpecPathOption,
244
- **options,
245
- ):
246
- """
247
- Updates an existing service with a new specification file.
248
- """
249
- return SingleQueryResult(
250
- ServiceManager().upgrade_spec(service_name=name.identifier, spec_path=spec_path)
251
- )
252
-
253
-
254
- @app.command("list-endpoints", requires_connection=True)
255
- def list_endpoints(name: FQN = ServiceNameArgument, **options):
256
- """
257
- Lists the endpoints in a service.
258
- """
259
- return QueryResult(ServiceManager().list_endpoints(service_name=name.identifier))
260
-
261
-
262
- @app.command(requires_connection=True)
263
- def suspend(name: FQN = ServiceNameArgument, **options) -> CommandResult:
264
- """
265
- Suspends the service, shutting down and deleting all its containers.
266
- """
267
- return SingleQueryResult(ServiceManager().suspend(name))
268
-
269
-
270
- @app.command(requires_connection=True)
271
- def resume(name: FQN = ServiceNameArgument, **options) -> CommandResult:
272
- """
273
- Resumes the service from a SUSPENDED state.
274
- """
275
- return SingleQueryResult(ServiceManager().resume(name))
276
-
277
-
278
- @app.command("set", requires_connection=True)
279
- def set_property(
280
- name: FQN = ServiceNameArgument,
281
- min_instances: Optional[int] = MinInstancesOption(default=None, show_default=False),
282
- max_instances: Optional[int] = MaxInstancesOption(show_default=False),
283
- query_warehouse: Optional[str] = QueryWarehouseOption(show_default=False),
284
- auto_resume: Optional[bool] = AutoResumeOption(default=None, show_default=False),
285
- comment: Optional[str] = CommentOption(help=_COMMENT_HELP, show_default=False),
286
- **options,
287
- ):
288
- """
289
- Sets one or more properties for the service.
290
- """
291
- cursor = ServiceManager().set_property(
292
- service_name=name.identifier,
293
- min_instances=min_instances,
294
- max_instances=max_instances,
295
- query_warehouse=query_warehouse,
296
- auto_resume=auto_resume,
297
- comment=comment,
298
- )
299
- return SingleQueryResult(cursor)
300
-
301
-
302
- @app.command("unset", requires_connection=True)
303
- def unset_property(
304
- name: FQN = ServiceNameArgument,
305
- min_instances: bool = MinInstancesOption(
306
- default=False,
307
- help=f"Reset the MIN_INSTANCES property - {_MIN_INSTANCES_HELP}",
308
- show_default=False,
309
- ),
310
- max_instances: bool = MaxInstancesOption(
311
- default=False,
312
- help=f"Reset the MAX_INSTANCES property - {_MAX_INSTANCES_HELP}",
313
- show_default=False,
314
- ),
315
- query_warehouse: bool = QueryWarehouseOption(
316
- default=False,
317
- help=f"Reset the QUERY_WAREHOUSE property - {_QUERY_WAREHOUSE_HELP}",
318
- show_default=False,
319
- ),
320
- auto_resume: bool = AutoResumeOption(
321
- default=False,
322
- param_decls=["--auto-resume"],
323
- help=f"Reset the AUTO_RESUME property - {_AUTO_RESUME_HELP}",
324
- show_default=False,
325
- ),
326
- comment: bool = CommentOption(
327
- default=False,
328
- help=f"Reset the COMMENT property - {_COMMENT_HELP}",
329
- callback=None,
330
- show_default=False,
331
- ),
332
- **options,
333
- ):
334
- """
335
- Resets one or more properties for the service to their default value(s).
336
- """
337
- cursor = ServiceManager().unset_property(
338
- service_name=name.identifier,
339
- min_instances=min_instances,
340
- max_instances=max_instances,
341
- query_warehouse=query_warehouse,
342
- auto_resume=auto_resume,
343
- comment=comment,
344
- )
345
- return SingleQueryResult(cursor)