@govuk-pay/cli 0.0.55 → 0.0.56
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.
- package/package.json +1 -1
- package/resources/legacy-ruby-cli/README.md +5 -74
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/doctor.rb +0 -85
- package/resources/legacy-ruby-cli/lib/pay_cli/config.rb +1 -23
- package/resources/legacy-ruby-cli/lib/pay_cli/entry_point.rb +4 -21
- package/resources/legacy-ruby-cli/.rspec +0 -1
- package/resources/legacy-ruby-cli/config/generate-secrets.yml +0 -9
- package/resources/legacy-ruby-cli/config/secrets.yml +0 -682
- package/resources/legacy-ruby-cli/config/service_secrets.yml +0 -203
- package/resources/legacy-ruby-cli/lib/pay_cli/aws/services.rb +0 -47
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/aws.rb +0 -29
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/browse.rb +0 -31
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/app_client.rb +0 -216
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/config.rb +0 -142
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/config.yaml +0 -198
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/docker.rb +0 -66
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/all.yaml +0 -847
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/card.yaml +0 -491
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/custom.yaml +0 -71
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/docker-compose.erb +0 -395
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/end-to-end.erb +0 -30
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/java.yaml +0 -456
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/localstack/init-aws.sh +0 -70
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/naxsi/readme.md +0 -1
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/postgres/docker-entrypoint-initdb.d/make_payments_databases.sql +0 -26
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/adminusers.env +0 -49
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/cardid.env +0 -2
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/connector.env +0 -70
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/demo-service.env +0 -10
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/egress/squid.conf +0 -47
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/frontend.env +0 -12
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/java_app.env +0 -1
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ledger.env +0 -7
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/products-ui.env +0 -14
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/products.env +0 -25
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/publicapi.env +0 -13
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/publicauth.env +0 -13
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/selfservice.env +0 -21
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/certs/frontend-proxy.crt +0 -18
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/certs/products-ui-proxy.crt +0 -20
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/certs/publicapi-proxy.crt +0 -18
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/certs/selfservice-proxy.crt +0 -20
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/certs/stubs-proxy.crt +0 -18
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/keys/frontend-proxy.key +0 -28
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/keys/products-ui-proxy.key +0 -28
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/keys/publicapi-proxy.key +0 -28
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/keys/selfservice-proxy.key +0 -28
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/keys/stubs-proxy.key +0 -28
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/ssl/make-selfsigned.sh +0 -2
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/stubs.env +0 -12
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/toolbox.env +0 -5
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/services/webhooks.env +0 -9
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/files/toolbox.yaml +0 -473
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local/image_extractor.rb +0 -20
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/local.rb +0 -451
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/secrets.rb +0 -114
- package/resources/legacy-ruby-cli/lib/pay_cli/commands/tunnel/services.yml +0 -49
- package/resources/legacy-ruby-cli/lib/pay_cli/naming.rb +0 -6
- package/resources/legacy-ruby-cli/lib/pay_cli/secrets.rb +0 -281
- package/resources/legacy-ruby-cli/package-lock.json +0 -6
- package/resources/legacy-ruby-cli/rds_access/connect.sh +0 -175
- package/resources/legacy-ruby-cli/spec/.rubocop.yml +0 -2
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.complex +0 -34
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.complex_differing_froms +0 -33
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.no_from +0 -3
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.simple +0 -5
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.simple_no_tag +0 -5
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.with_sha +0 -5
- package/resources/legacy-ruby-cli/spec/fixtures/dockerfile_examples/Dockerfile.with_sha_no_tag +0 -5
- package/resources/legacy-ruby-cli/spec/lib/pay_cli/commands/local/image_extractor_spec.rb +0 -55
- package/resources/legacy-ruby-cli/spec/naming_spec.rb +0 -19
- package/resources/legacy-ruby-cli/spec/spec_helper.rb +0 -106
|
@@ -1,451 +0,0 @@
|
|
|
1
|
-
require 'English'
|
|
2
|
-
require 'erb'
|
|
3
|
-
require 'yaml'
|
|
4
|
-
require 'rest-client'
|
|
5
|
-
require 'rotp'
|
|
6
|
-
require 'base32'
|
|
7
|
-
require 'securerandom'
|
|
8
|
-
require 'active_support'
|
|
9
|
-
require 'active_support/core_ext'
|
|
10
|
-
require 'digest'
|
|
11
|
-
require 'mkmf'
|
|
12
|
-
require 'pathname'
|
|
13
|
-
|
|
14
|
-
REQUIRES_COMPILATION = %w[frontend products-ui selfservice toolbox].freeze
|
|
15
|
-
|
|
16
|
-
class PayCLI::Commands::Local < Thor
|
|
17
|
-
CLUSTERS=['admin', 'card', 'paymentlinks', 'webhooks', 'endtoend', 'java', 'toolbox']
|
|
18
|
-
|
|
19
|
-
warn "🏠 Local Pay for local people\n\n"
|
|
20
|
-
map "up" => :launch
|
|
21
|
-
desc 'launch | up [--cluster <cluster>] [--local <app>] [--proxy] [--apps] [--rebuild] [--with-egress-proxy]',
|
|
22
|
-
'Launch a predefined cluster, or a user specified list of apps.' \
|
|
23
|
-
' Specify a list of apps that should use your locally checked out code using --local'
|
|
24
|
-
option :local, :type => :array, :default => []
|
|
25
|
-
option :proxy, :type => :boolean, :default => false
|
|
26
|
-
option :cluster, :enum => CLUSTERS
|
|
27
|
-
option :apps, :type => :array
|
|
28
|
-
option :rebuild, :type => :boolean, :default => true
|
|
29
|
-
option :experimental, :type => :boolean, :default => false
|
|
30
|
-
option :with_egress_proxy, :type => :boolean, :default => false
|
|
31
|
-
option :mount_local_node_apps, :type => :boolean, :default => false, :desc => "Mount your apps directory in your \$WORKSPACE folder into the container, this makes local changes take effect immedaitely in the container via nodemon"
|
|
32
|
-
option :pull, :type => :boolean, :default => true, :desc => "Pull the latest versions of containers prior to launching, override with --no-pull"
|
|
33
|
-
|
|
34
|
-
def launch()
|
|
35
|
-
all = options[:experimental] ? Config::all : Config.boring
|
|
36
|
-
if options[:cluster]
|
|
37
|
-
cluster = options[:cluster]
|
|
38
|
-
warn "🚀 Launching #{cluster} cluster 🚀\n\n"
|
|
39
|
-
apps = Config::cluster cluster, all
|
|
40
|
-
elsif options[:apps]
|
|
41
|
-
cluster = 'custom'
|
|
42
|
-
warn "🚀 Launching #{options[:apps]} 🚀\n\n"
|
|
43
|
-
apps = Config::filter options[:apps], all
|
|
44
|
-
else
|
|
45
|
-
cluster = 'all'
|
|
46
|
-
apps = all
|
|
47
|
-
end
|
|
48
|
-
|
|
49
|
-
@egress_proxy_required = options[:with_egress_proxy]
|
|
50
|
-
|
|
51
|
-
@node_apps = Config::node apps
|
|
52
|
-
@java_apps = Config::java apps
|
|
53
|
-
|
|
54
|
-
local_app_names = options.fetch :local
|
|
55
|
-
@local_node_apps = Config.local local_app_names, @node_apps
|
|
56
|
-
@local_java_apps = Config.local local_app_names, @java_apps
|
|
57
|
-
@remote_node_apps = Config.remote local_app_names, @node_apps
|
|
58
|
-
@remote_java_apps = Config.remote local_app_names, @java_apps
|
|
59
|
-
|
|
60
|
-
@mount_local_node_apps = options[:mount_local_node_apps]
|
|
61
|
-
|
|
62
|
-
@dbs = Config.db_configs Config.has_db apps
|
|
63
|
-
@queue_apps = Config.has_queue apps
|
|
64
|
-
@sns_topic_apps = Config.has_sns_topics apps
|
|
65
|
-
|
|
66
|
-
# Force restart of localstack (which mocks aws services)
|
|
67
|
-
Docker.remove('localstack') if Config.uses_localstack(apps)
|
|
68
|
-
|
|
69
|
-
@proxies = if options[:proxy] then Config::proxy_configs Config::has_proxy apps else [] end
|
|
70
|
-
|
|
71
|
-
@no_proxy_env_var = [
|
|
72
|
-
"localhost",
|
|
73
|
-
"127.0.0.1",
|
|
74
|
-
"172.18.0.253",
|
|
75
|
-
"localstack",
|
|
76
|
-
"redis",
|
|
77
|
-
Config.all.map { |app| app[:name] },
|
|
78
|
-
@dbs.map { |app| app[:name] },
|
|
79
|
-
@proxies.map { |app| app[:name] },
|
|
80
|
-
].flatten!.join(",")
|
|
81
|
-
|
|
82
|
-
@localstack_init_file = File.realpath(
|
|
83
|
-
File.join(__dir__, 'local', 'files', 'localstack', 'init-aws.sh')
|
|
84
|
-
)
|
|
85
|
-
|
|
86
|
-
if options[:rebuild]
|
|
87
|
-
check_for_workspace_env
|
|
88
|
-
|
|
89
|
-
threads = []
|
|
90
|
-
(@local_java_apps + @local_node_apps).each do |app|
|
|
91
|
-
check_for_local_repo("pay-#{app[:name]}")
|
|
92
|
-
|
|
93
|
-
threads << Thread.new do
|
|
94
|
-
ws_dir = Pathname.new(ENV['WORKSPACE']).join("pay-#{app[:name]}")
|
|
95
|
-
|
|
96
|
-
if RUBY_PLATFORM.include? 'arm64'
|
|
97
|
-
arm_dockerfile = ws_dir.join('m1', 'arm64.Dockerfile')
|
|
98
|
-
dockerfile = arm_dockerfile.exist? ? arm_dockerfile : ws_dir.join('Dockerfile')
|
|
99
|
-
|
|
100
|
-
warn "🐋 generating arm64 governmentdigitalservice/pay-#{app[:name]}:local from #{dockerfile}"
|
|
101
|
-
`(cd #{ws_dir} && docker build -q . -f #{dockerfile} --load -t governmentdigitalservice/pay-#{app[:name]}:local)`
|
|
102
|
-
else
|
|
103
|
-
warn "🐋 generating governmentdigitalservice/pay-#{app[:name]}:local"
|
|
104
|
-
`(cd #{ws_dir} && docker build -q -t governmentdigitalservice/pay-#{app[:name]}:local .)`
|
|
105
|
-
end
|
|
106
|
-
|
|
107
|
-
report_status! $CHILD_STATUS, app[:name], 'loading image for'
|
|
108
|
-
end
|
|
109
|
-
end
|
|
110
|
-
|
|
111
|
-
threads.each(&:join)
|
|
112
|
-
end
|
|
113
|
-
|
|
114
|
-
Docker::write_compose_file cluster, binding
|
|
115
|
-
|
|
116
|
-
if cluster.include? 'endtoend'
|
|
117
|
-
warn "💁 Here are the endtoend environment variables\n\n#{Config::write_end_to_end_config binding}\n\n"
|
|
118
|
-
end
|
|
119
|
-
|
|
120
|
-
puts Docker::pull cluster if options[:pull]
|
|
121
|
-
puts Docker::up cluster
|
|
122
|
-
|
|
123
|
-
AppClient::wait_for_apps apps
|
|
124
|
-
AppClient::report_state apps
|
|
125
|
-
end
|
|
126
|
-
|
|
127
|
-
desc 'down [--cluster <cluster>]',
|
|
128
|
-
'Bring down a cluster'
|
|
129
|
-
option :cluster, :enum => CLUSTERS
|
|
130
|
-
def down()
|
|
131
|
-
cluster = options.fetch(:cluster, 'all')
|
|
132
|
-
unless Docker::compose_file_exists_for_cluster?(cluster)
|
|
133
|
-
$stderr.puts "Error: cluster #{cluster} has not been launched, its docker-compose file was not found"
|
|
134
|
-
return
|
|
135
|
-
end
|
|
136
|
-
|
|
137
|
-
warn "🛬 bringing down #{cluster} cluster"
|
|
138
|
-
puts Docker::down cluster
|
|
139
|
-
puts Docker::cleanup_old_network
|
|
140
|
-
end
|
|
141
|
-
|
|
142
|
-
desc 'healthcheck <cluster>',
|
|
143
|
-
"Healthcheck"
|
|
144
|
-
|
|
145
|
-
def healthcheck(cluster)
|
|
146
|
-
AppClient::report_state Config::cluster cluster, Config::all
|
|
147
|
-
end
|
|
148
|
-
|
|
149
|
-
desc 'nuke',
|
|
150
|
-
"Kill and completely destroy all containers previously started by pay local"
|
|
151
|
-
|
|
152
|
-
def nuke
|
|
153
|
-
warn "💥 Nuking all containers previously started by pay local 💥"
|
|
154
|
-
warn "🚨 WARNING - this deletes the database files too, stop it now or accept your fate 🚨"
|
|
155
|
-
|
|
156
|
-
Config::all.each do |app|
|
|
157
|
-
Docker::remove("#{app[:name]}")
|
|
158
|
-
Docker::remove("#{app[:name]}-proxy") if app[:proxy]
|
|
159
|
-
Docker::remove("#{app[:name]}_db") if app[:db]
|
|
160
|
-
end
|
|
161
|
-
Docker::remove('localstack')
|
|
162
|
-
Docker::remove('localRedis')
|
|
163
|
-
Docker::remove('egress')
|
|
164
|
-
Docker::remove_network
|
|
165
|
-
end
|
|
166
|
-
|
|
167
|
-
desc 'restart [--cluster <cluster>] <app>',
|
|
168
|
-
'Restart a container and waits for it to be healthy.'
|
|
169
|
-
option :cluster, :enum => CLUSTERS
|
|
170
|
-
def restart(app_name)
|
|
171
|
-
cluster = options.fetch(:cluster, 'all')
|
|
172
|
-
unless Docker::compose_file_exists_for_cluster?(cluster)
|
|
173
|
-
$stderr.puts "error: cluster #{cluster} has not been launched, its docker-compose file was not found"
|
|
174
|
-
return
|
|
175
|
-
end
|
|
176
|
-
|
|
177
|
-
Docker::restart(cluster, app_name)
|
|
178
|
-
app = Config::app_by_name(app_name)
|
|
179
|
-
AppClient::wait_for_apps(app)
|
|
180
|
-
AppClient::report_state(app)
|
|
181
|
-
end
|
|
182
|
-
|
|
183
|
-
desc 'paymentlink',
|
|
184
|
-
'Create a new payment link, requires an api token.'
|
|
185
|
-
option :api_key, :required => true
|
|
186
|
-
|
|
187
|
-
def paymentlink
|
|
188
|
-
product = AppClient::create_payment_link options.fetch :api_key
|
|
189
|
-
|
|
190
|
-
links = {}
|
|
191
|
-
product["_links"].each {|link| links[link["rel"]] = link["href"]}
|
|
192
|
-
|
|
193
|
-
warn links
|
|
194
|
-
`open #{links["pay"]}`
|
|
195
|
-
end
|
|
196
|
-
|
|
197
|
-
map :populate => :user
|
|
198
|
-
desc 'user',
|
|
199
|
-
'create a local user'
|
|
200
|
-
option :create_payments, :type => :boolean, :default => true
|
|
201
|
-
|
|
202
|
-
def user
|
|
203
|
-
warn '🏗️🏗 Constructing useful things for you...'
|
|
204
|
-
gateway_account_ids = []
|
|
205
|
-
|
|
206
|
-
service = AppClient::create_service()
|
|
207
|
-
service_id = service.fetch('external_id')
|
|
208
|
-
|
|
209
|
-
if AppClient::is_app_up?('connector')
|
|
210
|
-
warn '💳 Card connector is up, creating card gateway account and API Token'
|
|
211
|
-
card_account = AppClient::create_account(service_id)
|
|
212
|
-
card_gateway_account_id = extract_gateway_account_id(card_account)
|
|
213
|
-
card_token = AppClient::create_token(card_gateway_account_id)
|
|
214
|
-
gateway_account_ids.push(card_gateway_account_id)
|
|
215
|
-
if options[:create_payments] and AppClient::is_app_up? 'publicapi'
|
|
216
|
-
warn '💸 Creating payments in card sandbox gateway account'
|
|
217
|
-
(1..11).to_a.each do
|
|
218
|
-
sleep 1
|
|
219
|
-
(1..5).to_a.each {AppClient::create_payment card_token}
|
|
220
|
-
end
|
|
221
|
-
end
|
|
222
|
-
end
|
|
223
|
-
|
|
224
|
-
warn '🤓 Creating admin user for service'
|
|
225
|
-
user = AppClient::create_user(gateway_account_ids: gateway_account_ids)
|
|
226
|
-
warn '😎 Creating read only user for service'
|
|
227
|
-
AppClient::create_user(gateway_account_ids: gateway_account_ids, role_name: 'view-only')
|
|
228
|
-
|
|
229
|
-
otp_key = user['otp_key']
|
|
230
|
-
|
|
231
|
-
warn TTY::Table.new([
|
|
232
|
-
['📧 Email', user[:email]],
|
|
233
|
-
['🛂 Password', user[:password]],
|
|
234
|
-
['🔑 OTP key', otp_key],
|
|
235
|
-
['📱 OTP token', generate_otp_token(otp_key)],
|
|
236
|
-
['💁 Service ID', service_id],
|
|
237
|
-
['💳 Card gateway account ID', card_gateway_account_id],
|
|
238
|
-
['🎫 Card API token', card_token],
|
|
239
|
-
]).render(:unicode, padding: 1, multiline: true)
|
|
240
|
-
|
|
241
|
-
pbcopy user[:email]
|
|
242
|
-
|
|
243
|
-
if AppClient::is_proxy_up? 'selfservice'
|
|
244
|
-
browse 'selfservice', true
|
|
245
|
-
elsif AppClient::is_app_up? 'selfservice'
|
|
246
|
-
browse 'selfservice'
|
|
247
|
-
end
|
|
248
|
-
end
|
|
249
|
-
|
|
250
|
-
desc 'account',
|
|
251
|
-
'create a local gateway account'
|
|
252
|
-
option :service_id
|
|
253
|
-
|
|
254
|
-
def account
|
|
255
|
-
service_id = options.fetch(:service_id, AppClient::create_service().fetch('external_id'))
|
|
256
|
-
warn "#{AppClient::create_account(service_id).to_json}"
|
|
257
|
-
end
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
desc 'token',
|
|
261
|
-
'create a token'
|
|
262
|
-
option :gateway_account_id
|
|
263
|
-
|
|
264
|
-
def token
|
|
265
|
-
service = AppClient::create_service()
|
|
266
|
-
service_id = service.fetch('external_id')
|
|
267
|
-
gateway_account_id = options.fetch(
|
|
268
|
-
:gateway_account_id,
|
|
269
|
-
extract_gateway_account_id( AppClient::create_account service_id)
|
|
270
|
-
)
|
|
271
|
-
newToken = AppClient::create_token gateway_account_id
|
|
272
|
-
warn newToken
|
|
273
|
-
pbcopy newToken
|
|
274
|
-
end
|
|
275
|
-
|
|
276
|
-
desc 'payment',
|
|
277
|
-
'create a payment'
|
|
278
|
-
option :api_key
|
|
279
|
-
option :email_collection_mode, :default => 'MANDATORY', :enum => ['MANDATORY', 'OPTIONAL', 'OFF']
|
|
280
|
-
|
|
281
|
-
def payment
|
|
282
|
-
api_token = options.fetch(:api_key, false)
|
|
283
|
-
|
|
284
|
-
unless api_token
|
|
285
|
-
warn "👔 Creating gateway account and service"
|
|
286
|
-
|
|
287
|
-
email_settings = { email_collection_mode: "#{options.fetch(:email_collection_mode)}" }
|
|
288
|
-
|
|
289
|
-
service = AppClient::create_service()
|
|
290
|
-
service_id = service.fetch('external_id')
|
|
291
|
-
|
|
292
|
-
gateway_account_id = extract_gateway_account_id(AppClient::create_account(service_id, email_settings))
|
|
293
|
-
|
|
294
|
-
api_token = AppClient::create_token(gateway_account_id)
|
|
295
|
-
|
|
296
|
-
warn TTY::Table.new([
|
|
297
|
-
['🆔 Gateway account ID', gateway_account_id],
|
|
298
|
-
['💁 Service ID', service_id]
|
|
299
|
-
]).render(:unicode, padding: 1, multiline: true)
|
|
300
|
-
end
|
|
301
|
-
|
|
302
|
-
warn "💸 Creating payment"
|
|
303
|
-
|
|
304
|
-
payment = AppClient::create_payment(api_token)
|
|
305
|
-
payment_id = payment.fetch('payment_id')
|
|
306
|
-
|
|
307
|
-
warn TTY::Table.new([
|
|
308
|
-
['💷 Payment ID', payment_id],
|
|
309
|
-
['🎫 API token', api_token]
|
|
310
|
-
]).render(:unicode, padding: 1, multiline: true)
|
|
311
|
-
|
|
312
|
-
next_url = payment.dig('_links', 'next_url', 'href')
|
|
313
|
-
`open #{next_url}`
|
|
314
|
-
end
|
|
315
|
-
|
|
316
|
-
desc 'otp <key>',
|
|
317
|
-
'create otp code'
|
|
318
|
-
|
|
319
|
-
def otp(key)
|
|
320
|
-
otp = generate_otp_token(key)
|
|
321
|
-
warn otp
|
|
322
|
-
pbcopy otp
|
|
323
|
-
end
|
|
324
|
-
|
|
325
|
-
desc 'db <app_name>',
|
|
326
|
-
'Connect to <app_name> database, optionally using psql inside the apps database ' \
|
|
327
|
-
'container (note this means you wont get, or save, your psql history)'
|
|
328
|
-
option :docker, type: :boolean, default: false
|
|
329
|
-
|
|
330
|
-
def db(app_name)
|
|
331
|
-
if options[:docker]
|
|
332
|
-
_db_with_docker(app_name)
|
|
333
|
-
elsif find_executable('psql').nil?
|
|
334
|
-
warn 'PSQL installation not found locally'
|
|
335
|
-
_db_with_docker(app_name)
|
|
336
|
-
else
|
|
337
|
-
_db_with_local_psql(app_name)
|
|
338
|
-
end
|
|
339
|
-
end
|
|
340
|
-
|
|
341
|
-
desc 'browse <service>',
|
|
342
|
-
'browse to local service'
|
|
343
|
-
|
|
344
|
-
def browse(app_name, proxy = false)
|
|
345
|
-
url = base_url(app_name, proxy)
|
|
346
|
-
`open #{url}`
|
|
347
|
-
end
|
|
348
|
-
|
|
349
|
-
desc 'url <service>',
|
|
350
|
-
'copy base URL of local service to clipboard'
|
|
351
|
-
|
|
352
|
-
def url(app_name, proxy = false)
|
|
353
|
-
pbcopy base_url(app_name, proxy)
|
|
354
|
-
end
|
|
355
|
-
|
|
356
|
-
no_commands do
|
|
357
|
-
def generate_otp_token(otp_key)
|
|
358
|
-
/^[A-Z2-7]+$/.match(otp_key) ? ROTP::TOTP.new(otp_key).now : ROTP::TOTP.new(Base32.encode(otp_key)).now
|
|
359
|
-
end
|
|
360
|
-
|
|
361
|
-
def pbcopy(input)
|
|
362
|
-
str = input.to_s
|
|
363
|
-
IO.popen('pbcopy', 'w') { |f| f << str }
|
|
364
|
-
warn "📋 “#{str}” copied to clipboard"
|
|
365
|
-
str
|
|
366
|
-
end
|
|
367
|
-
|
|
368
|
-
def extract_gateway_account_id(account)
|
|
369
|
-
account.fetch('gateway_account_external_id', account.fetch('gateway_account_id'))
|
|
370
|
-
end
|
|
371
|
-
|
|
372
|
-
def base_url(app_name, proxy)
|
|
373
|
-
if proxy then
|
|
374
|
-
AppClient::base_proxy_url app_name
|
|
375
|
-
else
|
|
376
|
-
AppClient::base_url app_name
|
|
377
|
-
end
|
|
378
|
-
end
|
|
379
|
-
|
|
380
|
-
def report_status!(child_status, name, action='building')
|
|
381
|
-
emoji = child_status.success? ? '✅' : '🔴'
|
|
382
|
-
status = child_status.success? ? 'success' : 'failure'
|
|
383
|
-
|
|
384
|
-
warn "#{emoji} #{action} #{name} was a #{status}"
|
|
385
|
-
end
|
|
386
|
-
|
|
387
|
-
def check_for_workspace_env
|
|
388
|
-
unless ENV.include? 'WORKSPACE'
|
|
389
|
-
abort '❌ Environment variable WORKSPACE must be set. ' \
|
|
390
|
-
'It should be the directory which contains all your other pay-* repos'
|
|
391
|
-
end
|
|
392
|
-
|
|
393
|
-
unless Dir.exist?(ENV['WORKSPACE'])
|
|
394
|
-
abort "❌ Environment variable WORKSPACE is set to #{ENV['WORKSPACE']} which does not exist." \
|
|
395
|
-
'It must point to the directory which contains all your other pay-* repos'
|
|
396
|
-
end
|
|
397
|
-
end
|
|
398
|
-
|
|
399
|
-
def check_for_local_repo(repo_name)
|
|
400
|
-
repo_path = File.join(ENV['WORKSPACE'], repo_name)
|
|
401
|
-
|
|
402
|
-
unless Dir.exist?(repo_path)
|
|
403
|
-
abort "❌ Repo #{repo_name} does not exist in #{ENV['WORKSPACE']}, "\
|
|
404
|
-
"you need to clone it with `git clone git@github.com:alphagov/#{repo_name}.git #{repo_path}"
|
|
405
|
-
end
|
|
406
|
-
end
|
|
407
|
-
|
|
408
|
-
def npm_install(repo_name)
|
|
409
|
-
repo_path = File.join(ENV['WORKSPACE'], repo_name)
|
|
410
|
-
`cd #{repo_path} && npm install >>/dev/null 2>&1`
|
|
411
|
-
end
|
|
412
|
-
|
|
413
|
-
def npm_run_compile(repo_name)
|
|
414
|
-
repo_path = File.join(ENV['WORKSPACE'], repo_name)
|
|
415
|
-
`cd #{repo_path} && npm run compile >>/dev/null 2>&1`
|
|
416
|
-
end
|
|
417
|
-
|
|
418
|
-
def get_image_from_dockerfile_in_repo(repo_name)
|
|
419
|
-
repo_path = File.join(ENV['WORKSPACE'], repo_name)
|
|
420
|
-
m1_dockerfile_path = File.join(repo_path, 'm1', 'arm64.Dockerfile')
|
|
421
|
-
default_dockerfile_path = File.join(repo_path, 'Dockerfile')
|
|
422
|
-
|
|
423
|
-
dockerfile_path =
|
|
424
|
-
if RUBY_PLATFORM.include?('arm64') && File.exist?(m1_dockerfile_path)
|
|
425
|
-
m1_dockerfile_path
|
|
426
|
-
else
|
|
427
|
-
default_dockerfile_path
|
|
428
|
-
end
|
|
429
|
-
|
|
430
|
-
PayCLI::Commands::Local::ImageExtractor.parse_image_without_sha(dockerfile_path)
|
|
431
|
-
end
|
|
432
|
-
|
|
433
|
-
def _db_with_docker(app_name)
|
|
434
|
-
normalised_app_name = app_name.tr('-', '_')
|
|
435
|
-
|
|
436
|
-
warn 'Running psql in running app db container.'
|
|
437
|
-
warn 'Note: This means you wont have a psql history, and one will not survive restarts of pay local'
|
|
438
|
-
|
|
439
|
-
exec "docker exec -ti -e PGPASSWORD=mysecretpassword #{normalised_app_name}_db \
|
|
440
|
-
psql --host localhost --user #{normalised_app_name} --dbname #{normalised_app_name}"
|
|
441
|
-
end
|
|
442
|
-
|
|
443
|
-
def _db_with_local_psql(app_name)
|
|
444
|
-
normalised_app_name = app_name.tr('-', '_')
|
|
445
|
-
|
|
446
|
-
port = Config.all.select { |app| app[:name] == app_name }.map { |app| app[:db_port] }.first
|
|
447
|
-
exec "PGPASSWORD=mysecretpassword \
|
|
448
|
-
psql -h localhost -p #{port} -U #{normalised_app_name} -d #{normalised_app_name}"
|
|
449
|
-
end
|
|
450
|
-
end
|
|
451
|
-
end
|
|
@@ -1,114 +0,0 @@
|
|
|
1
|
-
require 'tty-table'
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
class PayCLI::Commands::Secrets < Thor
|
|
5
|
-
desc 'fetch <env> <service> <secret_name> --use-ssm ',
|
|
6
|
-
'Fetches a <named secret> for <service> for <env>, if use-ssm is set then get the secret from ssm'
|
|
7
|
-
method_option :use_ssm, :aliases => "-s", :desc => "Query ssm to get the value"
|
|
8
|
-
def fetch(env, service, secret_name)
|
|
9
|
-
PayCLI::StopYubicoAuthenticator.stop_yubico_authenticator!
|
|
10
|
-
secret_value = PayCLI::Secrets.fetch! env, service, secret_name, options[:use_ssm]
|
|
11
|
-
|
|
12
|
-
STDERR.puts "Found value for #{secret_name} in #{env} for #{service}"
|
|
13
|
-
print secret_value.chomp
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
desc 'audit <service> <env1> [<env2> ... <envn>]',
|
|
17
|
-
'Audits secrets for <service> for the given <envs*>'
|
|
18
|
-
def audit(service, *envs)
|
|
19
|
-
PayCLI::StopYubicoAuthenticator.stop_yubico_authenticator!
|
|
20
|
-
STDERR.puts "Auditing secrets for #{service} in #{envs.inspect}"
|
|
21
|
-
|
|
22
|
-
secrets_for_env = PayCLI::Secrets.secrets_for_service service
|
|
23
|
-
secrets_in_envs = PayCLI::Secrets.secrets_in_envs_for_service envs, service
|
|
24
|
-
|
|
25
|
-
header = [service].concat(envs)
|
|
26
|
-
rows = secrets_for_env.map do |secret|
|
|
27
|
-
[secret].concat(
|
|
28
|
-
envs.map { |e| secrets_in_envs[e].include?(secret) ? '✓' : '' }
|
|
29
|
-
)
|
|
30
|
-
end
|
|
31
|
-
footer = ["Other"].concat(
|
|
32
|
-
envs.map { |e| (secrets_in_envs[e] - secrets_for_env).join("\n") }
|
|
33
|
-
)
|
|
34
|
-
|
|
35
|
-
table = TTY::Table.new [header] + rows + [footer]
|
|
36
|
-
STDERR.puts table.render(
|
|
37
|
-
:unicode,
|
|
38
|
-
alignment: :center,
|
|
39
|
-
padding: 1,
|
|
40
|
-
multiline: true,
|
|
41
|
-
)
|
|
42
|
-
end
|
|
43
|
-
|
|
44
|
-
desc 'copy <service> <src_env> <dest_env>',
|
|
45
|
-
'Copies secrets for <service> from <src_env> to <dest_env>'
|
|
46
|
-
def copy(service, src_env, dest_env)
|
|
47
|
-
PayCLI::StopYubicoAuthenticator.stop_yubico_authenticator!
|
|
48
|
-
PayCLI::Secrets.secrets_in_envs_for_service(
|
|
49
|
-
[src_env],
|
|
50
|
-
service
|
|
51
|
-
)[src_env].each do |secret_name|
|
|
52
|
-
secret_value = PayCLI::Secrets::fetch_secret_for_service_from_env(
|
|
53
|
-
src_env, service, secret_name
|
|
54
|
-
)
|
|
55
|
-
|
|
56
|
-
old_value = PayCLI::Secrets::fetch_single_secret_from_env_for_service!(
|
|
57
|
-
dest_env,
|
|
58
|
-
service,
|
|
59
|
-
secret_name
|
|
60
|
-
)
|
|
61
|
-
|
|
62
|
-
if old_value == secret_value
|
|
63
|
-
STDERR.puts "✅ Copying #{secret_name} into #{dest_env} for #{service} would apply no change"
|
|
64
|
-
next
|
|
65
|
-
end
|
|
66
|
-
|
|
67
|
-
STDERR.puts PayCLI::Secrets.diff_table(
|
|
68
|
-
old_value,
|
|
69
|
-
secret_value
|
|
70
|
-
)
|
|
71
|
-
|
|
72
|
-
STDERR.puts "❓ Update value of #{secret_name} in #{dest_env} for #{service}?"
|
|
73
|
-
if (STDERR.print " Type 'yes' exactly > "; STDIN.gets.chomp == 'yes')
|
|
74
|
-
|
|
75
|
-
STDERR.puts "✅ Updated #{secret_name} in #{dest_env}"
|
|
76
|
-
PayCLI::Secrets::write_secret_for_service_in_env!(
|
|
77
|
-
dest_env,
|
|
78
|
-
service,
|
|
79
|
-
secret_name,
|
|
80
|
-
secret_value
|
|
81
|
-
)
|
|
82
|
-
end
|
|
83
|
-
end
|
|
84
|
-
end
|
|
85
|
-
|
|
86
|
-
desc 'provision <service> <env>',
|
|
87
|
-
'Provisions secrets from config for <service> in <env>'
|
|
88
|
-
def provision(service, env)
|
|
89
|
-
PayCLI::StopYubicoAuthenticator.stop_yubico_authenticator!
|
|
90
|
-
PayCLI::Secrets.secrets_for_service(service).each do |secret_name|
|
|
91
|
-
old_value = PayCLI::Secrets::fetch_single_secret_from_env_for_service!(
|
|
92
|
-
env,
|
|
93
|
-
service,
|
|
94
|
-
secret_name
|
|
95
|
-
)
|
|
96
|
-
new_value = PayCLI::Secrets::fetch!(env, service, secret_name)
|
|
97
|
-
|
|
98
|
-
if old_value == new_value
|
|
99
|
-
STDERR.puts "✅ Provisioning #{secret_name} in #{env} for #{service} would apply no change"
|
|
100
|
-
next
|
|
101
|
-
end
|
|
102
|
-
|
|
103
|
-
STDERR.puts "❓ Update value of #{secret_name} in #{env} for #{service}?"
|
|
104
|
-
STDERR.puts PayCLI::Secrets.diff_table(
|
|
105
|
-
old_value,
|
|
106
|
-
new_value
|
|
107
|
-
)
|
|
108
|
-
if (STDERR.print " Type 'yes' exactly > "; STDIN.gets.chomp == 'yes')
|
|
109
|
-
PayCLI::Secrets.write_secret_for_service_in_env!(env,service,secret_name, new_value)
|
|
110
|
-
STDERR.puts "✅ Updated #{secret_name} for #{service} in #{env}"
|
|
111
|
-
end
|
|
112
|
-
end
|
|
113
|
-
end
|
|
114
|
-
end
|
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
- service_name: adminusers
|
|
3
|
-
local_port: 9001
|
|
4
|
-
remote_port: 50603
|
|
5
|
-
|
|
6
|
-
# There are no longer live servers for cardid so it's
|
|
7
|
-
# not possible to tunnel to it
|
|
8
|
-
# - service_name: cardid
|
|
9
|
-
# local_port: 9002
|
|
10
|
-
# remote_port: 50503
|
|
11
|
-
|
|
12
|
-
- service_name: connector
|
|
13
|
-
local_port: 9003
|
|
14
|
-
remote_port: 50103
|
|
15
|
-
|
|
16
|
-
- service_name: products
|
|
17
|
-
local_port: 9005
|
|
18
|
-
remote_port: 51003
|
|
19
|
-
|
|
20
|
-
- service_name: publicauth
|
|
21
|
-
local_port: 9006
|
|
22
|
-
remote_port: 50303
|
|
23
|
-
|
|
24
|
-
- service_name: ledger
|
|
25
|
-
local_port: 9007
|
|
26
|
-
remote_port: 50104
|
|
27
|
-
|
|
28
|
-
- service_name: adminusers_db
|
|
29
|
-
local_port: 5432
|
|
30
|
-
remote_port: 5432
|
|
31
|
-
|
|
32
|
-
- service_name: connector_db
|
|
33
|
-
local_port: 5432
|
|
34
|
-
remote_port: 5432
|
|
35
|
-
|
|
36
|
-
- service_name: products_db
|
|
37
|
-
local_port: 5432
|
|
38
|
-
remote_port: 5432
|
|
39
|
-
|
|
40
|
-
- service_name: publicauth_db
|
|
41
|
-
local_port: 5432
|
|
42
|
-
remote_port: 5432
|
|
43
|
-
|
|
44
|
-
- service_name: ledger_db
|
|
45
|
-
local_port: 5432
|
|
46
|
-
remote_port: 5432
|
|
47
|
-
instance_version:
|
|
48
|
-
production-2: 1
|
|
49
|
-
...
|