すべてのプロダクト
Search
ドキュメントセンター

Resource Orchestration Service:ALIYUN::SAE::Application

最終更新日:Feb 07, 2026

ALIYUN::SAE::Application リソースタイプは、Serverless App Engine (SAE) アプリケーションを作成します。

構文

{
  "Type": "ALIYUN::SAE::Application",
  "Properties": {
    "Timezone": String,
    "AppDescription": String,
    "MountDesc": String,
    "NasId": String,
    "WarStartOptions": String,
    "Liveness": String,
    "Memory": Integer,
    "WebContainer": String,
    "SlsConfigs": String,
    "Cpu": Integer,
    "Deploy": Boolean,
    "PackageVersion": String,
    "AppName": String,
    "Jdk": String,
    "JarStartArgs": String,
    "PreStop": String,
    "Readiness": String,
    "PackageType": String,
    "CommandArgs": String,
    "Envs": String,
    "VSwitchId": String,
    "ImageUrl": String,
    "PostStart": String,
    "JarStartOptions": String,
    "MountHost": String,
    "Replicas": Integer,
    "CustomHostAlias": String,
    "VpcId": String,
    "Tags": List,
    "SecurityGroupId": String,
    "Command": String,
    "EdasContainerVersion": String,
    "PackageUrl": String,
    "NamespaceId": String,
    "AssociateEip": Boolean,
    "AcrInstanceId": String,
    "OssAkId": String,
    "ProgrammingLanguage": String,
    "OssAkSecret": String,
    "Python": String,
    "BaseAppId": String,
    "EnableEbpf": String,
    "PhpArmsConfigLocation": String,
    "PhpConfig": String,
    "MicroRegistrationConfig": String,
    "TerminationGracePeriodSeconds": Integer,
    "ConfigMapMountDesc": String,
    "PvtzDiscoverySvc": String,
    "AcrAssumeRoleArn": String,
    "TomcatConfig": String,
    "AppSource": String,
    "PythonModules": String,
    "NasConfigs": String,
    "MicroRegistration": String,
    "ServiceTags": String,
    "ImagePullSecrets": String,
    "AutoConfig": Boolean,
    "KafkaConfigs": String,
    "Php": String,
    "OssMountDescs": List,
    "PhpConfigLocation": String,
    "SaeVersion": String,
    "NewSaeVersion": String,
    "EnableNewArms": Boolean,
    "EnableSidecarResourceIsolated": Boolean,
    "SidecarContainersConfig": List,
    "InitContainersConfig": List
  }
}

プロパティ

プロパティ名

タイプ

必須

更新可能

説明

制約

AppName

String

はい

いいえ

アプリケーションの名前です。

名前は 1~36 文字である必要があります。先頭は英字である必要があり、英字、数字、ハイフン (-) を使用できます。

Cpu

Integer

はい

いいえ

各インスタンスに必要な CPU。固定仕様のみがサポートされています。

有効値:

  • 500

  • 1000

  • 2000

  • 4000

  • 8000

  • 16000

  • 32000

単位:ミリコア。

Memory

Integer

はい

いいえ

各インスタンスに必要なメモリ。固定仕様のみがサポートされています。

メモリと CPU は 1 対 1 でマッピングされます。以下の組み合わせがサポートされています:

  • 1024:500 ミリコアの CPU を表します。

  • 2048:CPU 値 500 および 1000 ミリコアに対応します。

  • 4096:1000 および 2000 ミリコアの CPU に対応します。

  • 8192:2000 または 4000 ミリコアの CPU 割り当てに対応します。

  • 16384:4000 ミリコアまたは 8000 ミリコアの CPU に対応します。

  • 32768:16,000 ミリコアの CPU を表します。

  • 65536:8,000、16,000、または 32,000 ミリコアの CPU を表します。

  • 131072:32,000 ミリコアの CPU を表します。

単位:MB。

Replicas

Integer

はい

いいえ

インスタンスの初期数です。

なし

PackageType

String

はい

いいえ

アプリケーションのパッケージタイプです。

有効値:

  • FatJar

  • War

  • Image

Timezone

String

いいえ

はい

タイムゾーンです。

デフォルト値:Asia/Shanghai。

AppDescription

String

いいえ

いいえ

アプリケーションの説明です。

説明は 1024 文字以内にする必要があります。

MountDesc

String

いいえ

はい

マウントの説明です。

なし

NasId

String

いいえ

はい

マウントする NAS ファイルシステムの ID です。

NAS ファイルシステムには、利用可能なマウントターゲットのクォータがあるか、またはそのマウントターゲットが VPC の vSwitch にすでに存在している必要があります。このパラメーターを指定せずに MountDesc を指定した場合、SAE は自動的に NAS ファイルシステムを購入し、VPC 内の vSwitch にマウントします。

WarStartOptions

String

いいえ

はい

WAR パッケージの起動オプションです。

デフォルトの起動コマンド:java $JAVA_OPTS $CATALINA_OPTS -Options org.apache.catalina.startup.Bootstrap "$@" start

Liveness

String

いいえ

はい

コンテナーのヘルスチェック。ヘルスチェックに失敗したコンテナーは再起動します。

コンテナー内でのコマンドベースのヘルスチェックのみがサポートされています。例:{"exec":{"command":["sleep","5s"]},"initialDelaySeconds":10,"timeoutSeconds":11}

WebContainer

String

いいえ

はい

デプロイパッケージが依存する Tomcat のバージョンです。

このパラメーターはイメージではサポートされていません。

SlsConfigs

String

いいえ

はい

ファイルログ収集の設定です。

なし

Deploy

Boolean

いいえ

いいえ

すぐにデプロイするかどうか。

有効値:

  • true:すぐにデプロイします。

  • false (デフォルト):すぐにはデプロイしません。

Tags

List

いいえ

はい

タグ。

最大 20 個のタグを指定できます。

詳細については、Tags の構文 および Tags のプロパティ をご参照ください。

PackageVersion

String

いいえ

はい

デプロイパッケージのバージョンです。

PackageType が War または FatJar に設定されている場合、このパラメーターは必須です。

Jdk

String

いいえ

はい

デプロイパッケージが依存する JDK のバージョンです。

このパラメーターはイメージではサポートされていません。

JarStartArgs

String

いいえ

はい

JAR パッケージの起動引数です。

デフォルトの起動コマンド:$JAVA_HOME/bin/java $JarStartOptions -jar $CATALINA_OPTS "$package_path" $JarStartArgs

PreStop

String

いいえ

はい

コンテナーが削除される前に実行するスクリプトです。

コンテナーが削除される前に実行するスクリプトです。例:{"exec":{"command":"cat","/etc/group"}}

Readiness

String

いいえ

はい

アプリケーションの起動ステータスを確認するスクリプトです。

アプリケーションの起動ステータスチェックのスクリプトです。例: {"exec":{"command":["sleep","6s"]},"initialDelaySeconds":15,"timeoutSeconds":12}

Readiness チェックに繰り返し失敗したコンテナーは再起動します。SLB からのトラフィックは、Readiness チェックに失敗したコンテナーには入りません。

CommandArgs

String

いいえ

はい

イメージを起動するためのコマンド引数です。

なし

Envs

String

いいえ

はい

コンテナーの環境変数です。

フォーマット:[{"name":"envtmp","value":"0"}]

  • name:環境変数の名前。

  • value:環境変数の値または参照。

VSwitchId

String

いいえ

いいえ

アプリケーションインスタンスの ENI が存在する vSwitch です。

vSwitch は指定された VPC 内にある必要があります。vSwitch は EDAS 名前空間にバインドされています。このパラメーターを指定しない場合、名前空間にバインドされている vSwitch が使用されます。

ImageUrl

String

いいえ

はい

イメージアドレスです。

Image タイプのアプリケーションのみがこのパラメーターをサポートします。

PostStart

String

いいえ

はい

コンテナーの起動後に実行するスクリプトです。

コンテナーの起動後にスクリプトを実行できます。例:{"exec":{"command":"cat","/etc/group"}}

JarStartOptions

String

いいえ

はい

JAR パッケージの起動オプションです。

デフォルトの起動コマンド:$JAVA_HOME/bin/java $JarStartOptions -jar $CATALINA_OPTS "$package_path" $JarStartArgs

MountHost

String

いいえ

はい

VPC 内の NAS ファイルシステムのマウントターゲットです。

なし

CustomHostAlias

String

いいえ

はい

コンテナー内のカスタムホストマッピングです。

コンテナー内のカスタムホストマッピング。フォーマット:[{"hostName":"samplehost","ip":"127.0.XX.XX"}]

  • hostName:ドメイン名またはホスト名。

  • ip:IP アドレス。

VpcId

String

いいえ

いいえ

SAE 名前空間に対応する VPC です。

SAE では、1 つの名前空間は 1 つの VPC にのみ対応でき、このバインディングは変更できません。名前空間で作成された最初のアプリケーションがバインディングを確立します。複数の名前空間が 1 つの VPC に対応できます。このパラメーターを指定しない場合、名前空間にバインドされている VPC が使用されます。

SecurityGroupId

String

いいえ

いいえ

セキュリティグループ ID です。

なし

Command

String

いいえ

はい

イメージを起動するコマンドです。

コマンドはコンテナー内の実行可能オブジェクトである必要があります。例:sleep。

このコマンドを指定すると、イメージのデフォルトの起動コマンドがオーバーライドされます。

EdasContainerVersion

String

いいえ

はい

EDAS Pandora アプリケーションが使用するランタイム環境です。

なし

PackageUrl

String

いいえ

はい

デプロイパッケージの URL です。

このパラメーターは、PackageType が War または FatJar に設定されている場合にのみ有効です。

NamespaceId

String

はい

いいえ

EDAS 名前空間の ID です。

小文字とハイフン (-) で構成される名前空間のみがサポートされます。名前は小文字で始まる必要があります。

AssociateEip

Boolean

いいえ

いいえ

EIP を関連付けるかどうか。

有効値:

  • true:アタッチします。

  • false:アタッチしません。

AcrInstanceId

String

いいえ

はい

ACR Enterprise インスタンスの ID です。

なし

OssAkId

String

いいえ

いいえ

OSS の読み書き操作のための AccessKey ID です。

なし

ProgrammingLanguage

String

いいえ

いいえ

アプリケーションのプログラミング言語です。

有効値:

  • java:Java

  • php:PHP

  • other:Python、C++、Go、.NET、Node.js などの多言語

OssAkSecret

String

いいえ

いいえ

OSS の読み書き操作のための AccessKey Secret です。

なし

Python

String

いいえ

いいえ

Python 環境です。

Python 3.9.15 がサポートされています。

BaseAppId

String

いいえ

いいえ

ベースアプリケーションの ID です。

なし

EnableEbpf

String

いいえ

いいえ

eBPF 技術に基づいて、非 Java アプリケーションのアプリケーション監視を有効にします。

有効値:

  • true:有効にします。

  • false:無効にします。これがデフォルト値です。

PhpArmsConfigLocation

String

いいえ

いいえ

PHP アプリケーション監視設定のマウントパス。PHP サーバーがこのパスから設定ファイルをロードすることを確認してください。

設定内容を管理する必要はありません。SAE は自動的に正しい設定ファイルをレンダリングします。

PhpConfig

String

いいえ

いいえ

PHP 設定ファイルの内容です。

なし

MicroRegistrationConfig

String

いいえ

いいえ

登録センターの設定です。

なし

TerminationGracePeriodSeconds

Integer

いいえ

いいえ

グレースフルシャットダウンのタイムアウト期間です。

デフォルト値:30。有効値:1~300。単位:秒。

ConfigMapMountDesc

String

いいえ

いいえ

ConfigMap のマウントの説明。

名前空間設定ページで作成された ConfigMap を使用して、設定情報をコンテナーに注入します。パラメーター:

  • configMapId:ConfigMap インスタンス ID。

  • key:キー。

  • mountPath:マウントパス。

説明

sae-sys-configmap-all パラメーターを渡すことで、すべてのキーをマウントできます。

PvtzDiscoverySvc

String

いいえ

いいえ

K8s Service の登録と検出を有効にします。

有効値は次のとおりです:

  • serviceName:サービス名。フォーマット:custom-namespace ID。サフィックス -namespace ID はカスタマイズできず、アプリケーションの名前空間と一致する必要があります。たとえば、中国 (北京) リージョンでデフォルトの名前空間を選択した場合、サフィックスは -cn-beijing-default です。

  • namespaceId:名前空間 ID。

  • portProtocols:ポートとプロトコル。有効なポート範囲:[1,65535]。サポートされているプロトコル:TCP および UDP

  • portAndProtocol:ポートとプロトコル。有効なポート範囲:[1,65535]。サポートされているプロトコル:TCP および UDPportProtocols の使用を推奨します。portProtocols が指定されている場合、portProtocols のみ有効になります。

  • enable:K8s Service の登録と検出を有効にします。

AcrAssumeRoleArn

String

いいえ

いいえ

アカウント間でイメージをプルするために必要な RAM ロールの ARN です。

詳細については、RAM ロールへの権限付与をご参照ください。

TomcatConfig

String

いいえ

いいえ

Tomcat ファイル設定。

このパラメーターを "" または "{}" に設定して、設定を削除します:

  • port:有効なポート範囲:1024~65535。1024 未満のポートには root 権限が必要です。コンテナーは管理者権限で実行されるため、1024 より大きいポートを指定してください。デフォルト値:8080。

  • contextPath:アクセスパス。デフォルト値:ルートディレクトリ "/"。

  • maxThreads:接続プールのサイズ。デフォルト値:400。

  • uriEncoding:Tomcat のエンコード形式。有効値:UTF-8ISO-8859-1GBKGB2312。デフォルト値:ISO-8859-1

  • useBodyEncodingForUriURL に BodyEncoding を使用するかどうかを指定します。デフォルト値:true

AppSource

String

いいえ

いいえ

マイクロサービスアプリケーション。

有効値:

  • micro_service

PythonModules

String

いいえ

いいえ

カスタムモジュール依存関係。

デフォルトでは、ルートディレクトリの requirements.txt で定義された依存関係がインストールされます。設定やカスタムパッケージが指定されていない場合、インストールする依存関係を指定できます。

NasConfigs

String

いいえ

いいえ

NAS のマウント設定です。

有効値は次のとおりです:

  • mountPath:コンテナーのマウントパス。

  • readOnly:マウントに読み書き権限があるかどうかを指定します。読み書き権限の場合は false に設定します。

  • nasId:NAS ID。

  • mountDomain:コンテナーのマウントターゲットアドレス。詳細については、DescribeMountTargets をご参照ください。

  • nasPath:NAS 内の相対ファイルディレクトリ。

MicroRegistration

String

いいえ

いいえ

Nacos レジストリを選択します。

有効値:

  • 0:SAE に組み込まれた Nacos。

  • 1:自己管理の Nacos。

  • 2:MSE 商用 Nacos。

ServiceTags

String

いいえ

いいえ

アプリケーションに設定されたグレースケールタグです。

なし

ImagePullSecrets

String

いいえ

いいえ

シークレットの ID です。

なし

AutoConfig

Boolean

いいえ

いいえ

ネットワーク環境を自動的に設定するかどうか。

有効値:

  • true:SAE はアプリケーション作成時にネットワーク環境を自動的に設定します。NamespaceIdVpcIdvSwitchIdSecurityGroupId の値は無視されます。

  • false:アプリケーション作成時にネットワーク環境を手動で設定します。

説明

このパラメーターを true に設定すると、NamespaceId の他の値は無視されます。

KafkaConfigs

String

いいえ

いいえ

Kafka へのログ収集のための集約設定です。

値は次のとおりです:

  • kafkaEndpoint:Kafka API のサービスエンドポイント。

  • kafkaInstanceId:Kafka インスタンス ID。

  • kafkaConfigs:1 つ以上のログの集約設定。詳細については、このトピックのリクエストパラメーター KafkaConfigs をご参照ください。

Php

String

いいえ

いいえ

PHP デプロイパッケージが依存する PHP のバージョンです。

なし。

OssMountDescs

List

いいえ

いいえ

OSS マウントの説明です。

パラメーター:

  • bucketName:バケット名。

  • bucketPath:OSS で作成したディレクトリまたは OSS オブジェクト。OSS マウントディレクトリが存在しない場合、例外が発生します。

  • mountPath:SAE のコンテナーパス。パスが存在する場合は上書きされます。パスが存在しない場合は作成されます。

  • readOnly:コンテナーパスがマウントされたディレクトリに対して読み取り権限を持つかどうかを指定します。有効値:

    • true:読み取り専用権限。

    • false:読み書き権限。

PhpConfigLocation

String

いいえ

いいえ

PHP アプリケーション起動設定のマウントパスです。

PHP サーバーがこの設定ファイルを使用して起動することを確認してください。

SaeVersion

String

いいえ

いいえ

SAE のバージョンです。

サポートされているバージョン:

  • v1

  • v2

NewSaeVersion

String

いいえ

いいえ

新しい SAE のバージョンです。

有効値:

  • lite

  • std

  • pro

EnableNewArms

Boolean

いいえ

いいえ

新しい ARMS 機能を有効にするかどうか。

有効値:

  • true:有効

  • false:無効

EnableSidecarResourceIsolated

Boolean

いいえ

はい

サイドカーリソースの隔離を有効にするかどうか。

有効値:

  • true:隔離を実行します。

  • false:リソースを隔離しません。

SidecarContainersConfig

List

いいえ

はい

コンテナー設定のリストです。

詳細については、SidecarContainersConfig のプロパティをご参照ください。

InitContainersConfig

List

いいえ

はい

init コンテナー設定のリストです。

詳細については、InitContainersConfig のプロパティをご参照ください。

SidecarContainersConfig の構文

"SidecarContainersConfig": [
  {
    "CommandArgs": String,
    "AcrInstanceId": String,
    "Memory": Integer,
    "Name": String,
    "EmptyDirDesc": String,
    "Command": String,
    "ImageUrl": String,
    "Cpu": Integer,
    "Envs": String,
    "ConfigMapMountDesc": String
  }
]  

SidecarContainersConfig のプロパティ

プロパティ名

タイプ

必須

更新可能

説明

制約

CommandArgs

String

いいえ

はい

init コンテナーで実行するコマンド引数です。

なし

AcrInstanceId

String

いいえ

はい

ACR インスタンスの ID です。

なし

Memory

Integer

はい

はい

サイドカーコンテナーに割り当てられるメモリ量です。

なし

Name

String

はい

はい

サイドカーコンテナーの名前です。

なし

EmptyDirDesc

String

いいえ

はい

EMPTYDIR マウントの説明です。

なし

Command

String

いいえ

はい

init コンテナーで実行するコマンドです。

なし

ImageUrl

String

いいえ

はい

イメージアドレスです。

イメージベースのアプリケーションに対してのみレジストリアドレスを設定できます。

Cpu

Integer

はい

はい

サイドカーコンテナーに割り当てられる CPU コア数です。

なし

Envs

String

いいえ

はい

コンテナーの環境変数です。

例:

[{ \"name\": \"envtmp\", \"value\": \"0\"}]

ConfigMapMountDesc

String

いいえ

はい

ConfigMap マウントの説明です。

なし

InitContainersConfig の構文

"InitContainersConfig": [
  {
    "Command": String,
    "ConfigMapMountDesc": String,
    "ImageUrl": String,
    "CommandArgs": String,
    "Envs": String,
    "Name": String
  }
]  

InitContainersConfig のプロパティ

プロパティ名

タイプ

必須

更新可能

説明

制約

Command

String

いいえ

はい

init コンテナーで実行するコマンドです。

なし

ConfigMapMountDesc

String

いいえ

いいえ

ConfigMap マウントの説明です。

なし

ImageUrl

String

いいえ

はい

イメージアドレスです。

Image タイプのアプリケーションのみがこのパラメーターをサポートします。

CommandArgs

String

いいえ

はい

init コンテナーで実行するコマンド引数です。

なし

Envs

String

いいえ

はい

コンテナーの環境変数です。

例:

[{ \"name\": \"envtmp\", \"value\": \"0\"}]

Name

String

はい

はい

init コンテナーの名前です。

なし

Tags の構文

"Tags": [
  {
    "Key": String,
    "Value": String
  }
]  

Tags のプロパティ

プロパティ名

タイプ

必須

更新可能

説明

制約

Key

String

はい

いいえ

タグキーです。

キーは 1~128 文字である必要があります。aliyun または acs: で始めることはできず、http:// または https:// を含めることはできません。

Value

String

いいえ

いいえ

タグ値です。

値は 0~128 文字である必要があります。aliyun または acs: で始めることはできず、http:// または https:// を含めることはできません。

戻り値

Fn::GetAtt

  • AppId:アプリケーション ID。

  • ChangeOrderId:リリースオーダー ID。タスクの実行ステータスを照会するために使用されます。

シナリオ 1:SAE アプリケーションの作成

クイック作成

ROSTemplateFormatVersion: '2015-09-01'
Parameters:
  NamespaceId:
    Type: String
    Description: |-
      ID に対応する EDAS 名前空間。
      名前空間名は小文字で始まる必要があります。名前空間は DescribeNamespaceList インターフェイスから取得できます。
  VpcId:
    Type: String
    AssociationProperty: ALIYUN::ECS::VPC::VPCId
  VSwitchId:
    Type: String
    AssociationProperty: ALIYUN::ECS::VSwitch::VSwitchId
    AssociationPropertyMetadata:
      VpcId: ${VpcId}
  SecurityGroupId:
    Type: String
    AssociationProperty: ALIYUN::ECS::SecurityGroup::SecurityGroupId
    AssociationPropertyMetadata:
      VpcId: ${VpcId}
Resources:
  Application:
    Type: ALIYUN::SAE::Application
    Properties:
      AppName: TestApp
      NamespaceId:
        Ref: NamespaceId
      VpcId:
        Ref: VpcId
      VSwitchId:
        Ref: VSwitchId
      SecurityGroupId:
        Ref: SecurityGroupId
      Cpu: 500
      Memory: 1024
      Replicas: 2
      PackageType: War
      Deploy: true
      Timezone: Asia/Shanghai
Outputs: {}
{
  "ROSTemplateFormatVersion": "2015-09-01",
  "Parameters": {
    "NamespaceId": {
      "Type": "String",
      "Description": "EDAS 名前空間に対応する ID。カナダでは、先頭が英字で始まる小文字の名前空間名のみがサポートされます。\n名前空間は、DescribeNamespaceList インターフェイスを介して取得できます。"
    },
    "VpcId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::VPC::VPCId"
    },
    "VSwitchId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::VSwitch::VSwitchId",
      "AssociationPropertyMetadata": {
        "VpcId": "${VpcId}"
      }
    },
    "SecurityGroupId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::SecurityGroup::SecurityGroupId",
      "AssociationPropertyMetadata": {
        "VpcId": "${VpcId}"
      }
    }
  },
  "Resources": {
    "Application": {
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "TestApp",
        "NamespaceId": {
          "Ref": "NamespaceId"
        },
        "VpcId": {
          "Ref": "VpcId"
        },
        "VSwitchId": {
          "Ref": "VSwitchId"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroupId"
        },
        "Cpu": 500,
        "Memory": 1024,
        "Replicas": 2,
        "PackageType": "War",
        "Deploy": true,
        "Timezone": "Asia/Shanghai"
      }
    }
  },
  "Outputs": {
  }
}

シナリオ 2:SAE アプリケーション、名前空間、SLB バインディングの作成

クイック作成

ROSTemplateFormatVersion: '2015-09-01'
Description:
  zh-cn: SAE アプリケーション、名前空間、SLB バインディングを作成し、負荷分散を使用して ECS リソースを設定し、コンテナー化されたアプリケーションのデプロイを自動化します。
  en: SAE アプリケーション、名前空間、SLB バインディングを作成し、負荷分散を使用して ECS リソースを設定し、コンテナー化されたアプリケーションのデプロイを自動化します。
Parameters:
  ZoneId:
    Type: String
    AssociationProperty: ALIYUN::ECS::Instance:ZoneId
  VpcId:
    Type: String
    AssociationProperty: ALIYUN::ECS::VPC::VPCId
  VSwitchId:
    Type: String
    AssociationProperty: ALIYUN::ECS::VSwitch::VSwitchId
    AssociationPropertyMetadata:
      VpcId: VpcId
      ZoneId: ZoneId
  SecurityGroupId:
    Type: String
    AssociationProperty: ALIYUN::ECS::SecurityGroup::SecurityGroupId
    AssociationPropertyMetadata:
      VpcId: VpcId
  NamespaceName:
    Type: String
    Description: 名前空間名
    Default: mytest
  NamespaceId:
    Type: String
    Description: 名前空間 ID
    Default: mytest
  Description:
    Type: String
    Description: 名前空間の説明
    Default: null
  AppName:
    Type: String
    Description: アプリケーション名
    Default: test
  LoadBalancerSpec:
    Type: String
    Description: SLB インスタンスの仕様
    Default: slb.s2.medium
Resources:
  LoadBalancer:
    Type: ALIYUN::SLB::LoadBalancer
    Properties:
      MasterZoneId:
        Ref: ZoneId
      LoadBalancerSpec:
        Ref: LoadBalancerSpec
  Namespace:
    Type: ALIYUN::SAE::Namespace
    Properties:
      NamespaceName:
        Ref: NamespaceName
      NamespaceId:
        Fn::Sub: ${ALIYUN::Region}:${NamespaceId}
      NamespaceDescription:
        Ref: Description
    DependsOn: LoadBalancer
  SaeApp:
    Type: ALIYUN::SAE::Application
    Properties:
      VpcId:
        Ref: VpcId
      VSwitchId:
        Ref: VSwitchId
      SecurityGroupId:
        Ref: SecurityGroupId
      AppName:
        Ref: AppName
      NamespaceId:
        Fn::GetAtt:
        - Namespace
        - NamespaceId
      Cpu: 500
      Memory: 1024
      Replicas: 2
      Deploy: true
      Timezone: Asia/Shanghai
      SaeVersion: v2
      AutoConfig: false

      PackageType: Image
      Jdk: Dragonwell 21
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:web-springboot-hellosae-v1.0
      ProgrammingLanguage: java
      AppSource: micro_service
    DependsOn:
    - Namespace
  BindSlb:
    Type: ALIYUN::SAE::SlbBinding
    Properties:
      AppId:
        Ref: SaeApp
      Intranet: '[{"port": 80, "targetPort": 8080, "protocol": "TCP"}]'
      InternetSlbId:
        Ref: LoadBalancer
    DependsOn:
    - LoadBalancer
    - SaeApp
Outputs:
  AppId:
    Value:
      Fn::GetAtt:
      - SaeApp
      - AppId
  ChangeOrderId:
    Value:
      Fn::GetAtt:
      - SaeApp
      - ChangeOrderId
  NamespaceId:
    Value:
      Fn::GetAtt:
      - Namespace
      - NamespaceId
{
  "ROSTemplateFormatVersion": "2015-09-01",
  "Description": {
    "zh-cn": "SAE アプリケーション、名前空間、SLB バインディングを作成し、負荷分散を使用して ECS リソースを設定し、コンテナー化されたアプリケーションのデプロイを自動化します。",
    "en": "SAE アプリケーション、名前空間、SLB バインディングを作成し、負荷分散を使用して ECS リソースを設定し、コンテナー化されたアプリケーションのデプロイを自動化します。"
  },
  "Parameters": {
    "ZoneId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::Instance:ZoneId"
    },
    "VpcId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::VPC::VPCId"
    },
    "VSwitchId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::VSwitch::VSwitchId",
      "AssociationPropertyMetadata": {
        "VpcId": "VpcId",
        "ZoneId": "ZoneId"
      }
    },
    "SecurityGroupId": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::SecurityGroup::SecurityGroupId",
      "AssociationPropertyMetadata": {
        "VpcId": "VpcId"
      }
    },
    "NamespaceName": {
      "Type": "String",
      "Description": "名前空間名",
      "Default": "mytest"
    },
    "NamespaceId": {
      "Type": "String",
      "Description": "名前空間 ID",
      "Default": "mytest"
    },
    "Description": {
      "Type": "String",
      "Description": "名前空間の説明",
      "Default": null
    },
    "AppName": {
      "Type": "String",
      "Description": "アプリケーション名",
      "Default": "test"
    },
    "LoadBalancerSpec": {
      "Type": "String",
      "Description": "SLB インスタンスの仕様",
      "Default": "slb.s2.medium"
    }
  },
  "Resources": {
    "LoadBalancer": {
      "Type": "ALIYUN::SLB::LoadBalancer",
      "Properties": {
        "MasterZoneId": {
          "Ref": "ZoneId"
        },
        "LoadBalancerSpec": {
          "Ref": "LoadBalancerSpec"
        }
      }
    },
    "Namespace": {
      "Type": "ALIYUN::SAE::Namespace",
      "Properties": {
        "NamespaceName": {
          "Ref": "NamespaceName"
        },
        "NamespaceId": {
          "Fn::Sub": "${ALIYUN::Region}:${NamespaceId}"
        },
        "NamespaceDescription": {
          "Ref": "Description"
        }
      },
      "DependsOn": "LoadBalancer"
    },
    "SaeApp": {
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "VpcId": {
          "Ref": "VpcId"
        },
        "VSwitchId": {
          "Ref": "VSwitchId"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroupId"
        },
        "AppName": {
          "Ref": "AppName"
        },
        "NamespaceId": {
          "Fn::GetAtt": [
            "Namespace",
            "NamespaceId"
          ]
        },
        "Cpu": 500,
        "Memory": 1024,
        "Replicas": 2,
        "Deploy": true,
        "Timezone": "Asia/Shanghai",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "PackageType": "Image",
        "Jdk": "Dragonwell 21",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:web-springboot-hellosae-v1.0"
        },
        "ProgrammingLanguage": "java",
        "AppSource": "micro_service"
      },
      "DependsOn": [
        "Namespace"
      ]
    },
    "BindSlb": {
      "Type": "ALIYUN::SAE::SlbBinding",
      "Properties": {
        "AppId": {
          "Ref": "SaeApp"
        },
        "Intranet": "[{\"port\": 80, \"targetPort\": 8080, \"protocol\": \"TCP\"}]",
        "InternetSlbId": {
          "Ref": "LoadBalancer"
        }
      },
      "DependsOn": [
        "LoadBalancer",
        "SaeApp"
      ]
    }
  },
  "Outputs": {
    "AppId": {
      "Value": {
        "Fn::GetAtt": [
          "SaeApp",
          "AppId"
        ]
      }
    },
    "ChangeOrderId": {
      "Value": {
        "Fn::GetAtt": [
          "SaeApp",
          "ChangeOrderId"
        ]
      }
    },
    "NamespaceId": {
      "Value": {
        "Fn::GetAtt": [
          "Namespace",
          "NamespaceId"
        ]
      }
    }
  }
}

シナリオ 3:Serverless App Engine を介した本番環境 Dify プラットフォームのデプロイ

クイック作成

ROSTemplateFormatVersion: '2015-09-01'
Description:
  zh-cn: Serverless App Engine を介して本番環境の Dify プラットフォームをデプロイします。
  en: Serverless App Engine (SAE) を使用して、本番環境に対応した Dify プラットフォームをデプロイします。
Parameters:
  CommonName:
    Type: String
    Default: Dify
  NamespaceName:
    Type: String
    Label:
      en: 名前空間名
      zh-cn: 名前空間名
    Description:
      zh-cn: 名前空間名。小文字と数字のみがサポートされます。
      en: 名前空間名。小文字と数字のみがサポートされます。
    AllowedPattern: '^[a-z0-9]+$'
    AssociationProperty: AutoCompleteInput
    AssociationPropertyMetadata:
      Length: 3
      Prefix: dify
      CharacterClasses:
        - Class: lowercase
          min: 2
        - Class: "number"
          min: 1
  ZoneId1:
    Type: String
    AssociationProperty: 'ALIYUN::ECS::Instance::ZoneId'
    AssociationPropertyMetadata:
      ExclusiveTo:
        - ZoneId2
    Label:
      en: アベイラビリティーゾーン 1
      zh-cn: アベイラビリティーゾーン 1
  ZoneId2:
    Type: String
    AssociationProperty: 'ALIYUN::ECS::Instance::ZoneId'
    AssociationPropertyMetadata:
      ExclusiveTo:
        - ZoneId1
    Label:
      en: アベイラビリティーゾーン 2
      zh-cn: アベイラビリティーゾーン 2
  InstanceType:
    Type: String
    AssociationProperty: 'ALIYUN::ECS::Instance::InstanceType'
    AssociationPropertyMetadata:
      InstanceChargeType: PostPaid
      SystemDiskCategory: cloud_essd
      ZoneId: ${ZoneId1}
    Label:
      en: インスタンスタイプ
      zh-cn: インスタンスタイプ
  ADBPGAccount:
    Default: dify
    Type: String
    Label:
      zh-cn: データベースアカウント
      en: データベースアカウント
  ADBPGPassword:
    NoEcho: true
    Type: String
    Label:
      zh-cn: データベースアカウントのパスワード
      en: データベースアカウントのパスワード
    AssociationProperty: ALIYUN::RDS::Instance::AccountPassword
  InstancePassword:
    Type: String
    Label:
      en: インスタンスのログインパスワード
      zh-cn: ログインパスワード
    Description:
      en: インスタンスのログインパスワードです。パスワードは 8~30 文字で、大文字、小文字、数字、特殊文字 ()`~!@#$%^&*_-+=|{}[]:;'<>,.?/ のうち少なくとも 3 種類を含める必要があります。
      zh-cn: サーバーのログインパスワード。長さ:8~30 文字。大文字、小文字、数字、特殊文字 ()`~!@#$%^&*_-+=|{}[]:;'<>,.?/ のうち少なくとも 3 種類を含める必要があります。
    AssociationProperty: ALIYUN::ECS::Instance::Password
  RedisInstancePassword:
    Type: String
    Label:
      en: Redis インスタンスのパスワード
      zh-cn: インスタンスのパスワード
    Description:
      en: Dify が使用する Redis インスタンスのパスワードです。パスワードは 8~32 文字で、大文字、小文字、数字のみを含める必要があります。
      zh-cn: Dify が使用する Redis のパスワードは 8~32 文字の長さで、大文字、小文字、数字のみを含める必要があります。他の文字は使用しないでください。
    ConstraintDescription:
      en: Dify が使用する Redis インスタンスのパスワードです。パスワードは 8~32 文字で、大文字、小文字、数字のみを含める必要があります。
      zh-cn: Dify が使用する Redis のパスワードは 8~32 文字の長さで、大文字、小文字、数字のみを含める必要があります。他の文字は使用しないでください。
    AllowedPattern: ^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?\d)[A-Za-z0-9]{8,32}$
    MinLength: '8'
    MaxLength: '32'
    NoEcho: true
  DBInstanceClass:
    Type: String
    Label:
      en: インスタンスタイプ
      zh-cn: インスタンスタイプ
    Default: pg.n4m.2c.2m
    Required: true
    AssociationProperty: ALIYUN::RDS::Instance::InstanceType
    AssociationPropertyMetadata:
      ZoneId: ${ZoneId}
      EngineVersion: '17.0'
      Engine: PostgreSQL
      Category: HighAvailability
      InstanceChargeType: Postpaid
      DBInstanceStorageType: cloud_essd
      CommodityCode: bards
  PostgresSQLPassword:
    Type: String
    NoEcho: true
    Label:
      en: データベースアカウントのパスワード
      zh-cn: データベースアカウントのパスワード
    AssociationProperty: ALIYUN::RDS::Instance::AccountPassword
  PostgresSQLUserName:
    Type: String
    Label:
      en: データベースアカウント
      zh-cn: データベースアカウント
    # This rule applies to MySQL 5.7 and 8.0
    AllowedPattern: ^(?!dbo\b|login\b|admin\b|administrator\b|adminsys\b|alimail\b|aliyun\b|apache\b|appadmin\b|apsara\b|aurora\b|bulkadmin\b|cangjie\b|cdn\b|client\b|cm\b|dataengine\b|dayu\b|dba\b|dbcreator\b|developer\b|diskadmin\b|distribution\b|dns\b|download\b|eagleye\b|f5\b|faq\b|fuxi\b|galaxy\b|gongcao\b|gongming\b|groupon\b|ha\b|help\b|host\b|hostmaster\b|houyi\b|hr\b|info\b|information_schema\b|kuafu\b|lvs\b|manager\b|master\b|meituan\b|model\b|monitor\b|msdb\b|mssqld\b|mssqlsystemresource\b|mysql\b|nas\b|net\b|netops\b|netweb\b|news\b|no-reply\b|ntp\b|nuwa\b|nvwa\b|operator\b|opr\b|ops\b|opsdb\b|oracle\b|pangu\b|pe\b|post\b|postmaster\b|processadmin\b|public\b|qq\b|replicator\b|reply\b|root\b|sa\b|sales\b|san\b|security\b|securityadmin\b|serveradmin\b|services\b|setupadmin\b|shennong\b|siteops\b|sqlengine\b|sqlonline\b|squid\b|ssladmin\b|support\b|sys\b|sysadmin\b|syslog\b|system\b|taoyun\b|tempdb\b|test\b|tianyun\b|wangwang\b|eb\b|webmaster\b|webnet\b|xtrabak\b|youchao\b|yum\b|yunti\b|zhongkui\b|database\b|add\b|except\b|percent\b|all\b|exec\b|plan\b|alter\b|execute\b|precision\b|and\b|exists\b|primary\b|any\b|exit\b|print\b|as\b|fetch\b|proc\b|asc\b|file\b|procedure\b|authorization\b|fillfactor\b|public\b|backup\b|for\b|raiserror\b|begin\b|foreign\b|read\b|between\b|freetext\b|readtext\b|break\b|freetexttable\b|reconfigure\b|browse\b|from\b|references\b|bulk\b|full\b|replication\b|by\b|function\b|restore\b|cascade\b|goto\b|restrict\b|case\b|grant\b|return\b|check\b|group\b|revoke\b|checkpoint\b|having\b|right\b|close\b|holdlock\b|rollback\b|clustered\b|identity\b|rowcount\b|coalesce\b|identity_insert\b|rowguidcol\b|collate\b|identitycol\b|rule\b|column\b|if\b|save\b|commit\b|in\b|schema\b|compute\b|index\b|select\b|constraint\b|inner\b|session_user\b|contains\b|insert\b|set\b|containstable\b|intersect\b|setuser\b|continue\b|into\b|shutdown\b|convert\b|is\b|some\b|create\b|join\b|statistics\b|cross\b|key\b|system_user\b|current\b|kill\b|table\b|current_date\b|left\b|textsize\b|current_time\b|like\b|then\b|current_timestamp\b|lineno\b|to\b|current_user\b|load\b|top\b|cursor\b|national\b|tran\b|database\b|nocheck\b|transaction\b|dbcc\b|nonclustered\b|trigger\b|deallocate\b|not\b|truncate\b|declare\b|null\b|tsequal\b|default\b|nullif\b|union\b|delete\b|of\b|unique\b|deny\b|off\b|update\b|desc\b|offsets\b|updatetext\b|disk\b|on\b|use\b|distinct\b|open\b|user\b|distributed\b|opendatasource\b|values\b|double\b|openquery\b|varying\b|drop\b|openrowset\b|view\b|dummy\b|openxml\b|waitfor\b|dump\b|option\b|when\b|else\b|or\b|where\b|end\b|order\b|while\b|errlvl\b|outer\b|with\b|escape\b|over\b|writetext\b|add\b|analyze\b|asc\b|between\b|blob\b|call\b|change\b|check\b|condition\b|continue\b|cross\b|current_timestamp\b|database\b|day_microsecond\b|dec\b|default\b|desc\b|distinct\b|double\b|each\b|enclosed\b|exit\b|fetch\b|float8\b|foreign\b|goto\b|having\b|hour_minute\b|ignore\b|infile\b|insensitive\b|int1\b|int4\b|interval\b|iterate\b|keys\b|leading\b|like\b|lines\b|localtimestamp\b|longblob\b|low_priority\b|mediumint\b|minute_microsecond\b|modifies\b|no_write_to_binlog\b|on\b|optionally\b|out\b|precision\b|purge\b|read\b|references\b|rename\b|require\b|revoke\b|schema\b|select\b|set\b|spatial\b|sqlexception\b|sql_big_result\b|ssl\b|table\b|tinyblob\b|to\b|true\b|unique\b|update\b|using\b|utc_timestamp\b|varchar\b|when\b|with\b|xor\b|all\b|and\b|asensitive\b|bigint\b|both\b|cascade\b|char\b|collate\b|connection\b|convert\b|current_date\b|current_user\b|databases\b|day_minute\b|decimal\b|delayed\b|describe\b|distinctrow\b|drop\b|else\b|escaped\b|explain\b|float\b|for\b|from\b|grant\b|high_priority\b|hour_second\b|in\b|inner\b|insert\b|int2\b|int8\b|into\b|join\b|kill\b|leave\b|limit\b|load\b|lock\b|longtext\b|match\b|mediumtext\b|minute_second\b|natural\b|null\b|optimize\b|or\b|outer\b|primary\b|raid0\b|reads\b|regexp\b|repeat\b|restrict\b|right\b|schemas\b|sensitive\b|show\b|specific\b|sqlstate\b|sql_calc_found_rows\b|starting\b|terminated\b|tinyint\b|trailing\b|undo\b|unlock\b|usage\b|utc_date\b|values\b|varcharacter\b|where\b|write\b|year_month\b|alter\b|as\b|before\b|binary\b|by\b|case\b|character\b|column\b|constraint\b|create\b|current_time\b|cursor\b|day_hour\b|day_second\b|declare\b|delete\b|deterministic\b|div\b|dual\b|elseif\b|exists\b|false\b|float4\b|force\b|fulltext\b|group\b|hour_microsecond\b|if\b|index\b|inout\b|int\b|int3\b|integer\b|is\b|key\b|label\b|left\b|linear\b|localtime\b|long\b|loop\b|mediumblob\b|middleint\b|mod\b|not\b|numeric\b|option\b|order\b|outfile\b|procedure\b|range\b|real\b|release\b|replace\b|return\b|rlike\b|second_microsecond\b|separator\b|smallint\b|sql\b|sqlwarning\b|sql_small_result\b|straight_join\b|then\b|tinytext\b|trigger\b|union\b|unsigned\b|use\b|utc_time\b|varbinary\b|varying\b|while\b|x509\b|zerofill)([a-zA-Z][a-zA-Z0-9_]{0,30}[a-zA-Z0-9])$
    ConstraintDescription:
      en: アカウント名には、英字、数字、アンダースコア (_) を含めることができます。先頭は英字、末尾は英字または数字である必要があります。名前の長さは最大 32 文字です。詳細については、<a href="https://www.alibabacloud.com/help/en/rds/developer-reference/forbidden-keywords" target="_blank">禁止キーワード</a>をご参照ください。
      zh-cn: 値には、小文字、大文字、数字、アンダースコア (_) を含めることができます。先頭は英字、末尾は英字または数字である必要があります。最大長は 32 文字です。無効な文字の詳細については、<a href="https://www.alibabacloud.com/help/zh/rds/developer-reference/forbidden-keywords" target="_blank">禁止キーワード表</a>をご参照ください。
    Default: db_user
Resources:
  Vpc:
    Type: 'ALIYUN::ECS::VPC'
    Properties:
      CidrBlock: 192.168.0.0/16
      VpcName:
        Fn::Sub: ${CommonName}-VPC_HZ
  VSwitch1:
    Type: 'ALIYUN::ECS::VSwitch'
    Properties:
      VpcId:
        Ref: Vpc
      CidrBlock: 192.168.1.0/24
      ZoneId:
        Ref: ZoneId1
      VSwitchName:
        Fn::Sub: ${CommonName}-vsw_001
  VSwitch2:
    Type: 'ALIYUN::ECS::VSwitch'
    Properties:
      VpcId:
        Ref: Vpc
      CidrBlock: 192.168.2.0/24
      ZoneId:
        Ref: ZoneId2
      VSwitchName:
        Fn::Sub: ${CommonName}-vsw_002
  Sleep:
    DependsOn:
      - VSwitch1
      - VSwitch2
    Type: ALIYUN::ROS::Sleep
    Properties:
      DeleteDuration: 300
  SecurityGroup:
    Type: 'ALIYUN::ECS::SecurityGroup'
    Properties:
      VpcId:
        Ref: Vpc
      SecurityGroupName:
        Fn::Sub: ${CommonName}-SecurityGroup_1
      SecurityGroupIngress:
        - PortRange: 80/80
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
        - PortRange: 3000/3000
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
        - PortRange: 5001/5001
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
        - PortRange: 5002/5002
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
        - PortRange: 5003/5003
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
        - PortRange: 8080/8080
          Priority: 1
          SourceCidrIp: 0.0.0.0/0
          IpProtocol: tcp
  EcsInstance:
    Type: 'ALIYUN::ECS::InstanceGroup'
    Properties:
      VpcId:
        Ref: Vpc
      ZoneId:
        Ref: ZoneId1
      VSwitchId:
        Ref: VSwitch1
      SecurityGroupId:
        Ref: SecurityGroup
      ImageId: aliyun_3_x64_20G_alibase_
      InstanceName:
        Fn::Sub: ${CommonName}-ecs
      InstanceType:
        Ref: InstanceType
      SystemDiskCategory: cloud_essd
      MaxAmount: 1
      SystemDiskSize: 40
      InternetMaxBandwidthOut: 5
      Password:
        Ref: InstancePassword
  RunCommand:
    Type: ALIYUN::ECS::RunCommand
    Properties:
      CommandContent:
        Fn::Sub:
          |
          #!/bin/sh
          echo "sk-$(openssl rand -hex 16)"
      Type: RunShellScript
      InstanceIds:
        - Ref: EcsInstance
  RunCommand2:
    DependsOn:
      - RunCommand
    Type: ALIYUN::ECS::RunCommand
    Properties:
      CommandContent:
        Fn::Sub:
          |
          #!/bin/sh
          export ROS_DEPLOY=true
          curl -fsSL https://help-static-aliyun-doc.aliyuncs.com/install-script/dify/sae/install.sh | bash
      Type: RunShellScript
      InstanceIds:
        - Ref: EcsInstance
  RedisInstance:
    Type: ALIYUN::REDIS::Instance
    Properties:
      ZoneId:
        Ref: ZoneId1
      SecondaryZoneId:
        Ref: ZoneId2
      VpcId:
        Ref: Vpc
      VSwitchId:
        Ref: VSwitch1
      InstanceClass: redis.shard.large.y.ee
      EvictionPolicy: noeviction
      InstanceName:
        Fn::Sub: ${CommonName}-Redis
      EngineVersion: '7.0'
      Password:
        Ref: RedisInstancePassword
  REDISWhitelist:
    Type: ALIYUN::REDIS::Whitelist
    Properties:
      InstanceId:
        Ref: RedisInstance
      SecurityIps: 192.168.0.0/16
  ADBPGInstance:
    Type: ALIYUN::GPDB::DBInstance
    Properties:
      EngineVersion: '7.0'
      VectorConfigurationStatus: True
      InstanceSpec: 4C32G
      ZoneId:
        Ref: ZoneId1
      VSwitchId:
        Ref: VSwitch1
      SegNodeNum: 4
      SegStorageType: cloud_essd
      SegDiskPerformanceLevel: pl1
      StorageSize: 50
      VPCId:
        Ref: Vpc
      SecurityIPList: 192.168.0.0/16
      DBInstanceDescription:
        Fn::Sub: ${CommonName}
      PayType: Postpaid
      DBInstanceCategory: HighAvailability
      DBInstanceMode: StorageElastic
      ProdType: standard
  GPDBAccount:
    Type: ALIYUN::GPDB::Account
    Properties:
      DBInstanceId:
        Fn::GetAtt:
          - ADBPGInstance
          - DBInstanceId
      AccountPassword:
        Ref: ADBPGPassword
      AccountName:
        Ref: ADBPGAccount
  SaeNamespace:
    DependsOn:
      - PostgreSQLInstance
      - RedisInstance
      - ADBPGInstance
      - PluginNas
      - APINas
    Type: ALIYUN::SAE::Namespace
    Properties:
      NamespaceName:
        Ref: NamespaceName
      NamespaceId:
        Fn::Sub: ${ALIYUN::Region}:${NamespaceName}
      VpcId:
        Ref: Vpc
  PostgreSQLInstance:
    Type: ALIYUN::RDS::DBInstance
    Properties:
      ZoneId:
        Ref: ZoneId1
      SlaveZoneIds:
        - Ref: ZoneId2
      VpcId:
        Ref: Vpc
      VSwitchId:
        Ref: VSwitch1
      DBInstanceClass:
        Ref: DBInstanceClass
      DBInstanceStorage: 50
      Engine: PostgreSQL
      EngineVersion: '17.0'
      SecurityIPList: 192.168.0.0/16
      Category: HighAvailability
      MasterUserType: Super
      MasterUserPassword:
        Ref: PostgresSQLPassword
      MasterUsername:
        Ref: PostgresSQLUserName
      DBInstanceStorageType: cloud_essd
  DifyDataBase:
    Type: ALIYUN::RDS::Database
    Properties:
      CharacterSetName: utf8
      DBInstanceId:
        Fn::GetAtt:
          - PostgreSQLInstance
          - DBInstanceId
      DBName: dify
  DifySetUpDataBase:
    Type: ALIYUN::RDS::Database
    DependsOn: DifyDataBase
    Properties:
      CharacterSetName: UTF8
      DBInstanceId:
        Fn::GetAtt:
          - PostgreSQLInstance
          - DBInstanceId
      DBName: dify_setups
  RdsAccountPrivilege:
    Type: ALIYUN::RDS::AccountPrivilege
    DependsOn: DifySetUpDataBase
    Properties:
      AccountPrivilege: DBOwner
      DBInstanceId:
        Ref: PostgreSQLInstance
      DBName: dify
      AccountName:
        Ref: PostgresSQLUserName
  NatGateway:
    Type: ALIYUN::VPC::NatGateway
    Properties:
      VpcId:
        Ref: Vpc
      VSwitchId:
        Ref: VSwitch1
      NatGatewayName:
        Fn::Sub: ${CommonName}-nat
      InternetChargeType: PayByLcu
      EipBindMode: NAT
  Eip:
    Type: 'ALIYUN::VPC::EIP'
    Properties:
      DeletionProtection: false
      Isp: BGP
      Bandwidth: 200
      InternetChargeType: PayByTraffic
  EipAssociation:
    Type: 'ALIYUN::VPC::EIPAssociation'
    Properties:
      InstanceId:
        Ref: NatGateway
      AllocationId:
        Ref: Eip
  SNat:
    Type: 'ALIYUN::VPC::SnatEntry'
    DependsOn: EipAssociation
    Properties:
      SnatTableId:
        Fn::GetAtt:
          - NatGateway
          - SNatTableId
      SnatEntryName:
        Fn::Sub: ${CommonName}-snat
      SourceVSwitchIds:
        - Ref: VSwitch1
        - Ref: VSwitch2
      SnatIp:
        Fn::GetAtt:
          - Eip
          - EipAddress
  APINas:
    Type: ALIYUN::NAS::FileSystem
    Properties:
      ProtocolType: NFS
      FileSystemType: standard
      DeletionForce: true
      StorageType: Performance
      Description:
        Fn::Sub: ${CommonName}-API-NAS
  APINasMountTarget:
    Type: ALIYUN::NAS::MountTarget
    Properties:
      VpcId:
        Ref: Vpc
      VSwitchId:
        Ref: VSwitch1
      NetworkType: Vpc
      AccessGroupName: DEFAULT_VPC_GROUP_NAME
      FileSystemId:
        Ref: APINas
  PluginNas:
    Type: ALIYUN::NAS::FileSystem
    Properties:
      ProtocolType: NFS
      FileSystemType: standard
      DeletionForce: true
      StorageType: Performance
      Description:
        Fn::Sub: ${CommonName}-Plugin-NAS
  PluginNasMountTarget:
    Type: ALIYUN::NAS::MountTarget
    Properties:
      VpcId:
        Ref: Vpc
      VSwitchId:
        Ref: VSwitch1
      NetworkType: Vpc
      AccessGroupName: DEFAULT_VPC_GROUP_NAME
      FileSystemId:
        Ref: PluginNas
  SuperOpsUser:
    Type: 'ALIYUN::RAM::User'
    Properties:
      UserName:
        Fn::Sub: SuperOps-${ALIYUN::StackId}
      Policies:
        - PolicyName:
            'Fn::Join':
              - '-'
              - - DifySuperOpsPolicy
                - Ref: 'ALIYUN::StackName'
          PolicyDocument:
            Version: '1'
            Statement:
              - Effect: Allow
                Action:
                  - 'gpdb:*'
                Resource:
                  - '*'
      PolicyAttachments:
        System:
          - AliyunSTSAssumeRoleAccess
          - AliyunRAMReadOnlyAccess
  AccessKey:
    Type: 'ALIYUN::RAM::AccessKey'
    Properties:
      UserName:
        'Fn::GetAtt':
          - SuperOpsUser
          - UserName
  DifyApiConfigMap:
    Type: ALIYUN::SAE::ConfigMap
    Properties:
      Data:
        MAIL_DEFAULT_SEND_FROM: 'YOUR EMAIL FROM (eg: no-reply <no-reply@dify.ai>)'
        SENTRY_PROFILES_SAMPLE_RATE: '1'
        MARKETPLACE_ENABLED: 'true'
        DB_PORT: '5432'
        VECTOR_STORE: analyticdb
        LOG_LEVEL: INFO
        DB_DATABASE: dify
        REDIS_USE_SSL: 'false'
        STORAGE_LOCAL_PATH: /app/api/storage
        SENTRY_TRACES_SAMPLE_RATE: '1'
        MODE: api
        WEB_API_CORS_ALLOW_ORIGINS: '*'
        RESEND_API_URL: https://api.resend.com
        ANALYTICDB_INSTANCE_ID:
          Fn::GetAtt:
            - ADBPGInstance
            - DBInstanceId
        CODE_EXECUTION_ENDPOINT: http://dify-sandbox:8194
        REDIS_HOST:
          Fn::GetAtt:
            - RedisInstance
            - ConnectionDomain
        REDIS_DB: '0'
        REDIS_PORT: '6379'
        MAIL_TYPE: resend
        ANALYTICDB_REGION_ID:
          Ref: ALIYUN::Region
        MIGRATION_ENABLED: 'true'
        CONSOLE_CORS_ALLOW_ORIGINS: '*'
        PLUGIN_DAEMON_URL: http://dify-plugin-daemon:5002
        STORAGE_TYPE: local
        DB_HOST:
          Fn::GetAtt:
            - PostgreSQLInstance
            - InnerConnectionString
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-api
  DifyApiSecret:
    Type: 'ALIYUN::SAE::Secret'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      SecretName: dify-api
      SecretType: Opaque
      SecretData:
        ANALYTICDB_ACCOUNT:
          Ref: ADBPGAccount
        ANALYTICDB_KEY_ID:
          Fn::GetAtt:
            - AccessKey
            - AccessKeyId
        ANALYTICDB_KEY_SECRET:
          Fn::GetAtt:
            - AccessKey
            - AccessKeySecret
        ANALYTICDB_NAMESPACE: difyns
        ANALYTICDB_NAMESPACE_PASSWORD:
          Ref: ADBPGPassword
        ANALYTICDB_PASSWORD:
          Ref: ADBPGPassword
        CELERY_BROKER_URL:
          Fn::Sub:
            - redis://:${REDIS_PASSWORD}@${REDIS_HOST}:6379/0
            - REDIS_PASSWORD:
                Ref: RedisInstancePassword
              REDIS_HOST:
                Fn::GetAtt:
                  - RedisInstance
                  - ConnectionDomain
        CODE_EXECUTION_API_KEY: dify-sandbox
        DB_PASSWORD:
          Ref: PostgresSQLPassword
        DB_USERNAME:
          Ref: PostgresSQLUserName
        INNER_API_KEY_FOR_PLUGIN: QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1
        PLUGIN_DAEMON_KEY: lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi
        REDIS_PASSWORD:
          Ref: RedisInstancePassword
        REDIS_USERNAME: default
        RESEND_API_KEY: xxxx
        SECRET_KEY:
          !Base64Decode
          Fn::Jq:
            - First
            - .[0].Output
            - Fn::GetAtt:
                - RunCommand
                - InvokeResults
  DifyWorkerConfigMap:
    Type: ALIYUN::SAE::ConfigMap
    Properties:
      Data:
        MAIL_DEFAULT_SEND_FROM: 'YOUR EMAIL FROM (eg: no-reply <no-reply@dify.ai>)'
        SENTRY_PROFILES_SAMPLE_RATE: '1'
        MARKETPLACE_ENABLED: 'true'
        DB_PORT: '5432'
        VECTOR_STORE: analyticdb
        LOG_LEVEL: INFO
        DB_DATABASE: dify
        REDIS_USE_SSL: 'false'
        STORAGE_LOCAL_PATH: /app/api/storage
        SENTRY_TRACES_SAMPLE_RATE: '1'
        MODE: worker
        WEB_API_CORS_ALLOW_ORIGINS: '*'
        RESEND_API_URL: https://api.resend.com
        ANALYTICDB_INSTANCE_ID:
          Fn::GetAtt:
            - ADBPGInstance
            - DBInstanceId
        REDIS_HOST:
          Fn::GetAtt:
            - RedisInstance
            - ConnectionDomain
        REDIS_DB: '0'
        REDIS_PORT: '6379'
        MAIL_TYPE: resend
        ANALYTICDB_REGION_ID:
          Ref: ALIYUN::Region
        MIGRATION_ENABLED: 'true'
        CONSOLE_CORS_ALLOW_ORIGINS: '*'
        PLUGIN_DAEMON_URL: http://dify-plugin-daemon:5002
        STORAGE_TYPE: local
        DB_HOST:
          Fn::GetAtt:
            - PostgreSQLInstance
            - InnerConnectionString
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-worker

  DifyWorkerSecret:
    Type: 'ALIYUN::SAE::Secret'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      SecretName: dify-worker
      SecretType: Opaque
      SecretData:
        ANALYTICDB_ACCOUNT:
          Ref: ADBPGAccount
        ANALYTICDB_KEY_ID:
          Fn::GetAtt:
            - AccessKey
            - AccessKeyId
        ANALYTICDB_KEY_SECRET:
          Fn::GetAtt:
            - AccessKey
            - AccessKeySecret
        ANALYTICDB_NAMESPACE: difyns
        ANALYTICDB_NAMESPACE_PASSWORD:
          Ref: ADBPGPassword
        ANALYTICDB_PASSWORD:
          Ref: ADBPGPassword
        CELERY_BROKER_URL:
          Fn::Sub:
            - redis://:${REDIS_PASSWORD}@${REDIS_HOST}:6379/0
            - REDIS_PASSWORD:
                Ref: RedisInstancePassword
              REDIS_HOST:
                Fn::GetAtt:
                  - RedisInstance
                  - ConnectionDomain
        DB_PASSWORD:
          Ref: PostgresSQLPassword
        DB_USERNAME:
          Ref: PostgresSQLUserName
        INNER_API_KEY_FOR_PLUGIN: QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1
        PLUGIN_DAEMON_KEY: lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi
        REDIS_PASSWORD:
          Ref: RedisInstancePassword
        REDIS_USERNAME: default
        RESEND_API_KEY: xxxx
        SECRET_KEY:
          !Base64Decode
          Fn::Jq:
            - First
            - .[0].Output
            - Fn::GetAtt:
                - RunCommand
                - InvokeResults
  DifyPluginDaemonConfigMap:
    Type: 'ALIYUN::SAE::ConfigMap'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-plugin-daemon
      Data:
        SERVER_PORT: "5002"
        PLUGIN_REMOTE_INSTALLING_HOST: "0.0.0.0"
        REDIS_DB: "0"
        REDIS_HOST:
          Fn::GetAtt:
            - RedisInstance
            - ConnectionDomain
        MARKETPLACE_ENABLED: "true"
        DB_PORT: "5432"
        REDIS_USE_SSL: "false"
        PLUGIN_WORKING_PATH: /app/storage/cwd
        DB_HOST:
          Fn::GetAtt:
            - PostgreSQLInstance
            - InnerConnectionString
        PIP_MIRROR_URL: http://mirrors.aliyun.com/pypi/simple/
        REDIS_PORT: "6379"
        PLUGIN_REMOTE_INSTALLING_PORT: "5003"
        MAX_PLUGIN_PACKAGE_SIZE: "52428800"
        DB_DATABASE: dify_plugin
        DIFY_INNER_API_URL: http://dify-api:5001
  DifyPluginDaemonSecret:
    Type: 'ALIYUN::SAE::Secret'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      SecretName: dify-plugin-daemon
      SecretType: Opaque
      SecretData:
        DB_PASSWORD:
          Ref: PostgresSQLPassword
        DB_USERNAME:
          Ref: PostgresSQLUserName
        DIFY_INNER_API_KEY: QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1
        REDIS_PASSWORD:
          Ref: RedisInstancePassword
        REDIS_USERNAME: default
        SERVER_KEY: lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi
  DifySandboxConfigMap:
    Type: 'ALIYUN::SAE::ConfigMap'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-sandbox
      Data:
        GIN_MODE: release
        SANDBOX_PORT: "8194"
  DifySandboxSecret:
    Type: 'ALIYUN::SAE::Secret'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      SecretName: dify-sandbox
      SecretType: Opaque
      SecretData:
        API_KEY: dify-sandbox
  DifyWebConfigMap:
    Type: 'ALIYUN::SAE::ConfigMap'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-web
      Data:
        MARKETPLACE_ENABLED: "true"
        MARKETPLACE_URL: https://marketplace.dify.ai
        MARKETPLACE_API_URL: https://marketplace.dify.ai
  DifyNginxConfigMap:
    Type: 'ALIYUN::SAE::ConfigMap'
    Properties:
      NamespaceId:
        Ref: SaeNamespace
      Name: dify-nginx
      Data:
        default.conf: |-
          server {
                  listen 80;
                  server_name _;

                  location /console/api {
                    proxy_pass http://dify-api:5001;
                    include proxy.conf;
                  }

                  location /api {
                    proxy_pass http://dify-api:5001;
                    include proxy.conf;
                  }

                  location /v1 {
                    proxy_pass http://dify-api:5001;
                    include proxy.conf;
                  }

                  location /files {
                    proxy_pass http://dify-api:5001;
                    include proxy.conf;
                  }

                  location /explore {
                    proxy_pass http://dify-web:3000;
                    proxy_set_header Dify-Hook-Url $scheme://$host$request_uri;
                    include proxy.conf;
                  }

                  location /e/ {
                    proxy_pass http://dify-plugin-daemon:5002;
                    proxy_set_header Dify-Hook-Url $scheme://$host$request_uri;
                    include proxy.conf;
                  }

                  location / {
                    proxy_pass http://dify-web:3000;
                    include proxy.conf;
                  }
              }
        nginx.conf: |-
          user  nginx;
              worker_processes  auto;
              pid        /var/run/nginx.pid;


              events {
                  worker_connections  1024;
              }


              http {
                  include       /etc/nginx/mime.types;
                  default_type  application/octet-stream;

                  log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                                    '$status $body_bytes_sent "$http_referer" '
                                    '"$http_user_agent" "$http_x_forwarded_for"';

                  sendfile        on;
                  #tcp_nopush     on;

                  keepalive_timeout  65;

                  #gzip  on;
                  client_max_body_size 15M;

                  include /etc/nginx/conf.d/*.conf;
              }
        proxy.conf: |-
          proxy_set_header Host $host;
          proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
          proxy_set_header X-Forwarded-Proto $scheme;
          proxy_set_header X-Forwarded-Port $server_port;
          proxy_http_version 1.1;
          proxy_set_header Connection "";
          proxy_buffering off;
          proxy_read_timeout 3600s;
          proxy_send_timeout 3600s;
  DifyApiApp:
    DependsOn:
      - SaeNamespace
      - DifyApiConfigMap
      - DifyApiSecret
      - ADBPGInstance
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-api
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-api-v1.6.0
      ProgrammingLanguage: python
      AppSource: micro_service
      Timezone: Asia/Shanghai
      NasConfigs:
        Fn::Sub:
          - '[{"mountDomain":"${MOUNT_DOMAIN}","mountPath":"/app/api/storage","nasId":"${NAS_ID}","nasPath":"dify-api","readOnly":false,"volumeName":"nas-1"}]'
          - MOUNT_DOMAIN:
              Fn::GetAtt:
                - APINasMountTarget
                - MountTargetDomain
            NAS_ID:
              Fn::GetAtt:
                - APINas
                - FileSystemId
      PvtzDiscoverySvc:
        Fn::Sub:
          - '{"enable":"true","namespaceId":"${REGION_ID}:${NAMESPACE}","portAndProtocol":{"5001:TCP":"5001"},"portProtocols":[],"pvtzDiscoveryName":"${REGION_ID}-${USER_ID}","serviceName":"dify-api.${NAMESPACE}"}'
          - NAMESPACE:
              Ref: NamespaceName
            USER_ID:
              Ref: ALIYUN::TenantId
            REGION_ID:
              Ref: ALIYUN::Region
      Envs:
        Fn::Sub:
          - '[{"name":"APP_WEB_URL"},{"name":"FILES_URL"},{"name":"CODE_MAX_DEPTH","value":"5"},{"name":"CODE_MAX_OBJECT_ARRAY_LENGTH","value":"30"},{"name":"CHECK_UPDATE_URL"},{"name":"CODE_MAX_STRING_ARRAY_LENGTH","value":"30"},{"name":"SERVICE_API_URL"},{"name":"sae-sys-secret-all-dify-api","valueFrom":{"secretRef":{"secretId":${SECRET_ID},"key":""}}},{"name":"CODE_MAX_PRECISION","value":"20"},{"name":"CONSOLE_API_URL"},{"name":"TEMPLATE_TRANSFORM_MAX_LENGTH","value":"80000"},{"name":"CODE_MAX_NUMBER","value":"9223372036854775807"},{"name":"CODE_MAX_NUMBER_ARRAY_LENGTH","value":"1000"},{"name":"CONSOLE_WEB_URL"},{"name":"CODE_MIN_NUMBER","value":"-9223372036854775808"},{"name":"CODE_MAX_STRING_LENGTH","value":"80000"},{"name":"SENTRY_DSN"},{"name":"CODE_EXECUTION_API_KEY","valueFrom":{"secretRef":{"secretId":${SANDBOX_SECRET_ID},"key":"API_KEY"}}},{"name":"sae-sys-configmap-all-dify-api","valueFrom":{"configMapRef":{"configMapId":${CONFIGMAP_ID},"key":""}}}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifyApiConfigMap
                - ConfigMapId
            SECRET_ID:
              Fn::GetAtt:
                - DifyApiSecret
                - SecretId
            SANDBOX_SECRET_ID:
              Fn::GetAtt:
                - DifySandboxSecret
                - SecretId
  DifyWorkerApp:
    DependsOn:
      - SaeNamespace
      - DifyWorkerConfigMap
      - DifyWorkerSecret
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-worker
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-api-v1.6.0
      ProgrammingLanguage: python
      AppSource: micro_service
      Timezone: Asia/Shanghai
      NasConfigs:
        Fn::Sub:
          - '[{"mountDomain":"${MOUNT_DOMAIN}","mountPath":"/app/api/storage","nasId":"${NAS_ID}","nasPath":"dify-api","readOnly":false,"volumeName":"nas-1"}]'
          - MOUNT_DOMAIN:
              Fn::GetAtt:
                - APINasMountTarget
                - MountTargetDomain
            NAS_ID:
              Fn::GetAtt:
                - APINas
                - FileSystemId
      Envs:
        Fn::Sub:
          - '[{"name":"sae-sys-secret-all-dify-worker","valueFrom":{"secretRef":{"secretId":${SECRET_ID},"key":""}}},{"name":"sae-sys-configmap-all-dify-worker","valueFrom":{"configMapRef":{"configMapId":${CONFIGMAP_ID},"key":""}}},{"name":"CONSOLE_WEB_URL"}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifyWorkerConfigMap
                - ConfigMapId
            SECRET_ID:
              Fn::GetAtt:
                - DifyWorkerSecret
                - SecretId
  DifyPluginDaemonApp:
    DependsOn:
      - SaeNamespace
      - DifyPluginDaemonConfigMap
      - DifyPluginDaemonSecret
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-plugin-daemon
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-plugin-daemon-v0.1.3-local
      ProgrammingLanguage: golang
      AppSource: micro_service
      Timezone: Asia/Shanghai
      NasConfigs:
        Fn::Sub:
          - '[{"mountDomain":"${MOUNT_DOMAIN}","mountPath":"/app/storage","nasId":"${NAS_ID}","nasPath":"dify-plugin-daemon","readOnly":false,"volumeName":"nas-1"}]'
          - MOUNT_DOMAIN:
              Fn::GetAtt:
                - PluginNasMountTarget
                - MountTargetDomain
            NAS_ID:
              Fn::GetAtt:
                - PluginNas
                - FileSystemId
      PvtzDiscoverySvc:
        Fn::Sub:
          - '{"enable":"true","namespaceId":"${REGION_ID}:${NAMESPACE}","portAndProtocol":{"5003:TCP":"5003","5002:TCP":"5002"},"portProtocols":[],"pvtzDiscoveryName":"${REGION_ID}-${USER_ID}","serviceName":"dify-plugin-daemon.${NAMESPACE}"}'
          - NAMESPACE:
              Ref: NamespaceName
            USER_ID:
              Ref: ALIYUN::TenantId
            REGION_ID:
              Ref: ALIYUN::Region
      Envs:
        Fn::Sub:
          - '[{"name":"sae-sys-secret-all-dify-plugin-daemon","valueFrom":{"secretRef":{"secretId":${SECRET_ID},"key":""}}},{"name":"sae-sys-configmap-all-dify-plugin-daemon","valueFrom":{"configMapRef":{"configMapId":${CONFIGMAP_ID},"key":""}}}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifyPluginDaemonConfigMap
                - ConfigMapId
            SECRET_ID:
              Fn::GetAtt:
                - DifyPluginDaemonSecret
                - SecretId
  DifySandboxApp:
    DependsOn:
      - SaeNamespace
      - DifySandboxConfigMap
      - DifySandboxSecret
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-sandbox
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-sandbox-v0.2.12
      ProgrammingLanguage: golang
      AppSource: micro_service
      Timezone: Asia/Shanghai
      PvtzDiscoverySvc:
        Fn::Sub:
          - '{"enable":"true","namespaceId":"${REGION_ID}:${NAMESPACE}","portAndProtocol":{"8194:TCP":"8194"},"portProtocols":[],"pvtzDiscoveryName":"${REGION_ID}-${USER_ID}","serviceName":"dify-sandbox.${NAMESPACE}"}'
          - NAMESPACE:
              Ref: NamespaceName
            USER_ID:
              Ref: ALIYUN::TenantId
            REGION_ID:
              Ref: ALIYUN::Region
      Envs:
        Fn::Sub:
          - '[{"name":"sae-sys-secret-all-dify-sandbox","valueFrom":{"secretRef":{"secretId":${SECRET_ID},"key":""}}},{"name":"WORKER_TIMEOUT","value":"15"},{"name":"sae-sys-configmap-all-dify-sandbox","valueFrom":{"configMapRef":{"configMapId":${CONFIGMAP_ID},"key":""}}}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifySandboxConfigMap
                - ConfigMapId
            SECRET_ID:
              Fn::GetAtt:
                - DifySandboxSecret
                - SecretId
  DifyWebApp:
    DependsOn:
      - SaeNamespace
      - DifyWebConfigMap
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-web
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-web-v1.6.0
      ProgrammingLanguage: other
      AppSource: micro_service
      Timezone: Asia/Shanghai
      PvtzDiscoverySvc:
        Fn::Sub:
          - '{"enable":"true","namespaceId":"${REGION_ID}:${NAMESPACE}","portAndProtocol":{"3000:TCP":"3000"},"portProtocols":[],"pvtzDiscoveryName":"${REGION_ID}-${USER_ID}","serviceName":"dify-web.${NAMESPACE}"}'
          - NAMESPACE:
              Ref: NamespaceName
            USER_ID:
              Ref: ALIYUN::TenantId
            REGION_ID:
              Ref: ALIYUN::Region
      Envs:
        Fn::Sub:
          - '[{"name":"sae-sys-configmap-all-dify-web","valueFrom":{"configMapRef":{"configMapId":${CONFIGMAP_ID},"key":""}}},{"name":"APP_API_URL"},{"name":"CONSOLE_API_URL"},{"name":"EDITION","value":"SELF_HOSTED"}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifyWebConfigMap
                - ConfigMapId
  DifyNginxApp:
    DependsOn:
      - SaeNamespace
      - DifyNginxConfigMap
    Type: 'ALIYUN::SAE::Application'
    Properties:
      AppName: dify-nginx
      SaeVersion: v2
      AutoConfig: false
      VpcId:
        Ref: Vpc
      SecurityGroupId:
        Ref: SecurityGroup
      VSwitchId:
        Fn::Sub:
          - '${VSwitch1},${VSwitch2}'
          - VSwitch1:
              Ref: VSwitch1
            VSwitch2:
              Ref: VSwitch2
      Replicas: 1
      NamespaceId:
        Ref: SaeNamespace
      Cpu: 1000
      Memory: 2048
      PackageType: Image
      ImageUrl:
        Fn::Sub: registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:nginx-v1.23.4
      ProgrammingLanguage: other
      AppSource: micro_service
      Timezone: Asia/Shanghai
      ConfigMapMountDesc:
        Fn::Sub:
          - '[{"MountPath":"/etc/nginx/conf.d/default.conf","ConfigMapId":${CONFIGMAP_ID},"ConfigMapName":"dify-nginx","Key":"default.conf"},{"MountPath":"/etc/nginx/nginx.conf","ConfigMapId":${CONFIGMAP_ID},"ConfigMapName":"dify-nginx","Key":"nginx.conf"},{"MountPath":"/etc/nginx/proxy.conf","ConfigMapId":${CONFIGMAP_ID},"ConfigMapName":"dify-nginx","Key":"proxy.conf"}]'
          - CONFIGMAP_ID:
              Fn::GetAtt:
                - DifyNginxConfigMap
                - ConfigMapId
  InternetClb:
    Type: ALIYUN::SLB::LoadBalancer
    Properties:
      LoadBalancerName:
        Ref: ALIYUN::StackName
      LoadBalancerSpec: slb.s2.medium
      AddressType: internet
  BackendAppBindClb:
    Type: 'ALIYUN::SAE::SlbBinding'
    DependsOn:
      - DifyNginxApp
      - InternetClb
    Properties:
      InternetSlbId:
        Fn::GetAtt:
          - InternetClb
          - LoadBalancerId
      Internet: '[{"port": 80, "targetPort": 80, "protocol": "TCP"}]'
      AppId:
        Fn::GetAtt:
          - DifyNginxApp
          - AppId
Outputs:
  DifyAddress:
    Label:
      zh-cn: Dify サービスアドレス。
      en: Dify サービスアドレス
    Description:
      zh-cn: Dify サービスアドレス。
      en: Dify プラットフォームのサービスアドレスです。
    Value:
      Fn::Sub:
        - http://${ServerAddress}:80
        - ServerAddress:
            Fn::GetAtt:
              - InternetClb
              - IpAddress
  PostgresName:
    Label:
      zh-cn: Postgres ユーザー名
      en: Postgres ユーザー名
    Description:
      zh-cn: AnalyticDB for PostgreSQL のユーザー名です。
      en: AnalyticDB for PostgreSQL データベースのユーザー名です。
    Value:
      Ref: ADBPGAccount
  PostgresPassword:
    Label:
      zh-cn: Postgres パスワード
      en: Postgres パスワード
    Description:
      zh-cn: AnalyticDB for PostgreSQL のパスワードです。
      en: AnalyticDB for PostgreSQL データベースのパスワードです。
    NoEcho: true
    Value:
      Ref: ADBPGPassword
  PostgresConnectionString:
    Label:
      zh-cn: Postgres データベースアドレス
      en: Postgres データベースアドレス
    Description:
      zh-cn: AnalyticDB for PostgreSQL の内部エンドポイントです。
      en: AnalyticDB for PostgreSQL データベースの内部エンドポイントです。
    Value:
      Fn::GetAtt:
        - ADBPGInstance
        - ConnectionString
  APINasFileSystemId:
    Label:
      zh-cn: API NAS ファイルシステム
      en: API NAS ファイルシステム
    Description:
      zh-cn: NAS ファイルシステムです。
      en: API 用の NAS ファイルシステムの ID です。
    Value:
      Ref: APINas
  APINasMountTarget:
    Label:
      zh-cn: API NAS マウントターゲット
      en: API NAS マウントターゲット
    Description:
      zh-cn: NAS マウントターゲットです。
      en: API 用の NAS ファイルシステムのマウントターゲットです。
    Value:
      Ref: APINasMountTarget
  PluginNasFileSystemId:
    Label:
      zh-cn: プラグイン NAS ファイルシステム
      en: プラグイン NAS ファイルシステム
    Description:
      zh-cn: NAS ファイルシステムです。
      en: プラグイン用の NAS ファイルシステムの ID です。
    Value:
      Ref: PluginNas
  PluginNasMountTarget:
    Label:
      zh-cn: プラグイン NAS マウントターゲット
      en: プラグイン NAS マウントターゲット
    Description:
      zh-cn: NAS マウントターゲットです。
      en: プラグイン用の NAS ファイルシステムのマウントターゲットです。
    Value:
      Ref: PluginNasMountTarget
  RedisConnectionString:
    Label:
      zh-cn: Redis 接続アドレス
      en: Redis 接続アドレス
    Description:
      zh-cn: Redis 接続アドレスです。
      en: Redis インスタンスの接続エンドポイントです。
    Value:
      Fn::GetAtt:
        - RedisInstance
        - ConnectionDomain
  RedisName:
    Label:
      zh-cn: Redis ユーザー名
      en: Redis ユーザー名
    Description:
      zh-cn: Redis ユーザー名です。
      en: Redis インスタンスのユーザー名です。
    Value: default
  RedisInstancePassword:
    Label:
      zh-cn: Redis パスワード
      en: Redis パスワード
    Description:
      zh-cn: Redis パスワードです。
      en: Redis インスタンスのパスワードです。
    NoEcho: true
    Value:
      Ref: RedisInstancePassword
  PostgreSQLDBName:
    Label:
      zh-cn: データベース名
      en: データベース名
    Description:
      zh-cn: ApsaraDB RDS for PostgreSQL のデータベース名です。
      en: ApsaraDB RDS for PostgreSQL インスタンスのデータベース名です。
    Value: dify
  PostgreSQLConnectionString:
    Label:
      zh-cn: RDS データベースアドレス
      en: RDS データベースアドレス
    Description:
      zh-cn: ApsaraDB RDS for PostgreSQL の内部エンドポイントです。
      en: ApsaraDB RDS for PostgreSQL インスタンスの内部エンドポイントです。
    Value:
      Fn::GetAtt:
        - PostgreSQLInstance
        - InnerConnectionString
  PostgreSQLAccount:
    Label:
      zh-cn: RDS ユーザー名
      en: RDS ユーザー名
    Description:
      zh-cn: ApsaraDB RDS for PostgreSQL のユーザー名です。
      en: ApsaraDB RDS for PostgreSQL インスタンスのユーザー名です。
    Value:
      Ref: PostgresSQLUserName
  PostgreSQLPassword:
    Label:
      zh-cn: RDS パスワード
      en: RDS パスワード
    Description:
      zh-cn: ApsaraDB RDS for PostgreSQL のパスワードです。
      en: ApsaraDB RDS for PostgreSQL インスタンスのパスワードです。
    NoEcho: true
    Value:
      Ref: PostgresSQLPassword
  NameSpace:
    Label:
      zh-cn: 名前空間
      en: 名前空間
    Description:
      zh-cn: 名前空間です。
      en: SAE 名前空間の ID です。
    Value:
      Fn::Sub: ${ALIYUN::Region}:${NamespaceName}
  Vpc:
    Label:
      zh-cn: VPC ID
      en: VPC ID
    Description:
      zh-cn: VPC ID です。
      en: VPC の ID です。
    Value:
      Ref: Vpc
  Vsw:
    Label:
      zh-cn: vSwitch ID
      en: vSwitch ID
    Description:
      zh-cn: vSwitch ID です。
      en: vSwitch の ID です。
    Value:
      Ref: VSwitch1
  Sg:
    Label:
      zh-cn: セキュリティグループ ID
      en: セキュリティグループ ID
    Description:
        zh-cn: セキュリティグループ ID です。
        en: セキュリティグループの ID です。
    Value:
        Ref: SecurityGroup
  SecretKey:
    Label:
      zh-cn: シークレットキー
      en: シークレットキー
    Description:
      zh-cn: データベース内のセキュア署名および機密情報の暗号化に使用されます。
      en: セキュア署名およびデータベース内の機密情報の暗号化に使用されるキーです。
    NoEcho: true
    Value:
      !Base64Decode
        Fn::Jq:
          - First
          - .[0].Output
          - Fn::GetAtt:
              - RunCommand
              - InvokeResults
  dify-nginx:
    Label:
      zh-cn: dify-nginx のアプリケーションアドレス
      en: dify-nginx アプリケーションアドレス
    Description:
      zh-cn: dify-nginx のアプリケーションアドレスです。アプリケーションアクセス設定で、CLB アクセスに基づくパブリックエンドポイントを表示します。
      en: dify-nginx アプリケーションのアドレスです。SLB アクセスのパブリックエンドポイントを表示するには、アプリケーションアクセス設定に移動します。
    Value:
      Fn::Sub: https://sae.console.alibabacloud.com/${ALIYUN::Region}/app-list/${DifyNginxApp.AppId}/micro-app/base?name=dify-nginx
  ECSInstanceId:
    Label:
      zh-cn: ECS インスタンス ID
      en: ECS インスタンス ID
    Description:
      zh-cn: ECS インスタンス ID です。このインスタンスは、サンプルの e コマースシステムをデプロイします。
      en: ECS インスタンスの ID です。このインスタンスは、インストールスクリプトの実行に使用されます。
    Value:
      Fn::Select:
        - 0
        - Fn::GetAtt:
            - EcsInstance
            - InstanceIds
  Console@DemoUrl:
    Description:
      zh-cn: アプリケーションアクセスドメイン名。このソリューションの e コマースシステムのアドレスです。
      en: ECS インスタンスのパブリック IP アドレスです。
    Value:
      Fn::Sub:
        - http://${PublicIp}
        - PublicIp:
            Fn::Select:
              - 0
              - Fn::GetAtt:
                  - EcsInstance
                  - PublicIps
Metadata:
  'ALIYUN::ROS::Interface':
    Outputs:
      - DifyAddress
      - ECSInstanceId
      - Console@DemoUrl
      - dify-nginx
      - NameSpace
      - Vpc
      - Vsw
      - Sg
      - PostgreSQLDBName
      - PostgreSQLConnectionString
      - PostgreSQLAccount
      - PostgreSQLPassword
      - PostgresName
      - PostgresPassword
      - PostgresConnectionString
      - APINasFileSystemId
      - APINasMountTarget
      - PluginNasFileSystemId
      - PluginNasMountTarget
      - RedisConnectionString
      - RedisName
      - RedisInstancePassword
      - SecretKey
    ParameterGroups:
      - Parameters:
          - ZoneId1
          - ZoneId2
        Label:
          default:
            en: アベイラビリティーゾーン
            zh-cn: アベイラビリティーゾーン
      - Parameters:
          - InstanceType
          - InstancePassword
        Label:
          default:
            en: Elastic Compute Service
            zh-cn: Elastic Compute Service
      - Parameters:
          - RedisInstancePassword
        Label:
          default:
            en: ApsaraDB for Redis
            zh-cn: ApsaraDB for Redis
      - Parameters:
          - ADBPGAccount
          - ADBPGPassword
        Label:
          default:
            en: AnalyticDB for PostgreSQL
            zh-cn: AnalyticDB for PostgreSQL
      - Parameters:
          - DBInstanceClass
          - RdsDatabaseName
          - PostgresSQLUserName
          - PostgresSQLPassword
        Label:
          default:
            en: ApsaraDB RDS for PostgreSQL
            zh-cn: ApsaraDB RDS for PostgreSQL
      - Parameters:
          - NamespaceName
        Label:
          default:
            en: Serverless App Engine
            zh-cn: Serverless App Engine
    TemplateTags:
      - acs:technical-solution:internet-application-development:Deploy a production-ready Dify platform using Serverless App Engine-tech_solu_251
    Hidden:
      - CommonName
{
  "ROSTemplateFormatVersion": "2015-09-01",
  "Description": {
    "zh-cn": "Serverless App Engine を介して本番環境の Dify プラットフォームをデプロイします。",
    "en": "Serverless App Engine (SAE) を使用して、本番環境に対応した Dify プラットフォームをデプロイします。"
  },
  "Parameters": {
    "CommonName": {
      "Type": "String",
      "Default": "Dify"
    },
    "NamespaceName": {
      "Type": "String",
      "Label": {
        "en": "名前空間名",
        "zh-cn": "名前空間名"
      },
      "Description": {
        "zh-cn": "名前空間名。小文字と数字のみがサポートされます。",
        "en": "名前空間名。小文字と数字のみがサポートされます。"
      },
      "AllowedPattern": "^[a-z0-9]+$",
      "AssociationProperty": "AutoCompleteInput",
      "AssociationPropertyMetadata": {
        "Length": 3,
        "Prefix": "dify",
        "CharacterClasses": [
          {
            "Class": "lowercase",
            "min": 2
          },
          {
            "Class": "number",
            "min": 1
          }
        ]
      }
    },
    "ZoneId1": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::Instance::ZoneId",
      "AssociationPropertyMetadata": {
        "ExclusiveTo": [
          "ZoneId2"
        ]
      },
      "Label": {
        "en": "アベイラビリティーゾーン 1",
        "zh-cn": "アベイラビリティーゾーン 1"
      }
    },
    "ZoneId2": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::Instance::ZoneId",
      "AssociationPropertyMetadata": {
        "ExclusiveTo": [
          "ZoneId1"
        ]
      },
      "Label": {
        "en": "アベイラビリティーゾーン 2",
        "zh-cn": "アベイラビリティーゾーン 2"
      }
    },
    "InstanceType": {
      "Type": "String",
      "AssociationProperty": "ALIYUN::ECS::Instance::InstanceType",
      "AssociationPropertyMetadata": {
        "InstanceChargeType": "PostPaid",
        "SystemDiskCategory": "cloud_essd",
        "ZoneId": "${ZoneId1}"
      },
      "Label": {
        "en": "インスタンスタイプ",
        "zh-cn": "インスタンスタイプ"
      }
    },
    "ADBPGAccount": {
      "Default": "dify",
      "Type": "String",
      "Label": {
        "zh-cn": "データベースアカウント",
        "en": "データベースアカウント"
      }
    },
    "ADBPGPassword": {
      "NoEcho": true,
      "Type": "String",
      "Label": {
        "zh-cn": "データベースアカウントのパスワード",
        "en": "データベースアカウントのパスワード"
      },
      "AssociationProperty": "ALIYUN::RDS::Instance::AccountPassword"
    },
    "InstancePassword": {
      "Type": "String",
      "Label": {
        "en": "インスタンスのログインパスワード",
        "zh-cn": "ログインパスワード"
      },
      "Description": {
        "en": "インスタンスのログインパスワードです。パスワードは 8~30 文字で、大文字、小文字、数字、特殊文字 ()`~!@#$%^&*_-+=|{}[]:;'<>,.?/ のうち少なくとも 3 種類を含める必要があります。",
        "zh-cn": "サーバーのログインパスワード。長さ:8~30 文字。大文字、小文字、数字、特殊文字 ()`~!@#$%^&*_-+=|{}[]:;'<>,.?/ のうち少なくとも 3 種類を含める必要があります。"
      },
      "AssociationProperty": "ALIYUN::ECS::Instance::Password"
    },
    "RedisInstancePassword": {
      "Type": "String",
      "Label": {
        "en": "Redis インスタンスのパスワード",
        "zh-cn": "インスタンスのパスワード"
      },
      "Description": {
        "en": "Dify が使用する Redis インスタンスのパスワードです。パスワードは 8~32 文字で、大文字、小文字、数字のみを含める必要があります。",
        "zh-cn": "Dify が使用する Redis のパスワードは 8~32 文字の長さで、大文字、小文字、数字のみを含める必要があります。他の文字は使用しないでください。"
      },
      "ConstraintDescription": {
        "en": "Dify が使用する Redis インスタンスのパスワードです。パスワードは 8~32 文字で、大文字、小文字、数字のみを含める必要があります。",
        "zh-cn": "Dify が使用する Redis のパスワードは 8~32 文字の長さで、大文字、小文字、数字のみを含める必要があります。他の文字は使用しないでください。"
      },
      "AllowedPattern": "^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?\\d)[A-Za-z0-9]{8,32}$",
      "MinLength": "8",
      "MaxLength": "32",
      "NoEcho": true
    },
    "DBInstanceClass": {
      "Type": "String",
      "Label": {
        "en": "インスタンスタイプ",
        "zh-cn": "インスタンスタイプ"
      },
      "Default": "pg.n4m.2c.2m",
      "Required": true,
      "AssociationProperty": "ALIYUN::RDS::Instance::InstanceType",
      "AssociationPropertyMetadata": {
        "ZoneId": "${ZoneId}",
        "EngineVersion": "17.0",
        "Engine": "PostgreSQL",
        "Category": "HighAvailability",
        "InstanceChargeType": "Postpaid",
        "DBInstanceStorageType": "cloud_essd",
        "CommodityCode": "bards"
      }
    },
    "PostgresSQLPassword": {
      "Type": "String",
      "NoEcho": true,
      "Label": {
        "en": "データベースアカウントのパスワード",
        "zh-cn": "データベースアカウントのパスワード"
      },
      "AssociationProperty": "ALIYUN::RDS::Instance::AccountPassword"
    },
    "PostgresSQLUserName": {
      "Type": "String",
      "Label": {
        "en": "データベースアカウント",
        "zh-cn": "データベースアカウント"
      },
      "AllowedPattern": "^(?!dbo\\b|login\\b|admin\\b|administrator\\b|adminsys\\b|alimail\\b|aliyun\\b|apache\\b|appadmin\\b|apsara\\b|aurora\\b|bulkadmin\\b|cangjie\\b|cdn\\b|client\\b|cm\\b|dataengine\\b|dayu\\b|dba\\b|dbcreator\\b|developer\\b|diskadmin\\b|distribution\\b|dns\\b|download\\b|eagleye\\b|f5\\b|faq\\b|fuxi\\b|galaxy\\b|gongcao\\b|gongming\\b|groupon\\b|ha\\b|help\\b|host\\b|hostmaster\\b|houyi\\b|hr\\b|info\\b|information_schema\\b|kuafu\\b|lvs\\b|manager\\b|master\\b|meituan\\b|model\\b|monitor\\b|msdb\\b|mssqld\\b|mssqlsystemresource\\b|mysql\\b|nas\\b|net\\b|netops\\b|netweb\\b|news\\b|no-reply\\b|ntp\\b|nuwa\\b|nvwa\\b|operator\\b|opr\\b|ops\\b|opsdb\\b|oracle\\b|pangu\\b|pe\\b|post\\b|postmaster\\b|processadmin\\b|public\\b|qq\\b|replicator\\b|reply\\b|root\\b|sa\\b|sales\\b|san\\b|security\\b|securityadmin\\b|serveradmin\\b|services\\b|setupadmin\\b|shennong\\b|siteops\\b|sqlengine\\b|sqlonline\\b|squid\\b|ssladmin\\b|support\\b|sys\\b|sysadmin\\b|syslog\\b|system\\b|taoyun\\b|tempdb\\b|test\\b|tianyun\\b|wangwang\\b|eb\\b|webmaster\\b|webnet\\b|xtrabak\\b|youchao\\b|yum\\b|yunti\\b|zhongkui\\b|database\\b|add\\b|except\\b|percent\\b|all\\b|exec\\b|plan\\b|alter\\b|execute\\b|precision\\b|and\\b|exists\\b|primary\\b|any\\b|exit\\b|print\\b|as\\b|fetch\\b|proc\\b|asc\\b|file\\b|procedure\\b|authorization\\b|fillfactor\\b|public\\b|backup\\b|for\\b|raiserror\\b|begin\\b|foreign\\b|read\\b|between\\b|freetext\\b|readtext\\b|break\\b|freetexttable\\b|reconfigure\\b|browse\\b|from\\b|references\\b|bulk\\b|full\\b|replication\\b|by\\b|function\\b|restore\\b|cascade\\b|goto\\b|restrict\\b|case\\b|grant\\b|return\\b|check\\b|group\\b|revoke\\b|checkpoint\\b|having\\b|right\\b|close\\b|holdlock\\b|rollback\\b|clustered\\b|identity\\b|rowcount\\b|coalesce\\b|identity_insert\\b|rowguidcol\\b|collate\\b|identitycol\\b|rule\\b|column\\b|if\\b|save\\b|commit\\b|in\\b|schema\\b|compute\\b|index\\b|select\\b|constraint\\b|inner\\b|session_user\\b|contains\\b|insert\\b|set\\b|containstable\\b|intersect\\b|setuser\\b|continue\\b|into\\b|shutdown\\b|convert\\b|is\\b|some\\b|create\\b|join\\b|statistics\\b|cross\\b|key\\b|system_user\\b|current\\b|kill\\b|table\\b|current_date\\b|left\\b|textsize\\b|current_time\\b|like\\b|then\\b|current_timestamp\\b|lineno\\b|to\\b|current_user\\b|load\\b|top\\b|cursor\\b|national\\b|tran\\b|database\\b|nocheck\\b|transaction\\b|dbcc\\b|nonclustered\\b|trigger\\b|deallocate\\b|not\\b|truncate\\b|declare\\b|null\\b|tsequal\\b|default\\b|nullif\\b|union\\b|delete\\b|of\\b|unique\\b|deny\\b|off\\b|update\\b|desc\\b|offsets\\b|updatetext\\b|disk\\b|on\\b|use\\b|distinct\\b|open\\b|user\\b|distributed\\b|opendatasource\\b|values\\b|double\\b|openquery\\b|varying\\b|drop\\b|openrowset\\b|view\\b|dummy\\b|openxml\\b|waitfor\\b|dump\\b|option\\b|when\\b|else\\b|or\\b|where\\b|end\\b|order\\b|while\\b|errlvl\\b|outer\\b|with\\b|escape\\b|over\\b|writetext\\b|add\\b|analyze\\b|asc\\b|between\\b|blob\\b|call\\b|change\\b|check\\b|condition\\b|continue\\b|cross\\b|current_timestamp\\b|database\\b|day_microsecond\\b|dec\\b|default\\b|desc\\b|distinct\\b|double\\b|each\\b|enclosed\\b|exit\\b|fetch\\b|float8\\b|foreign\\b|goto\\b|having\\b|hour_minute\\b|ignore\\b|infile\\b|insensitive\\b|int1\\b|int4\\b|interval\\b|iterate\\b|keys\\b|leading\\b|like\\b|lines\\b|localtimestamp\\b|longblob\\b|low_priority\\b|mediumint\\b|minute_microsecond\\b|modifies\\b|no_write_to_binlog\\b|on\\b|optionally\\b|out\\b|precision\\b|purge\\b|read\\b|references\\b|rename\\b|require\\b|revoke\\b|schema\\b|select\\b|set\\b|spatial\\b|sqlexception\\b|sql_big_result\\b|ssl\\b|table\\b|tinyblob\\b|to\\b|true\\b|unique\\b|update\\b|using\\b|utc_timestamp\\b|varchar\\b|when\\b|with\\b|xor\\b|all\\b|and\\b|asensitive\\b|bigint\\b|both\\b|cascade\\b|char\\b|collate\\b|connection\\b|convert\\b|current_date\\b|current_user\\b|databases\\b|day_minute\\b|decimal\\b|delayed\\b|describe\\b|distinctrow\\b|drop\\b|else\\b|escaped\\b|explain\\b|float\\b|for\\b|from\\b|grant\\b|high_priority\\b|hour_second\\b|in\\b|inner\\b|insert\\b|int2\\b|int8\\b|into\\b|join\\b|kill\\b|leave\\b|limit\\b|load\\b|lock\\b|longtext\\b|match\\b|mediumtext\\b|minute_second\\b|natural\\b|null\\b|optimize\\b|or\\b|outer\\b|primary\\b|raid0\\b|reads\\b|regexp\\b|repeat\\b|restrict\\b|right\\b|schemas\\b|sensitive\\b|show\\b|specific\\b|sqlstate\\b|sql_calc_found_rows\\b|starting\\b|terminated\\b|tinyint\\b|trailing\\b|undo\\b|unlock\\b|usage\\b|utc_date\\b|values\\b|varcharacter\\b|where\\b|write\\b|year_month\\b|alter\\b|as\\b|before\\b|binary\\b|by\\b|case\\b|character\\b|column\\b|constraint\\b|create\\b|current_time\\b|cursor\\b|day_hour\\b|day_second\\b|declare\\b|delete\\b|deterministic\\b|div\\b|dual\\b|elseif\\b|exists\\b|false\\b|float4\\b|force\\b|fulltext\\b|group\\b|hour_microsecond\\b|if\\b|index\\b|inout\\b|int\\b|int3\\b|integer\\b|is\\b|key\\b|label\\b|left\\b|linear\\b|localtime\\b|long\\b|loop\\b|mediumblob\\b|middleint\\b|mod\\b|not\\b|numeric\\b|option\\b|order\\b|outfile\\b|procedure\\b|range\\b|real\\b|release\\b|replace\\b|return\\b|rlike\\b|second_microsecond\\b|separator\\b|smallint\\b|sql\\b|sqlwarning\\b|sql_small_result\\b|straight_join\\b|then\\b|tinytext\\b|trigger\\b|union\\b|unsigned\\b|use\\b|utc_time\\b|varbinary\\b|varying\\b|while\\b|x509\\b|zerofill)([a-zA-Z][a-zA-Z0-9_]{0,30}[a-zA-Z0-9])$",
      "ConstraintDescription": {
        "en": "アカウント名には、英字、数字、アンダースコア (_) を含めることができます。先頭は英字、末尾は英字または数字である必要があります。名前の長さは最大 32 文字です。詳細については、<a href=\"https://www.alibabacloud.com/help/en/rds/developer-reference/forbidden-keywords\" target=\"_blank\">禁止キーワード</a>をご参照ください。",
        "zh-cn": "値には、小文字、大文字、数字、アンダースコア (_) を含めることができます。先頭は英字、末尾は英字または数字である必要があります。最大長は 32 文字です。無効な文字の詳細については、<a href=\"https://www.alibabacloud.com/help/zh/rds/developer-reference/forbidden-keywords\" target=\"_blank\">禁止キーワード表</a>をご参照ください。"
      },
      "Default": "db_user"
    }
  },
  "Resources": {
    "Vpc": {
      "Type": "ALIYUN::ECS::VPC",
      "Properties": {
        "CidrBlock": "192.168.0.0/16",
        "VpcName": {
          "Fn::Sub": "${CommonName}-VPC_HZ"
        }}
      }
    },
    "VSwitch1": {
      "Type": "ALIYUN::ECS::VSwitch",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "CidrBlock": "192.168.1.0/24",
        "ZoneId": {
          "Ref": "ZoneId1"
        },
        "VSwitchName": {
          "Fn::Sub": "${CommonName}-vsw_001"
        }
      }
    },
    "VSwitch2": {
      "Type": "ALIYUN::ECS::VSwitch",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "CidrBlock": "192.168.2.0/24",
        "ZoneId": {
          "Ref": "ZoneId2"
        },
        "VSwitchName": {
          "Fn::Sub": "${CommonName}-vsw_002"
        }
      }
    },
    "Sleep": {
      "DependsOn": [
        "VSwitch1",
        "VSwitch2"
      ],
      "Type": "ALIYUN::ROS::Sleep",
      "Properties": {
        "DeleteDuration": 300
      }
    },
    "SecurityGroup": {
      "Type": "ALIYUN::ECS::SecurityGroup",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupName": {
          "Fn::Sub": "${CommonName}-SecurityGroup_1"
        },
        "SecurityGroupIngress": [
          {
            "PortRange": "80/80",
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          },
          {
            "PortRange": "3000/3000",
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          },
          {
            "PortRange": "5001/5001",
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          },
          {
            "PortRange": "5002/5002",
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          },
          {
            "PortRange": "5003/5003",
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          },
          {
            "PortRange": "8080/8080",
            "Priority": 1,
            "SourceCidrIp": "0.0.0.0/0",
            "IpProtocol": "tcp"
          }
        ]
      }
    },
    "EcsInstance": {
      "Type": "ALIYUN::ECS::InstanceGroup",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "ZoneId": {
          "Ref": "ZoneId1"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "ImageId": "aliyun_3_x64_20G_alibase_",
        "InstanceName": {
          "Fn::Sub": "${CommonName}-ecs"
        },
        "InstanceType": {
          "Ref": "InstanceType"
        },
        "SystemDiskCategory": "cloud_essd",
        "MaxAmount": 1,
        "SystemDiskSize": 40,
        "InternetMaxBandwidthOut": 5,
        "Password": {
          "Ref": "InstancePassword"
        }
      }
    },
    "RunCommand": {
      "Type": "ALIYUN::ECS::RunCommand",
      "Properties": {
        "CommandContent": {
          "Fn::Sub": "#!/bin/sh\necho \"sk-$(openssl rand -hex 16)\"\n"
        },
        "Type": "RunShellScript",
        "InstanceIds": [
          {
            "Ref": "EcsInstance"
          }
        ]
      }
    },
    "RunCommand2": {
      "DependsOn": [
        "RunCommand"
      ],
      "Type": "ALIYUN::ECS::RunCommand",
      "Properties": {
        "CommandContent": {
          "Fn::Sub": "#!/bin/sh\nexport ROS_DEPLOY=true\ncurl -fsSL https://help-static-aliyun-doc.aliyuncs.com/install-script/dify/sae/install.sh | bash\n"
        },
        "Type": "RunShellScript",
        "InstanceIds": [
          {
            "Ref": "EcsInstance"
          }
        ]
      }
    },
    "RedisInstance": {
      "Type": "ALIYUN::REDIS::Instance",
      "Properties": {
        "ZoneId": {
          "Ref": "ZoneId1"
        },
        "SecondaryZoneId": {
          "Ref": "ZoneId2"
        },
        "VpcId": {
          "Ref": "Vpc"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "InstanceClass": "redis.shard.large.y.ee",
        "EvictionPolicy": "noeviction",
        "InstanceName": {
          "Fn::Sub": "${CommonName}-Redis"
        },
        "EngineVersion": "7.0",
        "Password": {
          "Ref": "RedisInstancePassword"
        }
      }
    },
    "REDISWhitelist": {
      "Type": "ALIYUN::REDIS::Whitelist",
      "Properties": {
        "InstanceId": {
          "Ref": "RedisInstance"
        },
        "SecurityIps": "192.168.0.0/16"
      }
    },
    "ADBPGInstance": {
      "Type": "ALIYUN::GPDB::DBInstance",
      "Properties": {
        "EngineVersion": "7.0",
        "VectorConfigurationStatus": true,
        "InstanceSpec": "4C32G",
        "ZoneId": {
          "Ref": "ZoneId1"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "SegNodeNum": 4,
        "SegStorageType": "cloud_essd",
        "SegDiskPerformanceLevel": "pl1",
        "StorageSize": 50,
        "VPCId": {
          "Ref": "Vpc"
        },
        "SecurityIPList": "192.168.0.0/16",
        "DBInstanceDescription": {
          "Fn::Sub": "${CommonName}"
        },
        "PayType": "Postpaid",
        "DBInstanceCategory": "HighAvailability",
        "DBInstanceMode": "StorageElastic",
        "ProdType": "standard"
      }
    },
    "GPDBAccount": {
      "Type": "ALIYUN::GPDB::Account",
      "Properties": {
        "DBInstanceId": {
          "Fn::GetAtt": [
            "ADBPGInstance",
            "DBInstanceId"
          ]
        },
        "AccountPassword": {
          "Ref": "ADBPGPassword"
        },
        "AccountName": {
          "Ref": "ADBPGAccount"
        }
      }
    },
    "SaeNamespace": {
      "DependsOn": [
        "PostgreSQLInstance",
        "RedisInstance",
        "ADBPGInstance",
        "PluginNas",
        "APINas"
      ],
      "Type": "ALIYUN::SAE::Namespace",
      "Properties": {
        "NamespaceName": {
          "Ref": "NamespaceName"
        },
        "NamespaceId": {
          "Fn::Sub": "${ALIYUN::Region}:${NamespaceName}"
        },
        "VpcId": {
          "Ref": "Vpc"
        }
      }
    },
    "PostgreSQLInstance": {
      "Type": "ALIYUN::RDS::DBInstance",
      "Properties": {
        "ZoneId": {
          "Ref": "ZoneId1"
        },
        "SlaveZoneIds": [
          {
            "Ref": "ZoneId2"
          }
        ],
        "VpcId": {
          "Ref": "Vpc"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "DBInstanceClass": {
          "Ref": "DBInstanceClass"
        },
        "DBInstanceStorage": 50,
        "Engine": "PostgreSQL",
        "EngineVersion": "17.0",
        "SecurityIPList": "192.168.0.0/16",
        "Category": "HighAvailability",
        "MasterUserType": "Super",
        "MasterUserPassword": {
          "Ref": "PostgresSQLPassword"
        },
        "MasterUsername": {
          "Ref": "PostgresSQLUserName"
        },
        "DBInstanceStorageType": "cloud_essd"
      }
    },
    "DifyDataBase": {
      "Type": "ALIYUN::RDS::Database",
      "Properties": {
        "CharacterSetName": "utf8",
        "DBInstanceId": {
          "Fn::GetAtt": [
            "PostgreSQLInstance",
            "DBInstanceId"
          ]
        },
        "DBName": "dify"
      }
    },
    "DifySetUpDataBase": {
      "Type": "ALIYUN::RDS::Database",
      "DependsOn": "DifyDataBase",
      "Properties": {
        "CharacterSetName": "UTF8",
        "DBInstanceId": {
          "Fn::GetAtt": [
            "PostgreSQLInstance",
            "DBInstanceId"
          ]
        },
        "DBName": "dify_setups"
      }
    },
    "RdsAccountPrivilege": {
      "Type": "ALIYUN::RDS::AccountPrivilege",
      "DependsOn": "DifySetUpDataBase",
      "Properties": {
        "AccountPrivilege": "DBOwner",
        "DBInstanceId": {
          "Ref": "PostgreSQLInstance"
        },
        "DBName": "dify",
        "AccountName": {
          "Ref": "PostgresSQLUserName"
        }
      }
    },
    "NatGateway": {
      "Type": "ALIYUN::VPC::NatGateway",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "NatGatewayName": {
          "Fn::Sub": "${CommonName}-nat"
        },
        "InternetChargeType": "PayByLcu",
        "EipBindMode": "NAT"
      }
    },
    "Eip": {
      "Type": "ALIYUN::VPC::EIP",
      "Properties": {
        "DeletionProtection": false,
        "Isp": "BGP",
        "Bandwidth": 200,
        "InternetChargeType": "PayByTraffic"
      }
    },
    "EipAssociation": {
      "Type": "ALIYUN::VPC::EIPAssociation",
      "Properties": {
        "InstanceId": {
          "Ref": "NatGateway"
        },
        "AllocationId": {
          "Ref": "Eip"
        }
      }
    },
    "SNat": {
      "Type": "ALIYUN::VPC::SnatEntry",
      "DependsOn": "EipAssociation",
      "Properties": {
        "SnatTableId": {
          "Fn::GetAtt": [
            "NatGateway",
            "SNatTableId"
          ]
        },
        "SnatEntryName": {
          "Fn::Sub": "${CommonName}-snat"
        },
        "SourceVSwitchIds": [
          {
            "Ref": "VSwitch1"
          },
          {
            "Ref": "VSwitch2"
          }
        ],
        "SnatIp": {
          "Fn::GetAtt": [
            "Eip",
            "EipAddress"
          ]
        }
      }
    },
    "APINas": {
      "Type": "ALIYUN::NAS::FileSystem",
      "Properties": {
        "ProtocolType": "NFS",
        "FileSystemType": "standard",
        "DeletionForce": true,
        "StorageType": "Performance",
        "Description": {
          "Fn::Sub": "${CommonName}-API-NAS"
        }
      }
    },
    "APINasMountTarget": {
      "Type": "ALIYUN::NAS::MountTarget",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "NetworkType": "Vpc",
        "AccessGroupName": "DEFAULT_VPC_GROUP_NAME",
        "FileSystemId": {
          "Ref": "APINas"
        }
      }
    },
    "PluginNas": {
      "Type": "ALIYUN::NAS::FileSystem",
      "Properties": {
        "ProtocolType": "NFS",
        "FileSystemType": "standard",
        "DeletionForce": true,
        "StorageType": "Performance",
        "Description": {
          "Fn::Sub": "${CommonName}-Plugin-NAS"
        }
      }
    },
    "PluginNasMountTarget": {
      "Type": "ALIYUN::NAS::MountTarget",
      "Properties": {
        "VpcId": {
          "Ref": "Vpc"
        },
        "VSwitchId": {
          "Ref": "VSwitch1"
        },
        "NetworkType": "Vpc",
        "AccessGroupName": "DEFAULT_VPC_GROUP_NAME",
        "FileSystemId": {
          "Ref": "PluginNas"
        }
      }
    },
    "SuperOpsUser": {
      "Type": "ALIYUN::RAM::User",
      "Properties": {
        "UserName": {
          "Fn::Sub": "SuperOps-${ALIYUN::StackId}"
        },
        "Policies": [
          {
            "PolicyName": {
              "Fn::Join": [
                "-",
                [
                  "DifySuperOpsPolicy",
                  {
                    "Ref": "ALIYUN::StackName"
                  }
                ]
              ]
            },
            "PolicyDocument": {
              "Version": "1",
              "Statement": [
                {
                  "Effect": "Allow",
                  "Action": [
                    "gpdb:*"
                  ],
                  "Resource": [
                    "*"
                  ]
                }
              ]
            }
          }
        ],
        "PolicyAttachments": {
          "System": [
            "AliyunSTSAssumeRoleAccess",
            "AliyunRAMReadOnlyAccess"
          ]
        }
      }
    },
    "AccessKey": {
      "Type": "ALIYUN::RAM::AccessKey",
      "Properties": {
        "UserName": {
          "Fn::GetAtt": [
            "SuperOpsUser",
            "UserName"
          ]
        }
      }
    },
    "DifyApiConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "Data": {
          "MAIL_DEFAULT_SEND_FROM": "YOUR EMAIL FROM (eg: no-reply <no-reply@dify.ai>)",
          "SENTRY_PROFILES_SAMPLE_RATE": "1",
          "MARKETPLACE_ENABLED": "true",
          "DB_PORT": "5432",
          "VECTOR_STORE": "analyticdb",
          "LOG_LEVEL": "INFO",
          "DB_DATABASE": "dify",
          "REDIS_USE_SSL": "false",
          "STORAGE_LOCAL_PATH": "/app/api/storage",
          "SENTRY_TRACES_SAMPLE_RATE": "1",
          "MODE": "api",
          "WEB_API_CORS_ALLOW_ORIGINS": "*",
          "RESEND_API_URL": "https://api.resend.com",
          "ANALYTICDB_INSTANCE_ID": {
            "Fn::GetAtt": [
              "ADBPGInstance",
              "DBInstanceId"
            ]
          },
          "CODE_EXECUTION_ENDPOINT": "http://dify-sandbox:8194",
          "REDIS_HOST": {
            "Fn::GetAtt": [
              "RedisInstance",
              "ConnectionDomain"
            ]
          },
          "REDIS_DB": "0",
          "REDIS_PORT": "6379",
          "MAIL_TYPE": "resend",
          "ANALYTICDB_REGION_ID": {
            "Ref": "ALIYUN::Region"
          },
          "MIGRATION_ENABLED": "true",
          "CONSOLE_CORS_ALLOW_ORIGINS": "*",
          "PLUGIN_DAEMON_URL": "http://dify-plugin-daemon:5002",
          "STORAGE_TYPE": "local",
          "DB_HOST": {
            "Fn::GetAtt": [
              "PostgreSQLInstance",
              "InnerConnectionString"
            ]
          }
        },
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-api"
      }
    },
    "DifyApiSecret": {
      "Type": "ALIYUN::SAE::Secret",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "SecretName": "dify-api",
        "SecretType": "Opaque",
        "SecretData": {
          "ANALYTICDB_ACCOUNT": {
            "Ref": "ADBPGAccount"
          },
          "ANALYTICDB_KEY_ID": {
            "Fn::GetAtt": [
              "AccessKey",
              "AccessKeyId"
            ]
          },
          "ANALYTICDB_KEY_SECRET": {
            "Fn::GetAtt": [
              "AccessKey",
              "AccessKeySecret"
            ]
          },
          "ANALYTICDB_NAMESPACE": "difyns",
          "ANALYTICDB_NAMESPACE_PASSWORD": {
            "Ref": "ADBPGPassword"
          },
          "ANALYTICDB_PASSWORD": {
            "Ref": "ADBPGPassword"
          },
          "CELERY_BROKER_URL": {
            "Fn::Sub": [
              "redis://:${REDIS_PASSWORD}@${REDIS_HOST}:6379/0",
              {
                "REDIS_PASSWORD": {
                  "Ref": "RedisInstancePassword"
                },
                "REDIS_HOST": {
                  "Fn::GetAtt": [
                    "RedisInstance",
                    "ConnectionDomain"
                  ]
                }
              }
            ]
          },
          "CODE_EXECUTION_API_KEY": "dify-sandbox",
          "DB_PASSWORD": {
            "Ref": "PostgresSQLPassword"
          },
          "DB_USERNAME": {
            "Ref": "PostgresSQLUserName"
          },
          "INNER_API_KEY_FOR_PLUGIN": "QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1",
          "PLUGIN_DAEMON_KEY": "lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi",
          "REDIS_PASSWORD": {
            "Ref": "RedisInstancePassword"
          },
          "REDIS_USERNAME": "default",
          "RESEND_API_KEY": "xxxx",
          "SECRET_KEY": {
            "Fn::Base64Decode": {
              "Fn::Jq": [
                "First",
                ".[0].Output",
                {
                  "Fn::GetAtt": [
                    "RunCommand",
                    "InvokeResults"
                  ]
                }
              ]
            }
          }
        }
      }
    },
    "DifyWorkerConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "Data": {
          "MAIL_DEFAULT_SEND_FROM": "YOUR EMAIL FROM (eg: no-reply <no-reply@dify.ai>)",
          "SENTRY_PROFILES_SAMPLE_RATE": "1",
          "MARKETPLACE_ENABLED": "true",
          "DB_PORT": "5432",
          "VECTOR_STORE": "analyticdb",
          "LOG_LEVEL": "INFO",
          "DB_DATABASE": "dify",
          "REDIS_USE_SSL": "false",
          "STORAGE_LOCAL_PATH": "/app/api/storage",
          "SENTRY_TRACES_SAMPLE_RATE": "1",
          "MODE": "worker",
          "WEB_API_CORS_ALLOW_ORIGINS": "*",
          "RESEND_API_URL": "https://api.resend.com",
          "ANALYTICDB_INSTANCE_ID": {
            "Fn::GetAtt": [
              "ADBPGInstance",
              "DBInstanceId"
            ]
          },
          "REDIS_HOST": {
            "Fn::GetAtt": [
              "RedisInstance",
              "ConnectionDomain"
            ]
          },
          "REDIS_DB": "0",
          "REDIS_PORT": "6379",
          "MAIL_TYPE": "resend",
          "ANALYTICDB_REGION_ID": {
            "Ref": "ALIYUN::Region"
          },
          "MIGRATION_ENABLED": "true",
          "CONSOLE_CORS_ALLOW_ORIGINS": "*",
          "PLUGIN_DAEMON_URL": "http://dify-plugin-daemon:5002",
          "STORAGE_TYPE": "local",
          "DB_HOST": {
            "Fn::GetAtt": [
              "PostgreSQLInstance",
              "InnerConnectionString"
            ]
          }
        },
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-worker"
      }
    },
    "DifyWorkerSecret": {
      "Type": "ALIYUN::SAE::Secret",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "SecretName": "dify-worker",
        "SecretType": "Opaque",
        "SecretData": {
          "ANALYTICDB_ACCOUNT": {
            "Ref": "ADBPGAccount"
          },
          "ANALYTICDB_KEY_ID": {
            "Fn::GetAtt": [
              "AccessKey",
              "AccessKeyId"
            ]
          },
          "ANALYTICDB_KEY_SECRET": {
            "Fn::GetAtt": [
              "AccessKey",
              "AccessKeySecret"
            ]
          },
          "ANALYTICDB_NAMESPACE": "difyns",
          "ANALYTICDB_NAMESPACE_PASSWORD": {
            "Ref": "ADBPGPassword"
          },
          "ANALYTICDB_PASSWORD": {
            "Ref": "ADBPGPassword"
          },
          "CELERY_BROKER_URL": {
            "Fn::Sub": [
              "redis://:${REDIS_PASSWORD}@${REDIS_HOST}:6379/0",
              {
                "REDIS_PASSWORD": {
                  "Ref": "RedisInstancePassword"
                },
                "REDIS_HOST": {
                  "Fn::GetAtt": [
                    "RedisInstance",
                    "ConnectionDomain"
                  ]
                }
              }
            ]
          },
          "DB_PASSWORD": {
            "Ref": "PostgresSQLPassword"
          },
          "DB_USERNAME": {
            "Ref": "PostgresSQLUserName"
          },
          "INNER_API_KEY_FOR_PLUGIN": "QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1",
          "PLUGIN_DAEMON_KEY": "lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi",
          "REDIS_PASSWORD": {
            "Ref": "RedisInstancePassword"
          },
          "REDIS_USERNAME": "default",
          "RESEND_API_KEY": "xxxx",
          "SECRET_KEY": {
            "Fn::Base64Decode": {
              "Fn::Jq": [
                "First",
                ".[0].Output",
                {
                  "Fn::GetAtt": [
                    "RunCommand",
                    "InvokeResults"
                  ]
                }
              ]
            }
          }
        }
      }
    },
    "DifyPluginDaemonConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-plugin-daemon",
        "Data": {
          "SERVER_PORT": "5002",
          "PLUGIN_REMOTE_INSTALLING_HOST": "0.0.0.0",
          "REDIS_DB": "0",
          "REDIS_HOST": {
            "Fn::GetAtt": [
              "RedisInstance",
              "ConnectionDomain"
            ]
          },
          "MARKETPLACE_ENABLED": "true",
          "DB_PORT": "5432",
          "REDIS_USE_SSL": "false",
          "PLUGIN_WORKING_PATH": "/app/storage/cwd",
          "DB_HOST": {
            "Fn::GetAtt": [
              "PostgreSQLInstance",
              "InnerConnectionString"
            ]
          },
          "PIP_MIRROR_URL": "http://mirrors.aliyun.com/pypi/simple/",
          "REDIS_PORT": "6379",
          "PLUGIN_REMOTE_INSTALLING_PORT": "5003",
          "MAX_PLUGIN_PACKAGE_SIZE": "52428800",
          "DB_DATABASE": "dify_plugin",
          "DIFY_INNER_API_URL": "http://dify-api:5001"
        }
      }
    },
    "DifyPluginDaemonSecret": {
      "Type": "ALIYUN::SAE::Secret",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "SecretName": "dify-plugin-daemon",
        "SecretType": "Opaque",
        "SecretData": {
          "DB_PASSWORD": {
            "Ref": "PostgresSQLPassword"
          },
          "DB_USERNAME": {
            "Ref": "PostgresSQLUserName"
          },
          "DIFY_INNER_API_KEY": "QaHbTe77CtuXmsfyhR7+vRjI/+XbV1AaFy691iy+kGDv2Jvy0/eAh8Y1",
          "REDIS_PASSWORD": {
            "Ref": "RedisInstancePassword"
          },
          "REDIS_USERNAME": "default",
          "SERVER_KEY": "lYkiYYT6owG+71oLerGzA7GXCgOT++6ovaezWAjpCjf+Sjc3ZtU+qUEi"
        }
      }
    },
    "DifySandboxConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-sandbox",
        "Data": {
          "GIN_MODE": "release",
          "SANDBOX_PORT": "8194"
        }
      }
    },
    "DifySandboxSecret": {
      "Type": "ALIYUN::SAE::Secret",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "SecretName": "dify-sandbox",
        "SecretType": "Opaque",
        "SecretData": {
          "API_KEY": "dify-sandbox"
        }
      }
    },
    "DifyWebConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-web",
        "Data": {
          "MARKETPLACE_ENABLED": "true",
          "MARKETPLACE_URL": "https://marketplace.dify.ai",
          "MARKETPLACE_API_URL": "https://marketplace.dify.ai"
        }
      }
    },
    "DifyNginxConfigMap": {
      "Type": "ALIYUN::SAE::ConfigMap",
      "Properties": {
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Name": "dify-nginx",
        "Data": {
          "default.conf": "server {\n        listen 80;\n        server_name _;\n\n        location /console/api {\n          proxy_pass http://dify-api:5001;\n          include proxy.conf;\n        }\n\n        location /api {\n          proxy_pass http://dify-api:5001;\n          include proxy.conf;\n        }\n\n        location /v1 {\n          proxy_pass http://dify-api:5001;\n          include proxy.conf;\n        }\n\n        location /files {\n          proxy_pass http://dify-api:5001;\n          include proxy.conf;\n        }\n\n        location /explore {\n          proxy_pass http://dify-web:3000;\n          proxy_set_header Dify-Hook-Url $scheme://$host$request_uri;\n          include proxy.conf;\n        }\n\n        location /e/ {\n          proxy_pass http://dify-plugin-daemon:5002;\n          proxy_set_header Dify-Hook-Url $scheme://$host$request_uri;\n          include proxy.conf;\n        }\n\n        location / {\n          proxy_pass http://dify-web:3000;\n          include proxy.conf;\n        }\n    }",
          "nginx.conf": "user  nginx;\n    worker_processes  auto;\n    pid        /var/run/nginx.pid;\n\n\n    events {\n        worker_connections  1024;\n    }\n\n\n    http {\n        include       /etc/nginx/mime.types;\n        default_type  application/octet-stream;\n\n        log_format  main  '$remote_addr - $remote_user [$time_local] \"$request\" '\n                          '$status $body_bytes_sent \"$http_referer\" '\n                          '\"$http_user_agent\" \"$http_x_forwarded_for\"';\n\n        sendfile        on;\n        #tcp_nopush     on;\n\n        keepalive_timeout  65;\n\n        #gzip  on;\n        client_max_body_size 15M;\n\n        include /etc/nginx/conf.d/*.conf;\n    }",
          "proxy.conf": "proxy_set_header Host $host;\nproxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;\nproxy_set_header X-Forwarded-Proto $scheme;\nproxy_set_header X-Forwarded-Port $server_port;\nproxy_http_version 1.1;\nproxy_set_header Connection \"\";\nproxy_buffering off;\nproxy_read_timeout 3600s;\nproxy_send_timeout 3600s;"
        }
      }
    },
    "DifyApiApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifyApiConfigMap",
        "DifyApiSecret",
        "ADBPGInstance"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-api",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-api-v1.6.0"
        },
        "ProgrammingLanguage": "python",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "NasConfigs": {
          "Fn::Sub": [
            "[{\"mountDomain\":\"${MOUNT_DOMAIN}\",\"mountPath\":\"/app/api/storage\",\"nasId\":\"${NAS_ID}\",\"nasPath\":\"dify-api\",\"readOnly\":false,\"volumeName\":\"nas-1\"}]",
            {
              "MOUNT_DOMAIN": {
                "Fn::GetAtt": [
                  "APINasMountTarget",
                  "MountTargetDomain"
                ]
              },
              "NAS_ID": {
                "Fn::GetAtt": [
                  "APINas",
                  "FileSystemId"
                ]
              }
            }
          ]
        },
        "PvtzDiscoverySvc": {
          "Fn::Sub": [
            "{\"enable\":\"true\",\"namespaceId\":\"${REGION_ID}:${NAMESPACE}\",\"portAndProtocol\":{\"5001:TCP\":\"5001\"},\"portProtocols\":[],\"pvtzDiscoveryName\":\"${REGION_ID}-${USER_ID}\",\"serviceName\":\"dify-api.${NAMESPACE}\"}",
            {
              "NAMESPACE": {
                "Ref": "NamespaceName"
              },
              "USER_ID": {
                "Ref": "ALIYUN::TenantId"
              },
              "REGION_ID": {
                "Ref": "ALIYUN::Region"
              }
            }
          ]
        },
        "Envs": {
          "Fn::Sub": [
            "[{\"name\":\"APP_WEB_URL\"},{\"name\":\"FILES_URL\"},{\"name\":\"CODE_MAX_DEPTH\",\"value\":\"5\"},{\"name\":\"CODE_MAX_OBJECT_ARRAY_LENGTH\",\"value\":\"30\"},{\"name\":\"CHECK_UPDATE_URL\"},{\"name\":\"CODE_MAX_STRING_ARRAY_LENGTH\",\"value\":\"30\"},{\"name\":\"SERVICE_API_URL\"},{\"name\":\"sae-sys-secret-all-dify-api\",\"valueFrom\":{\"secretRef\":{\"secretId\":${SECRET_ID},\"key\":\"\"}}},{\"name\":\"CODE_MAX_PRECISION\",\"value\":\"20\"},{\"name\":\"CONSOLE_API_URL\"},{\"name\":\"TEMPLATE_TRANSFORM_MAX_LENGTH\",\"value\":\"80000\"},{\"name\":\"CODE_MAX_NUMBER\",\"value\":\"9223372036854775807\"},{\"name\":\"CODE_MAX_NUMBER_ARRAY_LENGTH\",\"value\":\"1000\"},{\"name\":\"CONSOLE_WEB_URL\"},{\"name\":\"CODE_MIN_NUMBER\",\"value\":\"-9223372036854775808\"},{\"name\":\"CODE_MAX_STRING_LENGTH\",\"value\":\"80000\"},{\"name\":\"SENTRY_DSN\"},{\"name\":\"CODE_EXECUTION_API_KEY\",\"valueFrom\":{\"secretRef\":{\"secretId\":${SANDBOX_SECRET_ID},\"key\":\"API_KEY\"}}},{\"name\":\"sae-sys-configmap-all-dify-api\",\"valueFrom\":{\"configMapRef\":{\"configMapId\":${CONFIGMAP_ID},\"key\":\"\"}}}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifyApiConfigMap",
                  "ConfigMapId"
                ]
              },
              "SECRET_ID": {
                "Fn::GetAtt": [
                  "DifyApiSecret",
                  "SecretId"
                ]
              },
              "SANDBOX_SECRET_ID": {
                "Fn::GetAtt": [
                  "DifySandboxSecret",
                  "SecretId"
                ]
              }
            }
          ]
        }
      }
    },
    "DifyWorkerApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifyWorkerConfigMap",
        "DifyWorkerSecret"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-worker",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-api-v1.6.0"
        },
        "ProgrammingLanguage": "python",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "NasConfigs": {
          "Fn::Sub": [
            "[{\"mountDomain\":\"${MOUNT_DOMAIN}\",\"mountPath\":\"/app/api/storage\",\"nasId\":\"${NAS_ID}\",\"nasPath\":\"dify-api\",\"readOnly\":false,\"volumeName\":\"nas-1\"}]",
            {
              "MOUNT_DOMAIN": {
                "Fn::GetAtt": [
                  "APINasMountTarget",
                  "MountTargetDomain"
                ]
              },
              "NAS_ID": {
                "Fn::GetAtt": [
                  "APINas",
                  "FileSystemId"
                ]
              }
            }
          ]
        },
        "Envs": {
          "Fn::Sub": [
            "[{\"name\":\"sae-sys-secret-all-dify-worker\",\"valueFrom\":{\"secretRef\":{\"secretId\":${SECRET_ID},\"key\":\"\"}}},{\"name\":\"sae-sys-configmap-all-dify-worker\",\"valueFrom\":{\"configMapRef\":{\"configMapId\":${CONFIGMAP_ID},\"key\":\"\"}}},{\"name\":\"CONSOLE_WEB_URL\"}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifyWorkerConfigMap",
                  "ConfigMapId"
                ]
              },
              "SECRET_ID": {
                "Fn::GetAtt": [
                  "DifyWorkerSecret",
                  "SecretId"
                ]
              }
            }
          ]
        }
      }
    },
    "DifyPluginDaemonApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifyPluginDaemonConfigMap",
        "DifyPluginDaemonSecret"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-plugin-daemon",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-plugin-daemon-v0.1.3-local"
        },
        "ProgrammingLanguage": "golang",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "NasConfigs": {
          "Fn::Sub": [
            "[{\"mountDomain\":\"${MOUNT_DOMAIN}\",\"mountPath\":\"/app/storage\",\"nasId\":\"${NAS_ID}\",\"nasPath\":\"dify-plugin-daemon\",\"readOnly\":false,\"volumeName\":\"nas-1\"}]",
            {
              "MOUNT_DOMAIN": {
                "Fn::GetAtt": [
                  "PluginNasMountTarget",
                  "MountTargetDomain"
                ]
              },
              "NAS_ID": {
                "Fn::GetAtt": [
                  "PluginNas",
                  "FileSystemId"
                ]
              }
            }
          ]
        },
        "PvtzDiscoverySvc": {
          "Fn::Sub": [
            "{\"enable\":\"true\",\"namespaceId\":\"${REGION_ID}:${NAMESPACE}\",\"portAndProtocol\":{\"5003:TCP\":\"5003\",\"5002:TCP\":\"5002\"},\"portProtocols\":[],\"pvtzDiscoveryName\":\"${REGION_ID}-${USER_ID}\",\"serviceName\":\"dify-plugin-daemon.${NAMESPACE}\"}",
            {
              "NAMESPACE": {
                "Ref": "NamespaceName"
              },
              "USER_ID": {
                "Ref": "ALIYUN::TenantId"
              },
              "REGION_ID": {
                "Ref": "ALIYUN::Region"
              }
            }
          ]
        },
        "Envs": {
          "Fn::Sub": [
            "[{\"name\":\"sae-sys-secret-all-dify-plugin-daemon\",\"valueFrom\":{\"secretRef\":{\"secretId\":${SECRET_ID},\"key\":\"\"}}},{\"name\":\"sae-sys-configmap-all-dify-plugin-daemon\",\"valueFrom\":{\"configMapRef\":{\"configMapId\":${CONFIGMAP_ID},\"key\":\"\"}}}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifyPluginDaemonConfigMap",
                  "ConfigMapId"
                ]
              },
              "SECRET_ID": {
                "Fn::GetAtt": [
                  "DifyPluginDaemonSecret",
                  "SecretId"
                ]
              }
            }
          ]
        }
      }
    },
    "DifySandboxApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifySandboxConfigMap",
        "DifySandboxSecret"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-sandbox",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-sandbox-v0.2.12"
        },
        "ProgrammingLanguage": "golang",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "PvtzDiscoverySvc": {
          "Fn::Sub": [
            "{\"enable\":\"true\",\"namespaceId\":\"${REGION_ID}:${NAMESPACE}\",\"portAndProtocol\":{\"8194:TCP\":\"8194\"},\"portProtocols\":[],\"pvtzDiscoveryName\":\"${REGION_ID}-${USER_ID}\",\"serviceName\":\"dify-sandbox.${NAMESPACE}\"}",
            {
              "NAMESPACE": {
                "Ref": "NamespaceName"
              },
              "USER_ID": {
                "Ref": "ALIYUN::TenantId"
              },
              "REGION_ID": {
                "Ref": "ALIYUN::Region"
              }
            }
          ]
        },
        "Envs": {
          "Fn::Sub": [
            "[{\"name\":\"sae-sys-secret-all-dify-sandbox\",\"valueFrom\":{\"secretRef\":{\"secretId\":${SECRET_ID},\"key\":\"\"}}},{\"name\":\"WORKER_TIMEOUT\",\"value\":\"15\"},{\"name\":\"sae-sys-configmap-all-dify-sandbox\",\"valueFrom\":{\"configMapRef\":{\"configMapId\":${CONFIGMAP_ID},\"key\":\"\"}}}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifySandboxConfigMap",
                  "ConfigMapId"
                ]
              },
              "SECRET_ID": {
                "Fn::GetAtt": [
                  "DifySandboxSecret",
                  "SecretId"
                ]
              }
            }
          ]
        }
      }
    },
    "DifyWebApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifyWebConfigMap"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-web",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:dify-web-v1.6.0"
        },
        "ProgrammingLanguage": "other",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "PvtzDiscoverySvc": {
          "Fn::Sub": [
            "{\"enable\":\"true\",\"namespaceId\":\"${REGION_ID}:${NAMESPACE}\",\"portAndProtocol\":{\"3000:TCP\":\"3000\"},\"portProtocols\":[],\"pvtzDiscoveryName\":\"${REGION_ID}-${USER_ID}\",\"serviceName\":\"dify-web.${NAMESPACE}\"}",
            {
              "NAMESPACE": {
                "Ref": "NamespaceName"
              },
              "USER_ID": {
                "Ref": "ALIYUN::TenantId"
              },
              "REGION_ID": {
                "Ref": "ALIYUN::Region"
              }
            }
          ]
        },
        "Envs": {
          "Fn::Sub": [
            "[{\"name\":\"sae-sys-configmap-all-dify-web\",\"valueFrom\":{\"configMapRef\":{\"configMapId\":${CONFIGMAP_ID},\"key\":\"\"}}},{\"name\":\"APP_API_URL\"},{\"name\":\"CONSOLE_API_URL\"},{\"name\":\"EDITION\",\"value\":\"SELF_HOSTED\"}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifyWebConfigMap",
                  "ConfigMapId"
                ]
              }
            }
          ]
        }
      }
    },
    "DifyNginxApp": {
      "DependsOn": [
        "SaeNamespace",
        "DifyNginxConfigMap"
      ],
      "Type": "ALIYUN::SAE::Application",
      "Properties": {
        "AppName": "dify-nginx",
        "SaeVersion": "v2",
        "AutoConfig": false,
        "VpcId": {
          "Ref": "Vpc"
        },
        "SecurityGroupId": {
          "Ref": "SecurityGroup"
        },
        "VSwitchId": {
          "Fn::Sub": [
            "${VSwitch1},${VSwitch2}",
            {
              "VSwitch1": {
                "Ref": "VSwitch1"
              },
              "VSwitch2": {
                "Ref": "VSwitch2"
              }
            }
          ]
        },
        "Replicas": 1,
        "NamespaceId": {
          "Ref": "SaeNamespace"
        },
        "Cpu": 1000,
        "Memory": 2048,
        "PackageType": "Image",
        "ImageUrl": {
          "Fn::Sub": "registry.${ALIYUN::Region}.aliyuncs.com/sae-serverless-demo/sae-demo:nginx-v1.23.4"
        },
        "ProgrammingLanguage": "other",
        "AppSource": "micro_service",
        "Timezone": "Asia/Shanghai",
        "ConfigMapMountDesc": {
          "Fn::Sub": [
            "[{\"MountPath\":\"/etc/nginx/conf.d/default.conf\",\"ConfigMapId\":${CONFIGMAP_ID},\"ConfigMapName\":\"dify-nginx\",\"Key\":\"default.conf\"},{\"MountPath\":\"/etc/nginx/nginx.conf\",\"ConfigMapId\":${CONFIGMAP_ID},\"ConfigMapName\":\"dify-nginx\",\"Key\":\"nginx.conf\"},{\"MountPath\":\"/etc/nginx/proxy.conf\",\"ConfigMapId\":${CONFIGMAP_ID},\"ConfigMapName\":\"dify-nginx\",\"Key\":\"proxy.conf\"}]",
            {
              "CONFIGMAP_ID": {
                "Fn::GetAtt": [
                  "DifyNginxConfigMap",
                  "ConfigMapId"
                ]
              }
            }
          ]
        }
      }
    },
    "InternetClb": {
      "Type": "ALIYUN::SLB::LoadBalancer",
      "Properties": {
        "LoadBalancerName": {
          "Ref": "ALIYUN::StackName"
        },
        "LoadBalancerSpec": "slb.s2.medium",
        "AddressType": "internet"
      }
    },
    "BackendAppBindClb": {
      "Type": "ALIYUN::SAE::SlbBinding",
      "DependsOn": [
        "DifyNginxApp",
        "InternetClb"
      ],
      "Properties": {
        "InternetSlbId": {
          "Fn::GetAtt": [
            "InternetClb",
            "LoadBalancerId"
          ]
        },
        "Internet": "[{\"port\": 80, \"targetPort\": 80, \"protocol\": \"TCP\"}]",
        "AppId": {
          "Fn::GetAtt": [
            "DifyNginxApp",
            "AppId"
          ]
        }
      }
    }
  },
  "Outputs": {
    "DifyAddress": {
      "Label": {
        "zh-cn": "Dify サービスアドレス。",
        "en": "Dify サービスアドレス"
      },
      "Description": {
        "zh-cn": "Dify サービスアドレス。",
        "en": "Dify プラットフォームのサービスアドレスです。"
      },
      "Value": {
        "Fn::Sub": [
          "http://${ServerAddress}:80",
          {
            "ServerAddress": {
              "Fn::GetAtt": [
                "InternetClb",
                "IpAddress"
              ]
            }
          }
        ]
      }
    },
    "PostgresName": {
      "Label": {
        "zh-cn": "Postgres ユーザー名",
        "en": "Postgres ユーザー名"
      },
      "Description": {
        "zh-cn": "AnalyticDB for PostgreSQL のユーザー名です。",
        "en": "AnalyticDB for PostgreSQL データベースのユーザー名です。"
      },
      "Value": {
        "Ref": "ADBPGAccount"
      }
    },
    "PostgresPassword": {
      "Label": {
        "zh-cn": "Postgres パスワード",
        "en": "Postgres パスワード"
      },
      "Description": {
        "zh-cn": "AnalyticDB for PostgreSQL のパスワードです。",
        "en": "AnalyticDB for PostgreSQL データベースのパスワードです。"
      },
      "NoEcho": true,
      "Value": {
        "Ref": "ADBPGPassword"
      }
    },
    "PostgresConnectionString": {
      "Label": {
        "zh-cn": "Postgres データベースアドレス",
        "en": "Postgres データベースアドレス"
      },
      "Description": {
        "zh-cn": "AnalyticDB for PostgreSQL の内部エンドポイントです。",
        "en": "AnalyticDB for PostgreSQL データベースの内部エンドポイントです。"
      },
      "Value": {
        "Fn::GetAtt": [
          "ADBPGInstance",
          "ConnectionString"
        ]
      }
    },
    "APINasFileSystemId": {
      "Label": {
        "zh-cn": "API NAS ファイルシステム",
        "en": "API NAS ファイルシステム"
      },
      "Description": {
        "zh-cn": "NAS ファイルシステムです。",
        "en": "API 用の NAS ファイルシステムの ID です。"
      },
      "Value": {
        "Ref": "APINas"
      }
    },
    "APINasMountTarget": {
      "Label": {
        "zh-cn": "API NAS マウントターゲット",
        "en": "API NAS マウントターゲット"
      },
      "Description": {
        "zh-cn": "NAS マウントターゲットです。",
        "en": "API 用の NAS ファイルシステムのマウントターゲットです。"
      },
      "Value": {
        "Ref": "APINasMountTarget"
      }
    },
    "PluginNasFileSystemId": {
      "Label": {
        "zh-cn": "プラグイン NAS ファイルシステム",
        "en": "プラグイン NAS ファイルシステム"
      },
      "Description": {
        "zh-cn": "NAS ファイルシステムです。",
        "en": "プラグイン用の NAS ファイルシステムの ID です。"
      },
      "Value": {
        "Ref": "PluginNas"
      }
    },
    "PluginNasMountTarget": {
      "Label": {
        "zh-cn": "プラグイン NAS マウントターゲット",
        "en": "プラグイン NAS マウントターゲット"
      },
      "Description": {
        "zh-cn": "NAS マウントターゲットです。",
        "en": "プラグイン用の NAS ファイルシステムのマウントターゲットです。"
      },
      "Value": {
        "Ref": "PluginNasMountTarget"
      }
    },
    "RedisConnectionString": {
      "Label": {
        "zh-cn": "Redis 接続アドレス",
        "en": "Redis 接続アドレス"
      },
      "Description": {
        "zh-cn": "Redis 接続アドレスです。",
        "en": "Redis インスタンスの接続エンドポイントです。"
      },
      "Value": {
        "Fn::GetAtt": [
          "RedisInstance",
          "ConnectionDomain"
        ]
      }
    },
    "RedisName": {
      "Label": {
        "zh-cn": "Redis ユーザー名",
        "en": "Redis ユーザー名"
      },
      "Description": {
        "zh-cn": "Redis ユーザー名です。",
        "en": "Redis インスタンスのユーザー名です。"
      },
      "Value": "default"
    },
    "RedisInstancePassword": {
      "Label": {
        "zh-cn": "Redis パスワード",
        "en": "Redis パスワード"
      },
      "Description": {
        "zh-cn": "Redis パスワードです。",
        "en": "Redis インスタンスのパスワードです。"
      },
      "NoEcho": true,
      "Value": {
        "Ref": "RedisInstancePassword"
      }
    },
    "PostgreSQLDBName": {
      "Label": {
        "zh-cn": "データベース名",
        "en": "データベース名"
      },
      "Description": {
        "zh-cn": "ApsaraDB RDS for PostgreSQL のデータベース名です。",
        "en": "ApsaraDB RDS for PostgreSQL インスタンスのデータベース名です。"
      },
      "Value": "dify"
    },
    "PostgreSQLConnectionString": {
      "Label": {
        "zh-cn": "RDS データベースアドレス",
        "en": "RDS データベースアドレス"
      },
      "Description": {
        "zh-cn": "ApsaraDB RDS for PostgreSQL の内部エンドポイントです。",
        "en": "ApsaraDB RDS for PostgreSQL インスタンスの内部エンドポイントです。"
      },
      "Value": {
        "Fn::GetAtt": [
          "PostgreSQLInstance",
          "InnerConnectionString"
        ]
      }
    },
    "PostgreSQLAccount": {
      "Label": {
        "zh-cn": "RDS ユーザー名",
        "en": "RDS ユーザー名"
      },
      "Description": {
        "zh-cn": "ApsaraDB RDS for PostgreSQL のユーザー名です。",
        "en": "ApsaraDB RDS for PostgreSQL インスタンスのユーザー名です。"
      },
      "Value": {
        "Ref": "PostgresSQLUserName"
      }
    },
    "PostgreSQLPassword": {
      "Label": {
        "zh-cn": "RDS パスワード",
        "en": "RDS パスワード"
      },
      "Description": {
        "zh-cn": "ApsaraDB RDS for PostgreSQL のパスワードです。",
        "en": "ApsaraDB RDS for PostgreSQL インスタンスのパスワードです。"
      },
      "NoEcho": true,
      "Value": {
        "Ref": "PostgresSQLPassword"
      }
    },
    "NameSpace": {
      "Label": {
        "zh-cn": "名前空間",
        "en": "名前空間"
      },
      "Description": {
        "zh-cn": "名前空間です。",
        "en": "SAE 名前空間の ID です。"
      },
      "Value": {
        "Fn::Sub": "${ALIYUN::Region}:${NamespaceName}"
      }
    },
    "Vpc": {
      "Label": {
        "zh-cn": "VPC ID",
        "en": "VPC ID"
      },
      "Description": {
        "zh-cn": "VPC ID です。",
        "en": "VPC の ID です。"
      },
      "Value": {
        "Ref": "Vpc"
      }
    },
    "Vsw": {
      "Label": {
        "zh-cn": "vSwitch ID",
        "en": "vSwitch ID"
      },
      "Description": {
        "zh-cn": "vSwitch ID です。",
        "en": "vSwitch の ID です。"
      },
      "Value": {
        "Ref": "VSwitch1"
      }
    },
    "Sg": {
      "Label": {
        "zh-cn": "セキュリティグループ ID",
        "en": "セキュリティグループ ID"
      },
      "Description": {
        "zh-cn": "セキュリティグループ ID です。",
        "en": "セキュリティグループの ID です。"
      },
      "Value": {
        "Ref": "SecurityGroup"
      }
    },
    "SecretKey": {
      "Label": {
        "zh-cn": "シークレットキー",
        "en": "シークレットキー"
      },
      "Description": {
        "zh-cn": "データベース内のセキュア署名および機密情報の暗号化に使用されます。",
        "en": "セキュア署名およびデータベース内の機密情報の暗号化に使用されるキーです。"
      },
      "NoEcho": true,
      "Value": {
        "Fn::Base64Decode": {
          "Fn::Jq": [
            "First",
            ".[0].Output",
            {
              "Fn::GetAtt": [
                "RunCommand",
                "InvokeResults"
              ]
            }
          ]
        }
      }
    },
    "dify-nginx": {
      "Label": {
        "zh-cn": "dify-nginx のアプリケーションアドレス",
        "en": "dify-nginx アプリケーションアドレス"
      },
      "Description": {
        "zh-cn": "dify-nginx のアプリケーションアドレスです。アプリケーションアクセス設定で、CLB アクセスに基づくパブリックエンドポイントを表示します。",
        "en": "dify-nginx アプリケーションのアドレスです。SLB アクセスのパブリックエンドポイントを表示するには、アプリケーションアクセス設定に移動します。"
      },
      "Value": {
        "Fn::Sub": "https://sae.console.alibabacloud.com/${ALIYUN::Region}/app-list/${DifyNginxApp.AppId}/micro-app/base?name=dify-nginx"
      }
    },
    "ECSInstanceId": {
      "Label": {
        "zh-cn": "ECS インスタンス ID",
        "en": "ECS インスタンス ID"
      },
      "Description": {
        "zh-cn": "ECS インスタンス ID です。このインスタンスは、サンプルの e コマースシステムをデプロイします。",
        "en": "ECS インスタンスの ID です。このインスタンスは、インストールスクリプトの実行に使用されます。"
      },
      "Value": {
        "Fn::Select": [
          0,
          {
            "Fn::GetAtt": [
              "EcsInstance",
              "InstanceIds"
            ]
          }
        ]
      }
    },
    "Console@DemoUrl": {
      "Description": {
        "zh-cn": "アプリケーションアクセスドメイン名。このソリューションの e コマースシステムのアドレスです。",
        "en": "ECS インスタンスのパブリック IP アドレスです。"
      },
      "Value": {
        "Fn::Sub": [
          "http://${PublicIp}",
          {
            "PublicIp": {
              "Fn::Select": [
                0,
                {
                  "Fn::GetAtt": [
                    "EcsInstance",
                    "PublicIps"
                  ]
                }
              ]
            }
          }
        ]
      }
    }
  },
  "Metadata": {
    "ALIYUN::ROS::Interface": {
      "Outputs": [
        "DifyAddress",
        "ECSInstanceId",
        "Console@DemoUrl",
        "dify-nginx",
        "NameSpace",
        "Vpc",
        "Vsw",
        "Sg",
        "PostgreSQLDBName",
        "PostgreSQLConnectionString",
        "PostgreSQLAccount",
        "PostgreSQLPassword",
        "PostgresName",
        "PostgresPassword",
        "PostgresConnectionString",
        "APINasFileSystemId",
        "APINasMountTarget",
        "PluginNasFileSystemId",
        "PluginNasMountTarget",
        "RedisConnectionString",
        "RedisName",
        "RedisInstancePassword",
        "SecretKey"
      ],
      "ParameterGroups": [
        {
          "Parameters": [
            "ZoneId1",
            "ZoneId2"
          ],
          "Label": {
            "default": {
              "en": "アベイラビリティーゾーン",
              "zh-cn": "アベイラビリティーゾーン"
            }
          }
        },
        {
          "Parameters": [
            "InstanceType",
            "InstancePassword"
          ],
          "Label": {
            "default": {
              "en": "Elastic Compute Service",
              "zh-cn": "Elastic Compute Service"
            }
          }
        },
        {
          "Parameters": [
            "RedisInstancePassword"
          ],
          "Label": {
            "default": {
              "en": "ApsaraDB for Redis",
              "zh-cn": "ApsaraDB for Redis"
            }
          }
        },
        {
          "Parameters": [
            "ADBPGAccount",
            "ADBPGPassword"
          ],
          "Label": {
            "default": {
              "en": "AnalyticDB for PostgreSQL",
              "zh-cn": "AnalyticDB for PostgreSQL"
            }
          }
        },
        {
          "Parameters": [
            "DBInstanceClass",
            "RdsDatabaseName",
            "PostgresSQLUserName",
            "PostgresSQLPassword"
          ],
          "Label": {
            "default": {
              "en": "ApsaraDB RDS for PostgreSQL",
              "zh-cn": "ApsaraDB RDS for PostgreSQL"
            }
          }
        },
        {
          "Parameters": [
            "NamespaceName"
          ],
          "Label": {
            "default": {
              "en": "Serverless App Engine",
              "zh-cn": "Serverless App Engine"
            }
          }
        }
      ],
      "TemplateTags": [
        "acs:technical-solution:internet-application-development:Deploy a production-ready Dify platform using Serverless App Engine-tech_solu_251"
      ],
      "Hidden": [
        "CommonName"
      ]
    }
  }
}

その他の例については、このリソースを含むパブリックテンプレートをご参照ください。