forked from Snowflake-Labs/terraform-provider-snowflake
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: Added Procedures Datasource (Snowflake-Labs#646)
- Loading branch information
1 parent
a16090a
commit eb931b0
Showing
8 changed files
with
240 additions
and
16 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
data "snowflake_procedures" "current" { | ||
database = "MYDB" | ||
schema = "MYSCHEMA" | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,128 @@ | ||
package datasources | ||
|
||
import ( | ||
"database/sql" | ||
"errors" | ||
"fmt" | ||
"log" | ||
"regexp" | ||
"strings" | ||
|
||
"github.com/chanzuckerberg/terraform-provider-snowflake/pkg/snowflake" | ||
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" | ||
) | ||
|
||
var proceduresSchema = map[string]*schema.Schema{ | ||
"database": { | ||
Type: schema.TypeString, | ||
Required: true, | ||
Description: "The database from which to return the schemas from.", | ||
}, | ||
"schema": { | ||
Type: schema.TypeString, | ||
Required: true, | ||
Description: "The schema from which to return the procedures from.", | ||
}, | ||
"procedures": { | ||
Type: schema.TypeList, | ||
Computed: true, | ||
Description: "The procedures in the schema", | ||
Elem: &schema.Resource{ | ||
Schema: map[string]*schema.Schema{ | ||
"name": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
}, | ||
"database": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
}, | ||
"schema": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
}, | ||
"comment": { | ||
Type: schema.TypeString, | ||
Optional: true, | ||
Computed: true, | ||
}, | ||
"argument_types": { | ||
Type: schema.TypeList, | ||
Elem: &schema.Schema{Type: schema.TypeString}, | ||
Optional: true, | ||
Computed: true, | ||
}, | ||
"return_type": { | ||
Type: schema.TypeString, | ||
Optional: true, | ||
Computed: true, | ||
}, | ||
}, | ||
}, | ||
}, | ||
} | ||
|
||
func Procedures() *schema.Resource { | ||
return &schema.Resource{ | ||
Read: ReadProcedures, | ||
Schema: proceduresSchema, | ||
} | ||
} | ||
|
||
func ReadProcedures(d *schema.ResourceData, meta interface{}) error { | ||
db := meta.(*sql.DB) | ||
databaseName := d.Get("database").(string) | ||
schemaName := d.Get("schema").(string) | ||
|
||
currentProcedures, err := snowflake.ListProcedures(databaseName, schemaName, db) | ||
if err == sql.ErrNoRows { | ||
// If not found, mark resource to be removed from statefile during apply or refresh | ||
log.Printf("[DEBUG] procedures in schema (%s) not found", d.Id()) | ||
d.SetId("") | ||
return nil | ||
} else if err != nil { | ||
log.Printf("[DEBUG] unable to parse procedures in schema (%s)", d.Id()) | ||
d.SetId("") | ||
return nil | ||
} | ||
|
||
procedures := []map[string]interface{}{} | ||
|
||
for _, procedure := range currentProcedures { | ||
procedureMap := map[string]interface{}{} | ||
|
||
procedureSignatureMap, err := parseArguments(procedure.Arguments.String) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
procedureMap["name"] = procedure.Name.String | ||
procedureMap["database"] = procedure.DatabaseName.String | ||
procedureMap["schema"] = procedure.SchemaName.String | ||
procedureMap["comment"] = procedure.Comment.String | ||
procedureMap["argument_types"] = procedureSignatureMap["argumentTypes"].([]string) | ||
procedureMap["return_type"] = procedureSignatureMap["returnType"].(string) | ||
|
||
procedures = append(procedures, procedureMap) | ||
} | ||
|
||
d.SetId(fmt.Sprintf(`%v|%v`, databaseName, schemaName)) | ||
return d.Set("procedures", procedures) | ||
} | ||
|
||
func parseArguments(arguments string) (map[string]interface{}, error) { | ||
r := regexp.MustCompile(`(?P<callable_name>[^(]+)\((?P<argument_signature>[^)]*)\) RETURN (?P<return_type>.*)`) | ||
matches := r.FindStringSubmatch(arguments) | ||
if len(matches) == 0 { | ||
return nil, errors.New(fmt.Sprintf(`Could not parse arguments: %v`, arguments)) | ||
} | ||
callableSignatureMap := make(map[string]interface{}) | ||
|
||
argumentTypes := strings.Split(matches[2], ", ") | ||
|
||
callableSignatureMap["callableName"] = matches[1] | ||
callableSignatureMap["argumentTypes"] = argumentTypes | ||
callableSignatureMap["returnType"] = matches[3] | ||
|
||
return callableSignatureMap, nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,74 @@ | ||
package datasources_test | ||
|
||
import ( | ||
"fmt" | ||
"strings" | ||
"testing" | ||
|
||
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" | ||
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" | ||
) | ||
|
||
func TestAccProcedures(t *testing.T) { | ||
databaseName := strings.ToUpper(acctest.RandStringFromCharSet(10, acctest.CharSetAlpha)) | ||
schemaName := strings.ToUpper(acctest.RandStringFromCharSet(10, acctest.CharSetAlpha)) | ||
procedureName := strings.ToUpper(acctest.RandStringFromCharSet(10, acctest.CharSetAlpha)) | ||
procedureWithArgumentsName := strings.ToUpper(acctest.RandStringFromCharSet(10, acctest.CharSetAlpha)) | ||
resource.ParallelTest(t, resource.TestCase{ | ||
Providers: providers(), | ||
Steps: []resource.TestStep{ | ||
{ | ||
Config: procedures(databaseName, schemaName, procedureName, procedureWithArgumentsName), | ||
Check: resource.ComposeTestCheckFunc( | ||
resource.TestCheckResourceAttr("data.snowflake_procedures.t", "database", databaseName), | ||
resource.TestCheckResourceAttr("data.snowflake_procedures.t", "schema", schemaName), | ||
resource.TestCheckResourceAttrSet("data.snowflake_procedures.t", "procedures.#"), | ||
resource.TestCheckResourceAttr("data.snowflake_procedures.t", "procedures.#", "2"), | ||
), | ||
}, | ||
}, | ||
}) | ||
} | ||
|
||
func procedures(databaseName string, schemaName string, procedureName string, procedureWithArgumentsName string) string { | ||
s := ` | ||
resource "snowflake_database" "test_database" { | ||
name = "%v" | ||
comment = "Terraform acceptance test" | ||
} | ||
resource "snowflake_schema" "test_schema" { | ||
name = "%v" | ||
database = snowflake_database.test_database.name | ||
comment = "Terraform acceptance test" | ||
} | ||
resource "snowflake_procedure" "test_proc_simple" { | ||
name = "%v" | ||
database = snowflake_database.test_database.name | ||
schema = snowflake_schema.test_schema.name | ||
return_type = "VARCHAR" | ||
statement = "return \"Hi\"" | ||
} | ||
resource "snowflake_procedure" "test_proc" { | ||
name = "%v" | ||
database = snowflake_database.test_database.name | ||
schema = snowflake_schema.test_schema.name | ||
arguments { | ||
name = "arg1" | ||
type = "varchar" | ||
} | ||
comment = "Terraform acceptance test" | ||
return_type = "varchar" | ||
statement = "var X=3\nreturn X" | ||
} | ||
data snowflake_procedures "t" { | ||
database = snowflake_database.test_database.name | ||
schema = snowflake_schema.test_schema.name | ||
depends_on = [snowflake_procedure.test_proc_simple, snowflake_procedure.test_proc] | ||
} | ||
` | ||
return fmt.Sprintf(s, databaseName, schemaName, procedureName, procedureWithArgumentsName) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters