jatai 1.4.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/jatai/cli.rb +1 -1
- data/lib/jatai/commands/base.rb +22 -0
- data/lib/jatai/commands/database.rb +1 -1
- data/lib/jatai/commands/deploy.rb +22 -2
- data/lib/jatai/commands/init.rb +17 -13
- data/lib/jatai/commands/redis.rb +3 -3
- data/lib/jatai/commands/scale.rb +1 -1
- data/lib/jatai/commands/status.rb +10 -4
- data/lib/jatai/commands/up.rb +14 -3
- data/lib/jatai/version.rb +1 -1
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: cce550fef38fbddcb460eaa4d1d5e2631dfc8b43e33d035c607680e24ea6fee6
|
|
4
|
+
data.tar.gz: 75eaffc25c616af78578cd43b077ef62604852b90a4319d961bc50b4190f067e
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: b16035861874a14cadbafff211bfb8517d30652187a0d428e377b5e3fff59a2f98aa0a04588bb8819e98aa1114429ea856e89432c7ef40657a987019eb63f4dc
|
|
7
|
+
data.tar.gz: 8a50d74a29189c5f21f62c1d16a73030fad4031be48a70957c6350c35d4935b14f6e76fd8b0fdb54365cc2f4a667519699e534e66913855293dfa6ac61fb1b29
|
data/lib/jatai/cli.rb
CHANGED
|
@@ -88,7 +88,7 @@ module Jatai
|
|
|
88
88
|
|
|
89
89
|
desc "scale", "Escalar a aplicação"
|
|
90
90
|
option :replicas, type: :numeric, desc: "Número de réplicas"
|
|
91
|
-
option :preset, type: :string, desc: "
|
|
91
|
+
option :preset, type: :string, desc: "Hex (base, escala_1, escala_2)"
|
|
92
92
|
def scale
|
|
93
93
|
Commands::Scale.new.execute(options)
|
|
94
94
|
end
|
data/lib/jatai/commands/base.rb
CHANGED
|
@@ -48,6 +48,22 @@ module Jatai
|
|
|
48
48
|
abort pastel.red("Não autenticado. Execute `jatai login` primeiro.")
|
|
49
49
|
end
|
|
50
50
|
|
|
51
|
+
# Rótulo do cliente para a unidade computacional. O slug é interno
|
|
52
|
+
# (`base`, `escala_1`); quem lê a tela lê "Hex Escala 1" — o mesmo texto
|
|
53
|
+
# que o painel e a fatura mostram (AppsHelper#hex_label no servidor).
|
|
54
|
+
def hex_label(tier)
|
|
55
|
+
return "-" if tier.to_s.empty?
|
|
56
|
+
|
|
57
|
+
"Hex #{tier.to_s.tr("_", " ").capitalize}"
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
# O banco é um addon; `database_plan` vem nulo no app que não tem nenhum.
|
|
61
|
+
def pg_label(plan)
|
|
62
|
+
return "sem banco" if plan.to_s.empty?
|
|
63
|
+
|
|
64
|
+
"PG #{plan.to_s.tr("_", " ").capitalize}"
|
|
65
|
+
end
|
|
66
|
+
|
|
51
67
|
def success(msg)
|
|
52
68
|
puts pastel.green(msg)
|
|
53
69
|
end
|
|
@@ -59,6 +75,12 @@ module Jatai
|
|
|
59
75
|
def info(msg)
|
|
60
76
|
puts pastel.cyan(msg)
|
|
61
77
|
end
|
|
78
|
+
|
|
79
|
+
# Nem verde nem vermelho: o deploy parcial subiu o site e deixou processo
|
|
80
|
+
# para trás — chamar de sucesso ou de falha mentiria nas duas direções.
|
|
81
|
+
def warning(msg)
|
|
82
|
+
puts pastel.yellow(msg)
|
|
83
|
+
end
|
|
62
84
|
end
|
|
63
85
|
end
|
|
64
86
|
end
|
|
@@ -14,7 +14,7 @@ module Jatai
|
|
|
14
14
|
db = helper.api.get("/api/v1/apps/#{slug}/database")
|
|
15
15
|
|
|
16
16
|
puts helper.pastel.bold("Banco de dados de #{slug}")
|
|
17
|
-
puts "
|
|
17
|
+
puts " Modo: #{db["mode"]}"
|
|
18
18
|
puts " Host: #{db["host"]}"
|
|
19
19
|
puts " Porta: #{db["port"]}"
|
|
20
20
|
puts " Nome: #{db["name"]}"
|
|
@@ -44,12 +44,15 @@ module Jatai
|
|
|
44
44
|
|
|
45
45
|
status = ws.wait_for("DeployStatusChannel",
|
|
46
46
|
params: { deploy_id: deploy_id },
|
|
47
|
-
until_status: %w[live failed],
|
|
47
|
+
until_status: %w[live failed partially_live],
|
|
48
48
|
timeout: DEPLOY_TIMEOUT)
|
|
49
49
|
|
|
50
50
|
elapsed = (Time.now - started).to_i
|
|
51
|
-
|
|
51
|
+
case status
|
|
52
|
+
when "live"
|
|
52
53
|
success("\nDeploy concluído com sucesso! (#{elapsed}s)")
|
|
54
|
+
when "partially_live"
|
|
55
|
+
print_partial_summary(slug, deploy_id, elapsed)
|
|
53
56
|
else
|
|
54
57
|
error("\nDeploy falhou.")
|
|
55
58
|
end
|
|
@@ -74,6 +77,9 @@ module Jatai
|
|
|
74
77
|
when "live"
|
|
75
78
|
success("\nDeploy concluído com sucesso! (#{(Time.now - started).to_i}s)")
|
|
76
79
|
return
|
|
80
|
+
when "partially_live"
|
|
81
|
+
print_partial_summary(slug, deploy_id, (Time.now - started).to_i)
|
|
82
|
+
return
|
|
77
83
|
when "failed"
|
|
78
84
|
error("\nDeploy falhou.")
|
|
79
85
|
return
|
|
@@ -92,6 +98,20 @@ module Jatai
|
|
|
92
98
|
error("\nTimeout (#{(Time.now - started).to_i}s). Verifique com: jatai status")
|
|
93
99
|
end
|
|
94
100
|
|
|
101
|
+
# O deploy parcial é terminal: o site subiu, mas processo(s) declarados
|
|
102
|
+
# ficaram no release anterior. Sem este ramo a CLI penduraria 20min
|
|
103
|
+
# esperando um "live" que não vem.
|
|
104
|
+
def print_partial_summary(slug, deploy_id, elapsed)
|
|
105
|
+
warning("\nDeploy parcialmente concluído (#{elapsed}s)")
|
|
106
|
+
deploy = api.get("/api/v1/apps/#{slug}/deploys/#{deploy_id}")
|
|
107
|
+
Array(deploy["process_failures"]).each do |failure|
|
|
108
|
+
warning(" #{failure['name']}: #{failure['reason']}")
|
|
109
|
+
end
|
|
110
|
+
warning("O site está no ar na versão nova; os processos acima seguem na anterior.")
|
|
111
|
+
rescue StandardError
|
|
112
|
+
warning(" (detalhe indisponível — ver o deploy no painel)")
|
|
113
|
+
end
|
|
114
|
+
|
|
95
115
|
def status_label(status)
|
|
96
116
|
{ "queued" => "Na fila...", "building" => "Construindo imagem...",
|
|
97
117
|
"deploying" => "Deployando..." }[status] || status
|
data/lib/jatai/commands/init.rb
CHANGED
|
@@ -5,10 +5,17 @@ require "yaml"
|
|
|
5
5
|
module Jatai
|
|
6
6
|
module Commands
|
|
7
7
|
class Init < Base
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
8
|
+
# O Hex é a unidade computacional da plataforma — web e worker custam o
|
|
9
|
+
# mesmo degrau. Os preços aqui são os que a fatura cobra (Pricing::HEX):
|
|
10
|
+
# esta lista já anunciou "hobby R$ 19" enquanto a plataforma debitava
|
|
11
|
+
# R$ 29, e o cliente só descobria na primeira fatura.
|
|
12
|
+
#
|
|
13
|
+
# O `Hex Dedicado` (R$ 299) fica de fora: ele reserva 2Gi, 51% do nó k3s
|
|
14
|
+
# atual, e só fica vendável após o retype da VM.
|
|
15
|
+
HEX = {
|
|
16
|
+
"base" => "Hex Base — R$ 29/mês (1 grátis por time)",
|
|
17
|
+
"escala_1" => "Hex Escala 1 — R$ 59/mês",
|
|
18
|
+
"escala_2" => "Hex Escala 2 — R$ 119/mês"
|
|
12
19
|
}.freeze
|
|
13
20
|
|
|
14
21
|
# Região única por enquanto (Sudeste). Quando houver multi-região, volta a ser um prompt.
|
|
@@ -19,11 +26,6 @@ module Jatai
|
|
|
19
26
|
"static" => "Estático (HTML/CSS/JS, sem build)",
|
|
20
27
|
"docker" => "Docker (custom Dockerfile)"
|
|
21
28
|
}.freeze
|
|
22
|
-
DATABASE_TIERS = {
|
|
23
|
-
"mini" => "Mini — 512MB, 20 conexões (Grátis)",
|
|
24
|
-
"essencial" => "Essencial — 1GB, 50 conexões (R$ 19/mês)",
|
|
25
|
-
"padrao" => "Padrão — 5GB, 100 conexões (R$ 49/mês)"
|
|
26
|
-
}.freeze
|
|
27
29
|
|
|
28
30
|
def execute(options = {})
|
|
29
31
|
prompt = TTY::Prompt.new
|
|
@@ -45,9 +47,7 @@ module Jatai
|
|
|
45
47
|
end
|
|
46
48
|
|
|
47
49
|
name, slug = ask_name_and_slug(prompt)
|
|
48
|
-
preset = prompt.select("
|
|
49
|
-
# Sites estáticos não têm banco — não pergunta o tier.
|
|
50
|
-
db_tier = stack == "static" ? nil : prompt.select("Banco de dados:", DATABASE_TIERS.map { |k, v| { name: v, value: k } })
|
|
50
|
+
preset = prompt.select("Hex:", HEX.map { |k, v| { name: v, value: k } })
|
|
51
51
|
branch = detect_git_branch || "main"
|
|
52
52
|
|
|
53
53
|
# `app` é o IDENTIFICADOR (slug) usado nas URLs da API; `name` é o nome de
|
|
@@ -61,12 +61,16 @@ module Jatai
|
|
|
61
61
|
"region" => DEFAULT_REGION,
|
|
62
62
|
"branch" => branch
|
|
63
63
|
}
|
|
64
|
-
config["database_tier"] = db_tier if db_tier
|
|
65
64
|
|
|
66
65
|
File.write(config_path, YAML.dump(config))
|
|
67
66
|
success("Arquivo .jatai.yml criado com sucesso!")
|
|
68
67
|
info("Identificador: #{slug}") if slug != name
|
|
69
68
|
info("Branch: #{branch}")
|
|
69
|
+
# O banco deixou de ser uma pergunta: o Provision::Orchestrator dá um
|
|
70
|
+
# Postgres a todo app não-estático, e o PG Base do app de cortesia do
|
|
71
|
+
# time é isento. Escolher tier aqui só antecipava uma decisão que a aba
|
|
72
|
+
# "Banco de dados" refaz melhor, com o app já rodando.
|
|
73
|
+
info("Banco: PG Base provisionado automaticamente no `jatai up`.") unless stack == "static"
|
|
70
74
|
info("Execute `jatai up` para criar e fazer deploy do app.")
|
|
71
75
|
end
|
|
72
76
|
|
data/lib/jatai/commands/redis.rb
CHANGED
data/lib/jatai/commands/scale.rb
CHANGED
|
@@ -18,7 +18,7 @@ module Jatai
|
|
|
18
18
|
end
|
|
19
19
|
|
|
20
20
|
estimate = api.post("/api/v1/apps/#{slug}/scale/estimate", body: body)
|
|
21
|
-
info("
|
|
21
|
+
info("Hex: #{hex_label(estimate["preset"])}")
|
|
22
22
|
info("Réplicas: #{estimate["replicas"]}") if estimate["replicas"]
|
|
23
23
|
info("CPU: #{estimate["cpu_limit"]} | RAM: #{estimate["memory_limit"]}") if estimate["cpu_limit"]
|
|
24
24
|
info("Custo estimado: R$ #{estimate["monthly_cost"]}/mês")
|
|
@@ -14,10 +14,16 @@ module Jatai
|
|
|
14
14
|
puts " Stack: #{app["stack"]}"
|
|
15
15
|
puts " Status: #{colorize_status(app["status"])}"
|
|
16
16
|
puts " Região: #{app["region"]}"
|
|
17
|
-
puts "
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
17
|
+
puts " Hex: #{hex_label(app["preset"])}"
|
|
18
|
+
# `database_tier` deixou de existir: o tier do banco vive no plano do
|
|
19
|
+
# addon, e é `database_plan` que a API devolve. Enquanto a CLI lia a
|
|
20
|
+
# chave antiga, esta linha saía sempre vazia.
|
|
21
|
+
puts " Banco: #{pg_label(app["database_plan"])}"
|
|
22
|
+
# A URL vem da API (ClientAppSerializer#url), como no `jatai up`: montá-la
|
|
23
|
+
# aqui hardcodando usebrasa.com.br fazia a CLI anunciar a marca antiga
|
|
24
|
+
# enquanto a documentação e o dashboard já mostram jataiapp.com.br — e
|
|
25
|
+
# deixava a CLI errada de novo no próximo passo do rebrand.
|
|
26
|
+
puts " URL: #{app["url"]}" if app["url"]
|
|
21
27
|
|
|
22
28
|
if app["last_deploy"]
|
|
23
29
|
deploy = app["last_deploy"]
|
data/lib/jatai/commands/up.rb
CHANGED
|
@@ -95,7 +95,6 @@ module Jatai
|
|
|
95
95
|
name: app_name, stack: config[:stack], preset: config[:preset],
|
|
96
96
|
region: config[:region], repo_url: detect_git_remote, repo_branch: config[:branch]
|
|
97
97
|
}
|
|
98
|
-
app_params[:database_tier] = config[:database_tier] if config[:database_tier]
|
|
99
98
|
app_params[:release_command] = config.dig(:release, :command) if config.dig(:release, :command)
|
|
100
99
|
api.post("/api/v1/apps", body: { app: app_params })
|
|
101
100
|
end
|
|
@@ -167,11 +166,14 @@ module Jatai
|
|
|
167
166
|
|
|
168
167
|
status = ws.wait_for("DeployStatusChannel",
|
|
169
168
|
params: { deploy_id: deploy_id },
|
|
170
|
-
until_status: %w[live failed],
|
|
169
|
+
until_status: %w[live failed partially_live],
|
|
171
170
|
timeout: DEPLOY_TIMEOUT)
|
|
172
171
|
|
|
173
|
-
|
|
172
|
+
case status
|
|
173
|
+
when "live"
|
|
174
174
|
true
|
|
175
|
+
when "partially_live"
|
|
176
|
+
partial_deploy_notice
|
|
175
177
|
else
|
|
176
178
|
error("\nDeploy falhou.")
|
|
177
179
|
false
|
|
@@ -188,6 +190,14 @@ module Jatai
|
|
|
188
190
|
Jatai::Websocket::CableClient.new.tap(&:connect!)
|
|
189
191
|
end
|
|
190
192
|
|
|
193
|
+
# `true` porque, para o `up`, o app ESTÁ no ar: o fluxo seguinte (mostrar
|
|
194
|
+
# a URL) continua válido. O que ficou fora do release sai no painel e no
|
|
195
|
+
# `jatai deploy`, que tem o resumo completo.
|
|
196
|
+
def partial_deploy_notice
|
|
197
|
+
warning("\nDeploy parcialmente concluído — processo(s) fora do release; ver o deploy no painel.")
|
|
198
|
+
true
|
|
199
|
+
end
|
|
200
|
+
|
|
191
201
|
def warn_fallback(err)
|
|
192
202
|
$stderr.puts "\n [WebSocket indisponível: #{err.message}. Usando polling...]"
|
|
193
203
|
end
|
|
@@ -227,6 +237,7 @@ module Jatai
|
|
|
227
237
|
DEPLOY_MAX_POLLS.times do |i|
|
|
228
238
|
deploy = api.get("/api/v1/apps/#{slug}/deploys/#{deploy_id}")
|
|
229
239
|
return true if deploy["status"] == "live"
|
|
240
|
+
return partial_deploy_notice if deploy["status"] == "partially_live"
|
|
230
241
|
if deploy["status"] == "failed"
|
|
231
242
|
error("\nDeploy falhou.")
|
|
232
243
|
return false
|
data/lib/jatai/version.rb
CHANGED