snowflake-cli-labs 2.8.0rc1__py3-none-any.whl → 2.8.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.
- README.md +21 -0
- {snowflake_cli_labs-2.8.0rc1.dist-info → snowflake_cli_labs-2.8.2.dist-info}/METADATA +7 -95
- snowflake_cli_labs-2.8.2.dist-info/RECORD +5 -0
- snowflake/cli/__about__.py +0 -17
- snowflake/cli/__init__.py +0 -13
- snowflake/cli/api/__init__.py +0 -48
- snowflake/cli/api/cli_global_context.py +0 -390
- snowflake/cli/api/commands/__init__.py +0 -13
- snowflake/cli/api/commands/alias.py +0 -23
- snowflake/cli/api/commands/decorators.py +0 -354
- snowflake/cli/api/commands/execution_metadata.py +0 -40
- snowflake/cli/api/commands/experimental_behaviour.py +0 -19
- snowflake/cli/api/commands/flags.py +0 -640
- snowflake/cli/api/commands/project_initialisation.py +0 -65
- snowflake/cli/api/commands/snow_typer.py +0 -237
- snowflake/cli/api/commands/typer_pre_execute.py +0 -26
- snowflake/cli/api/config.py +0 -348
- snowflake/cli/api/console/__init__.py +0 -17
- snowflake/cli/api/console/abc.py +0 -89
- snowflake/cli/api/console/console.py +0 -134
- snowflake/cli/api/console/enum.py +0 -17
- snowflake/cli/api/constants.py +0 -79
- snowflake/cli/api/errno.py +0 -27
- snowflake/cli/api/exceptions.py +0 -164
- snowflake/cli/api/feature_flags.py +0 -55
- snowflake/cli/api/identifiers.py +0 -154
- snowflake/cli/api/output/__init__.py +0 -13
- snowflake/cli/api/output/formats.py +0 -20
- snowflake/cli/api/output/types.py +0 -118
- snowflake/cli/api/plugins/__init__.py +0 -13
- snowflake/cli/api/plugins/command/__init__.py +0 -72
- snowflake/cli/api/plugins/command/plugin_hook_specs.py +0 -21
- snowflake/cli/api/plugins/plugin_config.py +0 -32
- snowflake/cli/api/project/__init__.py +0 -13
- snowflake/cli/api/project/definition.py +0 -84
- snowflake/cli/api/project/definition_manager.py +0 -134
- snowflake/cli/api/project/errors.py +0 -56
- snowflake/cli/api/project/project_verification.py +0 -23
- snowflake/cli/api/project/schemas/__init__.py +0 -13
- snowflake/cli/api/project/schemas/entities/application_entity.py +0 -44
- snowflake/cli/api/project/schemas/entities/application_package_entity.py +0 -66
- snowflake/cli/api/project/schemas/entities/common.py +0 -78
- snowflake/cli/api/project/schemas/entities/entities.py +0 -30
- snowflake/cli/api/project/schemas/identifier_model.py +0 -49
- snowflake/cli/api/project/schemas/native_app/__init__.py +0 -13
- snowflake/cli/api/project/schemas/native_app/application.py +0 -62
- snowflake/cli/api/project/schemas/native_app/native_app.py +0 -93
- snowflake/cli/api/project/schemas/native_app/package.py +0 -78
- snowflake/cli/api/project/schemas/native_app/path_mapping.py +0 -65
- snowflake/cli/api/project/schemas/project_definition.py +0 -199
- snowflake/cli/api/project/schemas/snowpark/__init__.py +0 -13
- snowflake/cli/api/project/schemas/snowpark/argument.py +0 -28
- snowflake/cli/api/project/schemas/snowpark/callable.py +0 -69
- snowflake/cli/api/project/schemas/snowpark/snowpark.py +0 -36
- snowflake/cli/api/project/schemas/streamlit/__init__.py +0 -13
- snowflake/cli/api/project/schemas/streamlit/streamlit.py +0 -46
- snowflake/cli/api/project/schemas/template.py +0 -77
- snowflake/cli/api/project/schemas/updatable_model.py +0 -194
- snowflake/cli/api/project/util.py +0 -261
- snowflake/cli/api/rendering/__init__.py +0 -13
- snowflake/cli/api/rendering/jinja.py +0 -112
- snowflake/cli/api/rendering/project_definition_templates.py +0 -39
- snowflake/cli/api/rendering/project_templates.py +0 -98
- snowflake/cli/api/rendering/sql_templates.py +0 -60
- snowflake/cli/api/rest_api.py +0 -172
- snowflake/cli/api/sanitizers.py +0 -43
- snowflake/cli/api/secure_path.py +0 -362
- snowflake/cli/api/secure_utils.py +0 -29
- snowflake/cli/api/sql_execution.py +0 -260
- snowflake/cli/api/utils/__init__.py +0 -13
- snowflake/cli/api/utils/cursor.py +0 -34
- snowflake/cli/api/utils/definition_rendering.py +0 -383
- snowflake/cli/api/utils/dict_utils.py +0 -73
- snowflake/cli/api/utils/error_handling.py +0 -23
- snowflake/cli/api/utils/graph.py +0 -97
- snowflake/cli/api/utils/models.py +0 -63
- snowflake/cli/api/utils/naming_utils.py +0 -13
- snowflake/cli/api/utils/path_utils.py +0 -36
- snowflake/cli/api/utils/templating_functions.py +0 -144
- snowflake/cli/api/utils/types.py +0 -35
- snowflake/cli/app/__init__.py +0 -22
- snowflake/cli/app/__main__.py +0 -31
- snowflake/cli/app/api_impl/__init__.py +0 -13
- snowflake/cli/app/api_impl/plugin/__init__.py +0 -13
- snowflake/cli/app/api_impl/plugin/plugin_config_provider_impl.py +0 -66
- snowflake/cli/app/build_and_push.sh +0 -8
- snowflake/cli/app/cli_app.py +0 -243
- snowflake/cli/app/commands_registration/__init__.py +0 -33
- snowflake/cli/app/commands_registration/builtin_plugins.py +0 -54
- snowflake/cli/app/commands_registration/command_plugins_loader.py +0 -169
- snowflake/cli/app/commands_registration/commands_registration_with_callbacks.py +0 -105
- snowflake/cli/app/commands_registration/exception_logging.py +0 -26
- snowflake/cli/app/commands_registration/threadsafe.py +0 -48
- snowflake/cli/app/commands_registration/typer_registration.py +0 -153
- snowflake/cli/app/constants.py +0 -19
- snowflake/cli/app/dev/__init__.py +0 -13
- snowflake/cli/app/dev/commands_structure.py +0 -48
- snowflake/cli/app/dev/docs/__init__.py +0 -13
- snowflake/cli/app/dev/docs/commands_docs_generator.py +0 -100
- snowflake/cli/app/dev/docs/generator.py +0 -35
- snowflake/cli/app/dev/docs/project_definition_docs_generator.py +0 -58
- snowflake/cli/app/dev/docs/project_definition_generate_json_schema.py +0 -227
- snowflake/cli/app/dev/docs/template_utils.py +0 -23
- snowflake/cli/app/dev/docs/templates/definition_description.rst.jinja2 +0 -38
- snowflake/cli/app/dev/docs/templates/overview.rst.jinja2 +0 -9
- snowflake/cli/app/dev/docs/templates/usage.rst.jinja2 +0 -57
- snowflake/cli/app/dev/pycharm_remote_debug.py +0 -46
- snowflake/cli/app/loggers.py +0 -199
- snowflake/cli/app/main_typer.py +0 -62
- snowflake/cli/app/printing.py +0 -181
- snowflake/cli/app/snow_connector.py +0 -243
- snowflake/cli/app/telemetry.py +0 -189
- snowflake/cli/plugins/__init__.py +0 -13
- snowflake/cli/plugins/connection/__init__.py +0 -13
- snowflake/cli/plugins/connection/commands.py +0 -330
- snowflake/cli/plugins/connection/plugin_spec.py +0 -30
- snowflake/cli/plugins/connection/util.py +0 -179
- snowflake/cli/plugins/cortex/__init__.py +0 -13
- snowflake/cli/plugins/cortex/commands.py +0 -327
- snowflake/cli/plugins/cortex/constants.py +0 -17
- snowflake/cli/plugins/cortex/manager.py +0 -189
- snowflake/cli/plugins/cortex/plugin_spec.py +0 -30
- snowflake/cli/plugins/cortex/types.py +0 -22
- snowflake/cli/plugins/git/__init__.py +0 -13
- snowflake/cli/plugins/git/commands.py +0 -305
- snowflake/cli/plugins/git/manager.py +0 -96
- snowflake/cli/plugins/git/plugin_spec.py +0 -30
- snowflake/cli/plugins/init/__init__.py +0 -13
- snowflake/cli/plugins/init/commands.py +0 -244
- snowflake/cli/plugins/init/plugin_spec.py +0 -30
- snowflake/cli/plugins/nativeapp/__init__.py +0 -13
- snowflake/cli/plugins/nativeapp/artifacts.py +0 -742
- snowflake/cli/plugins/nativeapp/codegen/__init__.py +0 -13
- snowflake/cli/plugins/nativeapp/codegen/artifact_processor.py +0 -91
- snowflake/cli/plugins/nativeapp/codegen/compiler.py +0 -130
- snowflake/cli/plugins/nativeapp/codegen/sandbox.py +0 -306
- snowflake/cli/plugins/nativeapp/codegen/setup/native_app_setup_processor.py +0 -172
- snowflake/cli/plugins/nativeapp/codegen/setup/setup_driver.py.source +0 -56
- snowflake/cli/plugins/nativeapp/codegen/snowpark/callback_source.py.jinja +0 -181
- snowflake/cli/plugins/nativeapp/codegen/snowpark/extension_function_utils.py +0 -217
- snowflake/cli/plugins/nativeapp/codegen/snowpark/models.py +0 -61
- snowflake/cli/plugins/nativeapp/codegen/snowpark/python_processor.py +0 -528
- snowflake/cli/plugins/nativeapp/commands.py +0 -439
- snowflake/cli/plugins/nativeapp/common_flags.py +0 -44
- snowflake/cli/plugins/nativeapp/constants.py +0 -27
- snowflake/cli/plugins/nativeapp/exceptions.py +0 -122
- snowflake/cli/plugins/nativeapp/feature_flags.py +0 -24
- snowflake/cli/plugins/nativeapp/init.py +0 -345
- snowflake/cli/plugins/nativeapp/manager.py +0 -823
- snowflake/cli/plugins/nativeapp/plugin_spec.py +0 -30
- snowflake/cli/plugins/nativeapp/policy.py +0 -50
- snowflake/cli/plugins/nativeapp/project_model.py +0 -195
- snowflake/cli/plugins/nativeapp/run_processor.py +0 -389
- snowflake/cli/plugins/nativeapp/teardown_processor.py +0 -301
- snowflake/cli/plugins/nativeapp/utils.py +0 -98
- snowflake/cli/plugins/nativeapp/v2_conversions/v2_to_v1_decorator.py +0 -135
- snowflake/cli/plugins/nativeapp/version/__init__.py +0 -13
- snowflake/cli/plugins/nativeapp/version/commands.py +0 -170
- snowflake/cli/plugins/nativeapp/version/version_processor.py +0 -362
- snowflake/cli/plugins/notebook/__init__.py +0 -13
- snowflake/cli/plugins/notebook/commands.py +0 -84
- snowflake/cli/plugins/notebook/exceptions.py +0 -20
- snowflake/cli/plugins/notebook/manager.py +0 -71
- snowflake/cli/plugins/notebook/plugin_spec.py +0 -30
- snowflake/cli/plugins/notebook/types.py +0 -16
- snowflake/cli/plugins/object/__init__.py +0 -13
- snowflake/cli/plugins/object/command_aliases.py +0 -94
- snowflake/cli/plugins/object/commands.py +0 -174
- snowflake/cli/plugins/object/common.py +0 -85
- snowflake/cli/plugins/object/manager.py +0 -96
- snowflake/cli/plugins/object/plugin_spec.py +0 -30
- snowflake/cli/plugins/object_stage_deprecated/__init__.py +0 -15
- snowflake/cli/plugins/object_stage_deprecated/commands.py +0 -122
- snowflake/cli/plugins/object_stage_deprecated/plugin_spec.py +0 -32
- snowflake/cli/plugins/snowpark/__init__.py +0 -13
- snowflake/cli/plugins/snowpark/commands.py +0 -548
- snowflake/cli/plugins/snowpark/common.py +0 -307
- snowflake/cli/plugins/snowpark/manager.py +0 -109
- snowflake/cli/plugins/snowpark/models.py +0 -156
- snowflake/cli/plugins/snowpark/package/__init__.py +0 -13
- snowflake/cli/plugins/snowpark/package/anaconda_packages.py +0 -233
- snowflake/cli/plugins/snowpark/package/commands.py +0 -256
- snowflake/cli/plugins/snowpark/package/manager.py +0 -43
- snowflake/cli/plugins/snowpark/package/utils.py +0 -26
- snowflake/cli/plugins/snowpark/package_utils.py +0 -354
- snowflake/cli/plugins/snowpark/plugin_spec.py +0 -30
- snowflake/cli/plugins/snowpark/snowpark_package_paths.py +0 -65
- snowflake/cli/plugins/snowpark/snowpark_shared.py +0 -95
- snowflake/cli/plugins/snowpark/zipper.py +0 -81
- snowflake/cli/plugins/spcs/__init__.py +0 -35
- snowflake/cli/plugins/spcs/common.py +0 -99
- snowflake/cli/plugins/spcs/compute_pool/__init__.py +0 -13
- snowflake/cli/plugins/spcs/compute_pool/commands.py +0 -240
- snowflake/cli/plugins/spcs/compute_pool/manager.py +0 -121
- snowflake/cli/plugins/spcs/image_registry/__init__.py +0 -13
- snowflake/cli/plugins/spcs/image_registry/commands.py +0 -65
- snowflake/cli/plugins/spcs/image_registry/manager.py +0 -105
- snowflake/cli/plugins/spcs/image_repository/__init__.py +0 -13
- snowflake/cli/plugins/spcs/image_repository/commands.py +0 -196
- snowflake/cli/plugins/spcs/image_repository/manager.py +0 -84
- snowflake/cli/plugins/spcs/jobs/__init__.py +0 -13
- snowflake/cli/plugins/spcs/jobs/commands.py +0 -78
- snowflake/cli/plugins/spcs/jobs/manager.py +0 -53
- snowflake/cli/plugins/spcs/plugin_spec.py +0 -30
- snowflake/cli/plugins/spcs/services/__init__.py +0 -13
- snowflake/cli/plugins/spcs/services/commands.py +0 -311
- snowflake/cli/plugins/spcs/services/manager.py +0 -170
- snowflake/cli/plugins/sql/__init__.py +0 -13
- snowflake/cli/plugins/sql/commands.py +0 -83
- snowflake/cli/plugins/sql/manager.py +0 -92
- snowflake/cli/plugins/sql/plugin_spec.py +0 -30
- snowflake/cli/plugins/sql/snowsql_templating.py +0 -28
- snowflake/cli/plugins/stage/__init__.py +0 -13
- snowflake/cli/plugins/stage/commands.py +0 -261
- snowflake/cli/plugins/stage/diff.py +0 -326
- snowflake/cli/plugins/stage/manager.py +0 -544
- snowflake/cli/plugins/stage/md5.py +0 -160
- snowflake/cli/plugins/stage/plugin_spec.py +0 -30
- snowflake/cli/plugins/streamlit/__init__.py +0 -13
- snowflake/cli/plugins/streamlit/commands.py +0 -186
- snowflake/cli/plugins/streamlit/manager.py +0 -222
- snowflake/cli/plugins/streamlit/plugin_spec.py +0 -30
- snowflake/cli/plugins/workspace/__init__.py +0 -13
- snowflake/cli/plugins/workspace/commands.py +0 -35
- snowflake/cli/plugins/workspace/plugin_spec.py +0 -30
- snowflake/cli/templates/default_snowpark/.gitignore +0 -4
- snowflake/cli/templates/default_snowpark/app/__init__.py +0 -0
- snowflake/cli/templates/default_snowpark/app/common.py +0 -2
- snowflake/cli/templates/default_snowpark/app/functions.py +0 -15
- snowflake/cli/templates/default_snowpark/app/procedures.py +0 -22
- snowflake/cli/templates/default_snowpark/requirements.txt +0 -1
- snowflake/cli/templates/default_snowpark/snowflake.yml +0 -23
- snowflake/cli/templates/default_streamlit/.gitignore +0 -4
- snowflake/cli/templates/default_streamlit/common/hello.py +0 -2
- snowflake/cli/templates/default_streamlit/environment.yml +0 -6
- snowflake/cli/templates/default_streamlit/pages/my_page.py +0 -3
- snowflake/cli/templates/default_streamlit/snowflake.yml +0 -10
- snowflake/cli/templates/default_streamlit/streamlit_app.py +0 -4
- snowflake_cli_labs-2.8.0rc1.dist-info/RECORD +0 -240
- snowflake_cli_labs-2.8.0rc1.dist-info/entry_points.txt +0 -2
- {snowflake_cli_labs-2.8.0rc1.dist-info → snowflake_cli_labs-2.8.2.dist-info}/WHEEL +0 -0
- {snowflake_cli_labs-2.8.0rc1.dist-info → snowflake_cli_labs-2.8.2.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,301 +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
|
-
from pathlib import Path
|
|
18
|
-
from textwrap import dedent
|
|
19
|
-
from typing import Dict, Optional
|
|
20
|
-
|
|
21
|
-
import typer
|
|
22
|
-
from snowflake.cli.api.console import cli_console as cc
|
|
23
|
-
from snowflake.cli.api.errno import APPLICATION_NO_LONGER_AVAILABLE
|
|
24
|
-
from snowflake.cli.api.exceptions import SnowflakeSQLExecutionError
|
|
25
|
-
from snowflake.cli.plugins.nativeapp.constants import (
|
|
26
|
-
ALLOWED_SPECIAL_COMMENTS,
|
|
27
|
-
COMMENT_COL,
|
|
28
|
-
EXTERNAL_DISTRIBUTION,
|
|
29
|
-
INTERNAL_DISTRIBUTION,
|
|
30
|
-
OWNER_COL,
|
|
31
|
-
)
|
|
32
|
-
from snowflake.cli.plugins.nativeapp.exceptions import (
|
|
33
|
-
CouldNotDropApplicationPackageWithVersions,
|
|
34
|
-
)
|
|
35
|
-
from snowflake.cli.plugins.nativeapp.manager import (
|
|
36
|
-
NativeAppCommandProcessor,
|
|
37
|
-
NativeAppManager,
|
|
38
|
-
ensure_correct_owner,
|
|
39
|
-
)
|
|
40
|
-
from snowflake.cli.plugins.nativeapp.utils import (
|
|
41
|
-
needs_confirmation,
|
|
42
|
-
)
|
|
43
|
-
from snowflake.connector import ProgrammingError
|
|
44
|
-
from snowflake.connector.cursor import DictCursor
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
class NativeAppTeardownProcessor(NativeAppManager, NativeAppCommandProcessor):
|
|
48
|
-
def __init__(self, project_definition: Dict, project_root: Path):
|
|
49
|
-
super().__init__(project_definition, project_root)
|
|
50
|
-
|
|
51
|
-
def drop_generic_object(
|
|
52
|
-
self, object_type: str, object_name: str, role: str, cascade: bool = False
|
|
53
|
-
):
|
|
54
|
-
"""
|
|
55
|
-
Drop object using the given role.
|
|
56
|
-
"""
|
|
57
|
-
with self.use_role(role):
|
|
58
|
-
cc.step(f"Dropping {object_type} {object_name} now.")
|
|
59
|
-
drop_query = f"drop {object_type} {object_name}"
|
|
60
|
-
if cascade:
|
|
61
|
-
drop_query += " cascade"
|
|
62
|
-
try:
|
|
63
|
-
self._execute_query(drop_query)
|
|
64
|
-
except:
|
|
65
|
-
raise SnowflakeSQLExecutionError(drop_query)
|
|
66
|
-
|
|
67
|
-
cc.message(f"Dropped {object_type} {object_name} successfully.")
|
|
68
|
-
|
|
69
|
-
def drop_application(
|
|
70
|
-
self, auto_yes: bool, interactive: bool = False, cascade: Optional[bool] = None
|
|
71
|
-
):
|
|
72
|
-
"""
|
|
73
|
-
Attempts to drop the application object if all validations and user prompts allow so.
|
|
74
|
-
"""
|
|
75
|
-
|
|
76
|
-
needs_confirm = True
|
|
77
|
-
|
|
78
|
-
# 1. If existing application is not found, exit gracefully
|
|
79
|
-
show_obj_row = self.get_existing_app_info()
|
|
80
|
-
if show_obj_row is None:
|
|
81
|
-
cc.warning(
|
|
82
|
-
f"Role {self.app_role} does not own any application object with the name {self.app_name}, or the application object does not exist."
|
|
83
|
-
)
|
|
84
|
-
return
|
|
85
|
-
|
|
86
|
-
# 2. Check for the right owner
|
|
87
|
-
ensure_correct_owner(
|
|
88
|
-
row=show_obj_row, role=self.app_role, obj_name=self.app_name
|
|
89
|
-
)
|
|
90
|
-
|
|
91
|
-
# 3. Check if created by the Snowflake CLI
|
|
92
|
-
row_comment = show_obj_row[COMMENT_COL]
|
|
93
|
-
if row_comment not in ALLOWED_SPECIAL_COMMENTS and needs_confirmation(
|
|
94
|
-
needs_confirm, auto_yes
|
|
95
|
-
):
|
|
96
|
-
should_drop_object = typer.confirm(
|
|
97
|
-
dedent(
|
|
98
|
-
f"""\
|
|
99
|
-
Application object {self.app_name} was not created by Snowflake CLI.
|
|
100
|
-
Application object details:
|
|
101
|
-
Name: {self.app_name}
|
|
102
|
-
Created on: {show_obj_row["created_on"]}
|
|
103
|
-
Source: {show_obj_row["source"]}
|
|
104
|
-
Owner: {show_obj_row[OWNER_COL]}
|
|
105
|
-
Comment: {show_obj_row[COMMENT_COL]}
|
|
106
|
-
Version: {show_obj_row["version"]}
|
|
107
|
-
Patch: {show_obj_row["patch"]}
|
|
108
|
-
Are you sure you want to drop it?
|
|
109
|
-
"""
|
|
110
|
-
)
|
|
111
|
-
)
|
|
112
|
-
if not should_drop_object:
|
|
113
|
-
cc.message(f"Did not drop application object {self.app_name}.")
|
|
114
|
-
# The user desires to keep the app, therefore we can't proceed since it would
|
|
115
|
-
# leave behind an orphan app when we get to dropping the package
|
|
116
|
-
raise typer.Abort()
|
|
117
|
-
|
|
118
|
-
# 4. Check for application objects owned by the application
|
|
119
|
-
# This query will fail if the application package has already been dropped, so handle this case gracefully
|
|
120
|
-
has_objects_to_drop = False
|
|
121
|
-
message_prefix = ""
|
|
122
|
-
cascade_true_message = ""
|
|
123
|
-
cascade_false_message = ""
|
|
124
|
-
interactive_prompt = ""
|
|
125
|
-
non_interactive_abort = ""
|
|
126
|
-
try:
|
|
127
|
-
if application_objects := self.get_objects_owned_by_application():
|
|
128
|
-
has_objects_to_drop = True
|
|
129
|
-
message_prefix = (
|
|
130
|
-
f"The following objects are owned by application {self.app_name}"
|
|
131
|
-
)
|
|
132
|
-
cascade_true_message = f"{message_prefix} and will be dropped:"
|
|
133
|
-
cascade_false_message = f"{message_prefix} and will NOT be dropped:"
|
|
134
|
-
interactive_prompt = "Would you like to drop these objects in addition to the application? [y/n/ABORT]"
|
|
135
|
-
non_interactive_abort = "Re-run teardown again with --cascade or --no-cascade to specify whether these objects should be dropped along with the application"
|
|
136
|
-
except ProgrammingError as e:
|
|
137
|
-
if e.errno != APPLICATION_NO_LONGER_AVAILABLE:
|
|
138
|
-
raise
|
|
139
|
-
application_objects = []
|
|
140
|
-
message_prefix = f"Could not determine which objects are owned by application {self.app_name}"
|
|
141
|
-
has_objects_to_drop = True # potentially, but we don't know what they are
|
|
142
|
-
cascade_true_message = (
|
|
143
|
-
f"{message_prefix}, an unknown number of objects will be dropped."
|
|
144
|
-
)
|
|
145
|
-
cascade_false_message = f"{message_prefix}, they will NOT be dropped."
|
|
146
|
-
interactive_prompt = f"Would you like to drop an unknown set of objects in addition to the application? [y/n/ABORT]"
|
|
147
|
-
non_interactive_abort = f"Re-run teardown again with --cascade or --no-cascade to specify whether any objects should be dropped along with the application."
|
|
148
|
-
|
|
149
|
-
if has_objects_to_drop:
|
|
150
|
-
if cascade is True:
|
|
151
|
-
# If the user explicitly passed the --cascade flag
|
|
152
|
-
cc.message(cascade_true_message)
|
|
153
|
-
with cc.indented():
|
|
154
|
-
for obj in application_objects:
|
|
155
|
-
cc.message(self._application_object_to_str(obj))
|
|
156
|
-
elif cascade is False:
|
|
157
|
-
# If the user explicitly passed the --no-cascade flag
|
|
158
|
-
cc.message(cascade_false_message)
|
|
159
|
-
with cc.indented():
|
|
160
|
-
for obj in application_objects:
|
|
161
|
-
cc.message(self._application_object_to_str(obj))
|
|
162
|
-
elif interactive:
|
|
163
|
-
# If the user didn't pass any cascade flag and the session is interactive
|
|
164
|
-
cc.message(message_prefix)
|
|
165
|
-
with cc.indented():
|
|
166
|
-
for obj in application_objects:
|
|
167
|
-
cc.message(self._application_object_to_str(obj))
|
|
168
|
-
user_response = typer.prompt(
|
|
169
|
-
interactive_prompt,
|
|
170
|
-
show_default=False,
|
|
171
|
-
default="ABORT",
|
|
172
|
-
).lower()
|
|
173
|
-
if user_response in ["y", "yes"]:
|
|
174
|
-
cascade = True
|
|
175
|
-
elif user_response in ["n", "no"]:
|
|
176
|
-
cascade = False
|
|
177
|
-
else:
|
|
178
|
-
raise typer.Abort()
|
|
179
|
-
else:
|
|
180
|
-
# Else abort since we don't know what to do and can't ask the user
|
|
181
|
-
cc.message(message_prefix)
|
|
182
|
-
with cc.indented():
|
|
183
|
-
for obj in application_objects:
|
|
184
|
-
cc.message(self._application_object_to_str(obj))
|
|
185
|
-
cc.message(non_interactive_abort)
|
|
186
|
-
raise typer.Abort()
|
|
187
|
-
elif cascade is None:
|
|
188
|
-
# If there's nothing to drop, set cascade to an explicit False value
|
|
189
|
-
cascade = False
|
|
190
|
-
|
|
191
|
-
# 5. All validations have passed, drop object
|
|
192
|
-
self.drop_generic_object(
|
|
193
|
-
object_type="application",
|
|
194
|
-
object_name=self.app_name,
|
|
195
|
-
role=self.app_role,
|
|
196
|
-
cascade=cascade,
|
|
197
|
-
)
|
|
198
|
-
return # The application object was successfully dropped, therefore exit gracefully
|
|
199
|
-
|
|
200
|
-
def drop_package(self, auto_yes: bool):
|
|
201
|
-
"""
|
|
202
|
-
Attempts to drop application package unless user specifies otherwise.
|
|
203
|
-
"""
|
|
204
|
-
needs_confirm = True
|
|
205
|
-
|
|
206
|
-
# 1. If existing application package is not found, exit gracefully
|
|
207
|
-
show_obj_row = self.get_existing_app_pkg_info()
|
|
208
|
-
if show_obj_row is None:
|
|
209
|
-
cc.warning(
|
|
210
|
-
f"Role {self.package_role} does not own any application package with the name {self.package_name}, or the application package does not exist."
|
|
211
|
-
)
|
|
212
|
-
return
|
|
213
|
-
|
|
214
|
-
# 2. Check for the right owner
|
|
215
|
-
ensure_correct_owner(
|
|
216
|
-
row=show_obj_row, role=self.package_role, obj_name=self.package_name
|
|
217
|
-
)
|
|
218
|
-
|
|
219
|
-
with self.use_role(self.package_role):
|
|
220
|
-
# 3. Check for versions in the application package
|
|
221
|
-
show_versions_query = (
|
|
222
|
-
f"show versions in application package {self.package_name}"
|
|
223
|
-
)
|
|
224
|
-
show_versions_cursor = self._execute_query(
|
|
225
|
-
show_versions_query, cursor_class=DictCursor
|
|
226
|
-
)
|
|
227
|
-
if show_versions_cursor.rowcount is None:
|
|
228
|
-
raise SnowflakeSQLExecutionError(show_versions_query)
|
|
229
|
-
|
|
230
|
-
if show_versions_cursor.rowcount > 0:
|
|
231
|
-
# allow dropping a package with versions when --force is set
|
|
232
|
-
if not auto_yes:
|
|
233
|
-
raise CouldNotDropApplicationPackageWithVersions(
|
|
234
|
-
"Drop versions first, or use --force to override."
|
|
235
|
-
)
|
|
236
|
-
|
|
237
|
-
# 4. Check distribution of the existing application package
|
|
238
|
-
actual_distribution = self.get_app_pkg_distribution_in_snowflake
|
|
239
|
-
if not self.verify_project_distribution(actual_distribution):
|
|
240
|
-
cc.warning(
|
|
241
|
-
f"Continuing to execute `snow app teardown` on application package {self.package_name} with distribution '{actual_distribution}'."
|
|
242
|
-
)
|
|
243
|
-
|
|
244
|
-
# 5. If distribution is internal, check if created by the Snowflake CLI
|
|
245
|
-
row_comment = show_obj_row[COMMENT_COL]
|
|
246
|
-
if actual_distribution == INTERNAL_DISTRIBUTION:
|
|
247
|
-
if row_comment in ALLOWED_SPECIAL_COMMENTS:
|
|
248
|
-
needs_confirm = False
|
|
249
|
-
else:
|
|
250
|
-
if needs_confirmation(needs_confirm, auto_yes):
|
|
251
|
-
cc.warning(
|
|
252
|
-
f"Application package {self.package_name} was not created by Snowflake CLI."
|
|
253
|
-
)
|
|
254
|
-
else:
|
|
255
|
-
if needs_confirmation(needs_confirm, auto_yes):
|
|
256
|
-
cc.warning(
|
|
257
|
-
f"Application package {self.package_name} in your Snowflake account has distribution property '{EXTERNAL_DISTRIBUTION}' and could be associated with one or more of your listings on Snowflake Marketplace."
|
|
258
|
-
)
|
|
259
|
-
|
|
260
|
-
if needs_confirmation(needs_confirm, auto_yes):
|
|
261
|
-
should_drop_object = typer.confirm(
|
|
262
|
-
dedent(
|
|
263
|
-
f"""\
|
|
264
|
-
Application package details:
|
|
265
|
-
Name: {self.app_name}
|
|
266
|
-
Created on: {show_obj_row["created_on"]}
|
|
267
|
-
Distribution: {actual_distribution}
|
|
268
|
-
Owner: {show_obj_row[OWNER_COL]}
|
|
269
|
-
Comment: {show_obj_row[COMMENT_COL]}
|
|
270
|
-
Are you sure you want to drop it?
|
|
271
|
-
"""
|
|
272
|
-
)
|
|
273
|
-
)
|
|
274
|
-
if not should_drop_object:
|
|
275
|
-
cc.message(f"Did not drop application package {self.package_name}.")
|
|
276
|
-
return # The user desires to keep the application package, therefore exit gracefully
|
|
277
|
-
|
|
278
|
-
# All validations have passed, drop object
|
|
279
|
-
self.drop_generic_object(
|
|
280
|
-
object_type="application package",
|
|
281
|
-
object_name=self.package_name,
|
|
282
|
-
role=self.package_role,
|
|
283
|
-
)
|
|
284
|
-
return # The application package was successfully dropped, therefore exit gracefully
|
|
285
|
-
|
|
286
|
-
def process(
|
|
287
|
-
self,
|
|
288
|
-
interactive: bool,
|
|
289
|
-
force_drop: bool = False,
|
|
290
|
-
cascade: Optional[bool] = None,
|
|
291
|
-
*args,
|
|
292
|
-
**kwargs,
|
|
293
|
-
):
|
|
294
|
-
|
|
295
|
-
# Drop the application object
|
|
296
|
-
self.drop_application(
|
|
297
|
-
auto_yes=force_drop, interactive=interactive, cascade=cascade
|
|
298
|
-
)
|
|
299
|
-
|
|
300
|
-
# Drop the application package
|
|
301
|
-
self.drop_package(auto_yes=force_drop)
|
|
@@ -1,98 +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 os
|
|
18
|
-
from pathlib import Path
|
|
19
|
-
from sys import stdin, stdout
|
|
20
|
-
from typing import Iterable, Optional, Union
|
|
21
|
-
|
|
22
|
-
from click import ClickException
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
def needs_confirmation(needs_confirm: bool, auto_yes: bool) -> bool:
|
|
26
|
-
return needs_confirm and not auto_yes
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
def is_tty_interactive():
|
|
30
|
-
return stdin.isatty() and stdout.isatty()
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
def get_first_paragraph_from_markdown_file(file_path: Path) -> Optional[str]:
|
|
34
|
-
"""
|
|
35
|
-
Reads a Markdown file at the given file path and finds the first paragraph
|
|
36
|
-
|
|
37
|
-
Parameters:
|
|
38
|
-
file_path (Path): Path to Markdown file
|
|
39
|
-
|
|
40
|
-
Returns:
|
|
41
|
-
Optional[str]: the first paragraph as a string, or None
|
|
42
|
-
if no paragraph could be found
|
|
43
|
-
|
|
44
|
-
Raises:
|
|
45
|
-
FileNotFoundError: if file_path to Markdown file does not exist
|
|
46
|
-
"""
|
|
47
|
-
if not file_path.exists():
|
|
48
|
-
raise FileNotFoundError(file_path)
|
|
49
|
-
|
|
50
|
-
with open(file_path, "r") as markdown_file:
|
|
51
|
-
paragraph_text = None
|
|
52
|
-
|
|
53
|
-
for line in markdown_file:
|
|
54
|
-
stripped_line = line.strip()
|
|
55
|
-
if not stripped_line.startswith("#") and stripped_line:
|
|
56
|
-
paragraph_text = stripped_line
|
|
57
|
-
break
|
|
58
|
-
|
|
59
|
-
return paragraph_text
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
def shallow_git_clone(url: Union[str, os.PathLike], to_path: Union[str, os.PathLike]):
|
|
63
|
-
"""
|
|
64
|
-
Performs a shallow clone of the repository at the provided url to the path specified
|
|
65
|
-
|
|
66
|
-
Parameters:
|
|
67
|
-
url (str | PathLike): Valid git url.
|
|
68
|
-
to_path (str | PathLike): Path to which the repository should be cloned to.
|
|
69
|
-
|
|
70
|
-
Returns:
|
|
71
|
-
Repo: the repository that was cloned
|
|
72
|
-
"""
|
|
73
|
-
from git import Repo
|
|
74
|
-
|
|
75
|
-
# Clone the repository in the directory with options.
|
|
76
|
-
repo = Repo.clone_from(
|
|
77
|
-
url=url,
|
|
78
|
-
to_path=to_path,
|
|
79
|
-
filter=["tree:0"],
|
|
80
|
-
depth=1,
|
|
81
|
-
)
|
|
82
|
-
# Close repo to avoid issues with permissions on Windows
|
|
83
|
-
repo.close()
|
|
84
|
-
|
|
85
|
-
return repo
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
def verify_no_directories(paths_to_sync: Iterable[Path]):
|
|
89
|
-
for path in paths_to_sync:
|
|
90
|
-
if path.is_dir():
|
|
91
|
-
raise ClickException(
|
|
92
|
-
f"{path} is a directory. Add the -r flag to deploy directories." #
|
|
93
|
-
)
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
def verify_exists(path: Path):
|
|
97
|
-
if not path.exists():
|
|
98
|
-
raise ClickException(f"The following path does not exist: {path}")
|
|
@@ -1,135 +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
|
-
from functools import wraps
|
|
18
|
-
from pathlib import Path
|
|
19
|
-
from typing import Any, Dict, Optional, Union
|
|
20
|
-
|
|
21
|
-
from click import ClickException
|
|
22
|
-
from snowflake.cli.api.cli_global_context import cli_context, cli_context_manager
|
|
23
|
-
from snowflake.cli.api.project.schemas.entities.application_entity import (
|
|
24
|
-
ApplicationEntity,
|
|
25
|
-
)
|
|
26
|
-
from snowflake.cli.api.project.schemas.entities.application_package_entity import (
|
|
27
|
-
ApplicationPackageEntity,
|
|
28
|
-
)
|
|
29
|
-
from snowflake.cli.api.project.schemas.native_app.path_mapping import PathMapping
|
|
30
|
-
from snowflake.cli.api.project.schemas.project_definition import (
|
|
31
|
-
DefinitionV11,
|
|
32
|
-
DefinitionV20,
|
|
33
|
-
)
|
|
34
|
-
from snowflake.cli.api.utils.definition_rendering import render_definition_template
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
def _convert_v2_artifact_to_v1_dict(
|
|
38
|
-
v2_artifact: Union[PathMapping, Path]
|
|
39
|
-
) -> Union[Dict, str]:
|
|
40
|
-
if isinstance(v2_artifact, PathMapping):
|
|
41
|
-
return {
|
|
42
|
-
"src": v2_artifact.src,
|
|
43
|
-
"dest": v2_artifact.dest,
|
|
44
|
-
"processors": v2_artifact.processors,
|
|
45
|
-
}
|
|
46
|
-
return str(v2_artifact)
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
def _pdf_v2_to_v1(v2_definition: DefinitionV20) -> DefinitionV11:
|
|
50
|
-
pdfv1: Dict[str, Any] = {"definition_version": "1.1", "native_app": {}}
|
|
51
|
-
|
|
52
|
-
app_package_definition: ApplicationPackageEntity = None
|
|
53
|
-
app_definition: Optional[ApplicationEntity] = None
|
|
54
|
-
|
|
55
|
-
for key, entity in v2_definition.entities.items():
|
|
56
|
-
if entity.get_type() == ApplicationPackageEntity.get_type():
|
|
57
|
-
if app_package_definition:
|
|
58
|
-
raise ClickException(
|
|
59
|
-
"More than one application package entity exists in the project definition file."
|
|
60
|
-
)
|
|
61
|
-
app_package_definition = entity
|
|
62
|
-
elif entity.get_type() == ApplicationEntity.get_type():
|
|
63
|
-
if app_definition:
|
|
64
|
-
raise ClickException(
|
|
65
|
-
"More than one application entity exists in the project definition file."
|
|
66
|
-
)
|
|
67
|
-
app_definition = entity
|
|
68
|
-
if not app_package_definition:
|
|
69
|
-
raise ClickException(
|
|
70
|
-
"Could not find an application package entity in the project definition file."
|
|
71
|
-
)
|
|
72
|
-
|
|
73
|
-
# NativeApp
|
|
74
|
-
if app_definition and app_definition.name:
|
|
75
|
-
pdfv1["native_app"]["name"] = app_definition.name
|
|
76
|
-
else:
|
|
77
|
-
pdfv1["native_app"]["name"] = app_package_definition.name.split("_pkg_")[0]
|
|
78
|
-
pdfv1["native_app"]["artifacts"] = [
|
|
79
|
-
_convert_v2_artifact_to_v1_dict(a) for a in app_package_definition.artifacts
|
|
80
|
-
]
|
|
81
|
-
pdfv1["native_app"]["source_stage"] = app_package_definition.stage
|
|
82
|
-
pdfv1["native_app"]["bundle_root"] = str(app_package_definition.bundle_root)
|
|
83
|
-
pdfv1["native_app"]["generated_root"] = str(app_package_definition.generated_root)
|
|
84
|
-
pdfv1["native_app"]["deploy_root"] = str(app_package_definition.deploy_root)
|
|
85
|
-
|
|
86
|
-
# Package
|
|
87
|
-
pdfv1["native_app"]["package"] = {}
|
|
88
|
-
pdfv1["native_app"]["package"]["name"] = app_package_definition.name
|
|
89
|
-
if app_package_definition.distribution:
|
|
90
|
-
pdfv1["native_app"]["package"][
|
|
91
|
-
"distribution"
|
|
92
|
-
] = app_package_definition.distribution
|
|
93
|
-
if app_package_definition.meta and app_package_definition.meta.post_deploy:
|
|
94
|
-
pdfv1["native_app"]["package"][
|
|
95
|
-
"post_deploy"
|
|
96
|
-
] = app_package_definition.meta.post_deploy
|
|
97
|
-
|
|
98
|
-
# Application
|
|
99
|
-
if app_definition:
|
|
100
|
-
pdfv1["native_app"]["application"] = {}
|
|
101
|
-
pdfv1["native_app"]["application"]["name"] = app_definition.name
|
|
102
|
-
if app_definition.meta and app_definition.meta.role:
|
|
103
|
-
pdfv1["native_app"]["application"]["role"] = app_definition.meta.role
|
|
104
|
-
if app_definition.meta and app_definition.meta.post_deploy:
|
|
105
|
-
pdfv1["native_app"]["application"][
|
|
106
|
-
"post_deploy"
|
|
107
|
-
] = app_definition.meta.post_deploy
|
|
108
|
-
|
|
109
|
-
result = render_definition_template(pdfv1, {})
|
|
110
|
-
# Override the definition object in global context
|
|
111
|
-
return result.project_definition
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
def nativeapp_definition_v2_to_v1(func):
|
|
115
|
-
"""
|
|
116
|
-
A command decorator that attempts to automatically convert a native app project from
|
|
117
|
-
definition v2 to v1.1. Assumes with_project_definition() has already been called.
|
|
118
|
-
The definition object in CliGlobalContext will be replaced with the converted object.
|
|
119
|
-
Exactly one application package entity type is expected, and up to one application
|
|
120
|
-
entity type is expected.
|
|
121
|
-
"""
|
|
122
|
-
|
|
123
|
-
@wraps(func)
|
|
124
|
-
def wrapper(*args, **kwargs):
|
|
125
|
-
original_pdf: DefinitionV20 = cli_context.project_definition
|
|
126
|
-
if not original_pdf:
|
|
127
|
-
raise ValueError(
|
|
128
|
-
"Project definition could not be found. The nativeapp_definition_v2_to_v1 command decorator assumes with_project_definition() was called before it."
|
|
129
|
-
)
|
|
130
|
-
if original_pdf.definition_version == "2":
|
|
131
|
-
pdfv1 = _pdf_v2_to_v1(original_pdf)
|
|
132
|
-
cli_context_manager.set_project_definition(pdfv1)
|
|
133
|
-
return func(*args, **kwargs)
|
|
134
|
-
|
|
135
|
-
return wrapper
|
|
@@ -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.
|