Parameters
The Actions receive data using function parameters.
GOX automatically converts the values sent from JavaScript to the corresponding Go type before invoking the Action.
The function receives directly the values declared in its signature, without the need to read the body of an request, parse JSON or manually access HTTP parameters.
Basic parameters
The parameters of an Action are declared using the same syntax as any Go function.
func Greeting(name string) gox.Action {
return "Hello, " + name
} The Action is invoked from JavaScript by passing the arguments in the same order in which they were declared.
const [message, err] = await Actions.Greeting("George") An Action can declare several parameters.
func Sum(a int, b int) gox.Action {
return a + b
} const [result, err] = await Actions.Sum(10, 20) The arguments are assigned by position. The first value sent corresponds to the first parameter, the second value to the second parameter and so on.
Data types
The parameters can use basic types of Go.
func UpdateProfile(name string, age int, active bool) gox.Action {
...
} const [result, err] = await Actions.UpdateProfile("George", 30, true) GOX converts each argument to the type declared in the signature before running the Action.
Slices, maps, structures and other composite types can also be used when the value sent from JavaScript can be represented by this type.
Structs
JavaScript objects can be received directly as Go structures.
type User struct {
Name string
Age int
Active bool
}
func SaveUser(user User) gox.Action {
...
} const [result, err] = await Actions.SaveUser({
Name: "George",
Age: 30,
Active: true
}) GOX uses the structure definition to rebuild the value before invoking the Action.
This allows you to work directly with Go types and avoids declaring a separate parameter for each property.
Slices
JavaScript arrays can be received as Go slices.
func DeleteUsers(ids []int) gox.Action {
...
} const [result, err] = await Actions.DeleteUsers([12, 18, 24]) Each element of the array is converted to the type defined by the slice.
Maps
JavaScript objects can also be received as maps when their properties represent a dynamic collection of values.
func SaveSettings(settings map[string]string) gox.Action {
...
} const [result, err] = await Actions.SaveSettings({
language: "es",
theme: "dark"
}) Maps are useful when the keys are not part of a fixed structure known during the compilation.
When the data structure is stable, it is generally preferable to use a structure.
Custom types
Actions can receive custom types defined from other types of Go.
type UserID int
type Email string
func InviteUser(id UserID, email Email) gox.Action {
...
} const [result, err] = await Actions.InviteUser(42, "[email protected]") GOX retains the type declared in the signature, allowing the Action to work with the same types used by the rest of the application.
Execution context
An Action can receive the execution context using a parameter *gox.Context.
func SaveUser(user User, ctx *gox.Context) gox.Action {
...
} The context should always be declared as the last parameter of the function.
func SaveUser(user User, ctx *gox.Context) gox.Action The following signature is not valid:
func SaveUser(ctx *gox.Context, user User) gox.Action The context is not sent from JavaScript. GOX provides it automatically when running the Action.
For this reason, invocation only includes the parameters prior to the context.
const [result, err] = await Actions.SaveUser({
Name: "George",
Age: 30,
Active: true
}) Since JavaScript, context presence does not change the public signature of the Action.
The context allows access to the current request, session, response and other resources associated with the execution of the page.
Number of arguments
The Actions use the normal rules of the Go functions.
All declared parameters should be given value and sent in the correct order.
func Transfer(from UserID, to UserID, amount float64) gox.Action {
...
} const [result, err] = await Actions.Transfer(10, 25, 150.50) GO does not support optional parameters and the Actions maintain this same behavior.
Variative functions cannot be used as Actions either.
func Invalid(values ...string) gox.Action When an operation needs to receive a variable amount of values, a slice should be used.
func SaveValues(values []string) gox.Action {
...
} const [result, err] = await Actions.SaveValues(["first", "second", "third"]) Conversion of values
Before running an Action, GOX converts every JavaScript argument to the type declared in the signature.
func UpdateScore(score int) gox.Action {
...
} const [result, err] = await Actions.UpdateScore(100) If the values sent cannot be converted to the expected types, the Action does not run.
func UpdateScore(score int) gox.Action {
...
} const [result, err] = await Actions.UpdateScore("invalid") Errors related to invalid arguments are returned by the same error mechanism used by the Actions.
Integration with Go
The parameters of an Action directly use the Go type system.
No annotations, decorators or additional syntax are required to describe the data received. The function signature contains all the information necessary to validate and convert the arguments.
The usual rules of Go are also maintained: the parameters are positional, cannot be optional and the varying functions are not part of the Action model.
The only special parameter is *gox.Context, which can be declared at the end of the signature and is automatically provided by GOX.
Best practices
- It uses individual parameters when an Action receives few simple values.
- When several values represent the same entity or operation, add them to a structure.
- It prefers structures for known structures and maps for collections whose keys are really dynamic.
- Keep
*gox.Contextas the last parameter and declare only when the Action needs access to the execution environment. - To receive a variable amount of values, use a slice instead of a variable function.
To learn more about ActionsSee your documentation. To learn more about FormsSee your documentation. To learn more about Return valuesSee your documentation. To learn more about Errors, check your documentation.