Skip to content

Commit 0aeb799

Browse files
authored
Adding new experimental resources (#1023)
Added `databricks_table` resource
1 parent 51addf3 commit 0aeb799

File tree

7 files changed

+175
-12
lines changed

7 files changed

+175
-12
lines changed

catalog/resource_external_location.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -71,11 +71,11 @@ func ResourceExternalLocation() *schema.Resource {
7171
var el ExternalLocationInfo
7272
common.DataToStructPointer(d, s, &el)
7373
return NewExternalLocationsAPI(ctx, c).update(d.Id(), ExternalLocationInfo{
74-
Name: d.Id(),
75-
URL: el.URL,
74+
Name: d.Id(),
75+
URL: el.URL,
7676
CredentialName: el.CredentialName,
77-
Comment: el.Comment,
78-
Owner: el.Owner,
77+
Comment: el.Comment,
78+
Owner: el.Owner,
7979
})
8080
},
8181
Delete: func(ctx context.Context, d *schema.ResourceData, c *common.DatabricksClient) error {

catalog/resource_external_location_test.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,9 @@ func TestCreateExternalLocation(t *testing.T) {
2525
},
2626
{
2727
Method: "GET",
28-
Resource: "/api/2.0/unity-catalog/external-locations/abc",
29-
Response: ExternalLocationInfo {
30-
Owner: "efg",
28+
Resource: "/api/2.0/unity-catalog/external-locations/abc",
29+
Response: ExternalLocationInfo{
30+
Owner: "efg",
3131
MetastoreID: "fgh",
3232
},
3333
},

catalog/resource_grants.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -130,10 +130,10 @@ var mapping = securableMapping{
130130
"ALL PRIVILEGES": true,
131131
},
132132
"storage_credential": {
133-
"CREATE TABLE": true,
134-
"READ FILES": true,
135-
"WRITE FILES": true,
136-
"ALL PRIVILEGES": true,
133+
"CREATE TABLE": true,
134+
"READ FILES": true,
135+
"WRITE FILES": true,
136+
"ALL PRIVILEGES": true,
137137
},
138138
"external_location": {
139139
"CREATE TABLE": true,

catalog/resource_grants_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -242,7 +242,7 @@ func TestGrantUpdate(t *testing.T) {
242242
},
243243
Resource: ResourceGrants(),
244244
Update: true,
245-
ID: "table/foo.bar.baz",
245+
ID: "table/foo.bar.baz",
246246
InstanceState: map[string]string{
247247
"table": "foo.bar.baz",
248248
},

catalog/resource_table.go

Lines changed: 102 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
package catalog
2+
3+
import (
4+
"context"
5+
"fmt"
6+
7+
"github.com/databrickslabs/terraform-provider-databricks/common"
8+
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
9+
)
10+
11+
type TablesAPI struct {
12+
client *common.DatabricksClient
13+
context context.Context
14+
}
15+
16+
func NewTablesAPI(ctx context.Context, m interface{}) TablesAPI {
17+
return TablesAPI{m.(*common.DatabricksClient), ctx}
18+
}
19+
20+
type ColumnInfo struct {
21+
Name string `json:"name"`
22+
TypeText string `json:"type_text"`
23+
TypeJson string `json:"type_json,omitempty"`
24+
TypeName string `json:"type_name"`
25+
TypePrecision int32 `json:"type_precision,omitempty"`
26+
TypeScale int32 `json:"type_scale,omitempty"`
27+
TypeIntervalType string `json:"type_interval_type,omitempty"`
28+
Position int32 `json:"position"`
29+
Comment string `json:"comment,omitempty"`
30+
Nullable bool `json:"nullable,omitempty" tf:"default:true"`
31+
PartitionIndex int32 `json:"partition_index,omitempty"`
32+
}
33+
34+
type TableInfo struct {
35+
Name string `json:"name" tf:"force_new"`
36+
CatalogName string `json:"catalog_name"`
37+
SchemaName string `json:"schema_name"`
38+
TableType string `json:"table_type"`
39+
DataSourceFormat string `json:"data_source_format"`
40+
ColumnInfos []ColumnInfo `json:"columns" tf:"alias:column"`
41+
StorageLocation string `json:"storage_location"`
42+
StorageCredentialName string `json:"storage_credential_name,omitempty"`
43+
ViewDefinition string `json:"view_definition,omitempty"`
44+
Owner string `json:"owner,omitempty" tf:"computed"`
45+
Comment string `json:"comment,omitempty"`
46+
Properties map[string]string `json:"properties,omitempty"`
47+
}
48+
49+
func (ti TableInfo) FullName() string {
50+
return fmt.Sprintf("%s.%s.%s", ti.CatalogName, ti.SchemaName, ti.Name)
51+
}
52+
53+
func (a TablesAPI) createTable(ti *TableInfo) error {
54+
return a.client.Post(a.context, "/unity-catalog/tables", ti, ti)
55+
}
56+
57+
func (a TablesAPI) getTable(name string) (ti TableInfo, err error) {
58+
err = a.client.Get(a.context, "/unity-catalog/tables/"+name, nil, &ti)
59+
return
60+
}
61+
62+
func (a TablesAPI) updateTable(ti TableInfo) error {
63+
return a.client.Patch(a.context, "/unity-catalog/tables/"+ti.Name, ti)
64+
}
65+
66+
func (a TablesAPI) deleteTable(name string) error {
67+
return a.client.Delete(a.context, "/unity-catalog/tables/"+name, nil)
68+
}
69+
70+
func ResourceTable() *schema.Resource {
71+
tableSchema := common.StructToSchema(TableInfo{},
72+
func(m map[string]*schema.Schema) map[string]*schema.Schema {
73+
return m
74+
})
75+
return common.Resource{
76+
Schema: tableSchema,
77+
Create: func(ctx context.Context, d *schema.ResourceData, c *common.DatabricksClient) error {
78+
var ti TableInfo
79+
common.DataToStructPointer(d, tableSchema, &ti)
80+
if err := NewTablesAPI(ctx, c).createTable(&ti); err != nil {
81+
return err
82+
}
83+
d.SetId(ti.FullName())
84+
return nil
85+
},
86+
Read: func(ctx context.Context, d *schema.ResourceData, c *common.DatabricksClient) error {
87+
ti, err := NewTablesAPI(ctx, c).getTable(d.Id())
88+
if err != nil {
89+
return err
90+
}
91+
return common.StructToData(ti, tableSchema, d)
92+
},
93+
Update: func(ctx context.Context, d *schema.ResourceData, c *common.DatabricksClient) error {
94+
var ti TableInfo
95+
common.DataToStructPointer(d, tableSchema, &ti)
96+
return NewTablesAPI(ctx, c).updateTable(ti)
97+
},
98+
Delete: func(ctx context.Context, d *schema.ResourceData, c *common.DatabricksClient) error {
99+
return NewTablesAPI(ctx, c).deleteTable(d.Id())
100+
},
101+
}.ToResource()
102+
}

catalog/resource_table_test.go

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
package catalog
2+
3+
import (
4+
"testing"
5+
6+
"github.com/databrickslabs/terraform-provider-databricks/qa"
7+
)
8+
9+
func TestTableCornerCases(t *testing.T) {
10+
qa.ResourceCornerCases(t, ResourceTable())
11+
}
12+
13+
func TestTableCreate(t *testing.T) {
14+
qa.ResourceFixture{
15+
Fixtures: []qa.HTTPFixture{
16+
{
17+
Method: "POST",
18+
Resource: "/api/2.0/unity-catalog/tables",
19+
ExpectedRequest: TableInfo{
20+
StorageLocation: "s3://ext-main/foo/bar",
21+
Name: "bar",
22+
CatalogName: "main",
23+
SchemaName: "foo",
24+
TableType: "EXTERNAL",
25+
DataSourceFormat: "JSON",
26+
ColumnInfos: []ColumnInfo{
27+
{
28+
Name: "id",
29+
Nullable: true,
30+
Position: 0,
31+
TypeName: "int",
32+
TypeText: "int",
33+
},
34+
},
35+
},
36+
},
37+
{
38+
Method: "GET",
39+
Resource: "/api/2.0/unity-catalog/tables/main.foo.bar",
40+
},
41+
},
42+
Resource: ResourceTable(),
43+
Create: true,
44+
HCL: `
45+
catalog_name = "main"
46+
schema_name = "foo"
47+
name = "bar"
48+
table_type = "EXTERNAL"
49+
data_source_format = "JSON"
50+
storage_location = "s3://ext-main/foo/bar"
51+
52+
column {
53+
name = "id"
54+
type_text = "int"
55+
type_name = "int"
56+
position = 0
57+
}
58+
`,
59+
}.ApplyNoError(t)
60+
}

provider/provider.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,7 @@ func DatabricksProvider() *schema.Provider {
103103
"databricks_sql_visualization": sqlanalytics.ResourceVisualization(),
104104
"databricks_sql_widget": sqlanalytics.ResourceWidget(),
105105
"databricks_storage_credential": catalog.ResourceStorageCredential(),
106+
"databricks_table": catalog.ResourceTable(),
106107
"databricks_token": tokens.ResourceToken(),
107108
"databricks_user": scim.ResourceUser(),
108109
"databricks_user_instance_profile": aws.ResourceUserInstanceProfile(),

0 commit comments

Comments
 (0)