legend-studio
legend-studio copied to clipboard
Bug: Unable to open query builder form editor for multiply `Boolean` expression of an explosion property.
Similar issues
- [X] I have searched and found no existing similar issues
How are you using Studio?
Legend Query
Current and expected behavior
When editing a query lambda on an explosion property with multiple booleans, the rendering of the query builder will fail with Can't display query in form mode due to: Can't process filter expression: no compatible filter operator processer available from plugins
.
We should be able to process the given lambda. If required we may need to enable derived filter expression support
Steps to reproduce
- Open query builder by right clicking on
model::Person
- Go to query builder text mode
- Copy below lambda and the query builder. Query
{date: Date[1],brands: String[*]|model::Person.all()->filter(
x|$x.firm->exists(
x_1|$x_1.brand->in(
$brands
) &&
($x_1.date ==
$date)
)
)->project(
[
x|$x.name
],
['name']
)}
Model data
###Relational
Database store::MyDatabase
(
Schema MySchema
(
Table PersonTable1
(
Brand VARCHAR(128) NOT NULL,
NAME VARCHAR(128),
LASTNAME VARCHAR(128),
Nick_Name VARCHAR(128) NOT NULL,
Hq1_State VARCHAR(128),
Hq1_Street VARCHAR(128),
Hq2_State VARCHAR(128),
Hq2_Street VARCHAR(128),
Value DOUBLE,
Locations INTEGER,
Found_Date DATE PRIMARY KEY,
ID VARCHAR(128) PRIMARY KEY
)
Table PersonTable2
(
Brand VARCHAR(128) NOT NULL,
NAME VARCHAR(128),
LASTNAME VARCHAR(128),
Nick_Name VARCHAR(128) NOT NULL,
Hq1_State VARCHAR(128),
Hq1_Street VARCHAR(128),
Hq2_State VARCHAR(128),
Hq2_Street VARCHAR(128),
Value DOUBLE,
Locations INTEGER,
Found_Date DATE PRIMARY KEY,
ID VARCHAR(128) PRIMARY KEY
)
)
)
###Pure
Class model::Firm
{
hq1: model::HQ[0..1];
hq2: model::HQ[0..1];
brand: String[1];
value: Float[1];
date: Date[1];
locations: Integer[1];
}
Class model::HQ
{
state: String[1];
street: String[1];
}
Class model::Person
{
name: String[1];
lastName: String[1];
nickName: String[1];
firm: model::Firm[*];
}
###Mapping
Mapping mapping::MyMapping
(
*model::Person: Operation
{
meta::pure::router::operations::union_OperationSetImplementation_1__SetImplementation_MANY_(person1,person2)
}
model::Person[person1]: Relational
{
~primaryKey
(
[store::MyDatabase]MySchema.PersonTable1.Found_Date,
[store::MyDatabase]MySchema.PersonTable1.ID
)
~mainTable [store::MyDatabase]MySchema.PersonTable1
name: [store::MyDatabase]MySchema.PersonTable1.NAME,
lastName: [store::MyDatabase]MySchema.PersonTable1.LASTNAME,
nickName: [store::MyDatabase]MySchema.PersonTable1.Nick_Name,
firm
(
hq1
(
state: [store::MyDatabase]MySchema.PersonTable1.Hq1_State,
street: [store::MyDatabase]MySchema.PersonTable1.Hq1_Street
),
hq2
(
state: [store::MyDatabase]MySchema.PersonTable1.Hq2_State,
street: [store::MyDatabase]MySchema.PersonTable1.Hq2_Street
),
brand: [store::MyDatabase]MySchema.PersonTable1.Brand,
locations: [store::MyDatabase]MySchema.PersonTable1.Locations,
value: [store::MyDatabase]MySchema.PersonTable1.Value,
date: [store::MyDatabase]MySchema.PersonTable1.Found_Date
)
}
model::Person[person2]: Relational
{
~primaryKey
(
[store::MyDatabase]MySchema.PersonTable2.Found_Date,
[store::MyDatabase]MySchema.PersonTable2.ID
)
~mainTable [store::MyDatabase]MySchema.PersonTable2
name: [store::MyDatabase]MySchema.PersonTable2.NAME,
lastName: [store::MyDatabase]MySchema.PersonTable2.LASTNAME,
nickName: [store::MyDatabase]MySchema.PersonTable2.Nick_Name,
firm
(
hq1
(
state: [store::MyDatabase]MySchema.PersonTable2.Hq1_State,
street: [store::MyDatabase]MySchema.PersonTable2.Hq1_Street
),
hq2
(
state: [store::MyDatabase]MySchema.PersonTable2.Hq2_State,
street: [store::MyDatabase]MySchema.PersonTable2.Hq2_Street
),
brand: [store::MyDatabase]MySchema.PersonTable2.Brand,
locations: [store::MyDatabase]MySchema.PersonTable2.Locations,
value: [store::MyDatabase]MySchema.PersonTable2.Value,
date: [store::MyDatabase]MySchema.PersonTable2.Found_Date
)
}
)
Environment
Windows
Possible solution and workaround
Equivalent query grammar will work.
{date: Date[1],nickNames: String[*],brands: String[*]|model::Person.all()->filter(
x|$x.firm->exists(
x_1|$x_1.brand->in(
$brands
)
) &&
($x.firm->exists(
x_1|$x_1.date ==
$date
) &&
$x.nickName->in(
$nickNames
))
)->project(
[
x|$x.name
],
['name']
)}
Contribution
- [X] I would like to work on the fix for this issue
Main issue is query builder is not understanding multiple grouped expression within the exists. Query Builder throws an error for the below as its expecting a single expression within the exists
$x.firm->exists(
x_1|$x_1.brand->in(
$brands
) &&
($x_1.date ==
$date)
)
It does not throw for the same logical expression below which separates the below into 2 exist expressions.
$x.firm->exists(
x_1|$x_1.brand->in(
$brands
)
) &&
($x.firm->exists(
x_1|$x_1.date ==
$date
)
Thoughts on solution
- [ ] During processing convert the first expression into the second
-
Drawback
Doesn't keep user intent. - Follows what we are doing in flattening grouped expression. Also maps to a corresponding supported UI component providing UI for the properties
-
- [ ] Implement #627. Will deal with similar cases as above. Also if we choose not to even handle the above it will keep the user intent.
Solution could be both the implementation of 627 and the flatten on this expression. @akphi thoughts???