Wat is 'Order Flow Trading' en hoe lees je de 'Tape' met code?

Portret van Alex de Vries, Quantitatief Analist & Algo-Trading Expert
Alex de Vries
Quantitatief Analist & Algo-Trading Expert
Algoritmische Strategieën · 2026-02-15 · 7 min leestijd

Je zit aan tafel, koffie naast je laptop, en je wilt weten wat er écht gebeurt in de markt. Order Flow Trading is de kunst om live te zien wat kopers en verkopers nu precies doen, niet wat ze gisteren deden.

Je leest de Tape (de Time & Sales) en herkent patronen in de stroom van orders. In dit stuk leg ik je uit wat Order Flow is, hoe je de Tape leest, en hoe je het vastlegt in Python-code voor je eigen trading bots. We blijven praktisch, met echte getallen en stappen die je vandaag nog kunt testen via een broker met API-toegang.

Wat je nodig hebt voordat je start

Order Flow werkt het beste op futures (bijvoorbeeld E-mini S&P 500 of Euro Bund) en op aandelen met diepe orderboeken. Je hebt een broker nodig met een snelle API en toegang tot Level 2 en Time & Sales.

Denk aan Interactive Brokers, NinjaTrader, of een futures-broker met Rithmic/CTCI. Voor Python kies je bibliotheken als ib_insync of ccxt, afhankelijk van je broker.

Zorg dat je een testaccount opent met minimaal €2.000–€5.000 voor kleine sizes. Gebruik een demo voor de eerste dagen, maar schakel daarna over naar een live micro-account om echte slippage te voelen. Installeer Python 3.10+, pip, en een IDE als VS Code.

Plan een dagdeel van 2–3 uur om te oefenen zonder druk. Je hebt verder nodig: een stabiele internetverbinding, een VPS in de buurt van de exchange (bijvoorbeeld Londen voor Euronext, Chicago voor CME) voor lage latency, en een risicomanagement-template (max risk per trade, daily loss limit). Verwacht een maandelijkse brokerkost van €10–€50 voor data, afhankelijk van je keuze. Veelgemaakte fouten: te snel live gaan zonder backtest, vergeten dat slippage en commissies meetellen, en te weinig oog voor de context (trend vs. range). Check ook of je broker tick-data levert; zonder tick-data mis je de echte Tape.

Stap 1: begrijp de Tape en de basis van Order Flow

De Tape toont elke transactie: tijd, prijs, volume en richting (bijvoorbeeld uptick of downtick).

Je ziet een stroom van prints en herkent of agressieve kopers (market buys) of verkopers (market sells) de boventoon voeren. Dat vertelt je of de markt aan het absorberen is (grote orders verteren zonder prijsbeweging) of aan het accelereren (prijs schiet door). Gebruik de footprint: een 1-minuut candle met links kopers en rechts verkopers per prijsniveau. Kijk naar delta (kopers minus verkopers) en volume.

Een hoge delta bij lage prijsbeweging wijst op absorptie; een lage delta bij sterke prijsstijging wijst op zwakte bovenin. Stel een concrete instelling: kies een tick-size van 0,5 punt voor E-mini S&P (ES) en een volume-per-print van 1–50 contracts.

Je analyseert een sessie van 30 minuten rond de openingsbel (9:30–10:00 EST).

Sla elke print op met timestamp, prijs, volume en richting. Veelgemaakte fouten: alleen naar prijs kijken en volume negeren, of elke print als signaal zien zonder context. Onthoud: één print is geen verhaal; een reeks prints met consistent volume wel.

Stap 2: sluit je broker-API aan en haal Time & Sales

Open een rekening bij een broker met Level 2 en Time & Sales. Voor Interactive Brokers activeer je Market Data Subscription (minimaal €10–€20/maand).

Voor futures via Rithmic krijg je tick-data. Gebruik een paper account voor de eerste verbinding en test met een klein instrument zoals ES of FDAX.

Installeer ib_insync voor IB of ccxt voor crypto/andere brokers. Maak een script dat inlogt, een instrument subscribeert, en live prints ontvangt. Sla de data op in een CSV of een lichte database (SQLite).

from ib_insync import IB, TickType
import time

ib = IB()
ib.connect('127.0.0.1', 7497, clientId=1)

contract = Index('ES', 'CME')  # vervang door je futures-contract
ib.reqMktData(contract, '', False, False)

def on_tick(ticker):
    tick = ticker.tick
    if tick.tickType == TickType.TRADE and tick.size and tick.price:
        print(f"Tick: {tick.time} | {tick.price} | {tick.size}")

ib.pendingTickersEvent += on_tick

# Luister 60 seconden
start = time.time()
while time.time() - start < 60:
    ib.sleep(0.01)

ib.disconnect()

Plan een testvenster van 60 minuten tijdens drukke uren. Code-voorbeeld (ib_insync):

Veelgemaakte fouten: verkeerde contract-specs (maand, exchange), vergeten subscripen op tick-data, of te snel disconnecten. Check je API-sleutel en firewall. Hou rekening met een vertraging van 100–300 ms bij een thuisverbinding; een VPS dichter bij de exchange verlaat dit naar 20–50 ms.

Stap 3: lees de Tape en herken patronen

Je kijkt naar drie dingen: volume per tick, delta per tick, en de tijd tussen prints. Een cluster van prints op één niveau met hoge delta en lage prijsbeweging is absorptie.

Een snelle stroom prints met oplopend volume en weinig tegenstand is acceleratie. Stel een template op: voor ES meet je delta in contracten per minuut. Een delta van +200 bij een range van 2–3 ticks is sterk.

Een delta van +50 bij een range van 10 ticks is zwak.

import pandas as pd

# Kolommen: timestamp, price, size, direction (1=buy, -1=sell)
df = pd.read_csv('tape_es.csv')
df['delta'] = df['size'] * df['direction']
df['minute'] = pd.to_datetime(df['timestamp']).dt.floor('T')
agg = df.groupby(['minute', 'price']).agg({'size':'sum', 'delta':'sum'}).reset_index()

# Detecteer absorptie: hoge delta, lage prijsverandering
agg['absorption'] = (agg['delta'] > 200) & (agg['size'] > 300)
print(agg[agg['absorption']].head())

Gebruik een eenvoudige regel: ga long bij absorptie onder een level en een oplopende delta, met een stop van 2–3 ticks onder het level. Code-voorbeeld (pandas, zonder live feed): Veelgemaakte fouten: patronen forceren in rustige uren, of vergeten dat elke instrument andere tick-sizes en volumes heeft. Test je regels op 5 verschillende sessies en noteer de winst/verlies na slippage en commissie (bij ES reken op €1–€2 per round-turn).

Stap 4: bouw een eenvoudige bot die de Tape gebruikt

Je bot luistert naar live prints, berekent delta per niveau, en plaatst orders als je criterium klopt. Gebruik een API voor orderplaatsing (bij IB via ib_insync, bij NinjaTrader via hun API).

Begin met micro-sizes: 1 contract ES of 0,1 lot op futures, met een daily risk van €50–€100. Stel parameters vast: risk per trade (1R = 2 ticks = €10), target (2R), stop (1R). Je bot moet een state-machine hebben: idle, in_position, exited.

Log elke actie met timestamp, prijs, grootte, en reden. Code-voorbeeld (ib_insync, basisstructuur):

from ib_insync import IB, Future, Order

ib = IB()
ib.connect('127.0.0.1', 7497, clientId=1)

contract = Future('ES', '202509', 'CME')  # vervang door juiste maand
ib.reqMktData(contract, '', False, False)

position = 0
stop_px = 0
target_px = 0

def on_tick(ticker):
    global position, stop_px, target_px
    tick = ticker.tick
    if tick.tickType == 0 and tick.price and tick.size:
        # Simpele logica: als price > vorige en volume stijgt, long
        if tick.price > stop_px and tick.size > 10:
            if position == 0:
                order = Order(action='BUY', totalQuantity=1, orderType='MKT')
                ib.placeOrder(contract, order)
                position = 1
                stop_px = tick.price - 2  # 2 ticks stop
                target_px = tick.price + 4  # 4 ticks target
        elif position == 1 and (tick.price <= stop_px or tick.price >= target_px):
            order = Order(action='SELL', totalQuantity=1, orderType='MKT')
            ib.placeOrder(contract, order)
            position = 0

ib.pendingTickersEvent += on_tick

# Draai 5 minuten
import time
start = time.time()
while time.time() - start < 300:
    ib.sleep(0.01)

ib.disconnect()

Veelgemaakte fouten: market orders zonder slippage-begrenzing, te grote sizes, en geen maximum daily loss. Begrijp goed hoe market making werkt, test je bot eerst op een demo, draai een backtest op tick-data, en pas de parameters handmatig aan.

Stap 5: backtesten met tick-data en risicomanagement

Gebruik tick-data van je broker of een data-provider (bv. TickData, CQG). Voor Python pak je vectorbt of backtrader.

Simuleer elke print, pas slippage en commissie toe (bij ES: 0,25 tick slippage en €1,50 commissie per round-turn). Test op minimaal 20 sessies uit verschillende marktomstandigheden, zoals wanneer je de carry trade strategie geautomatiseerd toepast. Stel een risicoprofiel op: max 1% risico per trade, daily loss limit van 2%, en een max drawdown van 10%. Gebruik een Kelly-correctie of fixed-fractional sizing.

Log alles: winst/verlies, gemiddelde slippage, winst per uur. Bekijk hier de meest succesvolle algoritmische trading strategieën. Code-voorbeeld (vectorbt, eenvoudige backtest):

import vectorbt as vbt
import pandas as pd

# df met kolommen: timestamp, price, volume, delta
df = pd.read_csv('tick_es.csv', parse_dates=['timestamp'])
df.set_index('timestamp', inplace=True)

# Signaal: delta > 200 en price stijgt
df['signal'] = (df['delta'] > 200) & (df['price'].diff() > 0)

# Simuleer entry/exit met slippage en commissie
pf = vbt.Portfolio.from_signals(
    close=df['price'],
    entries=df['signal'],
    exits=~df['signal'],
    freq='1T',
    init_cash=10000,
    fees=0.0005,  # 0.05% per trade
    slippage=0.0002  # 0.02% slippage
)

print(pf.stats())
print(pf.total_return())

Veelgemaakte fouten: curve-fitting op één sessie, negeren van slippage, en te weinig aandacht voor variance.

Verifieer of je bot positief blijft na transaction costs en of de drawdown beheersbaar is.

Verificatie-checklist

  • Broker API actief, Level 2 & Time & Sales beschikbaar, data-abonnement betaald (€10–€20/maand).
  • Python-omgeving werkend, bibliotheken geïnstalleerd (ib_insync/ccxt, pandas, vectorbt/backtrader).
  • Testaccount met €2.000–€5.000 of demo, daily risk limit ingesteld op €50–€100.
  • Tick-data opgeslagen voor minimaal 20 sessies, slippage en commissie meegenomen.
  • Code getest op paper, daarna op micro-sizes (1 contract ES of 0,1 lot), met logging en state-machine.
  • Risicomanagement actief: 1% per trade, daily loss limit 2%, drawdown max 10%.
  • VPS of lage-latency verbinding, eventuele firewall/SSL-checks uitgevoerd.
  • Resultaten geëvalueerd: winst per uur, gemiddelde slippage, drawdown, en robuustheid over verschillende uren.

Als je deze checklist afvinkt, ben je klaar om Order Flow Trading te verfijnen en je bot geleidelijk live te draaien. Blijf experimenteren, hou het simpel, en onthoud: de Tape liegt niet, maar context is koning.

Portret van Alex de Vries, Quantitatief Analist & Algo-Trading Expert
Over Alex de Vries

Alex is een ervaren quantitatief analist en Python-ontwikkelaar die complexe trading concepten vertaalt naar begrijpelijke, praktische handleidingen voor zowel beginners als gevorderden.

Volgende stap
Bekijk alle artikelen over Algoritmische Strategieën
Ga naar overzicht →