Dynamic Attributes

Version Date Notes By
0.3 2018-10-23 Complete overhaul of the attribute system, with grouping and further targeting ability ROB
0.2 2018-07-17 Value artifact target ROB
0.1 2017-08-28 Initial release ROB

This system allows any object (Backend Model) to define or store dynamic attributes. Dynamic attributes are extra fields that the user may wish to add to an object as a way to complement that object's information. Dynamic attributes come in many types (defined in the T00AttributeTypesTableSeeder class).

Since the version 0.3 of this document, all dynamic attributes must be inside a group in order to be displayed in the frontend. Attribute groups join multiple attributes together and can be used (optionally) to display them inside a <fieldset-bordered> component.

Using the attribute system (as a developer) is divided into two parts; setting up the attribute definition object and the attribute values object. For example in the Documents module there is the Document Family (defining the attributes) and the Document (storing the values of the defined attributes).

Setting Up Attribute Definition

Attribute definitions are where the attribute fields are defined, ordered and their validation properties are set.

New in 0.2: Attribute definitions can specify which v10 artifact (Document, DocumentRevision) the definition is refering to. That definition will appear in that artifact.

New in 0.3 Attribute defining artifacts can specify which v10 artifacts the definition refers to (see above) as well as a field value pair that the attribute is made available in (e.g.: when using artifact field status_id = Status::IN_ELABORATION)

Frontend

You must define the view for this particular form (that is create the .html file corresponding to the view model where the attributes are to be defined). Inside the view you must include the administration generic component for adding / removing attribute definitions to the model (via compose):


<compose view-model="wemake-modules/administration/attributes/reusable-components/attribute-definitions/index" model.bind="model"></compose>

The reusable component may bind a model or an object like so:

{
    model: model_variable,
        attributable_fqcn
:
    'WeMake\\Sgi\\Modules\\Plans\\Models\\PlanTypeDefinition'
}

Note that the attributable_fqcn parameter defines the artifact that defines the attributes. In this example plan type definition can define attributes for plans and plan actions (we'll see how to set this up in the backend). If your definer of attributes only defines attributes for a single artifact just leave this out (or bind the model direcly to reusable components / attribute definitions).

The frontend model must define a variable named attributes initialized with an empty array.

Setting up attribute value storage

Attribute value storage is where the attribute value is stored

NOTE: The frontend way of providing the dynamic attributes has changed from a FormSchema class in version 0.2 of this document to a component that you compose into the view in version 0.3 of this document.

Compose the attribute values form component like so:


<compose view-model="wemake-modules/administration/attributes/reusable-components/attribute-values-form/index" model.bind="dynamicAttributeOptions"></compose>

After the frontend has obtained the attributes define the model for the compose above like so:

this.dynamicAttributeOptions = {
    // Model to which the values are to be attached
    attributable_fqcn_filter: 'WeMake\\Sgi\\Modules\\Plans\\Models\\Plan',

    // If a target filter has been defined, enter it here
    artifact_field_filter: null,

    // If a target value has been defined, enter it here
    artifact_field_value_filter: null,

    // List of attributes as sent from the backend
    attribute_definitions: attributes,

    // Model instance
    model: this.model,

    // Place within the model where the attribute values are stored
    // (Optional, used if a single model stores multiple attribute value 
    // groups for multiple backend models)
    attribute_model_override: 'plan_attributes'
};

Note: if the definer of these attributes can target multiple artifacts, you must set the attributable_fqcn_filter to the artifact being created / edited.

The values entered in the attribute fields will be transmited to the server allong with everything else when the user submits the information.