func revokeByKeyID(s storage.Store, keyID string) error { k := s.KeyByID(keyID) if k == nil { return fmt.Errorf("cannot find certificate or key with given ID: %q", keyID) } var merr storage.MultiError s.VisitCertificates(func(c *storage.Certificate) error { if c.Key != k { return nil // continue } err := RevokeByCertificateOrKeyID(s, c.ID()) if err != nil { merr = append(merr, fmt.Errorf("failed to mark %v for revocation: %v", c, err)) } return nil }) if len(merr) > 0 { return merr } return nil }
func FindBestCertificateSatisfying(s storage.Store, t *storage.Target) (*storage.Certificate, error) { var bestCert *storage.Certificate err := s.VisitCertificates(func(c *storage.Certificate) error { if DoesCertificateSatisfy(c, t) { isBetterThan, err := CertificateBetterThan(c, bestCert) if err != nil { return err } if isBetterThan { log.Tracef("findBestCertificateSatisfying: %v > %v", c, bestCert) bestCert = c } else { log.Tracef("findBestCertificateSatisfying: %v <= %v", c, bestCert) } } return nil }) if err != nil { return nil, err } if bestCert == nil { return nil, fmt.Errorf("%v: no certificate satisfies this target", t) } return bestCert, nil }
func importLEAccount(s storage.Store, lePath, accountName string) (*storage.Account, error) { providerURL, err := getProviderURLFromAccountName(accountName) if err != nil { return nil, err } knownProviderURLs[providerURL] = struct{}{} pkPath := filepath.Join(lePath, "accounts", accountName, "private_key.json") b, err := ioutil.ReadFile(pkPath) if err != nil { return nil, err } k := jose.JsonWebKey{} err = k.UnmarshalJSON(b) if err != nil { return nil, err } acct, err := s.ImportAccount(providerURL, k.Key) if err != nil { return nil, err } return acct, nil }
func importCert(s *storage.Store, filename string) error { certURL, err := determineLECertificateURL(filename) if err != nil { return err } return s.ImportCertificate(certURL) }
func importKey(s *storage.Store, filename string) error { f, err := os.Open(filename) if err != nil { return err } defer f.Close() return s.ImportKey(f) }
func HaveUncachedCertificates(s storage.Store) bool { haveUncached := false s.VisitCertificates(func(c *storage.Certificate) error { if !c.Cached { haveUncached = true } return nil }) return haveUncached }
func importKey(s storage.Store, filename string) error { b, err := ioutil.ReadFile(filename) if err != nil { return err } pk, err := acmeutils.LoadPrivateKey(b) if err != nil { return err } _, err = s.ImportKey(pk) return err }
func RevokeByCertificateOrKeyID(s storage.Store, id string) error { c := s.CertificateByID(id) if c == nil { return revokeByKeyID(s, id) } if c.Revoked { log.Warnf("%v already revoked", c) return nil } c.RevocationDesired = true return s.SaveCertificate(c) }
// Update targets to remove any mention of hostname from all targets. The // targets are resaved to disk. func RemoveTargetHostname(s storage.Store, hostname string) error { return s.VisitTargets(func(t *storage.Target) error { if !containsName(t.Satisfy.Names, hostname) { return nil // continue } t.Satisfy.Names = removeStringFromList(t.Satisfy.Names, hostname) t.Request.Names = removeStringFromList(t.Request.Names, hostname) if len(t.Satisfy.Names) == 0 { return s.RemoveTarget(t.Filename) } return s.SaveTarget(t) }) }
func Cull(s storage.Store, simulate bool) error { certificatesToCull := map[string]*storage.Certificate{} // Relink before culling. err := Relink(s) if err != nil { return err } // Select all certificates. s.VisitCertificates(func(c *storage.Certificate) error { certificatesToCull[c.ID()] = c return nil }) // Unselect any certificate which is currently referenced. s.VisitPreferredCertificates(func(hostname string, c *storage.Certificate) error { delete(certificatesToCull, c.ID()) return nil }) // Now delete any certificate which is not generally valid. for certID, c := range certificatesToCull { if CertificateGenerallyValid(c) { continue } if simulate { log.Noticef("would delete certificate %s", certID) } else { log.Noticef("deleting certificate %s", certID) err := s.RemoveCertificate(certID) log.Errore(err, "failed to delete certificate ", certID) } } return nil }
func StatusString(s storage.Store) string { var buf bytes.Buffer fmt.Fprintf(&buf, "Settings:\n") fmt.Fprintf(&buf, " ACME_STATE_DIR: %s\n", s.Path()) fmt.Fprintf(&buf, " ACME_HOOKS_DIR: %s\n", hooks.DefaultPath) fmt.Fprintf(&buf, " Default directory URL: %s\n", s.DefaultTarget().Request.Provider) fmt.Fprintf(&buf, " Preferred key type: %v\n", &s.DefaultTarget().Request.Key) fmt.Fprintf(&buf, " Additional webroots:\n") for _, wr := range s.DefaultTarget().Request.Challenge.WebrootPaths { fmt.Fprintf(&buf, " %s\n", wr) } fmt.Fprintf(&buf, "\nAvailable accounts:\n") s.VisitAccounts(func(a *storage.Account) error { fmt.Fprintf(&buf, " %v\n", a) thumbprint, _ := acmeutils.Base64Thumbprint(a.PrivateKey) fmt.Fprintf(&buf, " thumbprint: %s\n", thumbprint) return nil }) fmt.Fprintf(&buf, "\n") s.VisitTargets(func(t *storage.Target) error { fmt.Fprintf(&buf, "%v\n", t) c, err := storageops.FindBestCertificateSatisfying(s, t) if err != nil { fmt.Fprintf(&buf, " error: %v\n", err) return nil // continue } renewStr := "" if storageops.CertificateNeedsRenewing(c) { renewStr = " needs-renewing" } fmt.Fprintf(&buf, " best: %v%s\n", c, renewStr) return nil }) if storageops.HaveUncachedCertificates(s) { fmt.Fprintf(&buf, "\nThere are uncached certificates.\n") } return buf.String() }