Crate forgefix

source ·
Expand description

An opinionated FIX 4.2 client library for the buy-side.

ForgeFIX is an engine that implements a subset of the FIX protocol which allows users to connect to brokers or exchanges to send and receive messages.

§Terminology

  • FIX Connection – A single connection to a FIX Session. A network connection is made over TCP, then a FIX logon handshake is performed to establish the FIX connection. The FIX connection ends properly with a FIX logout, but is considered ended if the TCP connection breaks.

    • Note, the term ‘connection’ is overloaded and can also mean TCP connection. When unclear, a ‘connection’ will be specified as TCP or FIX.
  • FIX Session – A conceptual construct that represents the bidirectional stream of ordered messages between two peers. A FIX Session can live across multiple instances of a FIX connection.

  • FIX Engine – A sub-process running in the background that manages a single FIX connection to a FIX Session. The engine starts, runs, and ends the FIX connection as defined by the FIX protocol, and manages all resources that support the connection.

§Examples

§Asynchronous API

use forgefix::{
    SessionSettings, FixApplicationHandle, FixApplicationInitiator, ApplicationError,
}; 

#[tokio::main]
async fn main() -> Result<(), ApplicationError> {
     
    // build session settings 
    let settings = SessionSettings::builder()
        .with_sender_comp_id("my_id")
        .with_target_comp_id("peer_id")
        .with_store_path("./store".into())
        .with_log_dir("./log".into())
        .with_socket_addr("127.0.0.1:0".parse().unwrap())
        .build()?; 

    // create a FIX engine and intiate TCP connection
    let (fix_handle, mut event_receiver) = FixApplicationInitiator::build(settings)?
        .initiate()
        .await?;

    // handle incoming messages in the background...
    tokio::spawn(async move {
        while let Some(msg) = event_receiver.recv().await {
            println!("got an application message: {}", msg);
        }
    });

    // start the FIX connection
    fix_handle.start_async().await?;

    // send messages here...

    // end the FIX connection
    fix_handle.end_async().await?;

    Ok(())
}

§Synchronous API*

use forgefix::{
    SessionSettings, FixApplicationHandle, FixApplicationInitiator, ApplicationError,
}; 

fn main() -> Result<(), ApplicationError> {

    let settings = SessionSettings::builder()
        .with_sender_comp_id("my_id")
        .with_target_comp_id("peer_id")
        .with_store_path("./store".into())
        .with_log_dir("./log".into())
        .with_socket_addr("127.0.0.1:0".parse().unwrap())
        .build()?; 

    let (fix_handle, mut event_receiver) = FixApplicationInitiator::build(settings)?
        .initiate_sync()?; 

    std::thread::spawn(move || {
        while let Some(msg) = event_receiver.blocking_recv() {
            println!("got an application message: {}", msg); 
        }
    }); 

    fix_handle.start_sync()?; 

    // send messages here...

    fix_handle.end_sync()?;
     
    Ok(())
}

*When using synchronous API, a tokio runtime is still created internally (see FixApplicationInitiator)

Modules§

Structs§

Enums§