Skip to content

Commit

Permalink
Add Data Source multipass_instance (#6)
Browse files Browse the repository at this point in the history
* Also some refactoring

* Started adding the possibility of provider configuration
  • Loading branch information
larstobi authored Jul 22, 2022
1 parent 7583ce0 commit 62afc6f
Show file tree
Hide file tree
Showing 8 changed files with 296 additions and 79 deletions.
29 changes: 29 additions & 0 deletions docs/data-sources/instance.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
---
# generated by https://github.com/hashicorp/terraform-plugin-docs
page_title: "multipass_instance Data Source - terraform-provider-multipass"
subcategory: ""
description: |-
Instance data source
---

# multipass_instance (Data Source)

Instance data source



<!-- schema generated by tfplugindocs -->
## Schema

### Required

- `name` (String) Instance name

### Read-Only

- `image` (String) The image of the instance
- `image_hash` (String) The image_hash of the instance
- `ipv4` (String) The IPv4 address of the instance
- `state` (String) The state of the instance


95 changes: 95 additions & 0 deletions internal/provider/instance_data_source.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
package provider

import (
"context"
"fmt"

"github.com/hashicorp/terraform-plugin-framework/diag"
"github.com/hashicorp/terraform-plugin-framework/tfsdk"
"github.com/hashicorp/terraform-plugin-framework/types"
"github.com/larstobi/go-multipass/multipass"
)

var _ tfsdk.DataSourceType = instanceDataSourceType{}
var _ tfsdk.DataSource = instanceDataSource{}

type instanceDataSourceType struct{}

func (t instanceDataSourceType) GetSchema(ctx context.Context) (tfsdk.Schema, diag.Diagnostics) {
return tfsdk.Schema{
MarkdownDescription: "Instance data source",

Attributes: map[string]tfsdk.Attribute{
"name": {
MarkdownDescription: "Instance name",
Type: types.StringType,
Required: true,
},
"ipv4": {
MarkdownDescription: "The IPv4 address of the instance",
Type: types.StringType,
Computed: true,
},
"state": {
MarkdownDescription: "The state of the instance",
Type: types.StringType,
Computed: true,
},
"image": {
MarkdownDescription: "The image of the instance",
Type: types.StringType,
Computed: true,
},
"image_hash": {
MarkdownDescription: "The image_hash of the instance",
Type: types.StringType,
Computed: true,
},
},
}, nil
}

func (t instanceDataSourceType) NewDataSource(ctx context.Context, in tfsdk.Provider) (tfsdk.DataSource, diag.Diagnostics) {
provider, diags := convertProviderType(in)

return instanceDataSource{
provider: provider,
}, diags
}

type instanceDataSourceData struct {
Name types.String `tfsdk:"name"`
IPv4 types.String `tfsdk:"ipv4"`
State types.String `tfsdk:"state"`
Image types.String `tfsdk:"image"`
ImageHash types.String `tfsdk:"image_hash"`
}

type instanceDataSource struct {
provider provider
}

func (d instanceDataSource) Read(ctx context.Context, req tfsdk.ReadDataSourceRequest, resp *tfsdk.ReadDataSourceResponse) {
var data instanceDataSourceData

diags := req.Config.Get(ctx, &data)
resp.Diagnostics.Append(diags...)

if resp.Diagnostics.HasError() {
return
}

instance, err := multipass.Info(&multipass.InfoRequest{Name: data.Name.Value})
if err != nil {
resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Unable to read instance, got error: %s", err))
return
}

data.IPv4 = types.String{Value: instance.IP}
data.State = types.String{Value: instance.State}
data.Image = types.String{Value: instance.Image}
data.ImageHash = types.String{Value: instance.ImageHash}

diags = resp.State.Set(ctx, &data)
resp.Diagnostics.Append(diags...)
}
99 changes: 99 additions & 0 deletions internal/provider/provider.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
package provider

import (
"context"
"fmt"
"os"

"github.com/hashicorp/terraform-plugin-framework/diag"
"github.com/hashicorp/terraform-plugin-framework/tfsdk"
// "github.com/hashicorp/terraform-plugin-framework/types"
)

var stderr = os.Stderr

type provider struct {
configured bool
version string
}

// type providerData struct {
// Address types.String `tfsdk:"address"`
// }

func (p *provider) GetSchema(_ context.Context) (tfsdk.Schema, diag.Diagnostics) {
return tfsdk.Schema{
Attributes: map[string]tfsdk.Attribute{},
}, nil
}

type providerData struct{}

func (p *provider) Configure(ctx context.Context, req tfsdk.ConfigureProviderRequest, resp *tfsdk.ConfigureProviderResponse) {
// Retrieve provider data from configuration
var data providerData
diags := req.Config.Get(ctx, &data)
resp.Diagnostics.Append(diags...)
if resp.Diagnostics.HasError() {
return
}

p.configured = true
}

func (p *provider) GetResources(_ context.Context) (map[string]tfsdk.ResourceType, diag.Diagnostics) {
return map[string]tfsdk.ResourceType{
"multipass_instance": instanceResourceType{},
}, nil
}

func (p *provider) GetDataSources(_ context.Context) (map[string]tfsdk.DataSourceType, diag.Diagnostics) {
return map[string]tfsdk.DataSourceType{
"multipass_instance": instanceDataSourceType{},
}, nil

}

// func (p *provider) GetSchema(ctx context.Context) (tfsdk.Schema, diag.Diagnostics) {
// return tfsdk.Schema{
// Attributes: map[string]tfsdk.Attribute{
// "address": {
// MarkdownDescription: "Specifies which address to use for the multipassd service. A socket can be specified using unix:<socket_file> or a TCP address can be specified using <server_name:port>",
// Optional: true,
// Type: types.StringType,
// },
// },
// }, nil
// }

func New(version string) func() tfsdk.Provider {
return func() tfsdk.Provider {
return &provider{
version: version,
}
}
}

func convertProviderType(in tfsdk.Provider) (provider, diag.Diagnostics) {
var diags diag.Diagnostics

p, ok := in.(*provider)

if !ok {
diags.AddError(
"Unexpected Provider Instance Type",
fmt.Sprintf("While creating the data source or resource, an unexpected provider type (%T) was received. This is always a bug in the provider code and should be reported to the provider developers.", p),
)
return provider{}, diags
}

if p == nil {
diags.AddError(
"Unexpected Provider Instance Type",
"While creating the data source or resource, an unexpected empty provider instance was received. This is always a bug in the provider code and should be reported to the provider developers.",
)
return provider{}, diags
}

return *p, diags
}
22 changes: 22 additions & 0 deletions internal/provider/provider_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package provider

import (
"testing"

"github.com/hashicorp/terraform-plugin-framework/providerserver"
"github.com/hashicorp/terraform-plugin-go/tfprotov6"
)

// testAccProtoV6ProviderFactories are used to instantiate a provider during
// acceptance testing. The factory function will be invoked for every Terraform
// CLI command executed to create a provider server to which the CLI can
// reattach.
var testAccProtoV6ProviderFactories = map[string]func() (tfprotov6.ProviderServer, error){
"scaffolding": providerserver.NewProtocol6WithError(New("test")()),
}

func testAccPreCheck(t *testing.T) {
// You can add code here to run prior to any test case execution, for example assertions
// about the appropriate environment variables being set are common to see in a pre-check
// function.
}
Loading

0 comments on commit 62afc6f

Please sign in to comment.