FluxaORM: A Golang ORM for MySQL and Redis
Guide
Plugins
GitHub
Guide
Plugins
GitHub
    • Introduction
    • Registry
    • Data pools
    • Entities
    • Entity fields
    • MySQL Indexes
    • Engine
    • ORM
    • Entity Schema
    • Schema Update
    • CRUD
    • Async flush
    • Searching for Entities
    • Redis Search Engine
    • MySQL Queries
    • Local Cache
    • Redis Operations
    • Distributed Lock
    • Queries Log
    • Plugins
    • Log tables

Entity fields

You have learned how to create a simple Entity. In this section, we will delve into defining other fields and how they are stored in the database.

By default, every public entity field (which starts with an uppercase letter) is stored in MySQL. However, you can specify different storage options for your fields if needed. It is important to carefully consider the types and names of your fields to ensure proper and efficient storage and retrieval of data.

Integers

Go offers a variety of integer types such as int8, int16, uint, and uint32, and FluxaORM supports all of them.

type PersonEntity struct {
    ID                 uint64
    Age                uint8
    BankAccountBalance int32
}

The table below shows how Go's integer types are mapped to MySQL column types:

goMySQLmin valuemax value
int8tinyint-128127
int16smallint-3276832767
int32 with tag orm:"mediumint"mediumint-83886088388607
int32,int,runeint-21474836482147483647
int64bigint-263263-1
uint8tinyint0255
uint16smallint065535
uint32 with tag orm:"mediumint"mediumint016777215
uint32,uintint04294967295
uint64bigint0264-1

Note that the minimum and maximum values for each type may vary depending on the MySQL version you are using. Refer to the MySQL documentation for more information.

Tips

Always take the time to carefully analyze your data and choose the best int type for each field:

  • If a field contains only positive numbers, use an unsigned type (e.g. uint, uint16, etc.).
  • Try to use the smallest possible bit size for each field. For example, using uint16 for the PersonAge field would be incorrect because people do not live longer than 255 years (at least not yet). In this case, uint8 would be a more appropriate choice.
  • It is important to use the correct type for primary keys and fields that are part of a MySQL index. Using a low bit size not only saves MySQL disk space, but also reduces the memory used to cache the index.

If you need to store a NULL value for any of the above MySQL fields, you can use a reference to the corresponding integer type (e.g. *int8, *int16, *int32, *int, *rune, *int64, *uint8, *uint16, *uint32, *uint, *uint64). In MySQL, these fields will be defined as DEFAULT NULL.

type PersonEntity struct {
    ID uint64
    // null if we don't know how many friends this person has
    // zero if no one likes him:)
    Friends *uint
}

Floats

Working with floating point values can be challenging. In FluxaORM, you can use either float32 or float64 as your primitive type. You can then use special tags to specify how the float value should be stored in MySQL.

type PersonEntity struct {
    ID          uint64
    Balance     float64
    Temperature float32 `orm:"decimal=3,1;unsigned"`
    Weight      float32 `orm:"unsigned"`
}
goMySQL
float32float
float32 with tag orm:"unsigned"float unsigned
float64double
float64 with tag orm:"unsigned"double unsigned
float32,float64 with tag orm:"decimal=X,Y"decimal(X,Y)
float32,float64 with tag orm:"decimal=X,Y;unsigned"decimal(X,Y) unsigned

All of the above MySQL fields are defined as NOT NULL. If you need to store a NULL value, you can use a reference to the corresponding floating point type (e.g. *float32, *float64). In MySQL, these fields will be defined as DEFAULT NULL.

Booleans

Working with boolean values is straightforward in FluxaORM. You can use the bool type to store boolean values in MySQL. If you need to allow NULL values in your MySQL field, you can use the *bool type instead.

type PersonEntity struct {
    ID           uint64
    Married      bool
    HasChildren  *bool
}

In MySQL, the IsActive field will be defined as NOT NULL, while the HasLicense field will be defined as DEFAULT NULL.

goMySQL
booltinyint(1)

Strings

To store text in Go, you can use the string type. Here is an example of how to use strings in a struct definition:

type ProductEntity struct {
    ID           uint64
    Title        string `orm:"required;length=150"`
    Description  string `orm:"required;length=max"`
    Brand        string
}
goMySQL
stringvarchar(255)
string with tag orm:"required"varchar(255) NOT NULL
string with tag orm:"length=X"varchar(X)
string with tag orm:"length=max"mediumtext
`

Tips

When defining string fields in your Go structs, consider adding the orm:"required" tag if the field should never hold an empty string. This can help to save space in the MySQL table where the data is stored, as the database will not need to reserve space for empty strings.

Dates and Times

To store date or date and time values, use time.Time in your struct::

type UserEntity struct {
    ID              uint64
    DateOfBirth     time.Time
    CreatedAt       time.Time `orm:"time"`
    UpdatedAt       *time.Time `orm:"time"`
}

The time.Time type will be mapped to a date NOT NULL column in MySQL. If you want to store a datetime value in MySQL, you can use the orm:"time" tag. This will map the time.Time field to a datetime NOT NULL column in MySQL.

If you want to store a nullable date or datetime value in MySQL, you can use a pointer to time.Time. A pointer to time.Time will be mapped to a date column in MySQL, and a pointer to time.Time with the orm:"time" tag will be mapped to a datetime column in MySQL.

Here is a summary of the mapping between Go types and MySQL columns:

goMySQL
time.Timedate NOT NULL
time.Time with tag orm:"time"datetime NOT NULL
*time.Timedate
*time.Time with tag orm:"time"datetime
`

Binary strings

To store binary strings in your database, use the []uint8 type in your struct:

type UserEntity struct {
    ID              uint64
    CVFileContent   []uint8
}

This will map the []uint8 field to a blob column in MySQL. If you want to store a mediumblob or longblob value in MySQL, you can use the orm:"mediumblob" or orm:"longblob" tag, respectively.

Here is a summary of the mapping between Go types and MySQL columns:

goMySQL
[]uint8blob
[]uint8 with tag orm:"mediumblob"mediumblob
[]uint8 with tag orm:"longblob"longblob

Enums and Sets

When you require the storage of a value from a predefined list in one of your fields, MySQL provides convenient options in the form of the ENUM or SET field types to accommodate this need. To enable this feature for string types, you can effortlessly implement the EnumValues interface:

type EnumValues interface {
	EnumValues() any
}

This interface is expected to return a struct that defines the valid ENUM values. For a more detailed understanding, please refer to the example below:

package main

import "github.com/latolukasz/fluxaorm"

type Color string

var Colors = struct{
	Red    Color
	Blue   Color
	Yellow Color
}{
	Red:    "red",
	Blue:   "blue",
	Yellow: "yellow",
}

func (c Color) EnumValues() any {
	return Colors
}


type UserEntity struct {
    ID              uint64
    FavoriteColor   Color `orm:"required"`
    HatedColors     []Color
}

Here is a summary of the mapping between Go types and MySQL columns:

goMySQL
ColorENUM(red,blue,yellow)
[]ColorSET(red,blue,yellow)

One-to-One References

In FluxaORM, you can define a one-to-one reference between two entities by declaring a field with the type of the Reference[EntityType]:

type CategoryEntity struct {
    ID     uint64
    Name   string  `orm:"required"`
}

type ProductEntity struct {
    ID       uint64
    Name     string  `orm:"required"`
    Category fluxaorm.Reference[CategoryEntity] `orm:"required"`
}

In the example above, FluxaORM will create a Category bigint NOT NULL column in the ProductEntity table. If the field is allowed to store NULL values, simply omit the orm:"required" tag.

Subfields

It is often useful to divide entity fields into logical groups, as this can help improve code readability and facilitate reuse of field definitions in other entities. In FluxaORM, you can do this by creating a struct for the subfields and using it as the type of a field. For example:

type Address struct  {
   Country    string
   City       string
   Street     string
   Building   uint
   PostalCode string
}

type UserEntity struct {
    ID             uint64
    HomeAddress    Address
    WorkAddress    Address
}

type CompanyEntity struct {
    ID         uint64
    Address    Address
}

You can also nest structs within structs to any desired level of complexity.

When working with structs in FluxaORM, a MySQL column is created for each field in the struct, with the field name added as a suffix to the column name. For example, the field HomeAddress.Country would be stored in a column named HomeAddressCountry varchar(255).

Anonymous Subfields

In addition to using named structs as subfields, you can also define fields using anonymous structs. For example:

type Address struct  {
   Country    string
   City       string
   Street     string
   Building   uint
   PostalCode string
}

type UserEntity struct {
    ID             uint64
    Address
}

When using anonymous structs in FluxaORM, the fields are represented in the MySQL table without a suffix. For example, the field Country would be stored in a column named Country varchar(255).

Arrays

You can also utilize Go arrays to group fields. Take a look at the example below:

type Address struct  {
    City       string
    Street     string
    PostalCode string
}

type TestEntity struct {
    ID              uint64
    Alias           [5]string
    Codes           [3]uint32
    Top10Categories [10]orm.Reference[CategoryEntity] `orm:"required"`
    Addresses       [3]Address
}

In this case, each element within the array is stored in a separate MySQL column. For instance, the example above generates columns like Alias_1 varchar(255), Alias_2 varchar(255) and so on.

Ignored Fields

Sometimes you may have public fields in an entity that should not be stored in the database. To instruct FluxaORM to ignore a field, you can use the orm:"ignore" tag:

type UserEntity struct {
    ID        uint64
    MyField   string `orm:"ignore"`
}

With this tag, FluxaORM will not create a column for the MyField field in the MySQL table for the UserEntity entity. This can be useful in cases where you want to store additional information in the struct that is not relevant to the database.

Edit this page
Last Updated: 8/8/25, 9:02 PM
Prev
Entities
Next
MySQL Indexes