Error clarification required:

ErrorCould not display interface. Please check definition and inputs. Interface Definition: Expression evaluation error at function a!forEach [line 40]: Error in a!forEach() expression during iteration 1: Expression evaluation error at function a!textField [line 46]: Invalid index: Cannot index property 'SourceDisplayName' of type Text into type Text

Please explain what this means? It seems ambiguous, as it is unable to map a Text type to Text.

Trying to retrieve records from DB with a Query Rule and with foreach trying to display in Editable Grid. The Expression Mode SAIL code is below:

 

=load(

local!sources: rule!CoE_RetrieveAllSources_QueryRule(),
a!formLayout(
label: "Add/Edit Sources of Technologies",
contents: {
a!gridLayout(
totalCount: count(local!sources),
headerCells: {
a!gridLayoutHeaderCell(label: "Display Name" ),
a!gridLayoutHeaderCell(label: "Full Name" ),
a!gridLayoutHeaderCell(label: "Description" ),
/* For the "Remove" column */
a!gridLayoutHeaderCell(label: "" )
},
/* Only needed when some columns need to be narrow */
columnConfigs: {
a!gridLayoutColumnConfig(width: "DISTRIBUTE", weight:3 ),
a!gridLayoutColumnConfig(width: "DISTRIBUTE", weight:3 ),
a!gridLayoutColumnConfig(width: "DISTRIBUTE", weight:5 ),
a!gridLayoutColumnConfig(width: "ICON")
},
/*
* a!forEach() will take local!employee data and used that data to loop through an
* expression that creates each row.
*
* When modifying the recipe to work with your data, you only need to change:
* 1.) the number of fields in each row
* 2.) the types of fields for each column (i.e. a!textField() for text data elements)
* 3.) the fv!item elements. For example fv!item.firstName would change to fv!item.yourdata
*/
rows: a!forEach(
items: local!sources,
expression: a!gridRowLayout(
contents: {
/* For the Last Name Column*/
a!textField(
label: "Display Name " & fv!index,
value: fv!item.SourceDisplayName,
saveInto: fv!item.SourceDisplayName,
required:true
),
/* For the Department Column*/
a!textField(
label: "Full Name " & fv!index,
value: fv!item.SourceFullName,
saveInto: fv!item.SourceFullName,
required:true
),
/* For the Title Column*/
a!textField(
label: "Description " & fv!index,
value: fv!item.SourceDescription,
saveInto: fv!item.SourceDescription,
required:true
),
/* For the Removal Column*/
a!imageField(
label: "Remove " & fv!index,
images: a!documentImage(
document: a!iconIndicator("REMOVE"),
altText: "Remove source",
caption: "Remove " & fv!item.SourceDisplayName,
link: a!dynamicLink(
value: fv!index,
saveInto: {
a!save(local!sources, remove(local!sources, save!value))
}
)
),
size: "ICON"
)
},
id: fv!index
)
),
addRowlink: a!dynamicLink(
label: "Add Source",
/*
* For your use case, set the value to a blank instance of your CDT using
* the type constructor, e.g. type!Employee(). Only specify the field
* if you want to give it a default value e.g. startDate: today()+1.
*/
value: {
startDate: today() + 1
},
saveInto: {
a!save(local!sources, append(local!sources, save!value))
}
)
)
},
buttons: a!buttonLayout(
primaryButtons: a!buttonWidgetSubmit(
label: "Submit"
)
)
)
)

  Discussion posts and replies are publicly visible