{"id":16304790,"url":"https://github.com/moznion/gonstructor","last_synced_at":"2025-09-03T13:31:55.646Z","repository":{"id":54414205,"uuid":"226480238","full_name":"moznion/gonstructor","owner":"moznion","description":"A command-line tool to generate a constructor for the struct.","archived":false,"fork":false,"pushed_at":"2024-06-28T01:51:05.000Z","size":88,"stargazers_count":86,"open_issues_count":5,"forks_count":10,"subscribers_count":4,"default_branch":"master","last_synced_at":"2024-12-23T14:17:11.911Z","etag":null,"topics":["code-generation","golang"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"bsd-3-clause","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/moznion.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2019-12-07T08:35:03.000Z","updated_at":"2024-10-28T19:57:34.000Z","dependencies_parsed_at":"2024-06-28T02:38:17.125Z","dependency_job_id":null,"html_url":"https://github.com/moznion/gonstructor","commit_stats":null,"previous_names":[],"tags_count":9,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moznion%2Fgonstructor","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moznion%2Fgonstructor/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moznion%2Fgonstructor/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moznion%2Fgonstructor/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/moznion","download_url":"https://codeload.github.com/moznion/gonstructor/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":231889019,"owners_count":18441359,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["code-generation","golang"],"created_at":"2024-10-10T21:04:50.515Z","updated_at":"2024-12-30T16:49:17.884Z","avatar_url":"https://github.com/moznion.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# gonstructor\n\nA command-line tool to generate a constructor for the struct.\n\n## Installation\n\n```\n$ go install github.com/moznion/gonstructor/cmd/gonstructor@latest\n```\n\nAlso, you can get the pre-built binaries on [Releases](https://github.com/moznion/gonstructor/releases).\n\nOr get it with [gobinaries.com](https://gobinaries.com):\n\n```bash\ncurl -sf https://gobinaries.com/moznion/gonstructor | sh\n```\n\n## Dependencies\n\ngonstructor depends on [goimports](https://pkg.go.dev/golang.org/x/tools/cmd/goimports) for fixing import paths and formatting code, you need to install it:\n\n```\n$ go install golang.org/x/tools/cmd/goimports@latest\n```\n\n## Usage\n\n```\nUsage of gonstructor:\n  -constructorTypes string\n        [optional] comma-separated list of constructor types; it expects \"allArgs\" and \"builder\" (default \"allArgs\")\n  -init string\n        [optional] name of function to call on object after creating it\n  -output string\n        [optional] Output file name (default \"srcdir/\u003ctype\u003e_gen.go\"). See also \"-type\" option's description.'\n  -propagateInitFuncReturns\n        [optional] If this option is specified, the generated constructor propagates the return values that come from the init function specified by the \"-init\" option, e.g. when the init function returns an \"error\" value, the generated constructor returns (*YourStructType, error). Known issue: If this option is used with the multiple --type options, probably it won't be the expected result.\n  -type value\n        [mandatory] A type name. It accepts this option occurs multiple times to output the generated code of the multi types into a single file. If this option is given multiple times, the \"-output\" option becomes mandatory.\n  -version\n        [optional] show the version information\n  -withGetter\n        [optional] generate a constructor along with getter functions for each field\n```\n\n## Motivation\n\nData encapsulation is a good practice to make software, and it is necessary to clearly indicate the boundary of the structure by controlling the accessibility of the data fields (i.e. private or public) for that. Basically keeping the data fields be private and immutable would be good to make software be robust because it can avoid unexpected field changing.\n\nGolang has a simple way to do that by choosing the initial character's type: upper case or lower case. Once it has decided to use a field as private, it needs to make something like a constructor function, but golang doesn't have a mechanism to support constructor now.\n\nTherefore this project aims to automatically generate constructors to use structures with private and immutable, easily.\n\n## Pre requirements to run\n\n- [goimports](https://godoc.org/golang.org/x/tools/cmd/goimports)\n\n## Synopsis\n\n### Generate all args constructor\n\n1. write a struct type with `go:generate`\n\ne.g.\n\n```go\n//go:generate gonstructor --type=Structure --constructorTypes=allArgs\ntype Structure struct {\n\tfoo string\n\tbar io.Reader\n\tBuz chan interface{}\n}\n```\n\n2. execute `go generate ./...`\n3. then `gonstructor` generates a constructor code\n\ne.g.\n\n```go\nfunc NewStructure(foo string, bar io.Reader, buz chan interface{}) *Structure {\n\treturn \u0026Structure{foo: foo, bar: bar, Buz: buz}\n}\n```\n\n### Generate builder (builder means GoF pattern's one)\n\n1. write a struct type with `go:generate`\n\ne.g.\n\n```go\n//go:generate gonstructor --type=Structure --constructorTypes=builder\ntype Structure struct {\n\tfoo string\n\tbar io.Reader\n\tBuz chan interface{}\n}\n```\n\n2. execute `go generate ./...`\n3. then `gonstructor` generates a buildr code\n\ne.g.\n\n```go\ntype StructureBuilder struct {\n\tfoo        string\n\tbar        io.Reader\n\tbuz        chan interface{}\n\tbufferSize int\n}\n\nfunc NewStructureBuilder() *StructureBuilder {\n\treturn \u0026StructureBuilder{}\n}\n\nfunc (b *StructureBuilder) Foo(foo string) *StructureBuilder {\n\tb.foo = foo\n\treturn b\n}\n\nfunc (b *StructureBuilder) Bar(bar io.Reader) *StructureBuilder {\n\tb.bar = bar\n\treturn b\n}\n\nfunc (b *StructureBuilder) Buz(buz chan interface{}) *StructureBuilder {\n\tb.buz = buz\n\treturn b\n}\n\nfunc (b *StructureBuilder) BufferSize(bufferSize int) *StructureBuilder {\n\tb.bufferSize = bufferSize\n\treturn b\n}\n\nfunc (b *StructureBuilder) Build() *Structure {\n\treturn \u0026Structure{\n\t\tfoo:        b.foo,\n\t\tbar:        b.bar,\n\t\tBuz:        b.buz,\n\t\tbufferSize: b.bufferSize,\n\t}\n}\n```\n\n### Call a initializer\n\n1. write a struct type with `go:generate`\n2. write a function that initializes internal fields\n3. pass its name to `-init` parameter\n\ne.g.\n\n```go\n//go:generate gonstructor --type=Structure -init construct\ntype Structure struct {\n\tfoo        string\n\tbar        io.Reader\n\tBuz        chan interface{}\n\tbufferSize int\n\tbuffer     chan []byte `gonstructor:\"-\"`\n}\n\nfunc (structure *Structure) construct() {\n\tstructure.buffer = make(chan []byte, structure.bufferSize)\n}\n```\n\n2. execute `go generate ./...`\n3. then `gonstructor` generates a buildr code\n\ne.g.\n\n```go\nfunc NewStructure(\n\tfoo string,\n\tbar io.Reader,\n\tbuz chan interface{},\n\tbufferSize int,\n) *Structure {\n\tr := \u0026Structure{\n\t\tfoo:        foo,\n\t\tbar:        bar,\n\t\tBuz:        buz,\n\t\tbufferSize: bufferSize,\n\t}\n\n\tr.construct()\n\n\treturn r\n}\n```\n\n## How to ignore to contain a field in a constructor\n\n`gonstructor:\"-\"` supports that.\n\ne.g.\n\n```go\ntype Structure struct {\n\tfoo string\n\tbar int64 `gonstructor:\"-\"`\n}\n```\n\nThe generated code according to the above structure doesn't contain `bar` field.\n\n## How to output the generated code of each type into a single file\n\nThis CLI tool can have the `--type` option multiple times, and it must have also `--output` option.\n\nexample:\n\n```\n//go:generate gonstructor --type=AlphaStructure --type=BravoStructure --constructorTypes=allArgs,builder --withGetter --output=./alpha_and_bravo_gen.go\"\n```\n\n## How to propagate the returned values come from `-init` func\n\n`-propagateInitFuncReturns` option supports that.\n\nFor example,\n\n```go\n//go:generate gonstructor --type=Struct --constructorTypes=allArgs,builder --init validate --propagateInitFuncReturns\ntype Struct struct {\n\tfoo string\n}\n\nfunc (s *Struct) validate() error {\n\t// do something with the created `Struct` value.\n\treturn err\n}\n```\n\nthen it generates the following Go code:\n\n```go\nfunc NewStruct(foo string) (*Struct, error) {\n\tr := \u0026Struct{\n\t\tfoo: foo,\n\t}\n\n\tret_validate0 := r.validate()\n\n\treturn r, ret_validate0\n}\n```\n\nAs you can see, the generated constructor `NewStruct()` returns the constructed value and an error that comes from `validate()` function.\n\n## How to build binaries\n\nBinaries are built and uploaded by [goreleaser](https://goreleaser.com/). Please refer to the configuration file: [.goreleaser.yml](./.goreleaser.yml)\n\n## Author\n\nmoznion (\u003cmoznion@gmail.com\u003e)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmoznion%2Fgonstructor","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmoznion%2Fgonstructor","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmoznion%2Fgonstructor/lists"}