diff --git a/.gitignore b/.gitignore index 800e842..2aa9e15 100644 --- a/.gitignore +++ b/.gitignore @@ -1,5 +1,5 @@ +api.yaml output.json go-islandora islandora-starter-site -islandora/* -!islandora/.keep +api/islandora.gen.go \ No newline at end of file diff --git a/api.yaml.tmpl b/api.yaml.tmpl new file mode 100644 index 0000000..710854b --- /dev/null +++ b/api.yaml.tmpl @@ -0,0 +1,47 @@ +openapi: 3.0.0 +info: + version: 1.0.0 + title: CSV Validation API +paths: + /upload: + post: + summary: Upload CSV file + requestBody: + required: true + content: + text/csv: + schema: + $ref: '#/components/schemas/IslandoraObject' + responses: + '200': + description: CSV file processed successfully +components: + schemas: + IslandoraObject: + type: object + properties: + {{- range .Fields }} + {{ .MachineName }}: + type: array + title: {{ .Title }} + {{- if .Description }} + description: "{{ .Description }}" + {{- end }} + items: + type: object + properties: + {{- range $k, $v := .OapiProperties }} + {{ $k }}: + type: {{ $v }} + {{- end }} + {{- if .GoType }} + x-go-type: {{ .GoType }} + {{- end }} + {{- if .TypeImport.Path }} + x-go-type-import: + path: {{ .TypeImport.Path }} + {{- if .TypeImport.Name }} + name: {{ .TypeImport.Name }} + {{- end }} + {{- end }} + {{- end }} diff --git a/api/cfg.yaml b/api/cfg.yaml new file mode 100644 index 0000000..a277bb7 --- /dev/null +++ b/api/cfg.yaml @@ -0,0 +1,5 @@ +package: api +generate: + std-http-server: true + models: true +output: islandora.gen.go diff --git a/api/generate.go b/api/generate.go new file mode 100644 index 0000000..99258e0 --- /dev/null +++ b/api/generate.go @@ -0,0 +1,3 @@ +package api + +//go:generate go run github.com/oapi-codegen/oapi-codegen/v2/cmd/oapi-codegen -config cfg.yaml ../api.yaml diff --git a/api/impl.go b/api/impl.go new file mode 100644 index 0000000..a84dfc8 --- /dev/null +++ b/api/impl.go @@ -0,0 +1,33 @@ +package api + +import ( + "encoding/json" + "net/http" + + islandoraModel "github.com/lehigh-university-libraries/go-islandora/model" +) + +// ensure that we've conformed to the `ServerInterface` with a compile-time check +var _ ServerInterface = (*Server)(nil) + +type Server struct{} + +func NewServer() Server { + return Server{} +} + +// (POST /upload) +func (Server) PostUpload(w http.ResponseWriter, r *http.Request) { + + // TODO: transform the vanilla CSV into workbench CSV + resp := IslandoraObject{ + Title: &islandoraModel.GenericField{ + islandoraModel.Generic{ + Value: "foo", + }, + }, + } + + w.WriteHeader(http.StatusOK) + _ = json.NewEncoder(w).Encode(resp) +} diff --git a/fixtures/node.csv b/fixtures/node.csv index 251d9cc..f78ae2a 100644 --- a/fixtures/node.csv +++ b/fixtures/node.csv @@ -1,2 +1,2 @@ -node_id,langcode,title,published,field_abstract,field_alt_title,field_classification,field_coordinates,field_coordinates_text,field_copyright_date,field_date_captured,field_date_modified,field_date_valid,field_description,field_dewey_classification,field_edition,field_edtf_date,field_edtf_date_created,field_edtf_date_issued,field_extent,field_frequency,field_full_title,field_genre,field_geographic_subject,field_identifier,field_isbn,field_language,field_lcc_classification,field_linked_agent,field_local_identifier,field_member_of,field_mode_of_issuance,field_model,field_note,field_oclc_number,field_physical_form,field_pid,field_place_published,field_place_published_country,field_publisher,field_representative_image,field_resource_type,field_rights,field_subject,field_subject_general,field_subjects_name,field_table_of_contents,field_temporal_subject,field_viewer_override,field_weight -19,,Portrait of J. Crichton-Patterson,1,,,,,,,,,,Portrait of J. Crichton-Patterson holding a computer and a stack of books.,,,,,1999,,,,,,61220/utsc10311,,,,"{""target_id"":906,""rel_type"":""relators:pht""}",,4,,894,,,,,,,University of Toronto Scarborough,,15,"Digital files found in the UTSC Library's Digital Collections are meant for research and private study used in compliance with copyright legislation. Access to digital images and text found on this website and the technical capacity to download or copy it does not imply permission to re-use. Prior written permission to publish, or otherwise use images and text found on the website must be obtained from the copyright holder. Please contact UTSC Library for further information.",,907,,,,34, +Changed,Created,FieldAbstract,FieldAltTitle,FieldClassification,FieldCoordinates,FieldCoordinatesText,FieldCopyrightDate,FieldDateCaptured,FieldDateModified,FieldDateValid,FieldDescription,FieldDeweyClassification,FieldEdition,FieldEdtfDate,FieldEdtfDateCreated,FieldEdtfDateIssued,FieldExtent,FieldFrequency,FieldFullTitle,FieldGenre,FieldGeographicSubject,FieldIdentifier,FieldIsbn,FieldLanguage,FieldLccClassification,FieldLinkedAgent,FieldLocalIdentifier,FieldMemberOf,FieldModeOfIssuance,FieldModel,FieldNote,FieldOclcNumber,FieldPhysicalForm,FieldPid,FieldPlacePublished,FieldPlacePublishedCountry,FieldPublisher,FieldRepresentativeImage,FieldResourceType,FieldRights,FieldSubject,FieldSubjectGeneral,FieldSubjectsName,FieldTableOfContents,FieldTemporalSubject,FieldViewerOverride,FieldWeight,Language,Nid,RevisionLog,RevisionTimestamp,RevisionUid,Status,Title,Type,Uid,Uuid,Vid +2024-06-27T04:05:47+00:00,2024-06-27T04:05:47+00:00,,,,,,,,,,Portrait of J. Crichton-Patterson holding a computer and a stack of books.,,,,,1999,,,,,,61220/utsc10311,,,,"{""target_id"":906,""rel_type"":""relators:pht""}",,4,,894,,,,,,,University of Toronto Scarborough,,15,"Digital files found in the UTSC Library's Digital Collections are meant for research and private study used in compliance with copyright legislation. Access to digital images and text found on this website and the technical capacity to download or copy it does not imply permission to re-use. Prior written permission to publish, or otherwise use images and text found on the website must be obtained from the copyright holder. Please contact UTSC Library for further information.",,907,,,,34,,,19,,2024-06-27T04:05:47+00:00,1,1,Portrait of J. Crichton-Patterson,"[{""target_id"":""islandora_object"",""target_type"":""node_type"",""target_uuid"":""6399fba1-f0d8-4c8a-8162-9c8dd4d357ff""}]",1,63c8ca1b-807f-4774-b9c6-a0d715b31452,19 diff --git a/go.mod b/go.mod index 73f26db..f1f13ce 100644 --- a/go.mod +++ b/go.mod @@ -4,6 +4,7 @@ go 1.22.2 require ( github.com/gocarina/gocsv v0.0.0-20240520201108-78e41c74b4b1 + github.com/oapi-codegen/oapi-codegen/v2 v2.3.0 github.com/stretchr/testify v1.9.0 golang.org/x/exp v0.0.0-20240613232115-7f521ea00fb8 gopkg.in/yaml.v2 v2.4.0 @@ -11,6 +12,17 @@ require ( require ( github.com/davecgh/go-spew v1.1.1 // indirect + github.com/getkin/kin-openapi v0.124.0 // indirect + github.com/go-openapi/jsonpointer v0.20.2 // indirect + github.com/go-openapi/swag v0.22.8 // indirect + github.com/invopop/yaml v0.2.0 // indirect + github.com/josharian/intern v1.0.0 // indirect + github.com/mailru/easyjson v0.7.7 // indirect + github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 // indirect + github.com/perimeterx/marshmallow v1.1.5 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect + golang.org/x/mod v0.18.0 // indirect + golang.org/x/text v0.15.0 // indirect + golang.org/x/tools v0.22.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/go.sum b/go.sum index 30045a7..98bfd5f 100644 --- a/go.sum +++ b/go.sum @@ -1,16 +1,54 @@ github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/getkin/kin-openapi v0.124.0 h1:VSFNMB9C9rTKBnQ/fpyDU8ytMTr4dWI9QovSKj9kz/M= +github.com/getkin/kin-openapi v0.124.0/go.mod h1:wb1aSZA/iWmorQP9KTAS/phLj/t17B5jT7+fS8ed9NM= +github.com/go-openapi/jsonpointer v0.20.2 h1:mQc3nmndL8ZBzStEo3JYF8wzmeWffDH4VbXz58sAx6Q= +github.com/go-openapi/jsonpointer v0.20.2/go.mod h1:bHen+N0u1KEO3YlmqOjTT9Adn1RfD91Ar825/PuiRVs= +github.com/go-openapi/swag v0.22.8 h1:/9RjDSQ0vbFR+NyjGMkFTsA1IA0fmhKSThmfGZjicbw= +github.com/go-openapi/swag v0.22.8/go.mod h1:6QT22icPLEqAM/z/TChgb4WAveCHF92+2gF0CNjHpPI= +github.com/go-test/deep v1.0.8 h1:TDsG77qcSprGbC6vTN8OuXp5g+J+b5Pcguhf7Zt61VM= +github.com/go-test/deep v1.0.8/go.mod h1:5C2ZWiW0ErCdrYzpqxLbTX7MG14M9iiw8DgHncVwcsE= github.com/gocarina/gocsv v0.0.0-20240520201108-78e41c74b4b1 h1:FWNFq4fM1wPfcK40yHE5UO3RUdSNPaBC+j3PokzA6OQ= github.com/gocarina/gocsv v0.0.0-20240520201108-78e41c74b4b1/go.mod h1:5YoVOkjYAQumqlV356Hj3xeYh4BdZuLE0/nRkf2NKkI= +github.com/invopop/yaml v0.2.0 h1:7zky/qH+O0DwAyoobXUqvVBwgBFRxKoQ/3FjcVpjTMY= +github.com/invopop/yaml v0.2.0/go.mod h1:2XuRLgs/ouIrW3XNzuNj7J3Nvu/Dig5MXvbCEdiBN3Q= +github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY= +github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= +github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE= +github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk= +github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= +github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0= +github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= +github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 h1:RWengNIwukTxcDr9M+97sNutRR1RKhG96O6jWumTTnw= +github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826/go.mod h1:TaXosZuwdSHYgviHp1DAtfrULt5eUgsSMsZf+YrPgl8= +github.com/oapi-codegen/oapi-codegen/v2 v2.3.0 h1:rICjNsHbPP1LttefanBPnwsSwl09SqhCO7Ee623qR84= +github.com/oapi-codegen/oapi-codegen/v2 v2.3.0/go.mod h1:4k+cJeSq5ntkwlcpQSxLxICCxQzCL772o30PxdibRt4= +github.com/perimeterx/marshmallow v1.1.5 h1:a2LALqQ1BlHM8PZblsDdidgv1mWi1DgC2UmX50IvK2s= +github.com/perimeterx/marshmallow v1.1.5/go.mod h1:dsXbUu8CRzfYP5a87xpp0xq9S3u0Vchtcl8we9tYaXw= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/rogpeppe/go-internal v1.12.0 h1:exVL4IDcn6na9z1rAb56Vxr+CgyK3nn3O+epU5NdKM8= +github.com/rogpeppe/go-internal v1.12.0/go.mod h1:E+RYuTGaKKdloAfM02xzb0FW3Paa99yedzYV+kq4uf4= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= +github.com/ugorji/go/codec v1.2.11 h1:BMaWp1Bb6fHwEtbplGBGJ498wD+LKlNSl25MjdZY4dU= +github.com/ugorji/go/codec v1.2.11/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= golang.org/x/exp v0.0.0-20240613232115-7f521ea00fb8 h1:yixxcjnhBmY0nkL253HFVIm0JsFHwrHdT3Yh6szTnfY= golang.org/x/exp v0.0.0-20240613232115-7f521ea00fb8/go.mod h1:jj3sYF3dwk5D+ghuXyeI3r5MFf+NT2An6/9dOA95KSI= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= +golang.org/x/mod v0.18.0 h1:5+9lSbEzPSdWkH32vYPBwEpX8KwDbM52Ud9xBUvNlb0= +golang.org/x/mod v0.18.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= +golang.org/x/sync v0.7.0 h1:YsImfSBoP9QPYL0xyKJPq0gcaJdG3rInoqxTWbfQu9M= +golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/text v0.15.0 h1:h1V/4gjBv8v9cjcR6+AR5+/cIYK5N/WAgiv4xlsEtAk= +golang.org/x/text v0.15.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= +golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= +golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= +gopkg.in/yaml.v3 v3.0.0/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/islandora/.keep b/islandora/.keep deleted file mode 100644 index e69de29..0000000 diff --git a/main.go b/main.go index 16671ee..c7233ac 100644 --- a/main.go +++ b/main.go @@ -14,9 +14,17 @@ import ( ) type Field struct { - Name string - Type string - MachineName string + Name string + Type string + Title string + Description string + MachineName string + Required bool + OapiProperties map[string]string + + // see https://github.com/oapi-codegen/oapi-codegen?tab=readme-ov-file#openapi-extensions + GoType string + TypeImport TypeImport } type StructData struct { @@ -24,6 +32,11 @@ type StructData struct { Fields []Field } +type TypeImport struct { + Path string + Name string +} + func main() { nodeCexYaml := flag.String("node-cex-yaml", "", "Path to the node CEX YAML file") output := flag.String("output", "./generated_structs.go", "Output file for generated structs") @@ -51,7 +64,7 @@ func main() { os.Exit(1) } - fields := []Field{} + fields := nodeFields() for _, file := range files { yamlFile, err := os.ReadFile(file) @@ -69,12 +82,18 @@ func main() { fieldName := data["field_name"].(string) fieldType := data["field_type"].(string) - - fieldTypeGo := mapFieldTypeToGoType(fieldType) fields = append(fields, Field{ - Name: toCamelCase(fieldName), - Type: fieldTypeGo, - MachineName: fieldName, + Name: toCamelCase(fieldName), + OapiProperties: mapFieldTypeToOapiProperties(fieldType), + Title: data["label"].(string), + Description: strings.ReplaceAll(data["description"].(string), `"`, `\"`), + MachineName: fieldName, + Required: data["required"].(bool), + GoType: mapFieldTypeToGoType(fieldType), + TypeImport: TypeImport{ + Path: "github.com/lehigh-university-libraries/go-islandora/model", + Name: "islandoraModel", + }, }) } @@ -84,7 +103,7 @@ func main() { Fields: fields, } - structCode, err := generateGoStruct(structData) + structCode, err := generateOapiSpec(structData) if err != nil { slog.Error("Error generating Go struct: %s", err) os.Exit(1) @@ -99,8 +118,8 @@ func main() { slog.Info("Structs generated and written", "file", *output) } -func generateGoStruct(data StructData) (string, error) { - tmpl, err := template.ParseFiles("node.go.tmpl") +func generateOapiSpec(data StructData) (string, error) { + tmpl, err := template.ParseFiles("api.yaml.tmpl") if err != nil { return "", err } @@ -114,6 +133,59 @@ func generateGoStruct(data StructData) (string, error) { return buf.String(), nil } +func mapFieldTypeToOapiProperties(fieldType string) map[string]string { + properties := map[string]string{} + switch fieldType { + case "boolean": + properties["value"] = "boolean" + case "entity_reference": + properties["target_id"] = "integer" + case "integer": + properties["value"] = "integer" + case "geolocation": + properties["lat"] = "number" + properties["lng"] = "number" + case "hierarchical_geographic": + properties["continent"] = "string" + properties["country"] = "string" + properties["region"] = "string" + properties["state"] = "string" + properties["territory"] = "string" + properties["county"] = "string" + properties["city"] = "string" + properties["city_section"] = "string" + properties["island"] = "string" + properties["area"] = "string" + properties["extraterrestrial_area"] = "string" + case "typed_relation": + properties["rel_type"] = "string" + properties["target_id"] = "integer" + case "related_item": + properties["identifier"] = "string" + properties["identifier_type"] = "string" + properties["number"] = "string" + properties["title"] = "string" + case "textfield_attr", "textarea_attr": + properties["attr0"] = "string" + properties["attr1"] = "string" + properties["value"] = "string" + if fieldType == "textarea_attr" { + properties["format"] = "string" + } + case "part_detail": + properties["type"] = "string" + properties["caption"] = "string" + properties["number"] = "string" + properties["title"] = "string" + case "config_reference": + properties["target_id"] = "string" + default: + properties["value"] = "string" + } + + return properties +} + func mapFieldTypeToGoType(fieldType string) string { switch fieldType { case "boolean": @@ -138,6 +210,8 @@ func mapFieldTypeToGoType(fieldType string) string { return "islandoraModel.TypedTextField" case "part_detail": return "islandoraModel.PartDetailField" + case "config_reference": + return "islandoraModel.ConfigReferenceField" default: return "islandoraModel.GenericField" } @@ -158,3 +232,39 @@ func toCamelCase(input string) string { } return output } + +// some base properties for the node entity +func nodeFields() []Field { + fields := []Field{} + f := map[string]string{ + "nid": "integer", + "vid": "integer", + "uuid": "string", + "language": "string", + "revision_timestamp": "string", + "revision_uid": "entity_reference", + "revision_log": "string", + "uid": "entity_reference", + "title": "string", + "type": "config_reference", + "status": "boolean", + "created": "string", + "changed": "string", + } + for fieldName, fieldType := range f { + fields = append(fields, Field{ + Name: toCamelCase(fieldName), + OapiProperties: mapFieldTypeToOapiProperties(fieldType), + Title: toCamelCase(fieldName), + Description: "", + MachineName: fieldName, + GoType: mapFieldTypeToGoType(fieldType), + TypeImport: TypeImport{ + Path: "github.com/lehigh-university-libraries/go-islandora/model", + Name: "islandoraModel", + }, + }) + } + + return fields +} diff --git a/main_test.go b/main_test.go index f3191dd..2070f16 100644 --- a/main_test.go +++ b/main_test.go @@ -6,7 +6,7 @@ import ( "os" "testing" - "github.com/lehigh-university-libraries/go-islandora/islandora" + islandora "github.com/lehigh-university-libraries/go-islandora/api" "github.com/gocarina/gocsv" "github.com/stretchr/testify/assert" @@ -67,12 +67,16 @@ func TestLoadJSON(t *testing.T) { if err != nil { t.Fatalf("Failed to load JSON: %v", err) } - - assert.Equal(t, "Digital files found in the UTSC Library's Digital Collections are meant for research and private study used in compliance with copyright legislation. Access to digital images and text found on this website and the technical capacity to download or copy it does not imply permission to re-use. Prior written permission to publish, or otherwise use images and text found on the website must be obtained from the copyright holder. Please contact UTSC Library for further information.", node.FieldRights[0].Value) - assert.Equal(t, "University of Toronto Scarborough", node.FieldPublisher[0].Value) - assert.Equal(t, 4, node.FieldMemberOf[0].TargetId) - assert.Equal(t, "1999", node.FieldEdtfDateIssued[0].Value) - assert.Equal(t, "islandora_object", node.Type[0].TargetId) + r := *node.FieldRights + p := *node.FieldPublisher + m := *node.FieldMemberOf + d := *node.FieldEdtfDateIssued + ty := *node.Type + assert.Equal(t, "Digital files found in the UTSC Library's Digital Collections are meant for research and private study used in compliance with copyright legislation. Access to digital images and text found on this website and the technical capacity to download or copy it does not imply permission to re-use. Prior written permission to publish, or otherwise use images and text found on the website must be obtained from the copyright holder. Please contact UTSC Library for further information.", r[0].Value) + assert.Equal(t, "University of Toronto Scarborough", p[0].Value) + assert.Equal(t, 4, m[0].TargetId) + assert.Equal(t, "1999", d[0].Value) + assert.Equal(t, "islandora_object", ty[0].TargetId) } func TestSaveJson(t *testing.T) { diff --git a/node.go.tmpl b/node.go.tmpl deleted file mode 100644 index 8e2e156..0000000 --- a/node.go.tmpl +++ /dev/null @@ -1,23 +0,0 @@ -package islandora - -import ( - islandoraModel "github.com/lehigh-university-libraries/go-islandora/model" -) - -type {{.StructName}} struct { - Nid islandoraModel.IntField `json:"nid" csv:"node_id"` - Vid islandoraModel.IntField `json:"vid" csv:"-"` - Uuid islandoraModel.GenericField `json:"uuid" csv:"-"` - Language islandoraModel.GenericField `json:"lang" csv:"langcode"` - RevisionTimestamp islandoraModel.GenericField `json:"revision_timestamp" csv:"-"` - RevisionUid islandoraModel.EntityReferenceField `json:"revision_uid" csv:"-"` - RevisionLog islandoraModel.GenericField `json:"revision_log" csv:"-"` - Uid islandoraModel.EntityReferenceField `json:"uid" csv:"-"` - Title islandoraModel.GenericField `json:"title" csv:"title"` - Type islandoraModel.ConfigReferenceField `json:"type" csv:"-"` - Status islandoraModel.BoolField `json:"status" csv:"published"` - Created islandoraModel.GenericField `json:"created" csv:"-"` - Changed islandoraModel.GenericField `json:"changed" csv:"-"` - -{{range .Fields}} {{ .Name }} {{ .Type }} `json:"{{ .MachineName }},omitempty" csv:"{{ .MachineName }}"` -{{end}}} diff --git a/tests/starter-site.sh b/tests/starter-site.sh index 667c1ba..fe602d1 100755 --- a/tests/starter-site.sh +++ b/tests/starter-site.sh @@ -8,10 +8,12 @@ fi go run main.go \ --node-cex-yaml=./islandora-starter-site/config/sync/node.type.islandora_object.yml \ - --output=islandora/islandora_object.go + --output=api.yaml -go fmt islandora/islandora_object.go > /dev/null +# TODO: if/once generation of YAML is deterministric add this check back in +# diff api.yaml fixtures/islandora_object.yaml || (echo "Failure Maybe starter site updated its data model?" && exit 1) -diff islandora/islandora_object.go fixtures/islandora_object.go || (echo "Failure Maybe starter site updated its data model?" && exit 1) +go generate ./api +ls -l api/islandora.gen.go -echo "Generated struct matches expected output 🚀" +echo "Generated Open API spec matches expected output 🚀" diff --git a/tools.go b/tools.go new file mode 100644 index 0000000..35e0f39 --- /dev/null +++ b/tools.go @@ -0,0 +1,8 @@ +//go:build tools +// +build tools + +package main + +import ( + _ "github.com/oapi-codegen/oapi-codegen/v2/cmd/oapi-codegen" +)