AshTypescript.Rpc.FieldProcessing.FieldSelector (ash_typescript v0.17.2)

Copy Markdown View Source

Unified field selection processor using type-driven recursive dispatch.

This module mirrors the architecture of ValueFormatter, using the same {type, constraints} pattern for type-driven dispatch. Each type is self-describing - no separate classification step is needed.

Design Principle

The key insight is that field selection and value formatting are parallel operations - both traverse composite types recursively based on type information. By using the same dispatch pattern, we achieve consistency and simplicity.

Type Categories

CategoryDetectionHandler
Ash ResourceAsh.Resource.Info.resource?(type)select_resource_fields/3
TypedStruct/NewType/CustomTypetypescript_field_names/0 callbackselect_typed_struct_fields/3
Typed Map/StructHas fields constraintsselect_typed_map_fields/3
TupleAsh.Type.Tupleselect_tuple_fields/3
UnionAsh.Type.Unionselect_union_fields/3
Array{:array, inner_type}Recurse with inner type
PrimitiveDefaultValidate no fields requested

Summary

Functions

Converts an action to its type specification.

Processes requested fields for a given resource and action.

Main recursive dispatch function for field selection.

Selects fields from an Ash resource.

Selects fields from a tuple type using named fields.

Selects fields from a typed map (Ash.Type.Map/Keyword with field constraints).

Selects fields from a TypedStruct or NewType with typescript_field_names callback.

Types

select_result()

@type select_result() :: {select :: [atom()], load :: [term()], template :: [term()]}

Functions

action_to_type_spec(resource, action)

@spec action_to_type_spec(module(), Ash.Resource.Actions.action()) ::
  {atom() | tuple(), keyword()}

Converts an action to its type specification.

Returns {type, constraints} tuple representing the action's return type.

process(resource, action_name, requested_fields)

@spec process(module(), atom(), list()) :: {:ok, select_result()} | {:error, term()}

Processes requested fields for a given resource and action.

Returns {:ok, {select_fields, load_fields, extraction_template}} or {:error, error}.

Parameters

  • resource - The Ash resource module
  • action_name - The action name (atom)
  • requested_fields - List of field selections (atoms, strings, or maps)

Examples

iex> process(MyApp.Todo, :read, [:id, :title, %{user: [:id, :name]}])
{:ok, {[:id, :title], [{:user, [:id, :name]}], [:id, :title, {:user, [:id, :name]}]}}

select_fields(type, constraints, requested_fields, path)

@spec select_fields(atom() | tuple(), keyword(), list(), list()) :: select_result()

Main recursive dispatch function for field selection.

Mirrors ValueFormatter.format/5 - uses the same type detection and dispatch pattern. Each type category has its own handler that may recurse back into this function.

select_resource_fields(resource, requested_fields, path)

Selects fields from an Ash resource.

Handles attributes, calculations, relationships, and aggregates.

select_tuple_fields(constraints, requested_fields, path)

Selects fields from a tuple type using named fields.

Tuples in Ash have named positions (like :latitude, :longitude) and the template stores both the field_name and its index for result processing. When no fields are requested, all fields are returned.

select_typed_map_fields(constraints, requested_fields, path, error_type \\ "field_constrained_type")

Selects fields from a typed map (Ash.Type.Map/Keyword with field constraints).

The error_type parameter allows distinguishing between different type categories for better error messages.

select_typed_struct_fields(constraints, requested_fields, path)

Selects fields from a TypedStruct or NewType with typescript_field_names callback.

select_union_fields(constraints, requested_fields, path, error_type \\ "union_type")

Selects fields from a union type.

Supports:

  • Simple member selection: [:member_name]
  • Member with nested fields: [%{member_name: fields}]
  • Multiple members in a single map: %{member1: fields1, member2: fields2}