Skip to content

Commit

Permalink
Merge pull request #44 from sl1pm4t/volume-secret-item
Browse files Browse the repository at this point in the history
Update Secret Volume to support `items`.
  • Loading branch information
radeksimko authored Aug 14, 2017
2 parents 4722806 + 97a6a63 commit 5e18a34
Show file tree
Hide file tree
Showing 6 changed files with 155 additions and 2 deletions.
72 changes: 72 additions & 0 deletions kubernetes/resource_kubernetes_pod_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -354,6 +354,32 @@ func TestAccKubernetesPod_with_empty_dir_volume(t *testing.T) {
})
}

func TestAccKubernetesPod_with_secret_vol_items(t *testing.T) {
var conf api.Pod

secretName := fmt.Sprintf("tf-acc-test-%s", acctest.RandStringFromCharSet(10, acctest.CharSetAlphaNum))
podName := fmt.Sprintf("tf-acc-test-%s", acctest.RandStringFromCharSet(10, acctest.CharSetAlphaNum))
imageName := "nginx:1.7.9"

resource.Test(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckKubernetesPodDestroy,
Steps: []resource.TestStep{
{
Config: testAccKubernetesPodConfigWithSecretItemsVolume(secretName, podName, imageName),
Check: resource.ComposeAggregateTestCheckFunc(
testAccCheckKubernetesPodExists("kubernetes_pod.test", &conf),
resource.TestCheckResourceAttr("kubernetes_pod.test", "spec.0.container.0.image", imageName),
resource.TestCheckResourceAttr("kubernetes_pod.test", "spec.0.volume.0.secret.0.items.#", "1"),
resource.TestCheckResourceAttr("kubernetes_pod.test", "spec.0.volume.0.secret.0.items.0.key", "one"),
resource.TestCheckResourceAttr("kubernetes_pod.test", "spec.0.volume.0.secret.0.items.0.path", "path/to/one"),
),
},
},
})
}

func TestAccKubernetesPod_with_nodeSelector(t *testing.T) {
var conf api.Pod

Expand Down Expand Up @@ -716,6 +742,52 @@ resource "kubernetes_pod" "test" {
`, secretName, podName, imageName)
}

func testAccKubernetesPodConfigWithSecretItemsVolume(secretName, podName, imageName string) string {
return fmt.Sprintf(`
resource "kubernetes_secret" "test" {
metadata {
name = "%s"
}
data {
one = "first"
}
}
resource "kubernetes_pod" "test" {
metadata {
labels {
app = "pod_label"
}
name = "%s"
}
spec {
container {
image = "%s"
name = "containername"
volume_mount {
mount_path = "/tmp/my_path"
name = "db"
}
}
volume {
name = "db"
secret {
secret_name = "${kubernetes_secret.test.metadata.0.name}"
items {
key = "one"
path = "path/to/one"
}
}
}
}
}
`, secretName, podName, imageName)
}

func testAccKubernetesPodConfigWithConfigMapVolume(secretName, podName, imageName string) string {
return fmt.Sprintf(`
resource "kubernetes_config_map" "test" {
Expand Down
37 changes: 37 additions & 0 deletions kubernetes/schema_pod_spec.go
Original file line number Diff line number Diff line change
Expand Up @@ -355,6 +355,43 @@ func volumeSchema() *schema.Resource {
MaxItems: 1,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"default_mode": {
Type: schema.TypeInt,
Description: "Optional: mode bits to use on created files by default. Must be a value between 0 and 0777. Defaults to 0644. Directories within the path are not affected by this setting. This might be in conflict with other options that affect the file mode, like fsGroup, and the result can be other mode bits set.",
Optional: true,
Default: 0644,
ValidateFunc: validateModeBits,
},
"items": {
Type: schema.TypeList,
Description: "If unspecified, each key-value pair in the Data field of the referenced Secret will be projected into the volume as a file whose name is the key and content is the value. If specified, the listed keys will be projected into the specified paths, and unlisted keys will not be present. If a key is specified which is not present in the Secret, the volume setup will error unless it is marked optional. Paths must be relative and may not contain the '..' path or start with '..'.",
Optional: true,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"key": {
Type: schema.TypeString,
Optional: true,
Description: "The key to project.",
},
"mode": {
Type: schema.TypeInt,
Optional: true,
Description: "Optional: mode bits to use on this file, must be a value between 0 and 0777. If not specified, the volume defaultMode will be used. This might be in conflict with other options that affect the file mode, like fsGroup, and the result can be other mode bits set.",
},
"path": {
Type: schema.TypeString,
Optional: true,
ValidateFunc: validateAttributeValueDoesNotContain(".."),
Description: "The relative path of the file to map the key to. May not be an absolute path. May not contain the path element '..'. May not start with the string '..'.",
},
},
},
},
"optional": {
Type: schema.TypeBool,
Description: "Optional: Specify whether the Secret or it's keys must be defined.",
Optional: true,
},
"secret_name": {
Type: schema.TypeString,
Description: "Name of the secret in the pod's namespace to use. More info: http://kubernetes.io/docs/user-guide/volumes#secrets",
Expand Down
28 changes: 27 additions & 1 deletion kubernetes/structures_pod.go
Original file line number Diff line number Diff line change
Expand Up @@ -279,9 +279,28 @@ func flattenEmptyDirVolumeSource(in *v1.EmptyDirVolumeSource) []interface{} {

func flattenSecretVolumeSource(in *v1.SecretVolumeSource) []interface{} {
att := make(map[string]interface{})
if in.DefaultMode != nil {
att["default_mode"] = *in.DefaultMode
}
if in.SecretName != "" {
att["secret_name"] = in.SecretName
}
if len(in.Items) > 0 {
items := make([]interface{}, len(in.Items))
for i, v := range in.Items {
m := map[string]interface{}{}
m["key"] = v.Key
if v.Mode != nil {
m["mode"] = int(*v.Mode)
}
m["path"] = v.Path
items[i] = m
}
att["items"] = items
}
if in.Optional != nil {
att["optional"] = *in.Optional
}
return []interface{}{att}
}

Expand Down Expand Up @@ -560,8 +579,15 @@ func expandSecretVolumeSource(l []interface{}) *v1.SecretVolumeSource {
}
in := l[0].(map[string]interface{})
obj := &v1.SecretVolumeSource{
SecretName: in["secret_name"].(string),
DefaultMode: ptrToInt32(int32(in["default_mode"].(int))),
SecretName: in["secret_name"].(string),
Optional: ptrToBool(in["optional"].(bool)),
}

if v, ok := in["items"].([]interface{}); ok && len(v) > 0 {
obj.Items = expandKeyPath(v)
}

return obj
}

Expand Down
2 changes: 1 addition & 1 deletion kubernetes/validators.go
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ func validateModeBits(value interface{}, key string) (ws []string, es []error) {
func validateAttributeValueDoesNotContain(searchString string) schema.SchemaValidateFunc {
return func(v interface{}, k string) (ws []string, errors []error) {
input := v.(string)
if !strings.Contains(input, searchString) {
if strings.Contains(input, searchString) {
errors = append(errors, fmt.Errorf(
"%q must not contain %q",
k, searchString))
Expand Down
9 changes: 9 additions & 0 deletions website/docs/r/pod.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -445,8 +445,17 @@ The following arguments are supported:

#### Arguments

* `default_mode` - (Optional) Mode bits to use on created files by default. Must be a value between 0 and 0777. Defaults to 0644. Directories within the path are not affected by this setting. This might be in conflict with other options that affect the file mode, like fsGroup, and the result can be other mode bits set.
* `items` - (Optional) List of Secret Items to project into the volume. See `items` block definition below. If unspecified, each key-value pair in the Data field of the referenced Secret will be projected into the volume as a file whose name is the key and content is the value. If specified, the listed keys will be projected into the specified paths, and unlisted keys will not be present. If a key is specified which is not present in the Secret, the volume setup will error unless it is marked `optional`. Paths must be relative and may not contain the '..' path or start with '..'.
* `optional` - (Optional) Specify whether the Secret or it's keys must be defined.
* `secret_name` - (Optional) Name of the secret in the pod's namespace to use. More info: http://kubernetes.io/docs/user-guide/volumes#secrets

The `items` block supports the following:

* `key` - (Required) The key to project.
* `mode` - (Optional) Mode bits to use on this file, must be a value between 0 and 0777. If not specified, the volume defaultMode will be used.
* `path` - (Required) The relative path of the file to map the key to. May not be an absolute path. May not contain the path element '..'. May not start with the string '..'.

### `secret_key_ref`

#### Arguments
Expand Down
9 changes: 9 additions & 0 deletions website/docs/r/replication_controller.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -472,8 +472,17 @@ The following arguments are supported:

#### Arguments

* `default_mode` - (Optional) Mode bits to use on created files by default. Must be a value between 0 and 0777. Defaults to 0644. Directories within the path are not affected by this setting. This might be in conflict with other options that affect the file mode, like fsGroup, and the result can be other mode bits set.
* `items` - (Optional) List of Secret Items to project into the volume. See `items` block definition below. If unspecified, each key-value pair in the Data field of the referenced Secret will be projected into the volume as a file whose name is the key and content is the value. If specified, the listed keys will be projected into the specified paths, and unlisted keys will not be present. If a key is specified which is not present in the Secret, the volume setup will error unless it is marked `optional`. Paths must be relative and may not contain the '..' path or start with '..'.
* `optional` - (Optional) Specify whether the Secret or it's keys must be defined.
* `secret_name` - (Optional) Name of the secret in the pod's namespace to use. More info: http://kubernetes.io/docs/user-guide/volumes#secrets

The `items` block supports:

* `key` - (Required) The key to project.
* `mode` - (Optional) Mode bits to use on this file, must be a value between 0 and 0777. If not specified, the volume defaultMode will be used.
* `path` - (Required) The relative path of the file to map the key to. May not be an absolute path. May not contain the path element '..'. May not start with the string '..'.

### `secret_key_ref`

#### Arguments
Expand Down

0 comments on commit 5e18a34

Please sign in to comment.