Skip to content

Commit

Permalink
Add custom plugin schema resource
Browse files Browse the repository at this point in the history
  • Loading branch information
scastrianni committed Jul 30, 2024
1 parent fcbd240 commit 26f9786
Show file tree
Hide file tree
Showing 5 changed files with 208 additions and 0 deletions.
24 changes: 24 additions & 0 deletions docs/resources/custom_plugin_schema.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
---
subcategory: "Runtime Configuration"
---
# Resource: konnect_custom_plugin_schema
Represents a custom plugin schema within a control plane
## Example usage
```hcl
data "konnect_control_plane" "ControlPlane" {
name = "TestControlPlane"
}
resource "konnect_custom_plugin_schema" "example" {
control_plane_id = data.konnect_control_plane.ControlPlane.id
name = "my-plugin"
schema_lua = "return { name=\"my-plugin\", fields = { { config = { type = \"record\", fields = { } } } } }"
}
```
## Argument Reference
* `control_plane_id` - **(Required, String)** The id of the control plane.
* `name` - **(Required, ForceNew, String)** The name of the custom plugin schema.
* `schema_lua` - **(Required, String)** The lua code that defines the schema. Typically, this is the content of the custom plugin schema.lua file.
## Attribute Reference
* `id` - **(String)** Same as `control_plane_id`:`name`
## Import
Custom plugin schemas can be imported using a proper value of `id` as described above
26 changes: 26 additions & 0 deletions konnect/client/custom_plugin_schema.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package client

import "strings"

const (
CustomPluginSchemaPath = ControlPlanePathGet + "/core-entities/plugin-schemas"
CustomPluginSchemaPathGet = CustomPluginSchemaPath + "/%s"
)

type CustomPluginSchema struct {
ControlPlaneId string `json:"-"`
Name string `json:"name"`
SchemaLua string `json:"lua_schema"`
}
type CustomPluginSchemaItem struct {
Item CustomPluginSchema `json:"item"`
}

func (s *CustomPluginSchema) CustomPluginSchemaEncodeId() string {
return s.ControlPlaneId + IdSeparator + s.Name
}

func CustomPluginSchemaDecodeId(s string) (string, string) {
tokens := strings.Split(s, IdSeparator)
return tokens[0], tokens[1]
}
1 change: 1 addition & 0 deletions konnect/provider.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ func Provider() *schema.Provider {
"konnect_consumer_hmac": resourceConsumerHMAC(),
"konnect_consumer_jwt": resourceConsumerJWT(),
"konnect_plugin": resourcePlugin(),
"konnect_custom_plugin_schema": resourceCustomPluginSchema(),
},
DataSourcesMap: map[string]*schema.Resource{
"konnect_control_plane": dataSourceControlPlane(),
Expand Down
151 changes: 151 additions & 0 deletions konnect/resource_custom_plugin_schema.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
package konnect

import (
"bytes"
"context"
"encoding/json"
"fmt"
"github.com/go-http-utils/headers"
"github.com/hashicorp/terraform-plugin-sdk/v2/diag"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
"github.com/scastria/terraform-provider-konnect/konnect/client"
"net/http"
)

func resourceCustomPluginSchema() *schema.Resource {
return &schema.Resource{
CreateContext: resourceCustomPluginSchemaCreate,
ReadContext: resourceCustomPluginSchemaRead,
UpdateContext: resourceCustomPluginSchemaUpdate,
DeleteContext: resourceCustomPluginSchemaDelete,
Importer: &schema.ResourceImporter{
StateContext: schema.ImportStatePassthroughContext,
},
Schema: map[string]*schema.Schema{
"control_plane_id": {
Type: schema.TypeString,
Required: true,
},
"name": {
Type: schema.TypeString,
Required: true,
ForceNew: true,
},
"schema_lua": {
Type: schema.TypeString,
Required: true,
},
},
}
}

func fillCustomPluginSchema(c *client.CustomPluginSchema, d *schema.ResourceData) {
c.ControlPlaneId = d.Get("control_plane_id").(string)
c.Name = d.Get("name").(string)
c.SchemaLua = d.Get("schema_lua").(string)
}

func fillResourceDataFromCustomPluginSchema(c *client.CustomPluginSchema, d *schema.ResourceData) {
d.Set("control_plane_id", c.ControlPlaneId)
d.Set("name", c.Name)
d.Set("schema_lua", c.SchemaLua)
}

func resourceCustomPluginSchemaCreate(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
var diags diag.Diagnostics
c := m.(*client.Client)
buf := bytes.Buffer{}
newCustomPluginSchema := client.CustomPluginSchema{}
fillCustomPluginSchema(&newCustomPluginSchema, d)
err := json.NewEncoder(&buf).Encode(newCustomPluginSchema)
if err != nil {
d.SetId("")
return diag.FromErr(err)
}
requestPath := fmt.Sprintf(client.CustomPluginSchemaPath, newCustomPluginSchema.ControlPlaneId)
requestHeaders := http.Header{
headers.ContentType: []string{client.ApplicationJson},
}
body, err := c.HttpRequest(ctx, true, http.MethodPost, requestPath, nil, requestHeaders, &buf)
if err != nil {
d.SetId("")
return diag.FromErr(err)
}
retVal := &client.CustomPluginSchemaItem{}
err = json.NewDecoder(body).Decode(retVal)
if err != nil {
d.SetId("")
return diag.FromErr(err)
}
retVal.Item.ControlPlaneId = newCustomPluginSchema.ControlPlaneId
d.SetId(retVal.Item.CustomPluginSchemaEncodeId())
fillResourceDataFromCustomPluginSchema(&(retVal.Item), d)
return diags
}

func resourceCustomPluginSchemaRead(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
var diags diag.Diagnostics
controlPlaneId, name := client.CustomPluginSchemaDecodeId(d.Id())
c := m.(*client.Client)
requestPath := fmt.Sprintf(client.CustomPluginSchemaPathGet, controlPlaneId, name)
body, err := c.HttpRequest(ctx, true, http.MethodGet, requestPath, nil, nil, &bytes.Buffer{})
if err != nil {
d.SetId("")
re := err.(*client.RequestError)
if re.StatusCode == http.StatusNotFound {
return diags
}
return diag.FromErr(err)
}
retVal := &client.CustomPluginSchemaItem{}
err = json.NewDecoder(body).Decode(retVal)
if err != nil {
d.SetId("")
return diag.FromErr(err)
}
retVal.Item.ControlPlaneId = controlPlaneId
fillResourceDataFromCustomPluginSchema(&(retVal.Item), d)
return diags
}

func resourceCustomPluginSchemaUpdate(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
var diags diag.Diagnostics
controlPlaneId, name := client.CustomPluginSchemaDecodeId(d.Id())
c := m.(*client.Client)
buf := bytes.Buffer{}
upCustomPluginSchema := client.CustomPluginSchema{}
fillCustomPluginSchema(&upCustomPluginSchema, d)
err := json.NewEncoder(&buf).Encode(upCustomPluginSchema)
if err != nil {
return diag.FromErr(err)
}
requestPath := fmt.Sprintf(client.CustomPluginSchemaPathGet, controlPlaneId, name)
requestHeaders := http.Header{
headers.ContentType: []string{client.ApplicationJson},
}
body, err := c.HttpRequest(ctx, true, http.MethodPut, requestPath, nil, requestHeaders, &buf)
if err != nil {
return diag.FromErr(err)
}
retVal := &client.CustomPluginSchemaItem{}
err = json.NewDecoder(body).Decode(retVal)
if err != nil {
return diag.FromErr(err)
}
retVal.Item.ControlPlaneId = controlPlaneId
fillResourceDataFromCustomPluginSchema(&(retVal.Item), d)
return diags
}

func resourceCustomPluginSchemaDelete(ctx context.Context, d *schema.ResourceData, m interface{}) diag.Diagnostics {
var diags diag.Diagnostics
controlPlaneId, name := client.CustomPluginSchemaDecodeId(d.Id())
c := m.(*client.Client)
requestPath := fmt.Sprintf(client.CustomPluginSchemaPathGet, controlPlaneId, name)
_, err := c.HttpRequest(ctx, true, http.MethodDelete, requestPath, nil, nil, &bytes.Buffer{})
if err != nil {
return diag.FromErr(err)
}
d.SetId("")
return diags
}
6 changes: 6 additions & 0 deletions test/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,12 @@ terraform {
provider "konnect" {
}

# resource "konnect_custom_plugin_schema" "CPS" {
# control_plane_id = data.konnect_control_plane.RG.id
# name = "shawn"
# schema_lua = "return { name=\"shawn\", fields = { { config = { type = \"record\", fields = { } } } } }"
# }

#resource "konnect_plugin" "P" {
# control_plane_id = data.konnect_control_plane.RG.id
# name = "rate-limiting"
Expand Down

0 comments on commit 26f9786

Please sign in to comment.