教程 3:使用容器升级应用程序¶
简介¶
Snowflake Native App Framework 允许提供商在 Snowflake Data Cloud 内构建、销售和分发应用程序。提供商可以创建利用 Snowflake 核心功能的应用程序,与使用者共享数据和应用程序逻辑。应用程序还可以实施 Snowpark Container Services,以促进 Snowflake 生态系统内容器化应用程序的部署、管理和扩展。
Snowflake Native App Framework 允许提供商更新应用程序并向使用者发布新版本或补丁。本教程介绍如何执行以下任务:
向应用程序添加版本初始化程序。
为应用程序变更创建版本和补丁。
在使用者账户中升级应用程序。
先决条件教程¶
本教程假设您知道如何开发基础 Snowflake Native App 并可以创建 Snowflake Native App with Snowpark Container Services。本教程以完成以下教程,并掌握其中的知识为基础:
在按照本教程升级使用容器的应用程序之前,请确保您已完成这两个教程。
小心
本教程基于您在 教程 2:创建带容器的应用程序 中创建的应用程序。如果您的账户中没有应用程序文件和 Snowflake 对象,则必须在开始本教程之前再次完成该教程。有关更多信息,请参阅 验证您的账户中是否存在上一个教程中的应用程序。
在本教程中学习的内容¶
本教程扩展了您在 教程 2:创建带容器的应用程序 中创建的使用容器的应用程序。在本教程中,您将学习如何执行以下操作:
使用版本初始化程序回调函数来处理服务升级和故障。
创建应用程序版本定义。
升级应用程序。
模拟应用程序升级故障。
为应用程序创建补丁以修复故障。
验证您的账户中是否存在上一个教程中的应用程序¶
要验证您在 教程 2:创建带容器的应用程序 中创建的使用容器的应用程序在您的账户中是否仍然可用,请执行以下任务:
小心
如果以下任何任务未成功完成,您将需要再次执行 教程 2:创建带容器的应用程序。
要验证 Snow CLI 是否配置正确,请运行以下命令:
snow connection test -c tut-connection
此命令的输出应类似于以下内容:
+----------------------------------------------------------------------------------+ | key | value | |-----------------+----------------------------------------------------------------| | Connection name | tut-connection | | Status | OK | | Host | USER_ACCOUNT.snowflakecomputing.cn | | Account | USER_ACCOUNT | | User | tutorial_user | | Role | TUTORIAL_ROLE | | Database | TUTORIAL_IMAGE_DATABASE | | Warehouse | TUTORIAL_WAREHOUSE | +----------------------------------------------------------------------------------+
此命令将验证以下要求:
Snow CLI 连接正常。
TUTORIAL_ROLE 存在。
TUTORIAL_WAREHOUSE 存在。
要验证其他必要 Snowflake 对象是否存在,请从工作表运行以下命令:
USE ROLE tutorial_role;
SHOW DATABASES LIKE 'tutorial_image_database';
SHOW SCHEMAS LIKE 'tutorial_image_schema';
SHOW IMAGE REPOSITORIES LIKE 'tutorial_image_repo';
这些命令都应该返回每个 Snowflake 对象的名称。
要验证服务是否仍在运行,请从工作表运行以下命令:
CALL na_spcs_tutorial_app.app_public.service_status();
确保您的本地目录结构如以下示例所示:
├── app └── manifest.yml └── README.md └── setup_script.sql ├── README.md ├── service └── echo_service.py ├── echo_spec.yaml ├── Dockerfile └── templates └── basic_ui.html ├── snowflake.yml
您可能还会看到一个名为
output
,且包含由snow app run
命令生成的应用程序文件的文件夹。
删除应用程序对象¶
如果您在处理 教程 2:创建带容器的应用程序 过程中创建的应用程序仍然在您的账户中,则必须先删除该应用程序对象,然后才能继续本教程。
备注
您必须删除现有的应用程序,因为直接从暂存文件以开发模式创建的应用程序无法升级。
要确定上一教程中的应用程序 (
na_spcs_tutorial_app
) 在您的账户中是否存在,请从工作表运行以下命令:SHOW APPLICATIONS LIKE 'na_spcs_tutorial_app';
如果
na_spcs_tutorial_app
应用程序出现在此命令的输出中,请通过从工作表运行以下命令来删除该应用程序:USE ROLE tutorial_role; DROP APPLICATION IF EXISTS na_spcs_tutorial_app CASCADE;
在本部分完成的内容¶
在本部分中,您确认了上一个教程中的应用程序文件和 Snowflake 对象仍在您的账户中运行。
下一部分中,您将了解有关 Snowflake Native App Framework 中版本和升级的更多信息。
了解版本、补丁和升级¶
本部分向您介绍本教程中涵盖的概念,包括:
版本和补丁
升级
版本初始化程序
关于版本和补丁¶
Snowflake Native App Framework 中的版本是版本号和补丁编号的组合。这些编号是在应用程序包中定义的。
. rst-class:: bulleted-definition-list
- 版本
通常包含对 Snowflake Native App 的重大更新。在应用程序包中定义版本。
- 补丁
通常包含对 Snowflake Native App 的较小更新。与版本一样,在应用程序包中定义补丁。
备注
一个应用程序包一次只能有两个活动版本。单个应用程序版本最多可以有 130 个补丁。
关于升级¶
在 Snowflake Native App Framework 上下文中,升级是对使用者账户中安装的 Snowflake Native App 版本或补丁的更新。Snowflake Native App Framework 支持两种类型的升级:
- 自动升级
自动升级是由提供商启动的升级。当有新版本或补丁可用时,提供商将修改应用程序包上的发布指令。这将触发发布指令指定的应用程序所有已安装实例的自动升级。
- 手动升级
手动升级是使用者为响应提供商的通信而启动的升级。当提供商需要向使用者快速发布更新(例如错误修复)时,手动升级很有用。
备注
本教程介绍如何对使用容器的应用程序进行手动升级。
当有新版本或补丁可用时,提供商会修改应用程序包上的发布指令,然后通知使用者有新版本可用。
使用者通过在其账户中运行 ALTER APPLICATION 命令来执行升级。通常,手动升级允许使用者比自动升级更快地升级已安装的应用程序。
关于版本初始化程序¶
版本初始化程序用于启动或升级服务或其他相关流程。版本初始化程序是在清单文件中定义并在安装脚本中实施的回调存储过程。系统会在以下情况下调用版本初始化程序回调函数:
安装过程中,应用程序安装脚本无误完成后,系统就会调用版本初始化程序。
升级过程中,有两种可能的情况会调用版本初始化程序:
如果新版本的安装脚本成功,则会调用新版本的版本初始化程序。
如果新版本的安装脚本或版本初始化程序失败,则会调用前一版本的版本初始化程序。这样,前一版本的版本初始化程序就可以使用 ALTER SERVICE 命令将服务恢复到前一版本。
向应用程序添加版本初始化程序¶
在上一个教程中,您创建了一个使用容器的基础应用程序。在本部分中,您将更新此应用程序,以向应用程序中添加版本初始化程序。您还向应用程序包中添加一个版本。
将版本初始化程序添加到清单文件¶
版本初始化程序在应用程序的清单文件中定义。要定义版本初始化程序,请将以下代码添加到 manifest.yml
文件的末尾:
lifecycle_callbacks:
version_initializer: app_public.version_init
这指定了用作版本初始化程序的存储过程的架构和名称。在下一部分中,您将实施 version_init
存储过程。
将版本初始化程序作为存储过程添加到安装脚本中¶
在上一部分中,您将版本初始化程序的名称添加到了清单文件中。在本部分中,您会将存储过程的代码添加到安装脚本中。
将以下代码添加到
setup_script.sql
文件的末尾:
CREATE OR REPLACE PROCEDURE app_public.version_init()
RETURNS STRING
LANGUAGE SQL
AS
$$
DECLARE
can_create_compute_pool BOOLEAN; -- Flag to check if 'CREATE COMPUTE POOL' privilege is held
BEGIN
-- Check if the account holds the 'CREATE COMPUTE POOL' privilege
SELECT SYSTEM$HOLD_PRIVILEGE_ON_ACCOUNT('CREATE COMPUTE POOL')
INTO can_create_compute_pool;
ALTER SERVICE IF EXISTS core.echo_service
FROM SPECIFICATION_FILE = 'service/echo_spec.yaml';
IF (can_create_compute_pool) THEN
-- When installing app, the app has no 'CREATE COMPUTE POOL' privilege at that time,
-- so it will not execute the code below
-- Since the ALTER SERVICE is an async process, wait for the service to be ready
SELECT SYSTEM$WAIT_FOR_SERVICES(120, 'core.echo_service');
END IF;
RETURN 'DONE';
END;
$$;
上传更改后的文件并创建版本¶
修改安装脚本后,请执行以下过程,将修改后的文件上传到暂存区并创建版本:
运行以下命令,上传文件并创建版本:
snow app version create v1 -c tut-connection
snow app version
命令将更新的文件上传到暂存区。如果应用程序包和文件已经存在,此命令将仅上传更改的文件。
此命令将创建一个名为 v1 的应用程序新版本,其默认补丁设置为 0。
设置应用程序的默认发布指令¶
在上一部分中,您上传了更改的文件并创建了应用程序的 v1
版本。在本部分中,您将设置默认发布指令以使用版本 v1
。
要更新默认发布指令,请从工作表运行以下命令:
ALTER APPLICATION PACKAGE na_spcs_tutorial_pkg
SET DEFAULT RELEASE DIRECTIVE VERSION=v1 PATCH=0;
如果为应用程序设置默认发布指令,使用者在其账户中安装该应用程序时会自动安装该版本。在下一部分中,您将根据发布指令在本地账户中创建应用程序。
创建并测试应用程序¶
您已经添加了版本并设置了默认发布指令,现在可以创建应用程序并授予所需权限:
通过运行以下命令,通过发布指令创建应用程序:
snow app run --from-release-directive -c tut-connection
此命令使用您在上一部分中定义的发布指令创建应用程序。
创建应用程序后,通过从工作表运行以下命令,向应用程序授予所需的权限,以便能够运行。
GRANT CREATE COMPUTE POOL ON ACCOUNT TO APPLICATION na_spcs_tutorial_app; GRANT BIND SERVICE ENDPOINT ON ACCOUNT TO APPLICATION na_spcs_tutorial_app;
调用您在
setup_script.sql`
文件中定义的app_public.start_app
过程:通过从工作表运行以下命令:CALL na_spcs_tutorial_app.app_public.start_app();
通过从工作表运行以下命令来确认该函数已创建:
SHOW FUNCTIONS LIKE '%my_echo_udf%' IN APPLICATION na_spcs_tutorial_app;
要验证服务是否已创建且正常运行,请从工作表运行以下命令:
CALL na_spcs_tutorial_app.app_public.service_status();
要调用服务函数向服务发送请求并验证响应,请从工作表运行以下命令:
SELECT na_spcs_tutorial_app.core.my_echo_udf('hello');
要查看有关应用程序的信息,请从工作表运行以下命令:
DESC APPLICATION na_spcs_tutorial_app;
回顾本部分所学内容¶
在本部分中,您完成了以下任务:
了解了版本初始化程序以及如何将其添加到清单文件和安装脚本。
了解了 Snowflake Native App Framework 中版本和补丁的基础知识。
设置默认发布指令以指向应用程序的特定版本。
根据发布指令安装了应用程序。
通过调用存储过程测试应用程序并使用 DESCRIBE APPLICATION 命令查看应用程序的状态。
备注
在本教程中,您在本地账户中创建了应用程序对象,并使用了 DESCRIBE APPLICATION 命令。这模仿了使用者账户中应用程序的行为。
更新应用程序并升级到新版本¶
在上一部分中,您通过添加版本初始化程序作为存储过程修改了原始应用程序。您还根据默认发布指令创建了应用程序的新版本,即版本 v1。
在本部分中,您将对应用程序进行另一项更改,创建版本 v2,更新默认发布指令,并将已安装的应用程序从版本 v1 升级到版本 v2。
向应用程序添加新表¶
要模拟向应用程序添加新功能,请在安装脚本中添加新表。
将以下命令添加到
setup_script.yml
的末尾CREATE TABLE IF NOT EXISTS core.setup_script_run(run_at TIMESTAMP); GRANT SELECT ON TABLE core.setup_script_run to APPLICATION ROLE app_user; INSERT INTO core.setup_script_run(run_at) values(current_timestamp());
创建应用程序版本¶
将修改后的安装脚本上传到暂存区并创建应用程序的 v2 版本:
在
na-spcs-tutorial
文件夹中运行以下命令:
snow app version create v2 -c tut-connection
此命令将创建一个名为 v2 的应用程序新版本,其默认补丁设置为 0。
snow app version
命令将更新的文件上传到暂存区。如果应用程序包和文件已经存在,此命令将仅上传更改的文件。
设置应用程序的默认发布指令¶
创建应用程序的 v2
版本后,通过从工作表运行以下命令来设置应用程序包的发布指令:
ALTER APPLICATION PACKAGE na_spcs_tutorial_pkg
SET DEFAULT RELEASE DIRECTIVE VERSION=v2 PATCH=0;
此命令将发布指令设置为版本 v2
和补丁 0
。
将应用程序从 v1 升级到 v2¶
现在您已将发布指令更新为指向新版本,请通过从工作表运行以下命令来升级应用程序:
snow app run --from-release-directive -c tut-connection
测试升级后的应用程序¶
升级应用程序后,通过从工作表运行以下命令来测试应用程序:
SELECT na_spcs_tutorial_app.core.my_echo_udf('hello');
回顾本部分所学内容¶
恭喜!您已成功将应用程序从版本 v1
升级到版本 v2
。
在本部分中,您完成了以下任务:
更新了应用程序以包含表。
根据此更新创建了应用程序的新版本。
更新了默认发布指令以指向新版本。
手动升级了应用程序。
在下一部分中,您将升级应用程序的服务,并通过在安装脚本中故意添加错误来模拟升级过程中的错误。
模拟升级错误¶
在上一部分中,您向应用程序添加了新表、创建了新版本并升级了应用程序。
在本部分中,您将更新服务规范以模拟服务更新。您还可以在安装脚本中故意添加错误来模拟升级失败,展示升级失败时版本初始化程序如何处理服务升级。
更新服务规范文件¶
在本部分中,您将更新应用程序的服务规范以模拟服务更改。
在
service/echo_spec.yaml
文件中,将CHARACTER_NAME
的值从Bob
更改为Tom
。此更改将导致服务返回以下消息:
`Tom said hello.`
此更改的目的是让您可以在以下部分中尝试升级后,查看正在运行的服务版本。
更新安装脚本以包含故意错误¶
为了模拟升级过程中的错误,请在安装脚本中故意引入错误,例如对不存在的表添加 SELECT 语句。
在 setup_script.sql
中 app_public.version_init()
过程的末尾,添加以下语句。
SELECT * FROM table_does_not_exist;
该语句从语法上来说是正确的,但是引用的表不存在。这会导致升级期间运行安装脚本时出现错误。
进行此更改后,app_public.version_init()
函数应类似于以下示例:
GRANT USAGE ON PROCEDURE app_public.service_status() TO APPLICATION ROLE app_user;
CREATE OR REPLACE PROCEDURE app_public.version_init()
RETURNS STRING
LANGUAGE SQL
AS
$$
DECLARE
-- Flag to check if 'CREATE COMPUTE POOL' privilege is held
can_create_compute_pool BOOLEAN;
BEGIN
-- Check if the account holds the 'CREATE COMPUTE POOL' privilege
SELECT SYSTEM$HOLD_PRIVILEGE_ON_ACCOUNT('CREATE COMPUTE POOL')
INTO can_create_compute_pool;
ALTER SERVICE IF EXISTS core.echo_service
FROM SPECIFICATION_FILE = 'service/echo_spec.yaml';
IF (can_create_compute_pool) THEN
-- When installing app, the app has no 'CREATE COMPUTE POOL' privilege at that time,
-- so it will not execute the code below
-- Since the ALTER SERVICE is an async process, wait for the service to be ready
SELECT SYSTEM$WAIT_FOR_SERVICES(120, 'core.echo_service');
END IF;
-- trigger an error. The upgrade fails
SELECT * FROM non_exist_table;
RETURN 'DONE';
END;
$$;
上传修改后的文件并创建新补丁¶
在前面的部分中,您更新了应用程序的服务规范和安装脚本。
要上传文件并为应用程序创建新补丁,请执行以下任务:
运行以下命令,向应用程序包添加补丁。
snow app version create v2 --patch 1 -c tut-connection
出现提示时,输入
y
即可向应用程序包中添加新补丁。
设置应用程序的默认发布指令¶
在上一部分中,您上传了文件并创建了更新补丁。要设置补丁的默认发布指令,请从工作表运行以下命令:
ALTER APPLICATION PACKAGE na_spcs_tutorial_pkg
SET DEFAULT RELEASE DIRECTIVE VERSION=v2 PATCH=1;
此命令将应用程序补丁设置为补丁 1
。
升级应用程序¶
在前面的部分中,您对应用程序进行了更新并创建了新补丁。在本部分中,您将升级应用程序,但预期会由于您在前面几节中引入的错误而失败。
要升级应用程序,请运行以下命令:
snow app run --from-release-directive -c tut-connection
要查看应用程序的升级状态,请从工作表运行以下命令:
DESC APPLICATION na_spcs_tutorial_app;
此命令显示有关应用程序的信息,包括升级状态、升级尝试次数以及升级失败的原因。
升级失败后,Snowflake CLI 将返回以下消息:
Object 'TABLE_DOES_NOT_EXIST' does not exist or not authorized.'
此外,升级失败后,DESC APPLICATION 命令还会显示与升级相关的以下属性:
属性
值
upgrade_state
FAILED
upgrade_failure_reason
upgrade_failure_reason[ErrorCode 2003] 未捕获的异常类型“STATEMENT_ERROR”在第 89 行位置 0 处:未捕获的异常类型“STATEMENT_ERROR”在第 19 行位置 3 处:SQL 编译错误:对象“TABLE_DOES_NOT_EXIST”不存在或未获得授权。
运行应用程序服务以查看正在运行的服务版本¶
在上一部分中,您模拟了从版本 v2、补丁 0 升级到版本 v2、补丁 1 时发生的故障。
要确定当前正在运行的服务版本,请从工作表运行以下命令。
SELECT na_spcs_tutorial_app.core.my_echo_udf('hello');
此命令将返回以下字符串:
Bob said hello
在这里可以看到,由于升级失败,应用程序将继续运行 v2 补丁 0 的服务。
但是,如果您没有在应用程序中包含版本初始化程序,则尽管应用程序升级失败,但升级过程仍会将服务升级到 v2 补丁 1。如果应用程序升级失败,版本初始化程序将确保服务版本不会升级,并继续与应用程序保持同步。
回顾本部分所学内容¶
在本部分中,您完成了以下任务:
在安装脚本中引入了错误来模拟升级过程中的错误。
失败后验证了应用程序和服务的版本。
了解了版本初始化程序如何确保升级失败时服务版本与应用程序版本同步。
创建补丁来修复升级错误¶
在上一部分中,您在应用程序的安装脚本中引入了一个错误。升级应用程序后,您可以验证应用程序和服务是否仍在使用版本 v2 补丁 0 继续运行。
在本部分中,您将修改应用程序的安装脚本以修复错误、创建更新补丁并升级应用程序。
修改安装脚本¶
要修复您在上一部分中故意引入的错误,请从 setup_script.yaml
文件移除以下语句:
SELECT * FROM table_does_not_exist;
上传更新的文件并创建新补丁¶
要将修改后的安装脚本上传到暂存区并创建新补丁,请执行以下任务:
运行以下命令,为应用程序创建新补丁:
出现提示时,输入
y
即可向应用程序包中添加新补丁。
更新默认发布指令¶
在上一部分中,您为应用程序创建了补丁 2
。要设置补丁的默认发布指令,请从工作表运行以下命令:
ALTER APPLICATION PACKAGE na_spcs_tutorial_pkg
SET DEFAULT RELEASE DIRECTIVE VERSION=v2 PATCH=2;
升级应用程序并验证服务版本¶
创建新版本并设置默认发布指令后,通过执行以下任务升级应用程序并测试服务:
要将应用程序从版本
v2
补丁0
升级到版本v2
补丁2
,请运行以下命令:snow app run --from-release-directive -c tut-connection
要验证当前正在运行的服务的版本,请从工作表运行以下命令:
SELECT na_spcs_tutorial_app.core.my_echo_udf('hello');
要查看应用程序的状态,包括当前安装的版本,请运行以下命令:
DESC APPLICATION na_spcs_tutorial_app;
在输出中,
version
属性为v2
,补丁属性为2
。
回顾本部分所学内容¶
恭喜!经历失败后,您终于成功升级了应用程序。
在本部分中,您完成了以下任务:
修复了安装脚本中的错误。
创建了新补丁
p2
,以更新应用程序。将应用程序升级到了新补丁。
删除教程中创建的应用程序和对象¶
由于该应用程序使用计算池,因此会使用您账户中的 Credit 且运行需要支付费用。要阻止应用程序消耗资源,您必须删除应用程序对象及其创建的任何账户级对象,例如计算池。
要确认计算池当前正在运行,请运行以下命令:
snow object list compute-pool -l "na_spcs_tutorial_app_%"
如果计算池正在运行,则会显示一行由应用程序对象创建的
ACTIVE
计算池。运行以下 Snowflake CLI 命令来删除应用程序:
snow app teardown --cascade --force -c tut-connection
此命令将移除应用程序创建的所有 Snowflake 对象。如果没有
--force
选项,此命令不会删除应用程序包,因为它包含多个版本。要确认计算池已删除,请再次运行以下命令:
snow object list compute-pool -l "na_spcs_tutorial_app_%"
如果计算池已成功删除,此命令将返回
no data
。
备注
snow app teardown
命令会删除应用程序包和应用程序对象。因此,任何有状态数据都会丢失。
了解详情¶
恭喜!在本教程中,您学习了如何手动升级使用容器的应用程序。
摘要¶
在本教程中,您完成了以下任务:
添加了版本初始化程序存储过程来处理升级和失败期间的服务。
在应用程序包中创建了应用程序的新版本定义。版本定义指定应用程序的版本号和补丁。
设置应用程序的默认发布指令。发布指令决定使用者安装或升级应用程序时,要安装哪个版本和补丁。
升级了应用程序并验证了升级失败时发生的情况。