I am using Validator package. I have the next Struct:
type User struct {
Name string `validate:"required"`
Email string `validate:"required,email"`
CreditCard string `validate:"credit_card"`
Password string `validate:"min=8,max=255"`
}
What can I do to generate valid random values for thats fields?
You can use faker package. It has functions like FirstName(), Email(), CCNumber(). You can also use tags (one, two) with this package in your struct.
If you're writing tests, you can use Fuzzing (implemented in Go 1.18).
Would look like this:
import "testing"
func TestHello(f *testing.F) {
// Add your seeds here
f.add("John", "john#test.com", "1234-5678-1234-5678", "#HelloWorld123")
f.Fuzz(func(t *testing.T, name, email, creditCard, pass string) {
// Write your test here
}))
}
Then run:
$ go test -fuzz
Related
I have written a custom tag reader using reflect package. Example:
type customType struct {
Prop1 string
Prop2 []float64
Prop3 map[float64]float64
}
type someStruct struct {
Var1 customType `customTag:"prop1:hello;prop2:0.15,0.1;prop3:0.15=2,3=4.1"`
}
func main() {
input := &someStruct{}
tagReader(input)
fmt.Println(input.Var1.Prop1) //prints hello
fmt.Println(input.Var1.Prop2[0]) //prints 0.15
}
The tags are written in a specific format for my custom tag reader. I would like to catch problems (if any) in the customTag tag at the compile itself. I run a make to build the whole project, so I can also add something in the make. Is there an option?
I am assuming there can be a way to check json tags at the build time, since it is the most popular tag. So, is there an option?
I'm building a graphql interface using golang. I'm using gqlgen package to implement it.
Here I need to pass all field names in a query to get it in response, But the problem is my data is huge, it is having more than 30 fields it would be difficult to pass all fields in a query.
This is my query
{Model{id, name, email, mobile,...............}}
Like this I need to pass all fields name.
Instead Im looking for a result which will return all fields without passing any fields. I mean if not passing any field names it should return all.
For example
{Model{}}
First, you really should list out all the fields in your query. That is the nature of graphql. It is verbose, but most client libraries get the fields from your data structure anyway, so it's not that bad.
So I recommend listing out all fields manually!
Using Scalars (must be on v0.11.3 or below, see https://github.com/99designs/gqlgen/issues/1293)
But if you insist, if there is a will, there is way. You can use GraphQL's scalar types and make your own. See this doc for how to make them with gqlgen: https://gqlgen.com/reference/scalars/
In your schema, you can make a JSON scalar:
scalar JSON
type Query {
random: JSON!
}
Make a model for this
// in your own models.go
// You can really play with this to make it better, easier to use
type JSONScalar json.RawMessage
// UnmarshalGQL implements the graphql.Unmarshaler interface
func (y *JSONScalar) UnmarshalGQL(v interface{}) error {
data, ok := v.(string)
if !ok {
return fmt.Errorf("Scalar must be a string")
}
*y = []byte(data)
return nil
}
// MarshalGQL implements the graphql.Marshaler interface
func (y JSONScalar) MarshalGQL(w io.Writer) {
_, _ = w.Write(y)
}
Then link the scalar to your custom type in the gql.yml
models:
JSON:
model: github.com/your-project/path/graph/model.JSONScalar
When you run the generate (use gqlgen v0.11.3 or below, gqlgen version), your resolvers will now use the custom type you made. And it's easy to use:
func (r *queryResolver) random(ctx context.Context) (model.JSONScalar, error) {
// something is the data structure you want to return as json
something := struct {
Value string
}{
Value: "Hello World",
}
d, _ := json.Marshal(something)
return model1.JSONScalar(d), nil
}
The resulting query of
// Query
{
random
}
// Response
{
"random" : {
"Value": "Hello World!"
}
}
Thank you for taking some time to read this question!
I'm new to Golang and I've been developing a simple social media API to practice the language in general. In this project I'm using a struct to represent the Model of a Post published by an user, as follows:
// models/post.go
package models
import "time"
type Post struct {
ID uint64
Title string
Content string
AuthorID uint64
Likes uint64
CreatedAt time.Time
}
func (p *Post) ValidateFields() error {
// validate fields
}
This post can be saved to the database with the help of a method that is inside a repository:
// repositories/posts.go
import (
"database/sql"
"models"
)
type PostsRepository struct {
db *sql.DB
}
func NewPostsRepository(db *sql.DB) *PostsRepository {
return &PostsRepository{db}
}
func (r *PostsRepository) Save(models.Post) (uint64, error) {
// Passing the model as a parameter
}
As you can see, the model is being passed as a parameter and that feels like a problem for two reasons:
I only need three fields to save the post to database (Title,
Content and AuthorID) because everything else will be generated
automatically
If I write an unit test to the Save function it will
rely on the model to work, therefore any problems with the model
would impact the test
So with that in mind I thought about changing the parameter from a model to an interface, but since interfaces only accept method signatures and in that specific case I only need attributes to save data on the database, I assume it would need a few getters such as:
type PostInterface interface {
GetTitle() string
GetContent() string
GetAuthorID() uint64
}
(I know it is not idiomatic to call a getter "GetAttribute", but it's just to give you an idea)
Due to that, I'd have to implement these three methods on my Post Model, which would look like
func (p Post) GetTitle() string {
return p.Title
}
func (p Post) GetContent() string {
return p.Content
}
func (p Post) GetAuthorID() uint64 {
return p.AuthorID
}
That doesn't look so good, but it gets worse when we go to the test.
Like I said, I do not want to use the model in the test so I would have to create a struct to serve as a stub or something that has only the three needed fields for the Save to work (which sounds good). However, I'd have to implement these three methods again so that the struct can be accepted as an interface by the Save function (which sounds bad)
It sounds like a lot of unecessary work, Is there any way to work around this? I'm not sure if I'm missing something conceptual about Go or if there are any changes on my architecture that could address to this issue, but I'm having trouble finding alternatives to this
Thank you!
Using a struct in the save function is perfectly fine and considered idiomatic. If this is just a data container I don't see any issues in testing this functionality. You could however opt for a slimmer version of the struct with just the respective fields you require when storing the content in the database.
For instance:
type Content struct {
Title string
Content string
AuthorID uint64
}
If you still want to decouple with an interface you can create a method on the Post model and return the Content struct, personally I don't see the need for this since it will not improve the testability and only increases complexity by using another layer of abstraction.
In your tests you can just create an instance of the Content struct and pass that to the Save function.
I have big structure with more than 50 params
type Application struct {
Id int64 `json:"id"`
FullName string `json:"fullName,omitempty"`
ActualAddress string `json:"actualAddress,omitempty"`
.....
}
I use gin-gonic and when I return application I need to omit some params I've created a function which makes empty some params (playLink) and then gin returns me correct json (without unnecessary values). I heard that reflection isn't fast operation so in our case we can use a lot of ugly if-else or switch-cases. Is there any other solutions faster than reflecting and more beautiful than if-elses?
The thing is that structure params have non-empty values, so they wont by omitted by gin. That's why I've created function to make some params empty before return
The thing is, if you only want to zero a few fields, it's more readable to do it without a function, e.g.
app := Application{}
app.FullName, app.ActualAddress = "", ""
If you want to create a function for it, at least use variadic parameter, so it's easier to call it:
func zeroFields(application *Application, fields ...string) {
// ...
}
So then calling it:
zeroFields(&app, "FullName", "ActualAddress")
Yes, this will have to use reflection, so it's slower than it could be, and error prone (mistyped names can only be detected at runtime). If you want to avoid using reflection, pass the address of the fields:
func zeroFields(ps ...*string) {
for _, p := range ps {
*p = ""
}
}
This way you have compile-time guarantee that you type field names correctly, and that they have string type.
Calling it:
zeroFields(&application.FullName, &application.ActualAddress)
Try it on the Go Playground.
If I understand correctly: you want to return some values from your struct but not all of them? Perhaps a nested struct?
type Application struct {
ID struct {
ID int64 `json:"id"`
} `json:"id"`
Person struct {
Fullname string `json:"Fullname"
} `json:"person"
}
That should let you filter out the fields you want to use.
I have a project which relies on a struct imported from another package, which I will call TheirEntity.
In the example below, I (ahem) embed TheirEntity in MyEntity, which is an extension of TheirEntity, with added functionality.
However, I don't want to export TheirEntity in the MyEntity structure, as I would rather the consumer not access TheirEntity directly.
I know that Go embedding is not the same as inheritance in classical OOP, so maybe this is not the correct approach, but is it possible to specify embedded structs as "private", even if they are imported from another package? How might one achieve the same thing in a more idiomatic fashion?
// TheirEntity contains functionality I would like to use...
type TheirEntity struct {
name string
}
func (t TheirEntity) PrintName() {
fmt.Println(t.name)
}
func NewTheirEntity(name string) *TheirEntity {
return &TheirEntity{name: name}
}
// ... by embedding in MyEntity
type MyEntity struct {
*TheirEntity // However, I don't want to expose
// TheirEntity directly. How to embed this
// without exporting and not changing this
// to a named field?
color string
}
func (m MyEntity) PrintFavoriteColor() {
fmt.Println(m.color)
}
func NewMyEntity(name string, color string) *MyEntity {
return &MyEntity{
TheirEntity: NewTheirEntity(name),
color: color,
}
}
Since the question was asked, Go saw the addition of type aliases to the language with the 1.9 release in 2017. It turns out that, through an unconventional use of type aliases, you can have your cake and eat it too!
First, declare an unexported alias for the third-party type you wish to embed in your struct:
type theirEntity = TheirEntity
Then, simply embed that alias instead of the original type:
type MyEntity struct {
*theirEntity
color string
}
(Playground)
[I]s it possible to specify embedded structs as "private", even if they are imported from another package?
No.
How might one achieve the same thing in a more idiomatic fashion?
By not-embedding but making it a unexported named field.
Like this:
type MyEntity struct {
*privateTheirEntity
}
type privateTheirEntity struct {
*TheirEntity
}