github.com/vtorhonen/terraform@v0.9.0-beta2.0.20170307220345-5d894e4ffda7/builtin/providers/tls/resource_cert_request.go (about) 1 package tls 2 3 import ( 4 "crypto/rand" 5 "crypto/x509" 6 "encoding/pem" 7 "fmt" 8 "net" 9 10 "github.com/hashicorp/terraform/helper/schema" 11 ) 12 13 const pemCertReqType = "CERTIFICATE REQUEST" 14 15 func resourceCertRequest() *schema.Resource { 16 return &schema.Resource{ 17 Create: CreateCertRequest, 18 Delete: DeleteCertRequest, 19 Read: ReadCertRequest, 20 21 Schema: map[string]*schema.Schema{ 22 23 "dns_names": &schema.Schema{ 24 Type: schema.TypeList, 25 Optional: true, 26 Description: "List of DNS names to use as subjects of the certificate", 27 ForceNew: true, 28 Elem: &schema.Schema{ 29 Type: schema.TypeString, 30 }, 31 }, 32 33 "ip_addresses": &schema.Schema{ 34 Type: schema.TypeList, 35 Optional: true, 36 Description: "List of IP addresses to use as subjects of the certificate", 37 ForceNew: true, 38 Elem: &schema.Schema{ 39 Type: schema.TypeString, 40 }, 41 }, 42 43 "key_algorithm": &schema.Schema{ 44 Type: schema.TypeString, 45 Required: true, 46 Description: "Name of the algorithm to use to generate the certificate's private key", 47 ForceNew: true, 48 }, 49 50 "private_key_pem": &schema.Schema{ 51 Type: schema.TypeString, 52 Required: true, 53 Description: "PEM-encoded private key that the certificate will belong to", 54 ForceNew: true, 55 StateFunc: func(v interface{}) string { 56 return hashForState(v.(string)) 57 }, 58 }, 59 60 "subject": &schema.Schema{ 61 Type: schema.TypeList, 62 Required: true, 63 Elem: nameSchema, 64 ForceNew: true, 65 }, 66 67 "cert_request_pem": &schema.Schema{ 68 Type: schema.TypeString, 69 Computed: true, 70 }, 71 }, 72 } 73 } 74 75 func CreateCertRequest(d *schema.ResourceData, meta interface{}) error { 76 key, err := parsePrivateKey(d, "private_key_pem", "key_algorithm") 77 if err != nil { 78 return err 79 } 80 81 subjectConfs := d.Get("subject").([]interface{}) 82 if len(subjectConfs) != 1 { 83 return fmt.Errorf("must have exactly one 'subject' block") 84 } 85 subjectConf := subjectConfs[0].(map[string]interface{}) 86 subject, err := nameFromResourceData(subjectConf) 87 if err != nil { 88 return fmt.Errorf("invalid subject block: %s", err) 89 } 90 91 certReq := x509.CertificateRequest{ 92 Subject: *subject, 93 } 94 95 dnsNamesI := d.Get("dns_names").([]interface{}) 96 for _, nameI := range dnsNamesI { 97 certReq.DNSNames = append(certReq.DNSNames, nameI.(string)) 98 } 99 ipAddressesI := d.Get("ip_addresses").([]interface{}) 100 for _, ipStrI := range ipAddressesI { 101 ip := net.ParseIP(ipStrI.(string)) 102 if ip == nil { 103 return fmt.Errorf("invalid IP address %#v", ipStrI.(string)) 104 } 105 certReq.IPAddresses = append(certReq.IPAddresses, ip) 106 } 107 108 certReqBytes, err := x509.CreateCertificateRequest(rand.Reader, &certReq, key) 109 if err != nil { 110 return fmt.Errorf("Error creating certificate request: %s", err) 111 } 112 certReqPem := string(pem.EncodeToMemory(&pem.Block{Type: pemCertReqType, Bytes: certReqBytes})) 113 114 d.SetId(hashForState(string(certReqBytes))) 115 d.Set("cert_request_pem", certReqPem) 116 117 return nil 118 } 119 120 func DeleteCertRequest(d *schema.ResourceData, meta interface{}) error { 121 d.SetId("") 122 return nil 123 } 124 125 func ReadCertRequest(d *schema.ResourceData, meta interface{}) error { 126 return nil 127 }