Skip to content

Commit

Permalink
Merge pull request #22 from dghubble/ct-snippets
Browse files Browse the repository at this point in the history
Add ability to append Container Linux snippets
  • Loading branch information
sdemos authored Apr 9, 2018
2 parents 7151571 + d0756fc commit 0dc99cc
Show file tree
Hide file tree
Showing 6 changed files with 441 additions and 12 deletions.
57 changes: 45 additions & 12 deletions ct/datasource_ct_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,15 @@ package ct

import (
"encoding/json"
"errors"
"fmt"
"strconv"

"github.com/hashicorp/terraform/helper/hashcode"
"github.com/hashicorp/terraform/helper/schema"

ct "github.com/coreos/container-linux-config-transpiler/config"
ignition "github.com/coreos/ignition/config/v2_1"
ignitionTypesV2_1 "github.com/coreos/ignition/config/v2_1/types"
)

func dataSourceCTConfig() *schema.Resource {
Expand All @@ -26,6 +28,14 @@ func dataSourceCTConfig() *schema.Resource {
Default: "",
ForceNew: true,
},
"snippets": &schema.Schema{
Type: schema.TypeList,
Elem: &schema.Schema{
Type: schema.TypeString,
},
Optional: true,
ForceNew: true,
},
"pretty_print": &schema.Schema{
Type: schema.TypeBool,
Optional: true,
Expand All @@ -52,27 +62,50 @@ func dataSourceCTConfigRead(d *schema.ResourceData, meta interface{}) error {
}

func renderCTConfig(d *schema.ResourceData) (string, error) {
config := d.Get("content").(string)
// unchecked assertions seem to be the norm in Terraform :S
content := d.Get("content").(string)
platform := d.Get("platform").(string)
snippetsIface := d.Get("snippets").([]interface{})
pretty := d.Get("pretty_print").(bool)

// parse bytes int a Container Linux Config
cfg, ast, rpt := ct.Parse([]byte(config))
if rpt.IsFatal() {
return "", errors.New(rpt.String())
snippets := make([]string, len(snippetsIface))
for i := range snippetsIface {
snippets[i] = snippetsIface[i].(string)
}

// convert Container Linux Config to an Ignition Config
ignition, rpt := ct.Convert(cfg, platform, ast)
if rpt.IsFatal() {
return "", errors.New(rpt.String())
ign, err := clcToIgnition([]byte(content), platform)
if err != nil {
return "", err
}

for _, content := range snippets {
ignext, err := clcToIgnition([]byte(content), platform)
if err != nil {
return "", err
}
ign = ignition.Append(ign, ignext)
}

if pretty {
ignitionJSON, err := json.MarshalIndent(&ignition, "", " ")
ignitionJSON, err := json.MarshalIndent(ign, "", " ")
return string(ignitionJSON), err
}

ignitionJSON, err := json.Marshal(&ignition)
ignitionJSON, err := json.Marshal(ign)
return string(ignitionJSON), err
}

// Parse Container Linux config and convert to Ignition v2.1.0 format.
func clcToIgnition(data []byte, platform string) (ignitionTypesV2_1.Config, error) {
// parse bytes into a Container Linux Config
clc, ast, report := ct.Parse([]byte(data))
if report.IsFatal() {
return ignitionTypesV2_1.Config{}, fmt.Errorf("error parsing Container Linux Config: %v", report.String())
}
// convert Container Linux Config to an Ignition Config
ign, report := ct.Convert(clc, platform, ast)
if report.IsFatal() {
return ignitionTypesV2_1.Config{}, fmt.Errorf("error converting to Ignition: %v", report.String())
}
return ign, nil
}
58 changes: 58 additions & 0 deletions ct/datasource_ct_config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,58 @@ const ec2Expected = `{
}
}`

const snippetsResource = `
data "ct_config" "combine" {
pretty_print = true
content = <<EOT
---
storage:
filesystems:
- name: "rootfs"
mount:
device: "/dev/disk/by-label/ROOT"
format: "ext4"
EOT
snippets = [
<<EOT
---
systemd:
units:
- name: docker.service
enable: true
EOT
]
}
`
const snippetsExpected = `{
"ignition": {
"config": {},
"timeouts": {},
"version": "2.1.0"
},
"networkd": {},
"passwd": {},
"storage": {
"filesystems": [
{
"mount": {
"device": "/dev/disk/by-label/ROOT",
"format": "ext4"
},
"name": "rootfs"
}
]
},
"systemd": {
"units": [
{
"enable": true,
"name": "docker.service"
}
]
}
}`

func TestRender(t *testing.T) {
r.UnitTest(t, r.TestCase{
Providers: testProviders,
Expand All @@ -147,6 +199,12 @@ func TestRender(t *testing.T) {
r.TestCheckResourceAttr("data.ct_config.ec2", "rendered", ec2Expected),
),
},
r.TestStep{
Config: snippetsResource,
Check: r.ComposeTestCheckFunc(
r.TestCheckResourceAttr("data.ct_config.combine", "rendered", snippetsExpected),
),
},
},
})
}
5 changes: 5 additions & 0 deletions glide.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 0dc99cc

Please sign in to comment.