]> git.proxmox.com Git - pve-docs.git/blame - certificate-management.adoc
cert management: split examples a bit up for readabillity
[pve-docs.git] / certificate-management.adoc
CommitLineData
aeecd9ea
SI
1[[sysadmin_certificate_management]]
2Certificate Management
3----------------------
4ifdef::wiki[]
5:pve-toplevel:
6endif::wiki[]
7
8
9Certificates for communication within the cluster
10~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
11
94958b8b 12Each {PVE} cluster creates its own (self-signed) Certificate Authority (CA) and
1a58a3c9
TL
13generates a certificate for each node which gets signed by the aforementioned
14CA. These certificates are used for encrypted communication with the cluster's
15`pveproxy` service and the Shell/Console feature if SPICE is used.
aeecd9ea 16
2971c735 17The CA certificate and key are stored in the xref:chapter_pmxcfs[Proxmox Cluster File System (pmxcfs)].
aeecd9ea
SI
18
19Certificates for API and web GUI
20~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
21
0e9c6c13
FG
22The REST API and web GUI are provided by the `pveproxy` service, which runs on
23each node.
aeecd9ea
SI
24
25You have the following options for the certificate used by `pveproxy`:
26
0e9c6c13
FG
271. By default the node-specific certificate in
28`/etc/pve/nodes/NODENAME/pve-ssl.pem` is used. This certificate is signed by
29the cluster CA and therefore not trusted by browsers and operating systems by
30default.
312. use an externally provided certificate (e.g. signed by a commercial CA).
da30f82a
TL
323. use ACME (e.g., Let's Encrypt) to get a trusted certificate with automatic
33renewal, this is also integrated in the {pve} API and Webinterface.
aeecd9ea 34
0e9c6c13 35For options 2 and 3 the file `/etc/pve/local/pveproxy-ssl.pem` (and
aeecd9ea
SI
36`/etc/pve/local/pveproxy-ssl.key`, which needs to be without password) is used.
37
da30f82a
TL
38NOTE: Keep in mind that `/etc/pve/local` is a node specific symlink to
39`/etc/pve/nodes/NODENAME`.
40
aeecd9ea
SI
41Certificates are managed with the {PVE} Node management command
42(see the `pvenode(1)` manpage).
43
0e9c6c13
FG
44WARNING: Do not replace or manually modify the automatically generated node
45certificate files in `/etc/pve/local/pve-ssl.pem` and
46`/etc/pve/local/pve-ssl.key` or the cluster CA files in
47`/etc/pve/pve-root-ca.pem` and `/etc/pve/priv/pve-root-ca.key`.
aeecd9ea
SI
48
49Getting trusted certificates via ACME
50^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
51{PVE} includes an implementation of the **A**utomatic **C**ertificate
52**M**anagement **E**nvironment **ACME** protocol, allowing {pve} admins to
0e9c6c13
FG
53interface with Let's Encrypt for easy setup of trusted TLS certificates which
54are accepted out of the box on most modern operating systems and browsers.
aeecd9ea
SI
55
56Currently the two ACME endpoints implemented are Let's Encrypt (LE) and its
0b447f1c
FG
57staging environment (see https://letsencrypt.org). Our ACME client supports
58validation of `http-01` challenges using a built-in webserver and validation of
59`dns-01` challenges using a DNS plugin.
aeecd9ea
SI
60
61Because of https://letsencrypt.org/docs/rate-limits/[rate-limits] you should use
62LE `staging` for experiments.
63
0b447f1c
FG
64ACME Plugin configuration is stored in `/etc/pve/priv/acme/plugins.cfg`. There
65is always an implicitly configured `standalone` plugin for validating `http-01`
66challenges via the built-in webserver spawned on port 80.
67
aeecd9ea
SI
68There are a few prerequisites to use Let's Encrypt:
69
0b447f1c
FG
70* You have to accept the ToS of Let's Encrypt to register an account.
71
72For `http-01` challenges:
73
74* **Port 80** of the node needs to be reachable from the internet.
75* There **must** be no other listener on port 80.
76* The requested (sub)domain needs to resolve to a public IP of the Node.
77
78For `dns-01` challenges:
79
80* DNS needs to be handled by a server that allows automatic provisioning of
81TXT records
aeecd9ea
SI
82
83At the moment the GUI uses only the default ACME account.
84
85.Example: Sample `pvenode` invocation for using Let's Encrypt certificates
86
b0014034 87----
aeecd9ea
SI
88root@proxmox:~# pvenode acme account register default mail@example.invalid
89Directory endpoints:
900) Let's Encrypt V2 (https://acme-v02.api.letsencrypt.org/directory)
911) Let's Encrypt V2 Staging (https://acme-staging-v02.api.letsencrypt.org/directory)
922) Custom
93Enter selection:
941
95
96Attempting to fetch Terms of Service from 'https://acme-staging-v02.api.letsencrypt.org/directory'..
97Terms of Service: https://letsencrypt.org/documents/LE-SA-v1.2-November-15-2017.pdf
98Do you agree to the above terms? [y|N]y
99
100Attempting to register account with 'https://acme-staging-v02.api.letsencrypt.org/directory'..
101Generating ACME account key..
102Registering ACME account..
103Registration successful, account URL: 'https://acme-staging-v02.api.letsencrypt.org/acme/acct/xxxxxxx'
104Task OK
105root@proxmox:~# pvenode acme account list
106default
107root@proxmox:~# pvenode config set --acme domains=example.invalid
108root@proxmox:~# pvenode acme cert order
109Loading ACME account details
110Placing ACME order
111Order URL: https://acme-staging-v02.api.letsencrypt.org/acme/order/xxxxxxxxxxxxxx
112
113Getting authorization details from
114'https://acme-staging-v02.api.letsencrypt.org/acme/authz/xxxxxxxxxxxxxxxxxxxxx-xxxxxxxxxxxxx-xxxxxxx'
115... pending!
116Setting up webserver
117Triggering validation
118Sleeping for 5 seconds
119Status is 'valid'!
120
121All domains validated!
122
123Creating CSR
124Finalizing order
125Checking order status
126valid!
127
128Downloading certificate
129Setting pveproxy certificate and key
130Restarting pveproxy
131Task OK
d75e644b 132----
0e9c6c13 133
19b04e77 134Switching from the `staging` to the regular ACME directory
b0014034 135^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
19b04e77
SI
136
137Changing the ACME directory for an account is unsupported. If you want to switch
138an account from the `staging` ACME directory to the regular, trusted, one you
139need to deactivate it and recreate it.
140
141This procedure is also needed to change the default ACME account used in the GUI.
142
143.Example: Changing the `default` ACME account from the `staging` to the regular directory
144
d75e644b 145----
19b04e77
SI
146root@proxmox:~# pvenode acme account info default
147Directory URL: https://acme-staging-v02.api.letsencrypt.org/directory
148Account URL: https://acme-staging-v02.api.letsencrypt.org/acme/acct/6332194
149Terms Of Service: https://letsencrypt.org/documents/LE-SA-v1.2-November-15-2017.pdf
150
151Account information:
152ID: xxxxxxx
153Contact:
154 - mailto:example@proxmox.com
155Creation date: 2018-07-31T08:41:44.54196435Z
156Initial IP: 192.0.2.1
157Status: valid
158
159root@proxmox:~# pvenode acme account deactivate default
160Renaming account file from '/etc/pve/priv/acme/default' to '/etc/pve/priv/acme/_deactivated_default_4'
161Task OK
d75e644b 162
19b04e77
SI
163root@proxmox:~# pvenode acme account register default example@proxmox.com
164Directory endpoints:
1650) Let's Encrypt V2 (https://acme-v02.api.letsencrypt.org/directory)
1661) Let's Encrypt V2 Staging (https://acme-staging-v02.api.letsencrypt.org/directory)
1672) Custom
168Enter selection:
1690
170
171Attempting to fetch Terms of Service from 'https://acme-v02.api.letsencrypt.org/directory'..
172Terms of Service: https://letsencrypt.org/documents/LE-SA-v1.2-November-15-2017.pdf
173Do you agree to the above terms? [y|N]y
174
175Attempting to register account with 'https://acme-v02.api.letsencrypt.org/directory'..
176Generating ACME account key..
177Registering ACME account..
178Registration successful, account URL: 'https://acme-v02.api.letsencrypt.org/acme/acct/39335247'
179Task OK
d75e644b 180----
19b04e77 181
0e9c6c13
FG
182Automatic renewal of ACME certificates
183^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
184
185If a node has been successfully configured with an ACME-provided certificate
186(either via pvenode or via the GUI), the certificate will be automatically
187renewed by the pve-daily-update.service. Currently, renewal will be attempted
da30f82a 188if the certificate has expired already, or will expire in the next 30 days.
0b447f1c
FG
189
190Configuring DNS APIs for validation
191^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
192
193On systems where external access for validation via the `http-01` method is
194not possible or desired, it is possible to use the `dns-01` validation method.
195This validation method requires a DNS server that allows provisioning of `TXT`
196records via an API.
197
198{PVE} re-uses the DNS plugins developed for the `acme.sh`
199footnote:[acme.sh https://github.com/acmesh-official/acme.sh]
200project, please refer to its documentation for details on configuration of
201specific APIs.
202
203Combining `http-01` and `dns-01` validation is possible in case your node is
204reachable via multiple domains with different requirements / DNS provisioning
205capabilities. Mixing DNS APIs from multiple providers or instances is also
206possible by specifying different plugin instances per domain.
207
208A special `alias` mode can be used to handle the validation on a different
209domain/DNS server, in case your primary/real DNS does not support provisioning
210via an API. Manually set up a permanent `CNAME` record for
211`_acme-challenge.domain1.example` pointing to `_acme-challenge.domain2.example`
212and set the `alias` property in the {PVE} node configuration file to
213`domain2.example` to allow the DNS server of `domain2.example` to validate all
214challenges for `domain1.example`.
215
216.Example: Setting up the OVH API for validating a domain
217
186c094b
TL
218NOTE: the account registration steps are the same no matter which plugins are
219used, and are not repeated here.
220
221NOTE: `OVH_AK` and `OVH_AS` need to be obtained from OVH according to the OVH
222API documentation
223
224
225First you need to get all information so you and {pve} can access the API.
0b447f1c
FG
226
227----
228root@proxmox:~# cat /path/to/api-token
229OVH_AK=XXXXXXXXXXXXXXXX
230OVH_AS=YYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYY
231root@proxmox:~# source /path/to/api-token
232root@proxmox:~# curl -XPOST -H"X-Ovh-Application: $OVH_AK" -H "Content-type: application/json" \
233https://eu.api.ovh.com/1.0/auth/credential -d '{
234 "accessRules": [
235 {"method": "GET","path": "/auth/time"},
236 {"method": "GET","path": "/domain"},
237 {"method": "GET","path": "/domain/zone/*"},
238 {"method": "GET","path": "/domain/zone/*/record"},
239 {"method": "POST","path": "/domain/zone/*/record"},
240 {"method": "POST","path": "/domain/zone/*/refresh"},
241 {"method": "PUT","path": "/domain/zone/*/record/"},
242 {"method": "DELETE","path": "/domain/zone/*/record/*"}
243]
244}'
245{"consumerKey":"ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ","state":"pendingValidation","validationUrl":"https://eu.api.ovh.com/auth/?credentialToken=AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"}
246
247(open validation URL and follow instructions to link Application Key with account/Consumer Key)
248
249root@proxmox:~# echo "OVH_CK=ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" >> /path/to/api-token
186c094b
TL
250----
251
252Now you can setup the the ACME plugin:
253
254----
0b447f1c
FG
255root@proxmox:~# pvenode acme plugin add dns example_plugin --api ovh --data /path/to/api_token
256root@proxmox:~# pvenode acme plugin config example_plugin
257┌────────┬──────────────────────────────────────────┐
258│ key │ value │
259╞════════╪══════════════════════════════════════════╡
260│ api │ ovh │
261├────────┼──────────────────────────────────────────┤
262│ data │ OVH_AK=XXXXXXXXXXXXXXXX │
263│ │ OVH_AS=YYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYY │
264│ │ OVH_CK=ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ │
265├────────┼──────────────────────────────────────────┤
266│ digest │ 867fcf556363ca1bea866863093fcab83edf47a1 │
267├────────┼──────────────────────────────────────────┤
268│ plugin │ example_plugin │
269├────────┼──────────────────────────────────────────┤
270│ type │ dns │
271└────────┴──────────────────────────────────────────┘
186c094b
TL
272----
273
274At last you can configure the domain you want to get certitficates for and
275place the certificate order for it:
276
277----
0b447f1c
FG
278root@proxmox:~# pvenode config set -acmedomain0 example.proxmox.com,plugin=example_plugin
279root@proxmox:~# pvenode acme cert order
280Loading ACME account details
281Placing ACME order
282Order URL: https://acme-staging-v02.api.letsencrypt.org/acme/order/11111111/22222222
283
284Getting authorization details from 'https://acme-staging-v02.api.letsencrypt.org/acme/authz-v3/33333333'
285The validation for example.proxmox.com is pending!
286[Wed Apr 22 09:25:30 CEST 2020] Using OVH endpoint: ovh-eu
287[Wed Apr 22 09:25:30 CEST 2020] Checking authentication
288[Wed Apr 22 09:25:30 CEST 2020] Consumer key is ok.
289[Wed Apr 22 09:25:31 CEST 2020] Adding record
290[Wed Apr 22 09:25:32 CEST 2020] Added, sleep 10 seconds.
291Add TXT record: _acme-challenge.example.proxmox.com
292Triggering validation
293Sleeping for 5 seconds
294Status is 'valid'!
295[Wed Apr 22 09:25:48 CEST 2020] Using OVH endpoint: ovh-eu
296[Wed Apr 22 09:25:48 CEST 2020] Checking authentication
297[Wed Apr 22 09:25:48 CEST 2020] Consumer key is ok.
298Remove TXT record: _acme-challenge.example.proxmox.com
299
300All domains validated!
301
302Creating CSR
303Checking order status
304Order is ready, finalizing order
305valid!
306
307Downloading certificate
308Setting pveproxy certificate and key
309Restarting pveproxy
310Task OK
311----