go library for complex struct mapping

Dto mapper

Go Report Card

dto-mapper is an easy-to-use library for complex struct mapping. It's intended for the creation of data transfer objects, hence the name.

When working with database relations and ORMs, you often fetch more data than needed. One could create subtypes for all kinds of queries, but this is not suitable for quick prototyping. Tools like go-funk and structs make your mapping code less verbose, but you still have to write it.

dto-mapper requries only a declaration and contraty to many other struct mappers uses only name-based field resolution, works with arbitrary deep structures, slices, maps, poiners, embedded structs, supports custom conversion functions, error handling... you name it!

Simple example

You just have to declare the values you want to extract and dto does the rest.

func GetUserPosts(c *gin.Context) {
    var userDto struct {
        Name  string
        Posts []struct {
          Id    int
          Title string
        }
    }
    userModel := LoadUserWithPosts(userId)
    dto.Map(&userDto, userModel)
    c.JSON(200, userDto)
}

Installation

go get github.com/dranikpg/dto-mapper

More examples

Slices, maps and structs

dto works its way down recursively through struct fields, slices and maps.

var shoppingCart struct {
    GroupedProducts map[string][]struct {
        Name      string
        Warehouse struct {
            Location string
        }
    }
}

Maps can be converted into slices of their values. What's more, a map of slices can be converted into a single slice.

var allProducts []Product = nil
var groupedProducts map[string][]Product = GetProducts()
dto.Map(&allProducts, groupedProducts)
Emedded structs and pointers

Embedded struct fields are included. Pointers are automatically dereferenced.

type User struct {
    gorm.Model
    CompanyRefer int
    Company      *Company `gorm:"foreignKey:CompanyRefer"`
}

type UserDto struct {
    ID      int
    Company struct {
        Name string
    }
}

Mapper instances

Local mapper instances can be used to add conversion and inspection functions. Mappers don't change their internal state during mapping, so they can be reused at any time.

mapper := dto.Mapper{}
mapper.Map(&to, from)
Conversion functions

They are used to convert one type into another. Conversion functions have the highest priority. The second argument is the current mapper instance and is optional.

mapper.AddConvFunc(func(p RawPassword, mapper *Mapper) PasswordHash {
    return hash(p)
})
Inspection functions

Those are triggered after a value has been successfully mapped. The value is always taken by pointer.

mapper.AddInspectFunc(func(dto *UserDto) {
    dto.Link = GenerateLink(dto.ID)
})

They can also be defined with a specific source type. The last argument is optional.

mapper.AddInspectFunc(func(dto *UserDto, user User, mapper *Mapper) {
    dto.Online = IsRecent(user.LastSeen)
})
Error handling
  • Both conversion and inspection functions can return errors by returning (value, error) and error respectively
  • If dto failed to map one value onto another, it returns ErrNoValidMapping
  • dto silently skips struct fields it found no source for (i.e. no fields with the same name)

Mapping stops as soon as an error is encountered.

mapper.AddInspectFunc(func(dto *UserDto) error {
    if len(dto.Link) == 0 {
        return errors.New("malformed link")
    }
    return nil
})

err := mapper.Map(&to, from) // error: malformed link

Performance

Dto is based on reflection and therefore much slower than handwritten mapping code. Furthermore, using custom functions disables direct assignment of composite types.

Contributing

Missing a common use case? Feel free to contribute!

Owner
Similar Resources

Data structure and algorithm library for go, designed to provide functions similar to C++ STL

GoSTL English | 简体中文 Introduction GoSTL is a data structure and algorithm library for go, designed to provide functions similar to C++ STL, but more p

Dec 26, 2022

Zero allocation Nullable structures in one library with handy conversion functions, marshallers and unmarshallers

nan - No Allocations Nevermore Package nan - Zero allocation Nullable structures in one library with handy conversion functions, marshallers and unmar

Dec 20, 2022

A Go library for an efficient implementation of a skip list: https://godoc.org/github.com/MauriceGit/skiplist

A Go library for an efficient implementation of a skip list: https://godoc.org/github.com/MauriceGit/skiplist

Fast Skiplist Implementation This Go-library implements a very fast and efficient Skiplist that can be used as direct substitute for a balanced tree o

Dec 30, 2022

Go Library [DEPRECATED]

Tideland Go Library Description The Tideland Go Library contains a larger set of useful Google Go packages for different purposes. ATTENTION: The cell

Nov 15, 2022

an R-Tree library for Go

rtreego A library for efficiently storing and querying spatial data in the Go programming language. About The R-tree is a popular data structure for e

Jan 3, 2023

Golang library for reading and writing Microsoft Excel™ (XLSX) files.

Golang library for reading and writing Microsoft Excel™ (XLSX) files.

Excelize Introduction Excelize is a library written in pure Go providing a set of functions that allow you to write to and read from XLSX / XLSM / XLT

Jan 9, 2023

Golang library for querying and parsing OFX

OFXGo OFXGo is a library for querying OFX servers and/or parsing the responses. It also provides an example command-line client to demonstrate the use

Nov 25, 2022

Go (golang) library for reading and writing XLSX files.

XLSX Introduction xlsx is a library to simplify reading and writing the XML format used by recent version of Microsoft Excel in Go programs. Tutorial

Jan 5, 2023

indexing library for Go

Bluge modern text indexing in go - blugelabs.com Features Supported field types: Text, Numeric, Date, Geo Point Supported query types: Term, Phrase, M

Jan 3, 2023
Comments
  • Panic on nil pointers in structs

    Panic on nil pointers in structs

    Hi,

    When mapping from a struct, to a struct, either of which contain nil pointers, the mapValue function will panic on the following line:

    tk, fk := toRv.Type().Kind(), fromRv.Type().Kind()

    This is due to a nil pointer dereference

    The following code snippet skips mapValues if either side is nil:

    func (m *Mapper) mapValue(toRv, fromRv reflect.Value) (returnError error) { if !toRv.IsValid() || !fromRv.IsValid() { return }

    That works for me but unsure of any unintended consequences.

    Thanks,

    Tom

Go package for mapping values to and from space-filling curves, such as Hilbert and Peano curves.
Go package for mapping values to and from space-filling curves, such as Hilbert and Peano curves.

Hilbert Go package for mapping values to and from space-filling curves, such as Hilbert and Peano curves. Documentation available here This is not an

Dec 23, 2022
Go iter tools (for iterating , mapping, filtering, reducing streams -represented as channels-)

Go iter tools (for iterating , mapping, filtering, reducing streams -represented as channels-)

Jan 1, 2023
A faster method to get elements from an interface (Struct or Slice type) for Go.

A faster method to get elements from an interface (Struct or Slice type) for Go.

May 13, 2022
Convert arbitrary formats to Go Struct (including json, toml, yaml, etc.)

go2struct Convert arbitrary formats to Go Struct (including json, toml, yaml, etc.) Installation Run the following command under your project: go get

Nov 15, 2022
An interesting go struct tag expression syntax for field validation, etc.

An interesting go struct tag expression syntax for field validation, etc.

Jan 8, 2023
Convert json string to Golang struct

json-to-go-cli Convert json string to Golang struct How to install git clone https://github.com/tiancheng92/json-to-go-cli.git cd json-to-go-cli go bu

May 10, 2022
GoStruct2Table - format your struct like a table.

GoStruct2Table format your struct like a table. Installing $ go get -u -v github.com/runningzyp/GoStruct2Table Simple Example import parser "github.c

Aug 15, 2022
A small flexible merge library in go
A small flexible merge library in go

conjungo A merge utility designed for flexibility and customizability. The library has a single simple point of entry that works out of the box for mo

Dec 27, 2022
Golang string comparison and edit distance algorithms library, featuring : Levenshtein, LCS, Hamming, Damerau levenshtein (OSA and Adjacent transpositions algorithms), Jaro-Winkler, Cosine, etc...

Go-edlib : Edit distance and string comparison library Golang string comparison and edit distance algorithms library featuring : Levenshtein, LCS, Ham

Dec 20, 2022
Go native library for fast point tracking and K-Nearest queries

Geo Index Geo Index library Overview Splits the earth surface in a grid. At each cell we can store data, such as list of points, count of points, etc.

Dec 3, 2022