1<SplashPage as |Page|> 2 {{#if keyData}} 3 <Page.header> 4 {{#let (or keyData.recovery_keys keyData.keys) as |keyArray|}} 5 <h1 class="title is-4"> 6 Vault has been initialized! 7 {{#if (eq keyArray.length 1)}} 8 Here is your key. 9 {{else}} 10 Here are your {{pluralize keyArray.length "key"}}. 11 {{/if}} 12 </h1> 13 {{/let}} 14 </Page.header> 15 <Page.content> 16 <div class="box is-marginless is-shadowless"> 17 <div class="content"> 18 <p> 19 {{#if keyData.recovery_keys}} 20 Please securely distribute the keys below. Certain privileged operations in Vault such as rekeying the 21 barrier or generating a new root token will require you to provide 22 at least <strong class="has-text-danger">{{secret_threshold}}</strong> of these keys to perform the 23 operation. 24 {{else}} 25 Please securely distribute the keys below. When the Vault is re-sealed, restarted, or stopped, you must 26 provide at least <strong class="has-text-danger">{{secret_threshold}}</strong> of these keys to unseal it 27 again. 28 Vault does not store the master key. Without at least <strong class="has-text-danger">{{secret_threshold}}</strong> 29 keys, your Vault will remain permanently sealed. 30 {{/if}} 31 </p> 32 </div> 33 <div 34 class="message is-list is-highlight" 35 > 36 <div class="message-body"> 37 <h4 class="title is-7 is-marginless"> 38 Initial root token 39 </h4> 40 <MaskedInput 41 @class="is-highlight has-label" 42 @displayOnly={{true}} 43 @value={{keyData.root_token}} 44 @allowCopy={{true}} 45 /> 46 </div> 47 </div> 48 {{#each (or keyData.recovery_keys_base64 keyData.recovery_keys keyData.keys_base64 keyData.keys) as |key index|}} 49 <div 50 data-test-key-box 51 class="message is-list" 52 > 53 <div class="message-body"> 54 <h4 class="title is-7 is-marginless"> 55 Key {{add index 1}} 56 </h4> 57 <MaskedInput 58 @class="has-label" 59 @displayOnly={{true}} 60 @value={{key}} 61 @allowCopy={{true}} 62 /> 63 </div> 64 </div> 65 {{/each}} 66 </div> 67 <div class="box is-marginless is-shadowless"> 68 <div class="field is-grouped-split"> 69 {{#if (and model.sealed (not keyData.recovery_keys))}} 70 <div 71 data-test-advance-button 72 class="control" 73 > 74 {{#link-to 'vault.cluster.unseal' model.name class="button is-primary"}} 75 Continue to Unseal 76 {{/link-to}} 77 </div> 78 {{else}} 79 <div 80 data-test-advance-button 81 class="control" 82 > 83 {{#link-to 'vault.cluster.auth' 84 model.name 85 class=(concat (if model.sealed 'is-loading ' '') 'button is-primary') 86 disabled=model.sealed 87 }} 88 Continue to Authenticate 89 {{/link-to}} 90 </div> 91 {{/if}} 92 <DownloadButton 93 @data={{keyData}} 94 @filename={{keyFilename}} 95 @mime="application/json" 96 @extension="json" 97 @class="button is-ghost" 98 @stringify={{true}} 99 > 100 <Icon @glyph="download" /> Download keys 101 </DownloadButton> 102 </div> 103 </div> 104 </Page.content> 105 {{else}} 106 <Page.header> 107 <h1 class="title h5"> 108 Let's set up the initial set of master keys that you’ll need in case of an emergency 109 </h1> 110 </Page.header> 111 <Page.content> 112 <form 113 {{action 'initCluster' (hash 114 secret_shares=secret_shares 115 secret_threshold=secret_threshold 116 pgp_keys=pgp_keys 117 use_pgp=use_pgp 118 use_pgp_for_root=use_pgp_for_root 119 root_token_pgp_key=root_token_pgp_key 120 ) 121 on="submit" 122 }} 123 id="init" 124 > 125 <div class="box is-marginless is-shadowless"> 126 <MessageError @errors={{errors}} /> 127 <div class="field"> 128 <label 129 for="key-shares" 130 class="is-label" 131 > 132 Key shares 133 </label> 134 <div class="control"> 135 {{input 136 data-test-key-shares="true" 137 class="input" 138 autocomplete="off" 139 spellcheck="false" 140 name="key-shares" 141 type="number" 142 step="1" 143 min="1" 144 pattern="[0-9]*" 145 value=secret_shares 146 }} 147 </div> 148 <p class="help has-text-grey"> 149 The number of key shares to split the master key into 150 </p> 151 </div> 152 <div class="field"> 153 <label 154 for="key-threshold" 155 class="is-label" 156 > 157 Key threshold 158 </label> 159 <div class="control"> 160 {{input 161 data-test-key-threshold="true" 162 class="input" 163 autocomplete="off" 164 spellcheck="false" 165 name="key-threshold" 166 type="number" 167 step="1" 168 min="1" 169 pattern="[0-9]*" 170 value=secret_threshold 171 }} 172 </div> 173 <p class="help has-text-grey"> 174 The number of key shares required to reconstruct the master key 175 </p> 176 </div> 177 <ToggleButton 178 @openLabel="Encrypt output with PGP" 179 @closedLabel="Encrypt output with PGP" 180 @toggleTarget={{this}} 181 @toggleAttr="use_pgp" 182 @class="is-block" 183 /> 184 {{#if use_pgp}} 185 <div class="box init-box"> 186 <p class="help has-text-grey"> 187 The output unseal keys will be encrypted and hex-encoded, in order, with the given public keys. 188 </p> 189 <PgpList 190 @listLength={{secret_shares}} 191 @onDataUpdate={{action 'setKeys'}} 192 /> 193 </div> 194 {{/if}} 195 <ToggleButton 196 @openLabel="Encrypt root token with PGP" 197 @closedLabel="Encrypt root token with PGP" 198 @toggleTarget={{this}} 199 @toggleAttr="use_pgp_for_root" 200 @class="is-block" 201 /> 202 {{#if use_pgp_for_root}} 203 <div class="box init-box"> 204 <p class="help has-text-grey"> 205 The root unseal key will be encrypted and hex-encoded with the given public key. 206 </p> 207 <PgpList 208 @listLength=1 209 @onDataUpdate={{action 'setRootKey'}} 210 /> 211 </div> 212 {{/if}} 213 </div> 214 <div class="box is-marginless is-shadowless"> 215 <button 216 data-test-init-submit 217 type="submit" 218 class="button is-primary {{if loading 'is-loading'}}" 219 disabled={{loading}} 220 > 221 Initialize 222 </button> 223 <div class="init-illustration"> 224 {{svg-jar "initialize"}} 225 </div> 226 </div> 227 </form> 228 </Page.content> 229 {{/if}} 230</SplashPage> 231