{"id":16582789,"url":"https://github.com/ribice/twisk","last_synced_at":"2025-04-06T02:08:51.700Z","repository":{"id":57495320,"uuid":"144939953","full_name":"ribice/twisk","owner":"ribice","description":"Golang RPC starter kit with Twirp","archived":false,"fork":false,"pushed_at":"2024-11-28T12:05:56.000Z","size":7785,"stargazers_count":127,"open_issues_count":1,"forks_count":4,"subscribers_count":5,"default_branch":"master","last_synced_at":"2025-03-30T01:07:35.325Z","etag":null,"topics":["golang","protobuf","rest-api","rpc","starter","starter-kit"],"latest_commit_sha":null,"homepage":"https://www.ribice.ba/twisk/","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ribice.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":"2018-08-16T05:17:31.000Z","updated_at":"2024-11-28T12:06:00.000Z","dependencies_parsed_at":"2024-12-30T05:20:06.605Z","dependency_job_id":"70519cfa-f8cc-4090-9c07-5ad33c011497","html_url":"https://github.com/ribice/twisk","commit_stats":null,"previous_names":[],"tags_count":0,"template":true,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ribice%2Ftwisk","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ribice%2Ftwisk/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ribice%2Ftwisk/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ribice%2Ftwisk/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ribice","download_url":"https://codeload.github.com/ribice/twisk/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247423515,"owners_count":20936626,"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":["golang","protobuf","rest-api","rpc","starter","starter-kit"],"created_at":"2024-10-11T22:34:08.970Z","updated_at":"2025-04-06T02:08:51.680Z","avatar_url":"https://github.com/ribice.png","language":"Go","funding_links":[],"categories":["Go"],"sub_categories":[],"readme":"# Twisk - Golang RPC starter kit\n\n[![Build Status](https://travis-ci.org/ribice/twisk.svg?branch=master)](https://travis-ci.org/ribice/twisk)\n[![codecov](https://codecov.io/gh/ribice/twisk/branch/master/graph/badge.svg)](https://codecov.io/gh/ribice/twisk)\n[![Go Report Card](https://goreportcard.com/badge/github.com/ribice/twisk)](https://goreportcard.com/report/github.com/ribice/twisk)\n\nTwisk is a starter kit for [Twirp](https://github.com/twitchtv/twirp) - a framework for service-to-service communication emphasizing simplicity and minimalism.\n\nIt contains things you need to kickstart your project - structured packaging, logging, autogenerated swagger docs, handlers for login/refresh and user CRUD.\n\nI made this project as a preparation for Gophercon 2018 Lightning Talk - [Building robust APIs with Twirp](https://gc2018-lightning.herokuapp.com/blocks/c8d55346-012d-4d72-83db-fc8a3f92a9a3/slots/9ccad9a7-1e67-4f40-8889-dfa86110ba9e).\n\nRead more about Twirp on the [official repo](https://github.com/twitchtv/twirp), [release blog post](https://blog.twitch.tv/twirp-a-sweet-new-rpc-framework-for-go-5f2febbf35f) and [documentation website](https://twitchtv.github.io/twirp/docs/intro.html).\n\nTwisk currently has:\n\n* Fully featured RESTful endpoints for authentication and CRUD operations on the user entity\n* Session handling using JWT claims\n* JWT Based authentication\n* Application configuration via config file (yaml)\n* RBAC (role-based access control)\n* Structured logging\n* Request marshaling and data validation\n* Autogenerated API Docs using SwaggerUI\n* Mocking using stdlib\n* Basic test coverage\n\nThe following dependencies are used in this project (generated using [Glice](https://github.com/ribice/glice)):\n\n```bash\n|---------------------------------------|-----------------------------------------------|-------------|\n|             DEPENDENCY                |                    REPOURL                    |   LICENSE   |\n|---------------------------------------|-----------------------------------------------|-------------|\n| github.com/golang/protobuf            | https://github.com/golang/protobuf            | bsd-3-clause|\n| gopkg.in/yaml.v2                      | https://github.com/go-yaml/yaml               | Apache-2.0  |\n| github.com/mwitkow/go-proto-validators| https://github.com/mwitkow/go-proto-validators| Apache-2.0  |\n| github.com/twitchtv/twirp             | https://github.com/twitchtv/twirp             | Other       |\n| github.com/gorilla/mux                | https://github.com/gorilla/mux                | bsd-3-clause|\n| github.com/justinas/alice             | https://github.com/justinas/alice             | MIT         |\n| github.com/go-pg/pg                   | https://github.com/go-pg/pg                   | bsd-2-clause|\n| github.com/rs/xid                     | https://github.com/rs/xid                     | MIT         |\n| github.com/nbutton23/zxcvbn-go        | https://github.com/nbutton23/zxcvbn-go        | MIT         |\n| github.com/rakyll/statik              | https://github.com/rakyll/statik              | Apache-2.0  |\n| github.com/dgrijalva/jwt-go           | https://github.com/dgrijalva/jwt-go           | MIT         |\n| github.com/rs/zerolog                 | https://github.com/rs/zerolog                 | MIT         |\n|---------------------------------------|-----------------------------------------------|-------------|\n```\n\n1. Protobuf - Proto formats (timestamp)\n2. Yaml - Unmarshalling YAML config file\n3. Twirp - RPC Framework\n4. Mux - Router\n5. Alice - Chaining middlewares\n6. PG - PostgreSQL ORM\n7. Statik - Static files to binary generator\n8. JWT-GO - JWT Authentication\n9. Zerolog - Logging\n10. XID - Refresh token generation\n11. ZXCVBN-Go - Password strength checker\n\nMost of these can easily be replaced with your own choices since their usage is abstracted and localized. In addition to these, the following tools were used:\n\n* Retool - Go executables vendoring\n* GoValidators - Proto (request/response) validation\n* TwirpSwagger - Swagger docs generator from proto definitions\n\n## Project Structure\n\nTwisk's project structure mostly follows [THIS](https://github.com/golang-standards/project-layout) example repository.\n\nTwisk doesn't follow all best practices advices by Twirp. For example, functions are named `List`, `Create` and `Delete` instead of `ListUsers`, `CreateUser` and `DeleteUser` (I prefer shorter function names, handlers and functions named `user.List` istead of `user.ListUsers`). You can read on Twirp's best practices [here](https://twitchtv.github.io/twirp/docs/best_practices.html).\n\n## Getting started\n\nUsing Twisk requires having Go 1.7 or above. Once you downloaded Twisk (either using Git or go get) you need to configure the following:\n\n1. To use Twisk as a starting point of a real project whose package name is something like `github.com/author/project`, move the directory `$GOPATH/github.com/ribice/twisk` to `$GOPATH/github.com/author/project` and do a global replacement of the string `github.com/ribice/twisk` with `github.com/author/project`.\n\n2. Change the configuration file according to your needs. The local config file is found in `cmd/api/conf.local.yaml`. You'll need to configure `database/psn` at least.\n\n3. In cmd/migration/main.go set up psn variable and then run it (go run main.go). It will create all tables, and necessary data, with a new account username/password admin/admin.\n\n4. Run the app using:\n\n```bash\ngo run cmd/api/main.go\n```\n\nThe application runs as an HTTP server at port 8080. It exposes the following endpoints:\n\n* `GET /openapi/swaggerui`: returns list of swagger specs in browser\n* `POST /twirp/twisk.iam.IAM/Auth`: accepts username or email and password. Returns jwt token and refresh token\n* `POST /twirp/twisk.iam.IAM/Refresh`: refreshes sessions and returns new jwt token\n* `POST /twirp/twisk.user.User/Create`:  creates a new user\n* `POST /twirp/twisk.user.User/List`:  returns list of users\n* `POST /twirp/twisk.user.User/View`: returns single user\n* `POST /twirp/twisk.user.User/Delete`: deletes a user\n* `POST /twirp/twisk.user.User/Update`: updates user's contact info\n\nYou can log in as admin to the application by sending a post request to localhost:8080/twirp/twisk.iam.IAM/Auth with auth `admin` and password `admin` in JSON body.\n\n## Implementing new APIs\n\n1. Under `proto` folder, create a new one named after your service. For example `tenant`. Inside it create `service.proto`\n\n2. Define your proto file. If you are not familiar with Protobufs, you can read more about it [here](https://developers.google.com/protocol-buffers/docs/proto3). You can use already existing proto files (`proto/user/service.proto` \u0026 `proto/iam/service.proto`) as a template.\n\n3. Run `make twirp -B`.\n\n4. Implement the Tenant interface from `service.twirp.go` in `internal/tenant`.\n\n5. Tenant service integrations are located in `internal/tenant/platform`. For example cloud storage, database, message queue etc.\n\n6. Implement the interface in logging.go, wrapping around the service implementation.\n\n7. Add service link to `openapi/swagger.html`. Alternatively, use build-links in your CI/CD pipeline to auto-generate the `swagger.html` from `swagger.html.template`.\n\n8. Wire up everything in `cmd/api/main.go`. If neeeded, you can easily skip auth checking on certain routes by passing the service name to `hooks.WithJWTAuth()`. For example `hooks.WithJWTAuth(j, \"View\",\"List\")`.\n\n## License\n\nTwisk is licensed under the MIT license. Check the [LICENSE](LICENSE.md) file for details.\n\n## Honorable mention\n\nSpecial thanks to [@tonto](https://github.com/tonto) for previously creating some parts of this project.\n\n## Author\n\n[Emir Ribic](https://dev.ribic.ba)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fribice%2Ftwisk","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fribice%2Ftwisk","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fribice%2Ftwisk/lists"}