mirror of
https://github.com/larksuite/cli.git
synced 2026-07-07 00:55:53 +08:00
99 lines
3.4 KiB
Go
99 lines
3.4 KiB
Go
// Copyright (c) 2026 Lark Technologies Pte. Ltd.
|
||
// SPDX-License-Identifier: MIT
|
||
|
||
package apps
|
||
|
||
import (
|
||
"context"
|
||
"fmt"
|
||
"io"
|
||
"strings"
|
||
|
||
"github.com/larksuite/cli/shortcuts/common"
|
||
)
|
||
|
||
const dbEnvCreateHint = "verify --app-id is correct; if the app is already multi-env this is a conflict — inspect current tables with `lark-cli apps +db-table-list --app-id <app_id> --env dev`"
|
||
|
||
// AppsDBEnvCreate creates a DB environment for an app(拆分单库为 dev/online 多环境)。
|
||
//
|
||
// 调 POST /apps/{app_id}/db_dev_init。--env 指定要创建的环境,由调用方传入,目前只支持 dev。
|
||
// 不可逆:单库一旦拆成 dev/online 双库无法回退。Risk: high-risk-write 触发框架自动注入 --yes 确认关卡。
|
||
var AppsDBEnvCreate = common.Shortcut{
|
||
Service: appsService,
|
||
Command: "+db-env-create",
|
||
Description: "Create a DB environment (split single-env DB into dev/online, irreversible)",
|
||
Risk: "high-risk-write",
|
||
Tips: []string{
|
||
"Example: lark-cli apps +db-env-create --env dev --sync-data --app-id <app_id> --yes",
|
||
},
|
||
Scopes: []string{"spark:app:write"},
|
||
AuthTypes: []string{"user"},
|
||
HasFormat: true,
|
||
Flags: []common.Flag{
|
||
{Name: "app-id", Desc: "app id", Required: true},
|
||
{Name: "env", Default: "dev", Enum: []string{"dev"}, Desc: "environment to create (only dev supported for now)"},
|
||
{Name: "sync-data", Type: "bool", Desc: "copy existing online data into the new environment (default off)"},
|
||
},
|
||
Validate: func(ctx context.Context, rctx *common.RuntimeContext) error {
|
||
_, err := requireAppID(rctx.Str("app-id"))
|
||
return err
|
||
},
|
||
DryRun: func(ctx context.Context, rctx *common.RuntimeContext) *common.DryRunAPI {
|
||
appID, _ := requireAppID(rctx.Str("app-id"))
|
||
return common.NewDryRunAPI().
|
||
POST(appDbEnvCreatePath(appID)).
|
||
Desc("Create app DB environment").
|
||
Body(buildDBEnvCreateBody(rctx))
|
||
},
|
||
Execute: func(ctx context.Context, rctx *common.RuntimeContext) error {
|
||
appID, err := requireAppID(rctx.Str("app-id"))
|
||
if err != nil {
|
||
return err
|
||
}
|
||
data, err := rctx.CallAPITyped("POST", appDbEnvCreatePath(appID), nil, buildDBEnvCreateBody(rctx))
|
||
if err != nil {
|
||
return withAppsHint(err, dbEnvCreateHint)
|
||
}
|
||
rctx.OutFormat(data, nil, func(w io.Writer) {
|
||
renderEnvCreatePretty(w, data)
|
||
})
|
||
return nil
|
||
},
|
||
}
|
||
|
||
// buildDBEnvCreateBody 构造 db 环境创建 body:sync_data(bool)。
|
||
// --env 目前只支持 dev、服务端接口本身即创建 dev 环境,故不下发 env 字段(仅做 CLI 入参校验/前向兼容)。
|
||
func buildDBEnvCreateBody(rctx *common.RuntimeContext) map[string]interface{} {
|
||
return map[string]interface{}{
|
||
"sync_data": rctx.Bool("sync-data"),
|
||
}
|
||
}
|
||
|
||
// renderEnvCreatePretty 输出 4 行(pretty 模式):
|
||
//
|
||
// ✓ Multi-env initialized
|
||
// Environments: dev, online
|
||
// Data synced: yes
|
||
// Note: structure changes in dev now need to be released to online.
|
||
func renderEnvCreatePretty(w io.Writer, data map[string]interface{}) {
|
||
fmt.Fprintln(w, "✓ Multi-env initialized")
|
||
|
||
if envs, ok := data["environments"].([]interface{}); ok && len(envs) > 0 {
|
||
names := make([]string, 0, len(envs))
|
||
for _, e := range envs {
|
||
if s, ok := e.(string); ok {
|
||
names = append(names, s)
|
||
}
|
||
}
|
||
fmt.Fprintf(w, "Environments: %s\n", strings.Join(names, ", "))
|
||
}
|
||
|
||
synced := "no"
|
||
if ds, ok := data["data_synced"].(bool); ok && ds {
|
||
synced = "yes"
|
||
}
|
||
fmt.Fprintf(w, "Data synced: %s\n", synced)
|
||
|
||
fmt.Fprintln(w, "Note: structure changes in dev now need to be released to online.")
|
||
}
|