aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--statuscake/provider.go40
-rw-r--r--statuscake/provider_test.go38
-rw-r--r--statuscake/resource_statuscaketest.go216
-rw-r--r--statuscake/resource_statuscaketest_test.go202
4 files changed, 496 insertions, 0 deletions
diff --git a/statuscake/provider.go b/statuscake/provider.go
new file mode 100644
index 0000000..abca376
--- /dev/null
+++ b/statuscake/provider.go
@@ -0,0 +1,40 @@
1package statuscake
2
3import (
4 "github.com/DreamItGetIT/statuscake"
5 "github.com/hashicorp/terraform/helper/schema"
6 "github.com/hashicorp/terraform/terraform"
7)
8
9func Provider() terraform.ResourceProvider {
10 return &schema.Provider{
11 Schema: map[string]*schema.Schema{
12 "username": &schema.Schema{
13 Type: schema.TypeString,
14 Required: true,
15 DefaultFunc: schema.EnvDefaultFunc("STATUSCAKE_USERNAME", nil),
16 Description: "Username for StatusCake Account.",
17 },
18 "apikey": &schema.Schema{
19 Type: schema.TypeString,
20 Required: true,
21 DefaultFunc: schema.EnvDefaultFunc("STATUSCAKE_APIKEY", nil),
22 Description: "API Key for StatusCake",
23 },
24 },
25
26 ResourcesMap: map[string]*schema.Resource{
27 "statuscake_test": resourceStatusCakeTest(),
28 },
29
30 ConfigureFunc: providerConfigure,
31 }
32}
33
34func providerConfigure(d *schema.ResourceData) (interface{}, error) {
35 auth := statuscake.Auth{
36 Username: d.Get("username").(string),
37 Apikey: d.Get("apikey").(string),
38 }
39 return statuscake.New(auth)
40}
diff --git a/statuscake/provider_test.go b/statuscake/provider_test.go
new file mode 100644
index 0000000..83045d0
--- /dev/null
+++ b/statuscake/provider_test.go
@@ -0,0 +1,38 @@
1package statuscake
2
3import (
4 "os"
5 "testing"
6
7 "github.com/hashicorp/terraform/helper/schema"
8 "github.com/hashicorp/terraform/terraform"
9)
10
11var testAccProviders map[string]terraform.ResourceProvider
12var testAccProvider *schema.Provider
13
14func init() {
15 testAccProvider = Provider().(*schema.Provider)
16 testAccProviders = map[string]terraform.ResourceProvider{
17 "statuscake": testAccProvider,
18 }
19}
20
21func TestProvider(t *testing.T) {
22 if err := Provider().(*schema.Provider).InternalValidate(); err != nil {
23 t.Fatalf("err: %s", err)
24 }
25}
26
27func TestProvider_impl(t *testing.T) {
28 var _ terraform.ResourceProvider = Provider()
29}
30
31func testAccPreCheck(t *testing.T) {
32 if v := os.Getenv("STATUSCAKE_USERNAME"); v == "" {
33 t.Fatal("STATUSCAKE_USERNAME must be set for acceptance tests")
34 }
35 if v := os.Getenv("STATUSCAKE_APIKEY"); v == "" {
36 t.Fatal("STATUSCAKE_APIKEY must be set for acceptance tests")
37 }
38}
diff --git a/statuscake/resource_statuscaketest.go b/statuscake/resource_statuscaketest.go
new file mode 100644
index 0000000..101ee83
--- /dev/null
+++ b/statuscake/resource_statuscaketest.go
@@ -0,0 +1,216 @@
1package statuscake
2
3import (
4 "fmt"
5 "strconv"
6
7 "log"
8
9 "github.com/DreamItGetIT/statuscake"
10 "github.com/hashicorp/terraform/helper/schema"
11)
12
13func resourceStatusCakeTest() *schema.Resource {
14 return &schema.Resource{
15 Create: CreateTest,
16 Update: UpdateTest,
17 Delete: DeleteTest,
18 Read: ReadTest,
19
20 Schema: map[string]*schema.Schema{
21 "test_id": {
22 Type: schema.TypeString,
23 Computed: true,
24 },
25
26 "website_name": {
27 Type: schema.TypeString,
28 Required: true,
29 },
30
31 "website_url": {
32 Type: schema.TypeString,
33 Required: true,
34 },
35
36 "contact_id": {
37 Type: schema.TypeInt,
38 Optional: true,
39 },
40
41 "check_rate": {
42 Type: schema.TypeInt,
43 Optional: true,
44 Default: 300,
45 },
46
47 "test_type": {
48 Type: schema.TypeString,
49 Required: true,
50 },
51
52 "paused": {
53 Type: schema.TypeBool,
54 Optional: true,
55 Default: false,
56 },
57
58 "timeout": {
59 Type: schema.TypeInt,
60 Optional: true,
61 Default: 40,
62 },
63
64 "confirmations": {
65 Type: schema.TypeInt,
66 Optional: true,
67 },
68
69 "port": {
70 Type: schema.TypeInt,
71 Optional: true,
72 },
73
74 "trigger_rate": {
75 Type: schema.TypeInt,
76 Optional: true,
77 Default: 5,
78 },
79 },
80 }
81}
82
83func CreateTest(d *schema.ResourceData, meta interface{}) error {
84 client := meta.(*statuscake.Client)
85
86 newTest := &statuscake.Test{
87 WebsiteName: d.Get("website_name").(string),
88 WebsiteURL: d.Get("website_url").(string),
89 CheckRate: d.Get("check_rate").(int),
90 TestType: d.Get("test_type").(string),
91 Paused: d.Get("paused").(bool),
92 Timeout: d.Get("timeout").(int),
93 ContactID: d.Get("contact_id").(int),
94 Confirmation: d.Get("confirmations").(int),
95 Port: d.Get("port").(int),
96 TriggerRate: d.Get("trigger_rate").(int),
97 }
98
99 log.Printf("[DEBUG] Creating new StatusCake Test: %s", d.Get("website_name").(string))
100
101 response, err := client.Tests().Update(newTest)
102 if err != nil {
103 return fmt.Errorf("Error creating StatusCake Test: %s", err.Error())
104 }
105
106 d.Set("test_id", fmt.Sprintf("%d", response.TestID))
107 d.SetId(fmt.Sprintf("%d", response.TestID))
108
109 return ReadTest(d, meta)
110}
111
112func UpdateTest(d *schema.ResourceData, meta interface{}) error {
113 client := meta.(*statuscake.Client)
114
115 params := getStatusCakeTestInput(d)
116
117 log.Printf("[DEBUG] StatusCake Test Update for %s", d.Id())
118 _, err := client.Tests().Update(params)
119 if err != nil {
120 return fmt.Errorf("Error Updating StatusCake Test: %s", err.Error())
121 }
122 return nil
123}
124
125func DeleteTest(d *schema.ResourceData, meta interface{}) error {
126 client := meta.(*statuscake.Client)
127
128 testId, parseErr := strconv.Atoi(d.Id())
129 if parseErr != nil {
130 return parseErr
131 }
132 log.Printf("[DEBUG] Deleting StatusCake Test: %s", d.Id())
133 err := client.Tests().Delete(testId)
134 if err != nil {
135 return err
136 }
137
138 return nil
139}
140
141func ReadTest(d *schema.ResourceData, meta interface{}) error {
142 client := meta.(*statuscake.Client)
143
144 testId, parseErr := strconv.Atoi(d.Id())
145 if parseErr != nil {
146 return parseErr
147 }
148 testResp, err := client.Tests().Detail(testId)
149 if err != nil {
150 return fmt.Errorf("Error Getting StatusCake Test Details for %s: Error: %s", d.Id(), err)
151 }
152 d.Set("website_name", testResp.WebsiteName)
153 d.Set("website_url", testResp.WebsiteURL)
154 d.Set("check_rate", testResp.CheckRate)
155 d.Set("test_type", testResp.TestType)
156 d.Set("paused", testResp.Paused)
157 d.Set("timeout", testResp.Timeout)
158 d.Set("contact_id", testResp.ContactID)
159 d.Set("confirmations", testResp.Confirmation)
160 d.Set("port", testResp.Port)
161 d.Set("trigger_rate", testResp.TriggerRate)
162
163 return nil
164}
165
166func getStatusCakeTestInput(d *schema.ResourceData) *statuscake.Test {
167 testId, parseErr := strconv.Atoi(d.Id())
168 if parseErr != nil {
169 log.Printf("[DEBUG] Error Parsing StatusCake TestID: %s", d.Id())
170 }
171 test := &statuscake.Test{
172 TestID: testId,
173 }
174 if v, ok := d.GetOk("website_name"); ok {
175 test.WebsiteName = v.(string)
176 }
177 if v, ok := d.GetOk("website_url"); ok {
178 test.WebsiteURL = v.(string)
179 }
180 if v, ok := d.GetOk("check_rate"); ok {
181 test.CheckRate = v.(int)
182 }
183 if v, ok := d.GetOk("contact_id"); ok {
184 test.ContactID = v.(int)
185 }
186 if v, ok := d.GetOk("test_type"); ok {
187 test.TestType = v.(string)
188 }
189 if v, ok := d.GetOk("paused"); ok {
190 test.Paused = v.(bool)
191 }
192 if v, ok := d.GetOk("timeout"); ok {
193 test.Timeout = v.(int)
194 }
195 if v, ok := d.GetOk("contact_id"); ok {
196 test.ContactID = v.(int)
197 }
198 if v, ok := d.GetOk("confirmations"); ok {
199 test.Confirmation = v.(int)
200 }
201 if v, ok := d.GetOk("port"); ok {
202 test.Port = v.(int)
203 }
204 if v, ok := d.GetOk("trigger_rate"); ok {
205 test.TriggerRate = v.(int)
206 }
207
208 defaultStatusCodes := "204, 205, 206, 303, 400, 401, 403, 404, 405, 406, " +
209 "408, 410, 413, 444, 429, 494, 495, 496, 499, 500, 501, 502, 503, " +
210 "504, 505, 506, 507, 508, 509, 510, 511, 521, 522, 523, 524, 520, " +
211 "598, 599"
212
213 test.StatusCodes = defaultStatusCodes
214
215 return test
216}
diff --git a/statuscake/resource_statuscaketest_test.go b/statuscake/resource_statuscaketest_test.go
new file mode 100644
index 0000000..f07fcc5
--- /dev/null
+++ b/statuscake/resource_statuscaketest_test.go
@@ -0,0 +1,202 @@
1package statuscake
2
3import (
4 "fmt"
5 "strconv"
6 "testing"
7
8 "github.com/DreamItGetIT/statuscake"
9 "github.com/hashicorp/terraform/helper/resource"
10 "github.com/hashicorp/terraform/terraform"
11)
12
13func TestAccStatusCake_basic(t *testing.T) {
14 var test statuscake.Test
15
16 resource.Test(t, resource.TestCase{
17 PreCheck: func() { testAccPreCheck(t) },
18 Providers: testAccProviders,
19 CheckDestroy: testAccTestCheckDestroy(&test),
20 Steps: []resource.TestStep{
21 {
22 Config: testAccTestConfig_basic,
23 Check: resource.ComposeTestCheckFunc(
24 testAccTestCheckExists("statuscake_test.google", &test),
25 testAccTestCheckAttributes("statuscake_test.google", &test),
26 ),
27 },
28 },
29 })
30}
31
32func TestAccStatusCake_tcp(t *testing.T) {
33 var test statuscake.Test
34
35 resource.Test(t, resource.TestCase{
36 PreCheck: func() { testAccPreCheck(t) },
37 Providers: testAccProviders,
38 CheckDestroy: testAccTestCheckDestroy(&test),
39 Steps: []resource.TestStep{
40 {
41 Config: testAccTestConfig_tcp,
42 Check: resource.ComposeTestCheckFunc(
43 testAccTestCheckExists("statuscake_test.google", &test),
44 testAccTestCheckAttributes("statuscake_test.google", &test),
45 ),
46 },
47 },
48 })
49}
50
51func TestAccStatusCake_withUpdate(t *testing.T) {
52 var test statuscake.Test
53
54 resource.Test(t, resource.TestCase{
55 PreCheck: func() { testAccPreCheck(t) },
56 Providers: testAccProviders,
57 CheckDestroy: testAccTestCheckDestroy(&test),
58 Steps: []resource.TestStep{
59 {
60 Config: testAccTestConfig_basic,
61 Check: resource.ComposeTestCheckFunc(
62 testAccTestCheckExists("statuscake_test.google", &test),
63 ),
64 },
65
66 {
67 Config: testAccTestConfig_update,
68 Check: resource.ComposeTestCheckFunc(
69 testAccTestCheckExists("statuscake_test.google", &test),
70 testAccTestCheckAttributes("statuscake_test.google", &test),
71 resource.TestCheckResourceAttr("statuscake_test.google", "check_rate", "500"),
72 resource.TestCheckResourceAttr("statuscake_test.google", "paused", "true"),
73 resource.TestCheckResourceAttr("statuscake_test.google", "timeout", "40"),
74 resource.TestCheckResourceAttr("statuscake_test.google", "contact_id", "0"),
75 resource.TestCheckResourceAttr("statuscake_test.google", "confirmations", "0"),
76 resource.TestCheckResourceAttr("statuscake_test.google", "trigger_rate", "20"),
77 ),
78 },
79 },
80 })
81}
82
83func testAccTestCheckExists(rn string, test *statuscake.Test) resource.TestCheckFunc {
84 return func(s *terraform.State) error {
85 rs, ok := s.RootModule().Resources[rn]
86 if !ok {
87 return fmt.Errorf("resource not found: %s", rn)
88 }
89
90 if rs.Primary.ID == "" {
91 return fmt.Errorf("TestID not set")
92 }
93
94 client := testAccProvider.Meta().(*statuscake.Client)
95 testId, parseErr := strconv.Atoi(rs.Primary.ID)
96 if parseErr != nil {
97 return fmt.Errorf("error in statuscake test CheckExists: %s", parseErr)
98 }
99
100 gotTest, err := client.Tests().Detail(testId)
101 if err != nil {
102 return fmt.Errorf("error getting test: %s", err)
103 }
104
105 *test = *gotTest
106
107 return nil
108 }
109}
110
111func testAccTestCheckAttributes(rn string, test *statuscake.Test) resource.TestCheckFunc {
112 return func(s *terraform.State) error {
113 attrs := s.RootModule().Resources[rn].Primary.Attributes
114
115 check := func(key, stateValue, testValue string) error {
116 if testValue != stateValue {
117 return fmt.Errorf("different values for %s in state (%s) and in statuscake (%s)",
118 key, stateValue, testValue)
119 }
120 return nil
121 }
122
123 for key, value := range attrs {
124 var err error
125
126 switch key {
127 case "website_name":
128 err = check(key, value, test.WebsiteName)
129 case "website_url":
130 err = check(key, value, test.WebsiteURL)
131 case "check_rate":
132 err = check(key, value, strconv.Itoa(test.CheckRate))
133 case "test_type":
134 err = check(key, value, test.TestType)
135 case "paused":
136 err = check(key, value, strconv.FormatBool(test.Paused))
137 case "timeout":
138 err = check(key, value, strconv.Itoa(test.Timeout))
139 case "contact_id":
140 err = check(key, value, strconv.Itoa(test.ContactID))
141 case "confirmations":
142 err = check(key, value, strconv.Itoa(test.Confirmation))
143 case "trigger_rate":
144 err = check(key, value, strconv.Itoa(test.TriggerRate))
145 }
146
147 if err != nil {
148 return err
149 }
150 }
151 return nil
152 }
153}
154
155func testAccTestCheckDestroy(test *statuscake.Test) resource.TestCheckFunc {
156 return func(s *terraform.State) error {
157 client := testAccProvider.Meta().(*statuscake.Client)
158 err := client.Tests().Delete(test.TestID)
159 if err == nil {
160 return fmt.Errorf("test still exists")
161 }
162
163 return nil
164 }
165}
166
167const testAccTestConfig_basic = `
168resource "statuscake_test" "google" {
169 website_name = "google.com"
170 website_url = "www.google.com"
171 test_type = "HTTP"
172 check_rate = 300
173 timeout = 10
174 contact_id = 43402
175 confirmations = 1
176 trigger_rate = 10
177}
178`
179
180const testAccTestConfig_update = `
181resource "statuscake_test" "google" {
182 website_name = "google.com"
183 website_url = "www.google.com"
184 test_type = "HTTP"
185 check_rate = 500
186 paused = true
187 trigger_rate = 20
188}
189`
190
191const testAccTestConfig_tcp = `
192resource "statuscake_test" "google" {
193 website_name = "google.com"
194 website_url = "www.google.com"
195 test_type = "TCP"
196 check_rate = 300
197 timeout = 10
198 contact_id = 43402
199 confirmations = 1
200 port = 80
201}
202`