For fraud detection, I'd default to PyTorch Geometric (PyG) unless you have a specific reason to choose DGL. Both are mature and capable, but the ecosystem has shifted over the past few years.
Here's how I'd think about it.
| Area | PyTorch Geometric (PyG) | DGL |
|---|
| Community | Larger | Smaller but still active |
| Research support | Usually first | Often follows |
| Documentation | Excellent | Good |
| Production scaling | Good | Very good historically |
| Heterogeneous graphs | Excellent | Excellent |
| Neighbor sampling | Excellent | Excellent |
| Integration with PyTorch | Native feeling | Slight abstraction layer |
Why GNNs work well for fraud
Fraud is rarely about an individual transaction.
It's about relationships:
- customer → device
- customer → email
- device → IP
- merchant → payment
- account → phone number
- customer → shipping address
A graph lets the model learn patterns like
"Five unrelated accounts suddenly sharing one device."
or
"This merchant is only one hop away from hundreds of previously banned entities."
These patterns are difficult for feature engineering alone.
Typical graph:
Customer ---- Device
| |
Address IP
|
Transaction ---- Merchant
Usually you're building a heterogeneous graph.
Production lesson #1: Don't build one gigantic graph
Many first implementations attempt
Entire company graph
100M nodes
2B edges
This becomes painful.
A more common production strategy is:
- partition by time
- partition by geography
- partition by business unit
- maintain rolling windows (30–90 days)
Fraud patterns are usually recent.
Production lesson #2: Dynamic graphs matter more than bigger models
Fraud graphs change every minute.
New:
- accounts
- devices
- cards
- IPs
- merchants
A stale graph is often worse than a simpler model.
The engineering investment usually goes toward:
- streaming graph updates
- incremental feature computation
- online inference
rather than inventing a more sophisticated GNN.
Production lesson #3: Sampling is everything
Nobody trains on the full graph.
Instead:
Target node
↓
2-hop neighbors
↓
Neighbor sampling
↓
Mini-batch
Methods include:
- GraphSAGE sampling
- PinSAGE
- Layer-wise sampling
- ClusterGCN
- GraphSAINT
Without sampling, memory usage explodes.
Production lesson #4: Heterogeneous graphs outperform homogeneous ones
Fraud isn't one node type.
You'll typically have:
Nodes
- Users
- Devices
- Cards
- Merchants
- IPs
- Emails
- Transactions
Edges
- uses
- owns
- paid_with
- shipped_to
- logged_in_from
Treating everything as one node type often loses important semantics.
Production lesson #5: Edge features are often more informative than node features
Example transaction edge:
Customer ---- Transaction ---- Merchant
Edge attributes:
- amount
- timestamp
- currency
- MCC
- payment channel
- risk score
Many production systems use edge-aware message passing rather than ignoring these attributes.
Production lesson #6: Explainability becomes important
Fraud investigators don't trust
"GNN score = 0.982"
They want something like
High risk because:
- shares device with 11 banned accounts
- merchant connected to known fraud ring
- two-hop connection to chargeback cluster
Graph explanations and subgraph extraction become part of the product.
Production lesson #7: Class imbalance is brutal
Typical fraud rates:
0.1%
0.01%
0.001%
You'll likely need:
- weighted loss
- focal loss
- hard negative mining
- balanced sampling
- precision-recall metrics rather than accuracy
Production lesson #8: Combine graph embeddings with tabular features
A common production architecture is:
Raw graph
↓
GNN
↓
Embedding (128–512 dims)
↓
Concatenate
↓
Tabular features
↓
XGBoost / LightGBM / MLP
↓
Fraud probability
The GNN learns relational structure, while the downstream model incorporates transaction-level features and business rules.
Production lesson #9: Latency can dominate model design
Training is offline.
Inference is the challenge.
If you need:
Authorization < 50 ms
running several GNN layers over neighbors at request time may be too slow.
A common approach is:
- compute node embeddings offline
- refresh periodically or incrementally
- serve embeddings from a fast feature store
- run only a lightweight classifier online
This often yields a good balance between latency and accuracy.
PyG vs DGL today
I'd choose PyG if:
- you're starting a new project
- you're doing research
- you expect to use recent GNN architectures
- your team already uses PyTorch
- you want strong community support
I'd consider DGL if:
- you have an existing DGL codebase
- you rely on features or infrastructure already built around it
- you've benchmarked it and found it fits your workloads better
For most new teams, PyG has become the more common choice.
A realistic production stack
One architecture that scales well looks like:
Kafka / Event Stream
│
▼
Graph Builder
│
▼
Feature Store
│
▼
PyG GraphSAGE / HGT
│
▼
Node Embeddings
│
▼
LightGBM / XGBoost
│
▼
Risk Score
│
▼
Rules + Human Review
This hybrid approach combines relational learning from the GNN with the robustness and operational simplicity of gradient-boosted trees, while keeping online inference fast enough for many real-world fraud detection systems.