@@ -24,9 +24,9 @@ import (
2424func getPassphraseRetriever () notary.PassRetriever {
2525 baseRetriever := passphrase .PromptRetriever ()
2626 env := map [string ]string {
27- "root" : os .Getenv ("SIGNY_ROOT_PASSPHRASE" ),
28- "targets" : os .Getenv ("SIGNY_TARGETS_PASSPHRASE" ),
29- "releases" : os .Getenv ("SIGNY_RELEASES_PASSPHRASE" ),
27+ "root" : os .Getenv ("SIGNY_ROOT_PASSPHRASE" ),
28+ "targets" : os .Getenv ("SIGNY_TARGETS_PASSPHRASE" ),
29+ "targets/ releases" : os .Getenv ("SIGNY_RELEASES_PASSPHRASE" ),
3030 }
3131
3232 return func (keyName string , alias string , createNew bool , numAttempts int ) (string , bool , error ) {
@@ -39,18 +39,20 @@ func getPassphraseRetriever() notary.PassRetriever {
3939
4040// Attempt to read a role key from a file, and return it as a data.PrivateKey
4141// If key is for the Root role, it must be encrypted
42- func readKey (role data.RoleName , keyFilename string , retriever notary.PassRetriever ) (data.PrivateKey , error ) {
42+ func readPrivateKey (role data.RoleName , keyFilename string , retriever notary.PassRetriever ) (data.PrivateKey , error ) {
4343 pemBytes , err := ioutil .ReadFile (keyFilename )
4444 if err != nil {
4545 return nil , fmt .Errorf ("Error reading input root key file: %v" , err )
4646 }
47+
4748 isEncrypted := true
4849 if err = cryptoservice .CheckRootKeyIsEncrypted (pemBytes ); err != nil {
4950 if role == data .CanonicalRootRole {
5051 return nil , err
5152 }
5253 isEncrypted = false
5354 }
55+
5456 var privKey data.PrivateKey
5557 if isEncrypted {
5658 privKey , _ , err = trustmanager .GetPasswdDecryptBytes (retriever , pemBytes , "" , data .CanonicalRootRole .String ())
@@ -71,7 +73,7 @@ func importRootKey(rootKey string, nRepo client.Repository, retriever notary.Pas
7173 var rootKeyList []string
7274
7375 if rootKey != "" {
74- privKey , err := readKey (data .CanonicalRootRole , rootKey , retriever )
76+ privKey , err := readPrivateKey (data .CanonicalRootRole , rootKey , retriever )
7577 if err != nil {
7678 return nil , err
7779 }
@@ -89,77 +91,91 @@ func importRootKey(rootKey string, nRepo client.Repository, retriever notary.Pas
8991 // Chooses the first root key available, which is initialization specific
9092 // but should return the HW one first.
9193 rootKeyID := rootKeyList [0 ]
92- log .Debugf ("Signy found root key, using: %s\n " , rootKeyID )
93-
94+ log .Debugf ("found root key: %s\n " , rootKeyID )
9495 return []string {rootKeyID }, nil
9596 }
9697
9798 return []string {}, nil
9899}
99100
101+ // Try to reuse a single targets/releases key across repositories.
102+ func reuseReleasesKey (r client.Repository ) (data.PublicKey , error ) {
103+ // Get all known targets keys.
104+ cryptoService := r .GetCryptoService ()
105+ keyList := cryptoService .ListKeys (releasesRoleName )
106+
107+ // Try to extract a single targets/releases key we can reuse.
108+ switch len (keyList ) {
109+ case 0 :
110+ log .Debugf ("No %s key available, need to make one" , releasesRoleName )
111+ return cryptoService .Create (releasesRoleName , r .GetGUN (), data .ECDSAKey )
112+ case 1 :
113+ log .Debugf ("Nothing to do, only one %s key available" , releasesRoleName )
114+ return cryptoService .GetKey (keyList [0 ]), nil
115+ default :
116+ return nil , fmt .Errorf ("there is more than one %s keys" , releasesRoleName )
117+ }
118+ }
119+
100120// Try to reuse a single targets key across repositories.
101121// FIXME: Unfortunately, short of forking Notary or sending a PR upstream, there isn't an easy way to prevent it
102122// from automagically creating a new, local targets key per TUF metadata repository. We fix this here by undoing
103123// more than one new, local targets key, and reusing any existing local targets key, just like the way Notary
104124// reuses the root key.
105125func reuseTargetsKey (r client.Repository ) error {
106- var (
107- err error
108- thisTargetsKeyID , thatTargetsKeyID string
109- )
110-
111126 // Get all known targets keys.
112- targetsKeyList := r .GetCryptoService ().ListKeys (data .CanonicalTargetsRole )
127+ keyList := r .GetCryptoService ().ListKeys (data .CanonicalTargetsRole )
128+
113129 // Try to extract a single targets key we can reuse.
114- switch len (targetsKeyList ) {
130+ switch len (keyList ) {
115131 case 0 :
116- err = fmt .Errorf ("no targets key despite having initialized a repo" )
132+ return fmt .Errorf ("no targets key despite having initialized a repo" )
117133 case 1 :
118134 log .Debug ("Nothing to do, only one targets key available" )
135+ return nil
119136 case 2 :
120137 // First, we publish current changes to repository in order to list roles.
121138 // FIXME: Find a find better way to list roles w/o publishing changes first.
122- publishErr := r .Publish ()
123- if publishErr != nil {
124- err = publishErr
125- break
139+ err := r .Publish ()
140+ if err != nil {
141+ return err
126142 }
127143
128144 // Get the current top-level roles.
129- roleWithSigs , listRolesErr := r .ListRoles ()
130- if listRolesErr != nil {
131- err = listRolesErr
132- break
145+ roleWithSigs , err := r .ListRoles ()
146+ if err != nil {
147+ return err
133148 }
134149
135150 // Get the current targets key.
136151 // NOTE: We do not delete it, in case the user wants to keep it.
152+ var thisKeyID string
137153 for _ , roleWithSig := range roleWithSigs {
138154 role := roleWithSig .Role
139155 if role .Name == data .CanonicalTargetsRole {
140156 if len (role .KeyIDs ) == 1 {
141- thisTargetsKeyID = role .KeyIDs [0 ]
142- log .Debugf ("This targets keyid: %s" , thisTargetsKeyID )
157+ thisKeyID = role .KeyIDs [0 ]
158+ log .Debugf ("This targets keyid: %s" , thisKeyID )
143159 } else {
144160 return fmt .Errorf ("this targets role has more than 1 key" )
145161 }
146162 }
147163 }
148164
149165 // Get and reuse the other targets key.
150- for _ , keyID := range targetsKeyList {
151- if keyID != thisTargetsKeyID {
152- thatTargetsKeyID = keyID
166+ var thatKeyID string
167+ for _ , keyID := range keyList {
168+ if keyID != thisKeyID {
169+ thatKeyID = keyID
153170 break
154171 }
155172 }
156- log .Debugf ("That targets keyID: %s" , thatTargetsKeyID )
157- log .Debugf ("Before rotating targets key from %s to %s" , thisTargetsKeyID , thatTargetsKeyID )
158- err = r .RotateKey (data .CanonicalTargetsRole , false , []string {thatTargetsKeyID })
173+ log .Debugf ("That targets keyID: %s" , thatKeyID )
174+ log .Debugf ("Before rotating targets key from %s to %s" , thisKeyID , thatKeyID )
175+ err = r .RotateKey (data .CanonicalTargetsRole , false , []string {thatKeyID })
159176 log .Debugf ("After targets key rotation" )
177+ return err
160178 default :
161- err = fmt .Errorf ("there are more than 2 targets keys" )
179+ return fmt .Errorf ("there are more than two targets keys" )
162180 }
163-
164- return err
165181}
0 commit comments