null

package module
v1.2.4 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 27, 2023 License: MIT Imports: 4 Imported by: 0

README

Description

Package provides generic nullable types.

Base usage

Example with JSON marshalling

func main() {
	type simpleStruct struct {
		Int     int                `json:"int"`
		NullInt null.Nullable[int] `json:"nullInt"`
	}

	type complicatedStruct struct {
		NullInt     null.Nullable[int64]        `json:"nullInt"`
		NullInt2    null.Nullable[int64]        `json:"nullInt2"`
		NullString  null.Nullable[string]       `json:"nullString"`
		NullString2 null.Nullable[string]       `json:"nullString2"`
		NullTime    null.Nullable[time.Time]    `json:"nullTime"`
		NullTime2   null.Nullable[time.Time]    `json:"nullTime2"`
		NullStruct  null.Nullable[simpleStruct] `json:"nullStruct"`
		NullStruct2 null.Nullable[simpleStruct] `json:"nullStruct2"`
	}

	someValue := complicatedStruct{
		NullInt:    null.NullableValue(int64(1)),
		NullString: null.NullableValue("ABC"),
		NullTime:   null.NullableValue(time.Now()),
		NullStruct: null.NullableValue(simpleStruct{
			Int:     1,
			NullInt: null.Nullable[int]{},
		}),
	}

	_ = json.NewEncoder(os.Stdout).Encode(&someValue)
}

Example with SQL handling

// ...
var nullableInt64 null.Nullable[int64]
// ...
_ = rows.Scan(&nullableInt64)
// ...
_, _ = conn.Exec(context.Background(), 'DELETE FROM table WHERE id = $1', &nullableInt64)
// ...

Compatible with pgx.
Keep in mind that only int64, float64, bool, []byte, string, time.Time can be used for such purposes.

Custom usage

Base type

type (
	//MyNullable is defined in order to implement custom JSON marshaling and unmarshaling and database sql compatability
	MyNullable[T any] struct {
		null.Type[T]
	}
)

Implementing json.Marshaler and json.Unmarshaler

func (t *MyNullable[T]) MarshalJSON() ([]byte, error) {
    if t.IsNull() {
        return []byte("null"), nil
    }

    vPtr := t.RawValuePtr()

    switch v := any(vPtr).(type) {
    case *time.Time: //Custom time.Time marshaling
        return []byte(v.Format("\"2006-01-02\"")), nil
    default:
        return json.Marshal(vPtr)
    }
}

func (t *MyNullable[T]) UnmarshalJSON(bytes []byte) error {
    if string(bytes) == "null" {
        t.SetNull()
        return nil
    }

    switch ptr := any(t.RawValuePtr()).(type) {
	case *time.Time: //Custom time.Time unmarshaling
        ts, err := time.Parse("\"2006-01-02\"", string(bytes))
        if err != nil {
            return err
        }

        t.SetValue(t.DefaultValue())
        *ptr = ts
    default:
        var v T
        err := json.Unmarshal(bytes, &v)
        if err != nil {
            return err
        }

        t.SetValue(v)
    }

    return nil
}

You can implement sql.Scanner and driver.Valuer for compatability with sql/database so provided nullable types can be used for either scanning as destinations, or performing query with parameters. Example:

// Value Implements driver.Valuer
func (t *MyNullable[T]) Value() (driver.Value, error) {
    if t.IsNull() {
        return nil, nil
    }

    return t.RawValue(), nil
}

// Scan implements sql.Scanner
func (t *MyNullable[T]) Scan(src any) error {
    switch src.(type) {
    case nil:
        t.SetNull()
    default:
        v, ok := src.(T)
        if !ok {
            return errors.New("unsupported")
        }
        t.SetValue(v)
    }
    return nil
}

Documentation

Overview

Package null provides generic nullable types.

Provided types are compatible with encoding/json (json.Marshaler and json.Unmarshaler) and sql/database (sql.Scanner and driver.Valuer)

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrScanningTypeMismatch = errors.New("scanning type mismatch")
	ErrTypeIsNotSupported   = errors.New("type is not supported by driver.Valuer")
)

Functions

This section is empty.

Types

type Nullable added in v1.2.3

type Nullable[T any] struct {
	Type[T]
}

Nullable is defined in order to implement default JSON marshaling and unmarshaling, and sql/database compatability

func NullableValue added in v1.2.3

func NullableValue[T any](value T) Nullable[T]

NullableValue returns not null Nullable with value.

func NullableValueFromPtr added in v1.2.3

func NullableValueFromPtr[T any](valuePtr *T) Nullable[T]

NullableValueFromPtr returns null Nullable if valuePtr is nil, Nullable with actual value otherwise.

func (Nullable[T]) MarshalJSON added in v1.2.3

func (t Nullable[T]) MarshalJSON() ([]byte, error)

func (*Nullable[T]) Scan added in v1.2.3

func (t *Nullable[T]) Scan(src any) error

Scan implements sql.Scanner. Supported T are: int, int32, int64, uint, uint32, uint64, float32, float64, bool, []byte, string, time.Time

func (*Nullable[T]) UnmarshalJSON added in v1.2.3

func (t *Nullable[T]) UnmarshalJSON(bytes []byte) error

func (Nullable[T]) Value added in v1.2.3

func (t Nullable[T]) Value() (driver.Value, error)

Value Implements driver.Valuer. Supported T are: int, int32, int64, uint, uint32, uint64, float32, float64, bool, []byte, string, time.Time

type Type

type Type[T any] struct {
	// contains filtered or unexported fields
}

Type represents a nullable type. Default value is null.

func TypeValue added in v1.2.3

func TypeValue[T any](value T) Type[T]

TypeValue returns not null value of T.

func TypeValueFromPtr added in v1.2.3

func TypeValueFromPtr[T any](valuePtr *T) Type[T]

TypeValueFromPtr returns null Type if valuePtr is nil, Type with actual value otherwise.

func (*Type[T]) CheckedValue added in v1.2.0

func (s *Type[T]) CheckedValue() (T, bool)

CheckedValue returns actual value and true if Type is not null, default value of T and false otherwise.

func (*Type[T]) CheckedValuePtr added in v1.2.0

func (s *Type[T]) CheckedValuePtr() (*T, bool)

CheckedValuePtr returns pointer to actual value and true if Type is not null, false otherwise

func (*Type[T]) DefaultValue added in v1.2.0

func (s *Type[T]) DefaultValue() T

DefaultValue returns default value of T

func (*Type[T]) IsNull

func (s *Type[T]) IsNull() bool

IsNull returns true if value is null.

func (*Type[T]) RawValue

func (s *Type[T]) RawValue() T

RawValue returns actual value if Type is not null, default value of T otherwise.

func (*Type[T]) RawValuePtr added in v1.2.0

func (s *Type[T]) RawValuePtr() *T

RawValuePtr returns pointer to actual value. Is useful only when Type is not null

func (*Type[T]) SetNull

func (s *Type[T]) SetNull()

SetNull sets Type to null.

func (*Type[T]) SetValue

func (s *Type[T]) SetValue(v T)

SetValue sets Type to not null value v.

func (*Type[T]) SetValueFromPtr added in v1.2.0

func (s *Type[T]) SetValueFromPtr(valuePtr *T)

SetValueFromPtr sets Type to not null value if valuePtr is not nil, null value otherwise.

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL