Guzfolio is a cryptocurrency portfolio tracker with the purpose of using it as a pattern for the implementation of good practices in the development of API's in GraphQL using Go. As main dependency we will use gqlgen to generate our API, probably the best option.
PG_CONNECTION_STRING
postgres://user:pass@localhost:5432/db_name?sslmode=disable
go run datastore/seed/seed.go
JWT_SECRET
environment variable with a cool password to sign your tokens
JWT_SECRET=my_best_kept_secret
go run server/*
I have chosen a JSON Web Token (JWT) authorization because is a compact and self-contained way for securely transmitting information between parties as a JSON object, and they are commonly used. In a traditional REST API, when applying the authorization pattern, using a middleware, we can choose which routes to secure and which are not, in this way we can separate the typical register/login calls from the rest of the API that we want to secure.
In the case of GraphQL we only have one endpoint, and we cannot use the schema to define the register/login mutations, to be honest, in a production environment, the authentication server would be separated in another service, generating the tokens that would be used in the service to consume.
I have created two register/login endpoints outside of the GraphQL API context to be able to generate the necessary tokens to be able to authenticate. To authenticate with the GraphQL API you have to register as a new user or login with an existing user (default pass is guzfolio1234) in the next endpoints:
/auth/register?email=default@guzfolio.dev&password=guzfolio1234&name=default_name
/auth/login?email=user@guzfolio.dev&password=guzfolio1234
When you obtain your JWT token you can use it in the header of your calls to the GraphQL service with the name
"Authorization"
and value "Bearer xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
. If you are using the Playground you can
include the following JSON in the HTTP HEADERS section at the bottom.
{
"Authorization": "Bearer xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
}
type Query {
profile: User!
user(id:ID!): User!
allUsers: [User!]!
allCurrencies: [Currency!]!
}
type Mutation {
createUser(input: CreateUserInput!): User!
createPortfolio(input: CreatePortfolioInput!): Portfolio!
createCurrency(input: CreateCurrencyInput!): Currency!
createTransaction(input: CreateTransactionInput!): Transaction!
}
Tech | Description |
---|---|
gqlgen | Go generate based graphql server library |
go-chi | Lightweight, idiomatic and composable router for building Go HTTP services |
go-gorm | Fantastic ORM library for Golang, aims to be developer friendly |
dataloaden | Go generate based DataLoader |
jwt-go | Golang implementation of JSON Web Tokens (JWT) |