]>
Commit | Line | Data |
---|---|---|
0a21fb6c IB |
1 | class role::cryptoportfolio ( |
2 | String $user, | |
3 | String $group, | |
4 | String $home, | |
5 | Optional[String] $env = "prod", | |
6 | Optional[String] $webhook_url = undef, | |
7 | String $pg_user, | |
8 | String $pg_user_replication, | |
9 | String $pg_db, | |
10 | Optional[String] $pg_hostname = "localhost", | |
11 | Optional[String] $pg_port = "5432", | |
12 | Optional[String] $web_host = undef, | |
13 | Optional[String] $web_port = "", | |
14 | Optional[Boolean] $web_ssl = true, | |
15 | Optional[String] $front_version = undef, | |
16 | Optional[String] $front_sha256 = undef, | |
17 | Optional[String] $bot_version = undef, | |
18 | Optional[String] $bot_sha256 = undef, | |
19 | ) { | |
68bbff61 IB |
20 | ensure_resource('exec', 'systemctl daemon-reload', { |
21 | command => '/usr/bin/systemctl daemon-reload', | |
22 | refreshonly => true | |
23 | }) | |
24 | ||
57ae81ea IB |
25 | include "base_installation" |
26 | ||
8af3ea1e | 27 | include "profile::tools" |
57ae81ea | 28 | include "profile::postgresql" |
2bb35074 | 29 | include "profile::apache" |
68bbff61 | 30 | include "profile::xmr_stak" |
57ae81ea | 31 | |
0a21fb6c IB |
32 | $password_seed = lookup("base_installation::puppet_pass_seed") |
33 | ||
34 | $pg_password = generate_password(24, $password_seed, "postgres_cryptoportfolio") | |
35 | $pg_replication_password = generate_password(24, $password_seed, "postgres_cryptoportfolio_replication") | |
36 | $pg_host = "${pg_hostname}:${pg_port}" | |
37 | ||
38 | $cf_front_app = "${home}/go/src/immae.eu/Immae/Projets/Cryptomonnaies/Cryptoportfolio/Front" | |
159df176 IB |
39 | $cf_front_app_api_workdir = "${cf_front_app}/cmd/app" |
40 | $cf_front_app_api_bin = "${cf_front_app_api_workdir}/cryptoportfolio-app" | |
0a21fb6c | 41 | $cf_front_app_api_conf = "${home}/conf.toml" |
159df176 IB |
42 | $cf_front_app_api_secret = generate_password(24, $password_seed, "cryptoportfolio_api_secret") |
43 | ||
44 | $cf_front_app_static_conf = "${cf_front_app}/cmd/web/env/prod.env" | |
45 | ||
0a21fb6c IB |
46 | $cf_bot_app = "${home}/bot" |
47 | $cf_bot_app_conf = "${home}/bot_config.ini" | |
48 | $cf_bot_app_reports = "${home}/bot_reports" | |
a4c92ff7 | 49 | |
b3015828 IB |
50 | file { "/var/lib/postgres/data/certs": |
51 | ensure => directory, | |
52 | mode => "0700", | |
53 | owner => $::profile::postgresql::pg_user, | |
54 | group => $::profile::postgresql::pg_user, | |
55 | require => File["/var/lib/postgres"], | |
56 | } | |
57 | ||
58 | file { "/var/lib/postgres/data/certs/cert.pem": | |
0a21fb6c | 59 | source => "file:///etc/letsencrypt/live/$web_host/cert.pem", |
b3015828 IB |
60 | mode => "0600", |
61 | links => "follow", | |
62 | owner => $::profile::postgresql::pg_user, | |
63 | group => $::profile::postgresql::pg_user, | |
0a21fb6c | 64 | require => [Letsencrypt::Certonly[$web_host], File["/var/lib/postgres/data/certs"]] |
b3015828 IB |
65 | } |
66 | ||
67 | file { "/var/lib/postgres/data/certs/privkey.pem": | |
0a21fb6c | 68 | source => "file:///etc/letsencrypt/live/$web_host/privkey.pem", |
b3015828 IB |
69 | mode => "0600", |
70 | links => "follow", | |
71 | owner => $::profile::postgresql::pg_user, | |
72 | group => $::profile::postgresql::pg_user, | |
0a21fb6c | 73 | require => [Letsencrypt::Certonly[$web_host], File["/var/lib/postgres/data/certs"]] |
b3015828 IB |
74 | } |
75 | ||
76 | postgresql::server::config_entry { "wal_level": | |
77 | value => "logical", | |
78 | } | |
79 | ||
80 | postgresql::server::config_entry { "ssl": | |
81 | value => "on", | |
0a21fb6c | 82 | require => Letsencrypt::Certonly[$web_host], |
b3015828 IB |
83 | } |
84 | ||
85 | postgresql::server::config_entry { "ssl_cert_file": | |
86 | value => "/var/lib/postgres/data/certs/cert.pem", | |
0a21fb6c | 87 | require => Letsencrypt::Certonly[$web_host], |
b3015828 IB |
88 | } |
89 | ||
90 | postgresql::server::config_entry { "ssl_key_file": | |
91 | value => "/var/lib/postgres/data/certs/privkey.pem", | |
0a21fb6c | 92 | require => Letsencrypt::Certonly[$web_host], |
b3015828 IB |
93 | } |
94 | ||
0a21fb6c IB |
95 | postgresql::server::db { $pg_db: |
96 | user => $pg_user, | |
97 | password => postgresql_password($pg_user, $pg_password), | |
b3015828 IB |
98 | } |
99 | -> | |
0a21fb6c IB |
100 | postgresql_psql { "CREATE PUBLICATION ${pg_db}_publication FOR ALL TABLES": |
101 | db => $pg_db, | |
102 | unless => "SELECT 1 FROM pg_catalog.pg_publication WHERE pubname = '${pg_db}_publication'", | |
b3015828 IB |
103 | } |
104 | -> | |
0a21fb6c IB |
105 | postgresql::server::role { $pg_user_replication: |
106 | db => $pg_db, | |
b3015828 | 107 | replication => true, |
0a21fb6c | 108 | password_hash => postgresql_password($pg_user_replication, $pg_replication_password), |
b3015828 IB |
109 | } |
110 | -> | |
0a21fb6c IB |
111 | postgresql::server::database_grant { $pg_user_replication: |
112 | db => $pg_db, | |
b3015828 | 113 | privilege => "CONNECT", |
0a21fb6c | 114 | role => $pg_user_replication, |
b3015828 IB |
115 | } |
116 | -> | |
0a21fb6c IB |
117 | postgresql::server::grant { "all tables in schema:public:$pg_user_replication": |
118 | db => $pg_db, | |
119 | role => $pg_user_replication, | |
b3015828 IB |
120 | privilege => "SELECT", |
121 | object_type => "ALL TABLES IN SCHEMA", | |
122 | object_name => "public", | |
123 | } | |
124 | -> | |
0a21fb6c IB |
125 | postgresql::server::grant { "all sequences in schema:public:$pg_user_replication": |
126 | db => $pg_db, | |
127 | role => $pg_user_replication, | |
b3015828 IB |
128 | privilege => "SELECT", |
129 | object_type => "ALL SEQUENCES IN SCHEMA", | |
130 | object_name => "public", | |
57ae81ea IB |
131 | } |
132 | ||
6a919776 IB |
133 | postgresql::server::pg_hba_rule { 'allow localhost TCP access to cryptoportfolio user': |
134 | type => 'host', | |
0a21fb6c IB |
135 | database => $pg_db, |
136 | user => $pg_user, | |
6a919776 IB |
137 | address => '127.0.0.1/32', |
138 | auth_method => 'md5', | |
139 | order => "b0", | |
140 | } | |
141 | postgresql::server::pg_hba_rule { 'allow localhost ip6 TCP access to cryptoportfolio user': | |
142 | type => 'host', | |
0a21fb6c IB |
143 | database => $pg_db, |
144 | user => $pg_user, | |
6a919776 IB |
145 | address => '::1/128', |
146 | auth_method => 'md5', | |
147 | order => "b0", | |
148 | } | |
0a4ec379 | 149 | |
b3015828 IB |
150 | postgresql::server::pg_hba_rule { 'allow TCP access to replication user from immae.eu': |
151 | type => 'hostssl', | |
0a21fb6c IB |
152 | database => $pg_db, |
153 | user => $pg_user_replication, | |
b3015828 IB |
154 | address => 'immae.eu', |
155 | auth_method => 'md5', | |
156 | order => "b0", | |
157 | } | |
158 | ||
e345248b | 159 | class { 'apache::mod::headers': } |
0a21fb6c | 160 | apache::vhost { $web_host: |
e345248b | 161 | port => '443', |
2bb35074 IB |
162 | docroot => false, |
163 | manage_docroot => false, | |
164 | proxy_dest => "http://localhost:8000", | |
e345248b IB |
165 | request_headers => 'set X-Forwarded-Proto "https"', |
166 | ssl => true, | |
0a21fb6c IB |
167 | ssl_cert => "/etc/letsencrypt/live/$web_host/cert.pem", |
168 | ssl_key => "/etc/letsencrypt/live/$web_host/privkey.pem", | |
169 | ssl_chain => "/etc/letsencrypt/live/$web_host/chain.pem", | |
170 | require => Letsencrypt::Certonly[$web_host], | |
e345248b IB |
171 | proxy_preserve_host => true; |
172 | default: * => $::profile::apache::apache_vhost_default; | |
0a4ec379 | 173 | } |
f67c5285 | 174 | |
a4c92ff7 IB |
175 | file { "/usr/local/bin/slack-notify": |
176 | mode => "0755", | |
177 | source => "puppet:///modules/role/cryptoportfolio/slack-notify.py", | |
178 | } | |
179 | ||
236d7e6d IB |
180 | unless empty($bot_version) { |
181 | ensure_packages(["python", "python-pip"]) | |
182 | ||
183 | file { $cf_bot_app: | |
184 | ensure => "directory", | |
185 | mode => "0700", | |
0a21fb6c IB |
186 | owner => $user, |
187 | group => $group, | |
188 | require => User["$user:"], | |
236d7e6d IB |
189 | } |
190 | ||
0a21fb6c IB |
191 | archive { "${home}/trader_${bot_version}.tar.gz": |
192 | path => "${home}/trader_${bot_version}.tar.gz", | |
236d7e6d IB |
193 | source => "https://git.immae.eu/releases/cryptoportfolio/trader/trader_${bot_version}.tar.gz", |
194 | checksum_type => "sha256", | |
195 | checksum => $bot_sha256, | |
196 | cleanup => false, | |
197 | extract => true, | |
0a21fb6c | 198 | user => $user, |
236d7e6d IB |
199 | username => $facts["ec2_metadata"]["hostname"], |
200 | password => generate_password(24, $password_seed, "ldap"), | |
201 | extract_path => $cf_bot_app, | |
0a21fb6c | 202 | require => [User["$user:"], File[$cf_bot_app]], |
236d7e6d IB |
203 | } ~> |
204 | exec { "py-cryptoportfolio-dependencies": | |
205 | cwd => $cf_bot_app, | |
0a21fb6c IB |
206 | user => $user, |
207 | environment => ["HOME=${home}"], | |
236d7e6d | 208 | command => "/usr/bin/make install", |
0a21fb6c | 209 | require => User["$user:"], |
236d7e6d | 210 | refreshonly => true, |
2542900d IB |
211 | before => [ |
212 | File[$cf_bot_app_conf], | |
213 | Cron["py-cryptoportfolio-before"], | |
214 | Cron["py-cryptoportfolio-after"], | |
215 | ] | |
236d7e6d | 216 | } |
c49d00da IB |
217 | |
218 | file { $cf_bot_app_conf: | |
0a21fb6c IB |
219 | owner => $user, |
220 | group => $group, | |
c49d00da | 221 | mode => "0600", |
9a6b0098 IB |
222 | content => template("role/cryptoportfolio/bot_config.ini.erb"), |
223 | require => [ | |
0a21fb6c IB |
224 | User["$user:"], |
225 | Archive["${home}/trader_${bot_version}.tar.gz"], | |
9a6b0098 | 226 | ], |
c49d00da | 227 | } |
2542900d IB |
228 | |
229 | cron { "py-cryptoportfolio-before": | |
230 | ensure => present, | |
231 | command => "cd $cf_bot_app ; python main.py --config $cf_bot_app_conf --before", | |
0a21fb6c | 232 | user => $user, |
2542900d IB |
233 | weekday => 7, # Sunday |
234 | hour => 22, | |
235 | minute => 30, | |
0a21fb6c | 236 | environment => ["HOME=${home}","PATH=/usr/bin/"], |
2542900d IB |
237 | require => [ |
238 | File[$cf_bot_app_conf], | |
0a21fb6c | 239 | Archive["${home}/trader_${bot_version}.tar.gz"] |
2542900d IB |
240 | ], |
241 | } | |
242 | ||
243 | cron { "py-cryptoportfolio-after": | |
244 | ensure => present, | |
245 | command => "cd $cf_bot_app ; python main.py --config $cf_bot_app_conf --after", | |
0a21fb6c | 246 | user => $user, |
2542900d IB |
247 | weekday => 1, # Monday |
248 | hour => 1, | |
9a6b0098 | 249 | minute => 0, |
0a21fb6c | 250 | environment => ["HOME=${home}","PATH=/usr/bin/"], |
2542900d IB |
251 | require => [ |
252 | File[$cf_bot_app_conf], | |
0a21fb6c | 253 | Archive["${home}/trader_${bot_version}.tar.gz"] |
2542900d IB |
254 | ], |
255 | } | |
a4c92ff7 | 256 | |
0a21fb6c | 257 | unless empty($webhook_url) { |
a4c92ff7 IB |
258 | exec { "bot-slack-notify": |
259 | refreshonly => true, | |
bd263a98 IB |
260 | environment => [ |
261 | "P_PROJECT=Trader", | |
0a21fb6c | 262 | "P_WEBHOOK=${webhook_url}", |
bd263a98 | 263 | "P_VERSION=${bot_version}", |
0a21fb6c IB |
264 | "P_HOST=${web_host}", |
265 | "P_HTTPS=${web_ssl}", | |
bd263a98 IB |
266 | ], |
267 | command => "/usr/local/bin/slack-notify", | |
a4c92ff7 IB |
268 | require => File["/usr/local/bin/slack-notify"], |
269 | subscribe => Exec["py-cryptoportfolio-dependencies"], | |
270 | } | |
271 | } | |
236d7e6d IB |
272 | } |
273 | ||
9a6b0098 | 274 | # FIXME: restore backup |
76a321e1 | 275 | unless empty($front_version) { |
159df176 | 276 | ensure_packages(["go", "npm", "nodejs", "yarn"]) |
76a321e1 | 277 | |
159df176 | 278 | file { [ |
0a21fb6c IB |
279 | "${home}/go/", |
280 | "${home}/go/src", | |
281 | "${home}/go/src/immae.eu", | |
282 | "${home}/go/src/immae.eu/Immae", | |
283 | "${home}/go/src/immae.eu/Immae/Projets", | |
284 | "${home}/go/src/immae.eu/Immae/Projets/Cryptomonnaies", | |
285 | "${home}/go/src/immae.eu/Immae/Projets/Cryptomonnaies/Cryptoportfolio", | |
159df176 IB |
286 | $cf_front_app]: |
287 | ensure => "directory", | |
76a321e1 | 288 | mode => "0700", |
0a21fb6c IB |
289 | owner => $user, |
290 | group => $group, | |
291 | require => User["$user:"], | |
76a321e1 IB |
292 | } |
293 | ||
0a21fb6c | 294 | file { "${home}/front": |
76a321e1 | 295 | ensure => "link", |
159df176 | 296 | target => $cf_front_app, |
f099c453 | 297 | before => File[$cf_front_app], |
159df176 IB |
298 | } |
299 | ||
300 | file { "/etc/systemd/system/cryptoportfolio-app.service": | |
301 | mode => "0644", | |
302 | owner => "root", | |
303 | group => "root", | |
304 | content => template("role/cryptoportfolio/cryptoportfolio-app.service.erb"), | |
68bbff61 | 305 | notify => Exec["systemctl daemon-reload"], |
159df176 IB |
306 | } |
307 | ||
308 | service { 'cryptoportfolio-app': | |
f099c453 IB |
309 | enable => true, |
310 | ensure => "running", | |
311 | subscribe => [Exec["go-cryptoportfolio-app"], Exec["web-cryptoportfolio-build"]], | |
312 | require => [ | |
b3015828 | 313 | File["/etc/systemd/system/cryptoportfolio-app.service"], |
0a21fb6c | 314 | Postgresql::Server::Db[$pg_db] |
b3015828 | 315 | ], |
43c4ee4e | 316 | } ~> |
0a21fb6c | 317 | exec { "dump $pg_db structure": |
43c4ee4e IB |
318 | refreshonly => true, |
319 | user => $::profile::postgresql::pg_user, | |
320 | group => $::profile::postgresql::pg_user, | |
0a21fb6c | 321 | command => "/usr/bin/pg_dump --schema-only --clean --no-publications $pg_db > /var/lib/postgres/${pg_db}.schema", |
159df176 IB |
322 | } |
323 | ||
0a21fb6c IB |
324 | archive { "${home}/front_${front_version}.tar.gz": |
325 | path => "${home}/front_${front_version}.tar.gz", | |
383fa18a IB |
326 | source => "https://git.immae.eu/releases/cryptoportfolio/front/front_${front_version}.tar.gz", |
327 | checksum_type => "sha256", | |
328 | checksum => $front_sha256, | |
329 | cleanup => false, | |
330 | extract => true, | |
0a21fb6c | 331 | user => $user, |
383fa18a IB |
332 | username => $facts["ec2_metadata"]["hostname"], |
333 | password => generate_password(24, $password_seed, "ldap"), | |
334 | extract_path => $cf_front_app, | |
0a21fb6c | 335 | require => [User["$user:"], File[$cf_front_app]], |
383fa18a IB |
336 | notify => [ |
337 | Exec["web-cryptoportfolio-dependencies"], | |
338 | Exec["go-get-dep"], | |
339 | ] | |
340 | } | |
341 | ||
342 | # Api | |
159df176 | 343 | file { $cf_front_app_api_conf: |
0a21fb6c IB |
344 | owner => $user, |
345 | group => $group, | |
159df176 IB |
346 | mode => "0600", |
347 | content => template("role/cryptoportfolio/api_conf.toml.erb"), | |
383fa18a IB |
348 | before => Exec["go-cryptoportfolio-app"], |
349 | } | |
350 | ||
351 | exec { "go-get-dep": | |
0a21fb6c IB |
352 | user => $user, |
353 | environment => ["HOME=${home}"], | |
354 | creates => "${home}/go/bin/dep", | |
383fa18a IB |
355 | command => "/usr/bin/go get -u github.com/golang/dep/cmd/dep", |
356 | refreshonly => true, | |
357 | } ~> | |
358 | exec { "go-cryptoportfolio-dependencies": | |
359 | cwd => $cf_front_app, | |
0a21fb6c IB |
360 | user => $user, |
361 | environment => ["HOME=${home}"], | |
362 | command => "${home}/go/bin/dep ensure", | |
383fa18a IB |
363 | refreshonly => true, |
364 | } ~> | |
365 | exec { "go-cryptoportfolio-app": | |
366 | cwd => $cf_front_app_api_workdir, | |
0a21fb6c IB |
367 | user => $user, |
368 | environment => ["HOME=${home}"], | |
383fa18a IB |
369 | command => "/usr/bin/make build", |
370 | refreshonly => true, | |
159df176 IB |
371 | } |
372 | ||
383fa18a | 373 | # Static pages |
159df176 | 374 | file { $cf_front_app_static_conf: |
0a21fb6c IB |
375 | owner => $user, |
376 | group => $group, | |
159df176 IB |
377 | mode => "0600", |
378 | content => template("role/cryptoportfolio/static_conf.env.erb"), | |
383fa18a | 379 | before => Exec["web-cryptoportfolio-build"], |
159df176 IB |
380 | } |
381 | ||
382 | exec { "web-cryptoportfolio-dependencies": | |
383 | cwd => "${cf_front_app}/cmd/web", | |
0a21fb6c IB |
384 | user => $user, |
385 | environment => ["HOME=${home}"], | |
159df176 | 386 | command => "/usr/bin/make install", |
e17078be | 387 | refreshonly => true, |
383fa18a IB |
388 | require => [Package["npm"], Package["nodejs"], Package["yarn"]] |
389 | } ~> | |
159df176 IB |
390 | exec { "web-cryptoportfolio-build": |
391 | cwd => "${cf_front_app}/cmd/web", | |
0a21fb6c IB |
392 | user => $user, |
393 | environment => ["HOME=${home}"], | |
6d512d3f | 394 | path => ["${cf_front_app}/cmd/web/node_modules/.bin/", "/usr/bin"], |
0a21fb6c | 395 | command => "/usr/bin/make static ENV=${env}", |
383fa18a | 396 | refreshonly => true, |
76a321e1 | 397 | } |
a4c92ff7 | 398 | |
0a21fb6c | 399 | unless empty($webhook_url) { |
a4c92ff7 IB |
400 | exec { "front-slack-notify": |
401 | refreshonly => true, | |
bd263a98 IB |
402 | environment => [ |
403 | "P_PROJECT=Front", | |
0a21fb6c | 404 | "P_WEBHOOK=${webhook_url}", |
bd263a98 | 405 | "P_VERSION=${front_version}", |
0a21fb6c IB |
406 | "P_HOST=${web_host}", |
407 | "P_HTTPS=${web_ssl}", | |
bd263a98 IB |
408 | ], |
409 | command => "/usr/local/bin/slack-notify", | |
a4c92ff7 IB |
410 | require => File["/usr/local/bin/slack-notify"], |
411 | subscribe => [Exec["go-cryptoportfolio-app"], Exec["web-cryptoportfolio-build"]], | |
412 | } | |
413 | } | |
76a321e1 | 414 | } |
57ae81ea | 415 | } |