You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

585 lines
18 KiB

6 years ago
  1. .\" Copyright (c) 2019 Rodolphe Bréard <rodolphe@breard.tf>
  2. .\"
  3. .\" Copying and distribution of this file, with or without modification,
  4. .\" are permitted in any medium without royalty provided the copyright
  5. .\" notice and this notice are preserved. This file is offered as-is,
  6. .\" without any warranty.
  7. .Dd May 9, 2019
  8. .Dt ACMED.TOML 5
  9. .Os
  10. .Sh NAME
  11. .Nm acmed.toml
  12. .Nd ACMEd configuration file
  13. .Sh DESCRIPTION
  14. .Nm
  15. is the configuration file for
  16. .Xr acmed 8 .
  17. It is written in the
  18. .Em TOML
  19. format. The allowed elements are described below.
  20. .Bl -tag
  21. .It Ic include
  22. Array containing the path to configuration file to include. The path can be either relative or absolute. If relative, it is relative to the configuration file which included it.
  23. .Pp
  24. In case or overlapping global option definition, the one of the last included file will be used. For example, if a file
  25. .Em A
  26. includes files
  27. .Em B
  28. and
  29. .Em C
  30. and all three defines the same global option, the final value will be the one defined in file
  31. .Em C .
  32. .It Ic global
  33. Table containing the global configuration options.
  34. .Bl -tag
  35. .It Cm accounts_directory Ar string
  36. Specify the directory where the accounts private and public keys are stored.
  37. .It Cm certificates_directory Ar string
  38. Specify the directory where the certificates and their associated private keys are stored.
  39. .It Cm cert_file_mode Ar integer
  40. Specify the permissions to use for newly-created certificates files. See
  41. .Xr chmod 2
  42. for more details.
  43. .It Cm cert_file_user Ar user_id Ft string
  44. Specify the user who will own newly-created certificates files. See
  45. .Xr chown 2
  46. for more details.
  47. .It Cm cert_file_group Ar group_id Ft string
  48. Specify the group who will own newly-created certificates files. See
  49. .Xr chown 2
  50. for more details.
  51. .It Ic env Ar table
  52. Table of environment variables that will be accessible from hooks.
  53. .It Cm pk_file_mode Ar integer
  54. Specify the permissions to use for newly-created private-key files. See
  55. .Xr chmod 2
  56. for more details.
  57. .It Cm pk_file_user Ar user_id Ft string
  58. Specify the user who will own newly-created private-key files. See
  59. .Xr chown 2
  60. for more details.
  61. .It Cm pk_file_group Ar group_id Ft string
  62. Specify the group who will own newly-created private-key files. See
  63. .Xr chown 2
  64. for more details.
  65. .El
  66. .It Ic endpoint
  67. Array of table where each element defines a Certificate Authority
  68. .Pq CA
  69. which may be used to request certificates.
  70. .Bl -tag
  71. .It Cm name Ar string
  72. The name the endpoint is registered under. Must be unique.
  73. .It Cm url Ar string
  74. The endpoint's directory URL.
  75. .It Cm tos_agreed Ar boolean
  76. Set whether or not the user agrees to the Terms Of Service
  77. .Pq TOS .
  78. .El
  79. .It Ic hook
  80. Array of table where each element defines a command that will be launched at a defined point. See section
  81. .Sx WRITING A HOOK
  82. for more details.
  83. .Bl -tag
  84. .It Cm allow_failure Ar boolean
  85. Defines if an error return value for this hook is allowed or not. If not allowed, a failure in this hook will fail the whole certificate request process. Default is false.
  86. .It Cm name Ar string
  87. The name the hook is registered under. Must be unique.
  88. .It Cm hook_type Ar array
  89. Array of strings. Possible types are:
  90. .Bl -dash -compact
  91. .It
  92. challenge-http-01
  93. .It
  94. challenge-http-01-clean
  95. .It
  96. challenge-dns-01
  97. .It
  98. challenge-dns-01-clean
  99. .It
  100. challenge-tls-alpn-01
  101. .It
  102. challenge-tls-alpn-01-clean
  103. .It
  104. file-pre-create
  105. .It
  106. file-pre-edit
  107. .It
  108. file-post-create
  109. .It
  110. file-post-edit
  111. .It
  112. post-operation
  113. .El
  114. .It Ic cmd Ar string
  115. The name of the command that will be launched.
  116. .It Ic args Ar array
  117. Array of strings representing the command's arguments.
  118. .It Ic stdin Ar string
  119. Path to the file that will be written into the command's standard intput. Mutually exclusive with
  120. .Em stdin_str .
  121. .It Ic stdin_str Ar string
  122. String that will be written into the command's standard input. Mutually exclusive with
  123. .Em stdin .
  124. .It Ic stdout Ar string
  125. Path to the file where the command's standard output if written.
  126. .It Ic stderr Ar string
  127. Path to the file where the command's standard error output if written.
  128. .El
  129. .It Ic group
  130. Array of table allowing to group several hooks as one. A group is considered as new hook.
  131. .Bl -tag
  132. .It Cm name Ar string
  133. The name the group is registered under. This name is considered as a hook name. Must be unique.
  134. .It Cm hooks Ar array
  135. Array containing the names of the hooks that are grouped. The hooks are guaranteed to be called sequentially in the declaration order.
  136. .El
  137. .It Ic account
  138. Array of table representing an account on one or several CA.
  139. .Bl -tag
  140. .It Ic name Ar string
  141. The name the account is registered under. Must be unique.
  142. .It Ic email Ar string
  143. The email address used to contact the account's holder.
  144. .El
  145. .It Ic certificate
  146. Array of table representing a certificate that will be requested to a CA.
  147. .Bl -tag
  148. .It Ic account Ar string
  149. Name of the account to use.
  150. .It Ic endpoint Ar string
  151. Name of the endpoint to use.
  152. .It Ic env Ar table
  153. Table of environment variables that will be accessible from hooks.
  154. .It Ic domains Ar array
  155. Array of tables listing the domains that should be included in the certificate along with the challenge to use for each one.
  156. .Bl -tag
  157. .It Ic challenge Ar string
  158. The name of the challenge to use to prove the domain's ownership. Possible values are:
  159. .Bl -dash -compact
  160. .It
  161. http-01
  162. .It
  163. dns-01
  164. .It
  165. tls-alpn-01
  166. .El
  167. .It Ic dns Ar string
  168. The domain name.
  169. .It Ic env Ar table
  170. Table of environment variables that will be accessible from hooks.
  171. .El
  172. .It Ic algorithm Ar string
  173. Name of the asymetric cryptography algorithm used to generate the certificate's key pair. Possible values are :
  174. .Bl -dash -compact
  175. .It
  176. rsa2048
  177. .Aq default
  178. .It
  179. rsa4096
  180. .It
  181. ecdsa_p256
  182. .It
  183. ecdsa_p384
  184. .El
  185. .It Ic kp_reuse Ar boolean
  186. Set whether or not the private key should be reused when renewing the certificate. Default is false.
  187. .It Ic directory Ar string
  188. Path to the directory where certificates and their associated private keys are stored.
  189. .It Ic hooks Ar array
  190. Names of hooks that will be called when requesting a new certificate. The hooks are guaranteed to be called sequentially in the declaration order.
  191. .El
  192. .Sh WRITING A HOOK
  193. When requesting a certificate to a CA using ACME, there is three steps that are hard to automatize. The first one is solving challenges in order to prove the ownership of every domains to be included: it requires to interact with the configuration of other services, hence depends on how the infrastructure works. The second one is restarting all the services that uses a given certificate, for the same reason. The last one is archiving: although several default methods can be implemented, sometimes admins wants or are required to do it in a different way.
  194. .Pp
  195. In order to allow a full automation of the three above steps without imposing arbitrary restrictions or methods,
  196. .Xr acmed 8
  197. uses hooks. Fundamentally, a hook is a command line template that will be called at a specific time of the process. Such approach allows admins to use any executable script or program located on the machine to customize the process.
  198. .Pp
  199. For a given certificate, hooks are guaranteed to be called sequentially in the declaration order. It is therefore possible to have a hook that depends on another one. Nevertheless, several certificates may be renewed at the same time. Hence, hooks shall not use globing or any other action that may disrupt hooks called by a different certificate.
  200. .Pp
  201. A hook have a type that will influence both the moment it is called and the available template variables. It is possible to declare several types. In such a case, the hook will be invoked whenever one of its type request it. When called, the hook only have access to template variable for the current type. If a hook uses a template variable that does not exists for the current type it is invoked for, the variable is empty.
  202. .Pp
  203. When writing a hook, the values of
  204. .Em args ,
  205. .Em stdin ,
  206. .Em stdin_str ,
  207. .Em stdout
  208. and
  209. .Em stderr
  210. are considered as template strings whereas
  211. .Em cmd
  212. is not. The template syntax is
  213. .Em Handlebars .
  214. See the
  215. .Sx STANDARDS
  216. section for a link to the
  217. .Em Handlebars
  218. specifications.
  219. .Pp
  220. The available types and the associated template variable are described below.
  221. .Bl -tag
  222. .It Ic challenge-http-01
  223. Invoked when the ownership of a domain must be proved using the
  224. .Em http-01
  225. challenge. The available template variables are:
  226. .Bl -tag -compact
  227. .It Cm challenge Ar string
  228. The name of the challenge type
  229. .Aq http-01 .
  230. Mostly used in hooks with multiple types.
  231. .It Cm domain Ar string
  232. The domain name whom ownership is currently being validated.
  233. .It Cm env Ar array
  234. Array containing all the environment variables.
  235. .It Cm file_name Ar string
  236. Name of the file containing the proof. This is not a full path and does not include the
  237. .Ql .well-known/acme-challenge/
  238. prefix.
  239. .It Cm is_clean_hook Ar bool
  240. False
  241. .It Cm proof Ar string
  242. The content of the proof that must be written to
  243. .Em file_name .
  244. .El
  245. .It Ic challenge-http-01-clean
  246. Invoked once a domain ownership has been proven using the
  247. .Em http-01
  248. challenge. This hook is intended to remove the proof since it is no longer required. The template variables are strictly identical to those given in the corresponding
  249. .Em challenge-http-01
  250. hook, excepted
  251. .Em is_clean_hook
  252. which is set to
  253. .Em true .
  254. .It Ic challenge-dns-01
  255. Invoked when the ownership of a domain must be proved using the
  256. .Em dns-01
  257. challenge. The available template variables are:
  258. .Bl -tag -compact
  259. .It Cm challenge Ar string
  260. The name of the challenge type
  261. .Aq dns-01 .
  262. Mostly used in hooks with multiple types.
  263. .It Cm domain Ar string
  264. The domain name whom ownership is currently being validated.
  265. .It Cm env Ar array
  266. Array containing all the environment variables.
  267. .It Cm is_clean_hook Ar bool
  268. False
  269. .It Cm proof Ar string
  270. The content of the proof that must be written to a
  271. .Ql TXT
  272. entry of the DNS zone for the
  273. .Ql _acme-challenge
  274. subdomain.
  275. .El
  276. .It Ic challenge-dns-01-clean
  277. Invoked once a domain ownership has been proven using the
  278. .Em dns-01
  279. challenge. This hook is intended to remove the proof since it is no longer required. The template variables are strictly identical to those given in the corresponding
  280. .Em challenge-dns-01
  281. hook, excepted
  282. .Em is_clean_hook
  283. which is set to
  284. .Em true .
  285. .It Ic challenge-tls-alpn-01
  286. Invoked when the ownership of a domain must be proved using the
  287. .Em tls-alpn-01
  288. challenge. The available template variables are:
  289. .Bl -tag -compact
  290. .It Cm challenge Ar string
  291. The name of the challenge type
  292. .Aq tls-alpn-01 .
  293. Mostly used in hooks with multiple types.
  294. .It Cm domain Ar string
  295. The domain name whom ownership is currently being validated.
  296. .It Cm env Ar array
  297. Array containing all the environment variables.
  298. .It Cm is_clean_hook Ar bool
  299. False
  300. .It Cm proof Ar string
  301. Plain-text representation of the
  302. .Em acmeIdentifier
  303. extension that should be used in the self-signed certificate presented when a TLS connection is initiated with the
  304. .Qd acme-tls/1
  305. ALPN extension value.
  306. .Xr acmed 8
  307. will not generate the certificate itself since it can be done using
  308. .Xr tacd 8 .
  309. .El
  310. .It Ic challenge-tls-alpn-01-clean
  311. Invoked once a domain ownership has been proven using the
  312. .Em tls-alpn-01
  313. challenge. This hook is intended to remove the proof since it is no longer required. The template variables are strictly identical to those given in the corresponding
  314. .Em challenge-tls-alpn-01
  315. hook, excepted
  316. .Em is_clean_hook
  317. which is set to
  318. .Em true .
  319. .It Ic file-pre-create
  320. Invoked
  321. .Em before
  322. a non-existent file
  323. .Em created .
  324. The available template variables are:
  325. .Bl -tag -compact
  326. .It Cm env Ar array
  327. Array containing all the environment variables.
  328. .It Cm file_directory Ar string
  329. Name of the directory where the impacted file is located.
  330. .It Cm file_name Ar string
  331. Name of the impacted file.
  332. .It Cm file_path Ar string
  333. Full path to the impacted file.
  334. .El
  335. .It Ic file-pre-edit
  336. Invoked
  337. .Em before
  338. an existent file
  339. .Em modified .
  340. The available template variables are the same as those available for the
  341. .Em file-pre-create
  342. type.
  343. .It Ic file-post-create
  344. Invoked
  345. .Em after
  346. a non-existent file
  347. .Em created .
  348. The available template variables are the same as those available for the
  349. .Em file-pre-create
  350. type.
  351. .It Ic file-post-edit
  352. Invoked
  353. .Em after
  354. an existent file
  355. .Em modified .
  356. The available template variables are the same as those available for the
  357. .Em file-pre-create
  358. type.
  359. .It Ic post-operation
  360. Invoked at the end of the certificate request process. The available template variables are:
  361. .Bl -tag -compact
  362. .It Cm algorithm Ar string
  363. Name of the algorithm used in the certificate.
  364. .It Cm domains Ar string
  365. Array containing the domain names included in the requested certificate.
  366. .It Cm env Ar array
  367. Array containing all the environment variables.
  368. .It Cm is_success Ar boolean
  369. True if the certificate request is successful.
  370. .It Cm status Ar string
  371. Human-readable status. If the certificate request failed, it contains the error description.
  372. .El
  373. .El
  374. .Sh DEFAULT HOOKS
  375. Because many people have the same needs, ACMEd comes with a set of hooks that should serve most situations. Hook names being unique, the following names and any other name starting by those is reserved and should not be used.
  376. .Bl -tag
  377. .It Pa git
  378. This hook uses
  379. .Xr git 1
  380. to archive private keys, public keys and certificates. It is possible to customize the commit username and email by using respectively the
  381. .Ev GIT_USERNAME
  382. and
  383. .Ev GIT_EMAIL
  384. environment variables.
  385. .It Pa http-01-echo
  386. This hook is designed to solve the http-01 challenge. For this purpose, it will write the proof into
  387. .Pa {{env.HTTP_ROOT}}/{{domain}}/.well-known/acme-challenge/{{file_name}} .
  388. .Pp
  389. The web server must be configured so the file
  390. .Pa http://{{domain}}/.well-known/acme-challenge/{{file_name}}
  391. can be accessed from the CA.
  392. .Pp
  393. If
  394. .Ev HTTP_ROOT
  395. is not specified, it will be set to
  396. .Pa /var/www .
  397. .It Pa tls-alpn-01-tacd-tcp
  398. This hook is designed to solve the tls-alpn-01 challenge using
  399. .Xr tacd 8 .
  400. It requires
  401. .Xr pkill 1
  402. to support the
  403. .Em Ar -F
  404. option.
  405. .Pp
  406. .Xr tacd 8
  407. will listen on the host defined by the
  408. .Ev TACD_HOST
  409. environment variable (default is the domain to be validated) and on the port defined by the
  410. .Ev TACD_PORT
  411. environment variable (default is 5001).
  412. .Pp
  413. .Xr tacd 8
  414. will store its pid into
  415. .Pa {{TACD_PID_ROOT}}/tacd_{{domain}}.pid .
  416. If
  417. .Ev TACD_PID_ROOT
  418. is not specified, it will be set to
  419. .Pa /run .
  420. .It Pa tls-alpn-01-tacd-unix
  421. This hook is designed to solve the tls-alpn-01 challenge using
  422. .Xr tacd 8 .
  423. It requires
  424. .Xr pkill 1
  425. to support the
  426. .Em Ar -F
  427. option.
  428. .Pp
  429. .Xr tacd 8
  430. will listen on the unix socket
  431. .Pa {{env.TACD_SOCK_ROOT}}/tacd_{{domain}}.sock .
  432. If
  433. .Ev TACD_SOCK_ROOT
  434. is not specified, it will be set to
  435. .Pa /run .
  436. .Pp
  437. .Xr tacd 8
  438. will store its pid into
  439. .Pa {{TACD_PID_ROOT}}/tacd_{{domain}}.pid .
  440. If
  441. .Ev TACD_PID_ROOT
  442. is not specified, it will be set to
  443. .Pa /run .
  444. .El
  445. .Sh FILES
  446. .Bl -tag
  447. .It Pa /etc/acmed/acmed.toml
  448. Default
  449. .Xr acmed 8
  450. configuration file.
  451. .It Pa /etc/acmed/accounts
  452. Default accounts private and public keys directory.
  453. .It Pa /etc/acmed/certs
  454. Default certificates and associated private keys directory.
  455. .Sh EXAMPLES
  456. The following example defines a typical endpoint, account and certificate for a domain and several subdomains.
  457. .Bd -literal -offset indent
  458. [[endpoint]]
  459. name = "example name"
  460. url = "https://acme.example.org/directory"
  461. tos_agreed = true
  462. [[account]]
  463. name = "my test account"
  464. email = "certs@exemple.net"
  465. [[certificate]]
  466. endpoint = "example name"
  467. account = "my test account"
  468. domains = [
  469. { dns = "exemple.net", challenge = "http-01"},
  470. { dns = "1.exemple.net", challenge = "dns-01"},
  471. { dns = "2.exemple.net", challenge = "tls-alpn-01", env.TACD_PORT="5010"},
  472. { dns = "3.exemple.net", challenge = "tls-alpn-01", env.TACD_PORT="5011"},
  473. ]
  474. hooks = ["git", "http-01-echo", "tls-alpn-01-tacd-tcp", "some-dns-01-hook"]
  475. env.HTTP_ROOT = "/srv/http"
  476. .Ed
  477. .Pp
  478. It is possible to use
  479. .Xr echo 1
  480. to solve the
  481. .Em http-01
  482. challenge and
  483. .Xr rm 1
  484. to clean it.
  485. .Xr mkdir 1
  486. and
  487. .Xr chmod 1
  488. are used to prevent issues related to file access.
  489. .Bd -literal -offset indent
  490. [[hook]]
  491. name = "http-01-echo-mkdir"
  492. type = ["challenge-http-01"]
  493. cmd = "mkdir"
  494. args = [
  495. "-m", "0755",
  496. "-p", "{{%if env.HTTP_ROOT}}{{env.HTTP_ROOT}}{{else}}/var/www{{/if}}/{{domain}}/.well-known/acme-challenge"
  497. ]
  498. [[hook]]
  499. name = "http-01-echo-echo"
  500. type = ["challenge-http-01"]
  501. cmd = "echo"
  502. args = ["{{proof}}"]
  503. stdout = "{{%if env.HTTP_ROOT}}{{env.HTTP_ROOT}}{{else}}/var/www{{/if}}/{{domain}}/.well-known/acme-challenge/{{file_name}}"
  504. [[hook]]
  505. name = "http-01-echo-chmod"
  506. type = ["challenge-http-01-clean"]
  507. cmd = "chmod"
  508. args = [
  509. "a+r",
  510. "{{%if env.HTTP_ROOT}}{{env.HTTP_ROOT}}{{else}}/var/www{{/if}}/{{domain}}/.well-known/acme-challenge/{{file_name}}"
  511. ]
  512. [[hook]]
  513. name = "http-01-echo-clean"
  514. type = ["challenge-http-01-clean"]
  515. cmd = "rm"
  516. args = [
  517. "-f",
  518. "{{%if env.HTTP_ROOT}}{{env.HTTP_ROOT}}{{else}}/var/www{{/if}}/{{domain}}/.well-known/acme-challenge/{{file_name}}"
  519. ]
  520. .Ed
  521. .Pp
  522. The hooks from the previous example can be grouped in order to reduce the number of hooks to define in the certificate.
  523. .Bd -literal -offset indent
  524. [[group]]
  525. name = "http-01-echo-var-www"
  526. hooks = [
  527. "http-01-echo-mkdir",
  528. "http-01-echo-echo",
  529. "http-01-echo-chmod",
  530. "http-01-echo-clean"
  531. ]
  532. [[certificate]]
  533. # Some fields omitted
  534. hooks = ["http-01-echo"]
  535. env.HTTP_ROOT = "/srv/http"
  536. .Ed
  537. .Pp
  538. It is also possible to use
  539. .Xr sendmail 8
  540. in a hook in order to notif someone when the certificate request process is done.
  541. .Bd -literal -offset indent
  542. [[hook]]
  543. name = "email-report"
  544. type = ["post-operation"]
  545. cmd = "sendmail"
  546. args = [
  547. "-f", "noreply.certs@example.net",
  548. "contact@example.net"
  549. ]
  550. stdin_str = """Subject: Certificate renewal {{#if is_success}}succeeded{{else}}failed{{/if}} for {{domains.[0]}}
  551. The following certificate has {{#unless is_success}}*not* {{/unless}}been renewed.
  552. domains: {{#each domains}}{{#if @index}}, {{/if}}{{this}}{{/each}}
  553. algorithm: {{algorithm}}
  554. status: {{status}}"""
  555. .Ed
  556. .Sh SEE ALSO
  557. .Xr acmed 8 ,
  558. .Xr tacd 8
  559. .Sh STANDARDS
  560. .Bl
  561. .It
  562. .Rs
  563. .%A Tom Preston-Werner
  564. .%D July 2018
  565. .%T TOML v0.5.0
  566. .%U https://github.com/toml-lang/toml
  567. .Re
  568. .It
  569. .Rs
  570. .%A Yehuda Katz
  571. .%T Handlebars
  572. .%U https://handlebarsjs.com/
  573. .Re
  574. .El
  575. .Sh AUTHORS
  576. .An Rodolphe Bréard
  577. .Aq rodolphe@breard.tf