With XPO, you can build criteria based on persistent objects that are not directly related (don't have explicitly defined associations) using Free Joins. In essence, XPO allows you to join any persistent objects on a condition, calculate aggregate functions against matching objects using their properties, and return aggregate values as the result of joining. To accomplish this, use JoinOperands in your criteria.
Options for creating the JoinOperand include:
The CriteriaOperator.Parse method.
The general format of the method's criteria string parameter is: [<JoinTypeName>][JoinCondition]
To indicate properties of the parent object within the join condition, prefix them with a caret and dot ('^.'), as shown below:
[<JoinTypeName>][[^.ParentObjectProperty] = [JoinedObjectProperty]]
The following code snippet demonstrates how to retrieve employees that closed more than 50 orders.
The JoinOperand constructors.
You can use specific constructors to create the JoinOperand, and initialize it with join and aggregate settings via corresponding constructor parameters.
CriteriaOperator joinCriteria = new OperandProperty("^.EmployeeID") == new OperandProperty("EmployeeID"); JoinOperand joinOperand = new JoinOperand("Orders", joinCriteria, Aggregate.Count, new OperandProperty("EmployeeID")); BinaryOperator criteria = new BinaryOperator(joinOperand, new OperandValue(50), BinaryOperatorType.Greater); XPCollection<Employee> employees = new XPCollection<Employee>(session, criteria);
The Join operation in LINQ to XPO.
The syntax is the same as the syntax of group joins (the JoinGroup method) in LINQ.