snowflake-cli 3.9.1__py3-none-any.whl → 3.10.1__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 (54) hide show
  1. snowflake/cli/__about__.py +1 -1
  2. snowflake/cli/_app/commands_registration/builtin_plugins.py +2 -2
  3. snowflake/cli/_app/printing.py +53 -13
  4. snowflake/cli/_app/snow_connector.py +1 -0
  5. snowflake/cli/_app/telemetry.py +2 -0
  6. snowflake/cli/_app/version_check.py +73 -6
  7. snowflake/cli/_plugins/cortex/commands.py +8 -3
  8. snowflake/cli/_plugins/cortex/manager.py +24 -20
  9. snowflake/cli/_plugins/dbt/commands.py +5 -2
  10. snowflake/cli/_plugins/dbt/manager.py +9 -7
  11. snowflake/cli/_plugins/{project → dcm}/commands.py +95 -48
  12. snowflake/cli/_plugins/{project/project_entity_model.py → dcm/dcm_project_entity_model.py} +5 -5
  13. snowflake/cli/_plugins/{project → dcm}/manager.py +35 -14
  14. snowflake/cli/_plugins/{project → dcm}/plugin_spec.py +1 -1
  15. snowflake/cli/_plugins/git/manager.py +1 -11
  16. snowflake/cli/_plugins/nativeapp/codegen/snowpark/python_processor.py +4 -0
  17. snowflake/cli/_plugins/nativeapp/commands.py +3 -4
  18. snowflake/cli/_plugins/nativeapp/entities/application_package.py +1 -1
  19. snowflake/cli/_plugins/nativeapp/release_channel/commands.py +1 -2
  20. snowflake/cli/_plugins/nativeapp/version/commands.py +1 -2
  21. snowflake/cli/_plugins/snowpark/common.py +23 -11
  22. snowflake/cli/_plugins/snowpark/snowpark_entity.py +13 -5
  23. snowflake/cli/_plugins/snowpark/snowpark_entity_model.py +10 -2
  24. snowflake/cli/_plugins/sql/commands.py +49 -1
  25. snowflake/cli/_plugins/sql/manager.py +14 -4
  26. snowflake/cli/_plugins/sql/repl.py +4 -0
  27. snowflake/cli/_plugins/stage/commands.py +30 -11
  28. snowflake/cli/_plugins/stage/diff.py +2 -0
  29. snowflake/cli/_plugins/stage/manager.py +79 -55
  30. snowflake/cli/_plugins/streamlit/streamlit_entity.py +17 -30
  31. snowflake/cli/api/artifacts/upload.py +1 -1
  32. snowflake/cli/api/cli_global_context.py +5 -14
  33. snowflake/cli/api/commands/decorators.py +7 -0
  34. snowflake/cli/api/commands/flags.py +12 -0
  35. snowflake/cli/api/commands/snow_typer.py +23 -2
  36. snowflake/cli/api/config.py +9 -5
  37. snowflake/cli/api/connections.py +1 -0
  38. snowflake/cli/api/constants.py +2 -2
  39. snowflake/cli/api/entities/common.py +16 -13
  40. snowflake/cli/api/entities/utils.py +15 -9
  41. snowflake/cli/api/feature_flags.py +2 -5
  42. snowflake/cli/api/output/formats.py +6 -0
  43. snowflake/cli/api/output/types.py +48 -2
  44. snowflake/cli/api/project/schemas/entities/entities.py +6 -6
  45. snowflake/cli/api/rendering/sql_templates.py +67 -11
  46. snowflake/cli/api/rest_api.py +1 -0
  47. snowflake/cli/api/stage_path.py +41 -5
  48. {snowflake_cli-3.9.1.dist-info → snowflake_cli-3.10.1.dist-info}/METADATA +46 -13
  49. {snowflake_cli-3.9.1.dist-info → snowflake_cli-3.10.1.dist-info}/RECORD +53 -54
  50. snowflake/cli/_plugins/project/feature_flags.py +0 -22
  51. /snowflake/cli/_plugins/{project → dcm}/__init__.py +0 -0
  52. {snowflake_cli-3.9.1.dist-info → snowflake_cli-3.10.1.dist-info}/WHEEL +0 -0
  53. {snowflake_cli-3.9.1.dist-info → snowflake_cli-3.10.1.dist-info}/entry_points.txt +0 -0
  54. {snowflake_cli-3.9.1.dist-info → snowflake_cli-3.10.1.dist-info}/licenses/LICENSE +0 -0
@@ -15,17 +15,17 @@
15
15
  from typing import List, Optional
16
16
 
17
17
  import typer
18
+ from snowflake.cli._plugins.dcm.dcm_project_entity_model import (
19
+ DCMProjectEntityModel,
20
+ )
21
+ from snowflake.cli._plugins.dcm.manager import DCMProjectManager
18
22
  from snowflake.cli._plugins.object.command_aliases import add_object_command_aliases
19
23
  from snowflake.cli._plugins.object.commands import scope_option
20
24
  from snowflake.cli._plugins.object.manager import ObjectManager
21
- from snowflake.cli._plugins.project.feature_flags import FeatureFlag
22
- from snowflake.cli._plugins.project.manager import ProjectManager
23
- from snowflake.cli._plugins.project.project_entity_model import (
24
- ProjectEntityModel,
25
- )
26
25
  from snowflake.cli.api.cli_global_context import get_cli_context
27
26
  from snowflake.cli.api.commands.decorators import with_project_definition
28
27
  from snowflake.cli.api.commands.flags import (
28
+ IfExistsOption,
29
29
  IfNotExistsOption,
30
30
  OverrideableOption,
31
31
  PruneOption,
@@ -39,6 +39,7 @@ from snowflake.cli.api.commands.utils import get_entity_for_operation
39
39
  from snowflake.cli.api.console.console import cli_console
40
40
  from snowflake.cli.api.constants import ObjectType
41
41
  from snowflake.cli.api.exceptions import CliError
42
+ from snowflake.cli.api.feature_flags import FeatureFlag
42
43
  from snowflake.cli.api.identifiers import FQN
43
44
  from snowflake.cli.api.output.types import (
44
45
  MessageResult,
@@ -47,16 +48,16 @@ from snowflake.cli.api.output.types import (
47
48
  )
48
49
 
49
50
  app = SnowTyperFactory(
50
- name="project",
51
- help="Manages projects in Snowflake.",
51
+ name="dcm",
52
+ help="Manages DCM Projects in Snowflake.",
52
53
  is_hidden=FeatureFlag.ENABLE_SNOWFLAKE_PROJECTS.is_disabled,
53
54
  )
54
55
 
55
- project_identifier = identifier_argument(sf_object="project", example="MY_PROJECT")
56
+ dcm_identifier = identifier_argument(sf_object="DCM Project", example="MY_PROJECT")
56
57
  version_flag = typer.Option(
57
58
  None,
58
59
  "--version",
59
- help="Version of the project to use. If not specified default version is used",
60
+ help="Version of the DCM Project to use. If not specified default version is used. For names containing '$', use single quotes to prevent shell expansion (e.g., 'VERSION$1').",
60
61
  show_default=False,
61
62
  )
62
63
  variables_flag = variables_option(
@@ -65,64 +66,77 @@ variables_flag = variables_option(
65
66
  configuration_flag = typer.Option(
66
67
  None,
67
68
  "--configuration",
68
- help="Configuration of the project to use. If not specified default configuration is used.",
69
+ help="Configuration of the DCM Project to use. If not specified default configuration is used.",
69
70
  show_default=False,
70
71
  )
71
72
  from_option = OverrideableOption(
72
73
  None,
73
74
  "--from",
74
- help="Create a new version using given stage instead of uploading local files.",
75
75
  show_default=False,
76
76
  )
77
77
 
78
78
 
79
79
  add_object_command_aliases(
80
80
  app=app,
81
- object_type=ObjectType.PROJECT,
82
- name_argument=project_identifier,
81
+ object_type=ObjectType.DCM_PROJECT,
82
+ name_argument=dcm_identifier,
83
83
  like_option=like_option(
84
- help_example='`list --like "my%"` lists all projects that begin with my'
84
+ help_example='`list --like "my%"` lists all DCM Projects that begin with "my"'
85
85
  ),
86
86
  scope_option=scope_option(help_example="`list --in database my_db`"),
87
- ommit_commands=["create", "describe"],
87
+ ommit_commands=["create"],
88
88
  )
89
89
 
90
90
 
91
91
  @app.command(requires_connection=True)
92
- def execute(
93
- identifier: FQN = project_identifier,
92
+ def deploy(
93
+ identifier: FQN = dcm_identifier,
94
94
  version: Optional[str] = version_flag,
95
+ from_stage: Optional[str] = from_option(
96
+ help="Apply changes defined in given stage instead of using a specific project version."
97
+ ),
95
98
  variables: Optional[List[str]] = variables_flag,
96
99
  configuration: Optional[str] = configuration_flag,
97
100
  **options,
98
101
  ):
99
102
  """
100
- Executes a project.
103
+ Applies changes defined in DCM Project to Snowflake.
101
104
  """
102
- result = ProjectManager().execute(
105
+ if version and from_stage:
106
+ raise CliError("--version and --from are mutually exclusive.")
107
+
108
+ result = DCMProjectManager().execute(
103
109
  project_name=identifier,
104
110
  configuration=configuration,
105
111
  version=version,
112
+ from_stage=from_stage,
106
113
  variables=variables,
107
114
  )
108
115
  return QueryJsonValueResult(result)
109
116
 
110
117
 
111
118
  @app.command(requires_connection=True)
112
- def dry_run(
113
- identifier: FQN = project_identifier,
119
+ def plan(
120
+ identifier: FQN = dcm_identifier,
114
121
  version: Optional[str] = version_flag,
122
+ from_stage: Optional[str] = from_option(
123
+ help="Plan DCM Project deployment from given stage instead of using a specific version."
124
+ ),
115
125
  variables: Optional[List[str]] = variables_flag,
116
126
  configuration: Optional[str] = configuration_flag,
117
127
  **options,
118
128
  ):
119
129
  """
120
- Validates a project.
130
+ Plans a DCM Project deployment (validates without executing).
121
131
  """
122
- result = ProjectManager().execute(
132
+ if version and from_stage:
133
+ raise CliError("--version and --from are mutually exclusive.")
134
+
135
+ result = DCMProjectManager().execute(
123
136
  project_name=identifier,
124
137
  configuration=configuration,
125
138
  version=version,
139
+ from_stage=from_stage,
126
140
  dry_run=True,
127
141
  variables=variables,
128
142
  )
@@ -132,11 +146,11 @@ def dry_run(
132
146
  @app.command(requires_connection=True)
133
147
  @with_project_definition()
134
148
  def create(
135
- entity_id: str = entity_argument("project"),
149
+ entity_id: str = entity_argument("dcm"),
136
150
  no_version: bool = typer.Option(
137
151
  False,
138
152
  "--no-version",
139
- help="Do not initialize project with a new version, only create the snowflake object.",
153
+ help="Do not initialize DCM Project with a new version, only create the snowflake object.",
140
154
  ),
141
155
  if_not_exists: bool = IfNotExistsOption(
142
156
  help="Do nothing if the project already exists."
@@ -144,19 +158,19 @@ def create(
144
158
  **options,
145
159
  ):
146
160
  """
147
- Creates a project in Snowflake.
148
- By default, the project is initialized with a new version created from local files.
161
+ Creates a DCM Project in Snowflake.
162
+ By default, the DCM Project is initialized with a new version created from local files.
149
163
  """
150
164
  cli_context = get_cli_context()
151
- project: ProjectEntityModel = get_entity_for_operation(
165
+ project: DCMProjectEntityModel = get_entity_for_operation(
152
166
  cli_context=cli_context,
153
167
  entity_id=entity_id,
154
168
  project_definition=cli_context.project_definition,
155
- entity_type="project",
169
+ entity_type="dcm",
156
170
  )
157
171
  om = ObjectManager()
158
- if om.object_exists(object_type="project", fqn=project.fqn):
159
- message = f"Project '{project.fqn}' already exists."
172
+ if om.object_exists(object_type="dcm", fqn=project.fqn):
173
+ message = f"DCM Project '{project.fqn}' already exists."
160
174
  if if_not_exists:
161
175
  return MessageResult(message)
162
176
  raise CliError(message)
@@ -166,22 +180,24 @@ def create(
166
180
  ):
167
181
  raise CliError(f"Stage '{project.stage}' already exists.")
168
182
 
169
- pm = ProjectManager()
170
- with cli_console.phase(f"Creating project '{project.fqn}'"):
171
- pm.create(project=project, initialize_version_from_local_files=not no_version)
183
+ dpm = DCMProjectManager()
184
+ with cli_console.phase(f"Creating DCM Project '{project.fqn}'"):
185
+ dpm.create(project=project, initialize_version_from_local_files=not no_version)
172
186
 
173
187
  if no_version:
174
- return MessageResult(f"Project '{project.fqn}' successfully created.")
188
+ return MessageResult(f"DCM Project '{project.fqn}' successfully created.")
175
189
  return MessageResult(
176
- f"Project '{project.fqn}' successfully created and initial version is added."
190
+ f"DCM Project '{project.fqn}' successfully created and initial version is added."
177
191
  )
178
192
 
179
193
 
180
194
  @app.command(requires_connection=True)
181
195
  @with_project_definition()
182
196
  def add_version(
183
- entity_id: str = entity_argument("project"),
184
- _from: Optional[str] = from_option(),
197
+ entity_id: str = entity_argument("dcm"),
198
+ _from: Optional[str] = from_option(
199
+ help="Create a new version using given stage instead of uploading local files."
200
+ ),
185
201
  _alias: Optional[str] = typer.Option(
186
202
  None, "--alias", help="Alias for the version.", show_default=False
187
203
  ),
@@ -191,25 +207,25 @@ def add_version(
191
207
  prune: bool = PruneOption(default=True),
192
208
  **options,
193
209
  ):
194
- """Uploads local files to Snowflake and cerates a new project version."""
210
+ """Uploads local files to Snowflake and cerates a new DCM Project version."""
195
211
  if _from is not None and prune:
196
212
  cli_console.warning(
197
213
  "When `--from` option is used, `--prune` option will be ignored and files from stage will be used as they are."
198
214
  )
199
215
  prune = False
200
216
  cli_context = get_cli_context()
201
- project: ProjectEntityModel = get_entity_for_operation(
217
+ project: DCMProjectEntityModel = get_entity_for_operation(
202
218
  cli_context=cli_context,
203
219
  entity_id=entity_id,
204
220
  project_definition=cli_context.project_definition,
205
- entity_type="project",
221
+ entity_type="dcm",
206
222
  )
207
223
  om = ObjectManager()
208
- if not om.object_exists(object_type="project", fqn=project.fqn):
224
+ if not om.object_exists(object_type="dcm", fqn=project.fqn):
209
225
  raise CliError(
210
- f"Project '{project.fqn}' does not exist. Use `project create` command first"
226
+ f"DCM Project '{project.fqn}' does not exist. Use `dcm create` command first."
211
227
  )
212
- ProjectManager().add_version(
228
+ DCMProjectManager().add_version(
213
229
  project=project,
214
230
  prune=prune,
215
231
  from_stage=_from,
@@ -218,18 +234,49 @@ def add_version(
218
234
  )
219
235
  alias_str = "" if _alias is None else f"'{_alias}' "
220
236
  return MessageResult(
221
- f"New project version {alias_str}added to project '{project.fqn}'"
237
+ f"New version {alias_str}added to DCM Project '{project.fqn}'."
222
238
  )
223
239
 
224
240
 
225
241
  @app.command(requires_connection=True)
226
242
  def list_versions(
227
- identifier: FQN = project_identifier,
243
+ identifier: FQN = dcm_identifier,
228
244
  **options,
229
245
  ):
230
246
  """
231
- Lists versions of given project.
247
+ Lists versions of given DCM Project.
232
248
  """
233
- pm = ProjectManager()
249
+ pm = DCMProjectManager()
234
250
  results = pm.list_versions(project_name=identifier)
235
251
  return QueryResult(results)
252
+
253
+
254
+ @app.command(requires_connection=True)
255
+ def drop_version(
256
+ identifier: FQN = dcm_identifier,
257
+ version_name: str = typer.Argument(
258
+ help="Name or alias of the version to drop. For names containing '$', use single quotes to prevent shell expansion (e.g., 'VERSION$1').",
259
+ show_default=False,
260
+ ),
261
+ if_exists: bool = IfExistsOption(help="Do nothing if the version does not exist."),
262
+ **options,
263
+ ):
264
+ """
265
+ Drops a version from the DCM Project.
266
+ """
267
+ # Detect potential shell expansion issues
268
+ if version_name and version_name.upper() == "VERSION":
269
+ cli_console.warning(
270
+ f"Version name '{version_name}' might be truncated due to shell expansion. "
271
+ f"If you meant to use a version like 'VERSION$1', try using single quotes: 'VERSION$1'."
272
+ )
273
+
274
+ dpm = DCMProjectManager()
275
+ dpm.drop_version(
276
+ project_name=identifier,
277
+ version_name=version_name,
278
+ if_exists=if_exists,
279
+ )
280
+ return MessageResult(
281
+ f"Version '{version_name}' dropped from DCM Project '{identifier}'."
282
+ )
@@ -35,10 +35,10 @@ T = TypeVar("T")
35
35
  MANIFEST_FILE_NAME = "manifest.yml"
36
36
 
37
37
 
38
- class ProjectEntityModel(EntityModelBaseWithArtifacts):
39
- type: Literal["project"] = DiscriminatorField() # noqa: A003
38
+ class DCMProjectEntityModel(EntityModelBaseWithArtifacts):
39
+ type: Literal["dcm"] = DiscriminatorField() # noqa: A003
40
40
  stage: Optional[str] = Field(
41
- title="Stage in which the project artifacts will be stored", default=None
41
+ title="Stage in which the DCM Project artifacts will be stored", default=None
42
42
  )
43
43
 
44
44
  @field_validator("artifacts")
@@ -54,6 +54,6 @@ class ProjectEntityModel(EntityModelBaseWithArtifacts):
54
54
  return super().transform_artifacts(orig_artifacts)
55
55
 
56
56
 
57
- @attach_spans_to_entity_actions(entity_name="project")
58
- class ProjectEntity(EntityBase[ProjectEntityModel]):
57
+ @attach_spans_to_entity_actions(entity_name="dcm")
58
+ class DCMProjectEntity(EntityBase[DCMProjectEntityModel]):
59
59
  """Placeholder for project entity"""
@@ -14,7 +14,7 @@
14
14
  from textwrap import dedent
15
15
  from typing import List, Optional
16
16
 
17
- from snowflake.cli._plugins.project.project_entity_model import ProjectEntityModel
17
+ from snowflake.cli._plugins.dcm.dcm_project_entity_model import DCMProjectEntityModel
18
18
  from snowflake.cli._plugins.stage.manager import StageManager
19
19
  from snowflake.cli.api.artifacts.upload import sync_artifacts_with_stage
20
20
  from snowflake.cli.api.cli_global_context import get_cli_context
@@ -27,16 +27,21 @@ from snowflake.cli.api.stage_path import StagePath
27
27
  from snowflake.connector.cursor import SnowflakeCursor
28
28
 
29
29
 
30
- class ProjectManager(SqlExecutionMixin):
30
+ class DCMProjectManager(SqlExecutionMixin):
31
31
  def execute(
32
32
  self,
33
33
  project_name: FQN,
34
34
  configuration: str | None = None,
35
35
  version: str | None = None,
36
+ from_stage: str | None = None,
36
37
  variables: List[str] | None = None,
37
38
  dry_run: bool = False,
38
39
  ):
39
- query = f"EXECUTE PROJECT {project_name.sql_identifier}"
40
+ query = f"EXECUTE DCM PROJECT {project_name.sql_identifier}"
41
+ if dry_run:
42
+ query += " PLAN"
43
+ else:
44
+ query += " DEPLOY"
40
45
  if configuration or variables:
41
46
  query += f" USING"
42
47
  if configuration:
@@ -47,16 +52,17 @@ class ProjectManager(SqlExecutionMixin):
47
52
  ).removeprefix(" using")
48
53
  if version:
49
54
  query += f" WITH VERSION {version}"
50
- if dry_run:
51
- query += " DRY_RUN=TRUE"
55
+ elif from_stage:
56
+ stage_path = StagePath.from_stage_str(from_stage)
57
+ query += f" FROM {stage_path.absolute_path()}"
52
58
  return self.execute_query(query=query)
53
59
 
54
60
  def _create_object(self, project_name: FQN) -> SnowflakeCursor:
55
- query = dedent(f"CREATE PROJECT {project_name.sql_identifier}")
61
+ query = dedent(f"CREATE DCM PROJECT {project_name.sql_identifier}")
56
62
  return self.execute_query(query)
57
63
 
58
64
  def create(
59
- self, project: ProjectEntityModel, initialize_version_from_local_files: bool
65
+ self, project: DCMProjectEntityModel, initialize_version_from_local_files: bool
60
66
  ) -> None:
61
67
  self._create_object(project.fqn)
62
68
  if initialize_version_from_local_files:
@@ -70,9 +76,9 @@ class ProjectManager(SqlExecutionMixin):
70
76
  comment: str | None = None,
71
77
  ):
72
78
  stage_path = StagePath.from_stage_str(from_stage)
73
- query = f"ALTER PROJECT {project_name.identifier} ADD VERSION"
79
+ query = f"ALTER DCM PROJECT {project_name.identifier} ADD VERSION"
74
80
  if alias:
75
- query += f' IF NOT EXISTS "{alias}"'
81
+ query += f" IF NOT EXISTS {alias}"
76
82
  query += f" FROM {stage_path.absolute_path(at_prefix=True)}"
77
83
  if comment:
78
84
  query += f" COMMENT = '{comment}'"
@@ -80,15 +86,15 @@ class ProjectManager(SqlExecutionMixin):
80
86
 
81
87
  def add_version(
82
88
  self,
83
- project: ProjectEntityModel,
89
+ project: DCMProjectEntityModel,
84
90
  prune: bool = False,
85
91
  from_stage: Optional[str] = None,
86
92
  alias: Optional[str] = None,
87
93
  comment: Optional[str] = None,
88
94
  ):
89
95
  """
90
- Adds a version to project. If [from_stage] is not defined,
91
- uploads local files to the stage defined in project definition.
96
+ Adds a version to DCM Project. If [from_stage] is not defined,
97
+ uploads local files to the stage defined in DCM Project definition.
92
98
  """
93
99
 
94
100
  if not from_stage:
@@ -102,7 +108,7 @@ class ProjectManager(SqlExecutionMixin):
102
108
  prune=prune,
103
109
  )
104
110
 
105
- with cli_console.phase(f"Creating project version from stage {from_stage}"):
111
+ with cli_console.phase(f"Creating DCM Project version from stage {from_stage}"):
106
112
  return self._create_version(
107
113
  project_name=project.fqn,
108
114
  from_stage=from_stage, # type:ignore
@@ -111,5 +117,20 @@ class ProjectManager(SqlExecutionMixin):
111
117
  )
112
118
 
113
119
  def list_versions(self, project_name: FQN):
114
- query = f"SHOW VERSIONS IN PROJECT {project_name.identifier}"
120
+ query = f"SHOW VERSIONS IN DCM PROJECT {project_name.identifier}"
121
+ return self.execute_query(query=query)
122
+
123
+ def drop_version(
124
+ self,
125
+ project_name: FQN,
126
+ version_name: str,
127
+ if_exists: bool = False,
128
+ ):
129
+ """
130
+ Drops a version from the DCM Project.
131
+ """
132
+ query = f"ALTER DCM PROJECT {project_name.identifier} DROP VERSION"
133
+ if if_exists:
134
+ query += " IF EXISTS"
135
+ query += f" {version_name}"
115
136
  return self.execute_query(query=query)
@@ -12,7 +12,7 @@
12
12
  # See the License for the specific language governing permissions and
13
13
  # limitations under the License.
14
14
 
15
- from snowflake.cli._plugins.project import commands
15
+ from snowflake.cli._plugins.dcm import commands
16
16
  from snowflake.cli.api.plugins.command import (
17
17
  SNOWCLI_ROOT_COMMAND_PATH,
18
18
  CommandSpec,
@@ -14,9 +14,8 @@
14
14
 
15
15
  from __future__ import annotations
16
16
 
17
- from pathlib import Path, PurePosixPath
17
+ from pathlib import PurePosixPath
18
18
  from textwrap import dedent
19
- from typing import List
20
19
 
21
20
  from click import UsageError
22
21
  from snowflake.cli._plugins.stage.manager import (
@@ -64,19 +63,10 @@ class GitStagePathParts(StagePathParts):
64
63
  def full_path(self) -> str:
65
64
  return f"{self.stage.rstrip('/')}/{self.directory}"
66
65
 
67
- def replace_stage_prefix(self, file_path: str) -> str:
68
- stage = Path(self.stage).parts[0]
69
- file_path_without_prefix = Path(file_path).parts[OMIT_FIRST]
70
- return f"{stage}/{'/'.join(file_path_without_prefix)}"
71
-
72
66
  def add_stage_prefix(self, file_path: str) -> str:
73
67
  stage = self.stage.rstrip("/")
74
68
  return f"{stage}/{file_path.lstrip('/')}"
75
69
 
76
- def get_directory_from_file_path(self, file_path: str) -> List[str]:
77
- stage_path_length = len(Path(self.directory).parts)
78
- return list(Path(file_path).parts[3 + stage_path_length : -1])
79
-
80
70
 
81
71
  class GitManager(StageManager):
82
72
  @staticmethod
@@ -49,6 +49,7 @@ from snowflake.cli._plugins.nativeapp.codegen.snowpark.models import (
49
49
  from snowflake.cli._plugins.stage.diff import to_stage_path
50
50
  from snowflake.cli.api.artifacts.bundle_map import BundleMap
51
51
  from snowflake.cli.api.cli_global_context import get_cli_context, span
52
+ from snowflake.cli.api.console import cli_console
52
53
  from snowflake.cli.api.console import cli_console as cc
53
54
  from snowflake.cli.api.metrics import CLICounterField
54
55
  from snowflake.cli.api.project.schemas.entities.common import (
@@ -181,6 +182,9 @@ class SnowparkAnnotationProcessor(ArtifactProcessor):
181
182
  setup script with generated SQL that registers these functions.
182
183
  """
183
184
 
185
+ cli_console.warning(
186
+ "Snowpark processor is not supported and will be removed soon."
187
+ )
184
188
  get_cli_context().metrics.set_counter(CLICounterField.SNOWPARK_PROCESSOR, 1)
185
189
 
186
190
  bundle_map = BundleMap(
@@ -55,7 +55,6 @@ from snowflake.cli.api.exceptions import (
55
55
  IncompatibleParametersError,
56
56
  UnmetParametersError,
57
57
  )
58
- from snowflake.cli.api.output.formats import OutputFormat
59
58
  from snowflake.cli.api.output.types import (
60
59
  CommandResult,
61
60
  MessageResult,
@@ -117,9 +116,9 @@ def app_diff(
117
116
  diff = ws.perform_action(
118
117
  package_id,
119
118
  EntityActions.DIFF,
120
- print_to_console=cli_context.output_format != OutputFormat.JSON,
119
+ print_to_console=not cli_context.output_format.is_json,
121
120
  )
122
- if cli_context.output_format == OutputFormat.JSON:
121
+ if cli_context.output_format.is_json:
123
122
  return ObjectResult(diff.to_dict())
124
123
 
125
124
  return None
@@ -373,7 +372,7 @@ def app_validate(
373
372
  )
374
373
  package_id = options["package_entity_id"]
375
374
  package = ws.get_entity(package_id)
376
- if cli_context.output_format == OutputFormat.JSON:
375
+ if cli_context.output_format.is_json:
377
376
  return ObjectResult(
378
377
  package.get_validation_result(
379
378
  action_ctx=ws.action_ctx,
@@ -1330,7 +1330,7 @@ class ApplicationPackageEntity(EntityBase[ApplicationPackageEntityModel]):
1330
1330
  role=self.role,
1331
1331
  prune=prune,
1332
1332
  recursive=recursive,
1333
- stage_path=stage_path,
1333
+ stage_path_parts=stage_path,
1334
1334
  local_paths_to_sync=paths,
1335
1335
  print_diff=print_diff,
1336
1336
  )
@@ -26,7 +26,6 @@ from snowflake.cli.api.cli_global_context import get_cli_context
26
26
  from snowflake.cli.api.commands.decorators import with_project_definition
27
27
  from snowflake.cli.api.commands.snow_typer import SnowTyperFactory
28
28
  from snowflake.cli.api.entities.utils import EntityActions
29
- from snowflake.cli.api.output.formats import OutputFormat
30
29
  from snowflake.cli.api.output.types import (
31
30
  CollectionResult,
32
31
  CommandResult,
@@ -68,7 +67,7 @@ def release_channel_list(
68
67
  release_channel=channel,
69
68
  )
70
69
 
71
- if cli_context.output_format == OutputFormat.JSON:
70
+ if cli_context.output_format.is_json:
72
71
  return CollectionResult(channels)
73
72
 
74
73
 
@@ -30,7 +30,6 @@ from snowflake.cli.api.commands.decorators import (
30
30
  )
31
31
  from snowflake.cli.api.commands.snow_typer import SnowTyperFactory
32
32
  from snowflake.cli.api.entities.utils import EntityActions
33
- from snowflake.cli.api.output.formats import OutputFormat
34
33
  from snowflake.cli.api.output.types import (
35
34
  CollectionResult,
36
35
  CommandResult,
@@ -105,7 +104,7 @@ def create(
105
104
  )
106
105
 
107
106
  message = "Version create is now complete."
108
- if cli_context.output_format == OutputFormat.JSON:
107
+ if cli_context.output_format.is_json:
109
108
  return ObjectResult(
110
109
  {
111
110
  "message": message,
@@ -79,7 +79,6 @@ class SnowparkObjectManager(SqlExecutionMixin):
79
79
  ) -> str:
80
80
  entity.imports.extend(artifact_files)
81
81
  imports = [f"'{x}'" for x in entity.imports]
82
- packages_list = ",".join(f"'{p}'" for p in snowflake_dependencies)
83
82
 
84
83
  object_type = entity.get_type()
85
84
 
@@ -91,7 +90,6 @@ class SnowparkObjectManager(SqlExecutionMixin):
91
90
  f"runtime_version={entity.runtime or DEFAULT_RUNTIME}",
92
91
  f"imports=({', '.join(imports)})",
93
92
  f"handler='{entity.handler}'",
94
- f"packages=({packages_list})",
95
93
  ]
96
94
 
97
95
  if entity.external_access_integrations:
@@ -100,17 +98,24 @@ class SnowparkObjectManager(SqlExecutionMixin):
100
98
  if entity.secrets:
101
99
  query.append(entity.get_secrets_sql())
102
100
 
103
- if isinstance(entity, ProcedureEntityModel) and entity.execute_as_caller:
104
- query.append("execute as caller")
101
+ if entity.artifact_repository_packages and entity.packages:
102
+ raise UsageError(
103
+ "You cannot specify both artifact_repository_packages and packages.",
104
+ )
105
105
 
106
- if entity.artifact_repository and entity.artifact_repository_packages:
107
- packages = [f"'{item}'" for item in entity.artifact_repository_packages]
108
- query.extend(
109
- [
110
- f"ARTIFACT_REPOSITORY= {entity.artifact_repository}",
111
- f"ARTIFACT_REPOSITORY_PACKAGES=({','.join(packages)})",
112
- ]
106
+ packages_list = snowflake_dependencies.copy()
107
+ if entity.artifact_repository and (
108
+ entity.artifact_repository_packages or entity.packages
109
+ ):
110
+ if entity.artifact_repository_packages:
111
+ packages_list.extend(entity.artifact_repository_packages)
112
+ else:
113
+ packages_list.extend(entity.packages)
114
+ query.append(
115
+ f"ARTIFACT_REPOSITORY= {entity.artifact_repository}",
113
116
  )
117
+ packages = [f"'{item}'" for item in packages_list]
118
+ query.append(f"packages=({','.join(packages)})")
114
119
 
115
120
  if entity.resource_constraint:
116
121
  constraints = ",".join(
@@ -118,6 +123,9 @@ class SnowparkObjectManager(SqlExecutionMixin):
118
123
  )
119
124
  query.append(f"RESOURCE_CONSTRAINT=({constraints})")
120
125
 
126
+ if isinstance(entity, ProcedureEntityModel) and entity.execute_as_caller:
127
+ query.append("execute as caller")
128
+
121
129
  return self.execute_query("\n".join(query))
122
130
 
123
131
  def deploy_entity(
@@ -215,6 +223,10 @@ def _check_if_replace_is_required(
215
223
  )
216
224
  return True
217
225
 
226
+ if entity.packages != resource_json.get("artifact_repository_packages", None):
227
+ log.info("Packages do not match. Replacing the %s", object_type)
228
+ return True
229
+
218
230
  if isinstance(entity, ProcedureEntityModel):
219
231
  if resource_json.get("execute as", "OWNER") != (
220
232
  "CALLER" if entity.execute_as_caller else "OWNER"