1. Help Center
  2. Order management

How does LUSID support the order process?

What are the entities involved in controlling the order lifecycle within LUSID and how are they related?

Note: LUSID support for the order lifecycle is currently in the Experimental stage, meaning that features will be in various stages of completion, and that data stored is not subject to the same guarantees as more established features.

The order lifecycle

The order lifecycle within LUSID is represented via a domain model of related entities and functions, which allows the client the freedom to model any bespoke relationship required. At a very high level, the model allows use cases such as the following:

  • Fund managers give verbal instructions to brokers to execute transactions.
  • Electronic RFQs are generated via eTrading platforms.
  • A large futures order is placed directly on an exchange, resulting in hundreds of small fills
  • An allocation process examines the participation and apportions the fills across multiple accounts
  • Transactions are matched back to the original orders and the remainder held over to be re-submitted at the next session

Different organisations use processes of varying complexity over different instruments, and typically interchange terms from a mostly common set to describe the entities involved. To support such a range of related systems, LUSID uses an extensible model that can be mapped onto any particular client use case.

In the diagram below, we show an example order workflow and how it interacts with the LUSID domain model. This is by no means representative of all use cases, and our intention is to ensure clients can consume as much or little of the model as needed.

Example order workflow 2.0

Once an order in LUSID has been blocked and placed with executing brokers or intermediaries in accordance with its participation, the allocation process distributes returned executions to allocations in line with its ruleset and the originating order's participation. Transactions are then created and booked from the allocations.

An orders and allocations book of record

Today, the LUSID trade lifecycle is in early development, offering the ability to record orders and allocations. Support exists via API endpoint (see orders and allocations) and examples of the implementation in code can be found in the SDK and in Jupyter Notebook.

Orders and allocations in LUSID support a small core of common properties, to which a client can add bespoke properties as appropriate. Both can be filtered on retrieval by any of the properties, the LusidInstrumentId (LUID), Quantity, OrderId or Portfolio.

Order and Allocation entities in LUSID

Further entities, as shown in the workflow above, are currently on the Finbourne roadmap; we intend to create first class entities of order books, blocks, executions, participations and placements. We are also working on a blended position view which includes pending orders across portfolios.

Mapping FIX messages

The most direct points of integration with the market would be via receipt of FIX New Order Single messages (which in the full model would map to the LUSID placement entity) and FIX Execution Report messages (which map to the LUSID execution entity), both via FIX drop copy, although LUSID also supports the bulk upload of order, allocation or other entity data directly to appropriate endpoints.

Currently, LUSID has some facility for processing FIX. In the full domain model a FIX Execution Report message, for example, would get mapped to a LUSID execution. However, as an example, it's possible to demonstrate its mapping to a LUSID allocation, mimicking the direct-allocation process a smaller investment concern might want to use.

Say the market produces an Execution Report for sale of 25 gold futures contracts:

8=FIX.4.2|9=266|35=8|49=ABC|56=XYZ|50=AZ12|57=NA|34=833|52=20200130-08:00:51.992|55=GLD|48=PL11YA|167=FUT|207=LIFFE|1=AA1|37=ORD000001234|17=ACBDFE|58=Fill|200=202009|205=13|32=25|151=0|14=25|54=2|40=2|77=O|59=0|150=2|20=0|39=2|442=1|44=99.06|38=25|31=99.06|6=99.06|60=20100130-08:00:52|10=136|

This would get mapped onto an allocation with:

Allocation
OrderId = ORD000001234
Quantity = 25
Instrument Identifiers = {
"Instrument/default/ZYX", "Something Here"
}
Portfolio = "ClientScope/AA1",
Properties = {
"Order/ClientScope/ExecId", "ACBDFE",
"Order/ClientScope/Symbol", "GLD",
"Order/ClientScope/SecurityId", "PL11YA",
"Order/ClientScope/SecurityType", "FUT",
"Order/ClientScope/SecurityExchange", "LIFFE",
"Order/ClientScope/MaturityMonthYear", "202009",
"Order/ClientScope/MaturityDay", "23",
"Order/ClientScope/LeavesQty", "0",
"Order/ClientScope/Side", "Sell", // mapped from 2
"Order/ClientScope/TimeInForce", "Day", // mapped from 0
"Order/ClientScope/Price", "99.06",
"Order/ClientScope/AvgPx", "99.06",
"Order/ClientScope/LastPx", "99.06",
"Order/ClientScope/TransactTime", "20200130-08:00:51.992",
...
}