Feature Poisoning Attacks
Techniques for poisoning feature store data to manipulate model behavior: direct feature value manipulation, time-travel attacks, online/offline store consistency exploitation, and targeted entity-level feature poisoning.
Feature Poisoning Attacks
Feature poisoning manipulates the data that models consume at inference time or during training, without modifying the model itself. This is a powerful attack vector because it bypasses all model-level security controls -- the model is genuine and unmodified, but it receives corrupted inputs. Feature stores amplify this risk by centralizing feature data: a single poisoning point affects every model that consumes the compromised feature.
Direct Feature Value Manipulation
Online Store Poisoning
The online store serves features for real-time inference. Modifying values in the online store immediately affects predictions.
Attack requirements:
- Write access to the online store (Redis, DynamoDB, Bigtable, etc.)
- Knowledge of the feature schema (entity keys, feature names, data types)
- Understanding of how target models use the features
Targeted Entity Poisoning
Rather than poisoning features broadly, an attacker can target specific entities (users, items, transactions) for precise manipulation:
Identify the target entity
Determine which entity's predictions you want to manipulate. In a credit risk model, this might be a specific applicant. In a recommendation system, a specific user.
Map features to model behavior
Understand which features have the most influence on the model's predictions. Feature importance can be estimated through model documentation, API probing, or public research on similar models.
Craft poisoned feature values
Modify the target entity's features in the online store to steer the model's prediction. For a credit risk model, increase income features and decrease debt features to change a denial to an approval.
import redis import struct # Connect to the feature store's online store (Redis) r = redis.Redis(host="feature-store-redis", port=6379) # Target entity: user_id = "target_user_123" # Feature: credit_score (stored as float) entity_key = "user_features:target_user_123" # Read current feature value current_score = struct.unpack('f', r.hget(entity_key, "credit_score"))[0] print(f"Current credit score: {current_score}") # Poison: set credit score to a high value poisoned_score = struct.pack('f', 850.0) r.hset(entity_key, "credit_score", poisoned_score) # The next inference request for this user will use # the manipulated credit scoreVerify the manipulation
Send an inference request for the target entity and confirm the prediction changed as expected. The model's response reflects the poisoned features.
Broad Feature Poisoning
For maximum disruption, poison features broadly to degrade overall model quality:
| Strategy | Technique | Impact |
|---|---|---|
| Value zeroing | Set all instances of a feature to zero | Model loses information from that feature |
| Value randomization | Replace feature values with random values | Model receives noise instead of signal |
| Distribution shift | Shift all values by a constant offset | Model operates outside trained distribution |
| Type coercion | Store string values where numbers are expected | Feature parsing errors or silent corruption |
| Null injection | Delete feature entries | Model falls back to defaults or errors |
Time-Travel Attacks
Point-in-Time Retrieval
Feature stores support point-in-time retrieval to prevent data leakage during training. Training pipelines request features as they existed at the time of each training example. This mechanism, designed for correctness, creates an attack surface.
Exploiting Time-Travel
Identify the training window
Determine when the target model's training data was sampled. Training pipelines typically use a specific date range for feature retrieval.
Backdate poisoned features
Insert or modify feature values with timestamps that fall within the training window. The feature store's point-in-time retrieval returns the poisoned values when training requests features from that time period.
Trigger retraining
Wait for (or trigger) model retraining. The new training run retrieves features from the poisoned time window and trains on corrupted data.
Maintain clean current values
Keep current feature values clean so that manual inspection of the online store shows correct data. The poison exists only in the historical record.
Time-Travel Attack Subtlety
Time-travel attacks are particularly difficult to detect because:
- Current feature values are correct; only historical values are poisoned
- Point-in-time queries return different results depending on the requested timestamp
- Data validation on current data does not inspect historical records
- The poison activates only when a training pipeline queries the poisoned time window
Online/Offline Consistency Exploitation
Intentional Skew Creation
Feature stores maintain online (serving) and offline (training) copies of features. The materialization process keeps them synchronized. Disrupting materialization or manipulating one store independently creates training-serving skew that attackers can exploit.
Skew Attack Patterns
| Pattern | Mechanism | Effect on Model |
|---|---|---|
| Materialization delay | Block or slow the materialization pipeline | Online store serves stale features; model predictions based on outdated data |
| Selective materialization failure | Cause materialization to fail for specific features | Some features stale, others current; model receives inconsistent feature snapshots |
| Offline-only modification | Modify offline store, let materialization propagate | Poison flows from offline to online via normal sync; appears as legitimate data update |
| Online-only modification | Modify online store after materialization | Poison affects serving until next materialization overwrites it; creates a time window for targeted attacks |
| Dual poisoning | Modify both stores consistently | Most complete but requires access to both stores; evades consistency monitoring |
Exploiting Consistency Checks
Some feature stores monitor consistency between online and offline stores. An attacker can exploit these checks:
False positive flooding. Introduce many small, harmless inconsistencies to trigger consistency alerts. When the team investigates and finds false positives, they may relax monitoring thresholds or ignore alerts, creating cover for the real poisoning.
Monitoring blind spots. Identify which features are monitored for consistency and target unmonitored features. Feature stores with thousands of features rarely monitor every one.
Evasion Techniques
Distribution-Preserving Poisoning
Naive feature poisoning shifts the statistical distribution of feature values, making it detectable by distribution monitoring. Sophisticated poisoning preserves aggregate statistics while targeting specific entities.
Mean-preserving poisoning. Increase the feature value for the target entity and decrease it for a non-critical entity by the same amount. The mean remains unchanged.
Variance-preserving poisoning. Modify values within the existing distribution's range so that statistical tests (KS test, chi-square) do not detect a shift.
Gradual poisoning. Modify feature values incrementally over time, staying within natural drift expectations. Each modification is too small to trigger alerts, but the cumulative effect is significant.
import numpy as np
def preserve_distribution_poison(
feature_values: dict,
target_entity: str,
target_value: float,
non_critical_entities: list
):
"""
Modify target entity's feature while preserving
overall distribution statistics.
"""
original_value = feature_values[target_entity]
delta = target_value - original_value
# Distribute the opposite delta across non-critical entities
# to preserve the mean
compensation_per_entity = -delta / len(non_critical_entities)
poisoned = feature_values.copy()
poisoned[target_entity] = target_value
for entity in non_critical_entities:
poisoned[entity] += compensation_per_entity
# Verify statistics preserved
original_mean = np.mean(list(feature_values.values()))
poisoned_mean = np.mean(list(poisoned.values()))
assert abs(original_mean - poisoned_mean) < 1e-6
return poisonedTiming-Based Evasion
Pre-monitoring windows. Execute poisoning before monitoring starts (e.g., before business hours when alerts are reviewed).
Post-materialization windows. Poison online store immediately after materialization. The next materialization will overwrite the poison, so the window is limited but may be sufficient for targeted exploitation.
Maintenance windows. Exploit scheduled maintenance periods when monitoring may be reduced.
Impact Assessment
Severity by Domain
| Domain | Feature Poisoning Impact |
|---|---|
| Financial services | Fraudulent transaction approval, credit score manipulation |
| Healthcare | Incorrect risk assessments, treatment recommendations |
| Advertising | Budget misallocation, competitor ad suppression |
| Content recommendation | Amplification of specific content, suppression of others |
| Autonomous systems | Sensor data manipulation, incorrect environmental assessment |
Blast Radius
The blast radius of feature poisoning depends on how many models consume the poisoned feature:
- A feature used by one model affects one prediction surface
- A shared feature used by ten models affects all ten
- Feature stores are designed for sharing, so shared features are the norm
Detection and Prevention
Detection Signals
| Signal | What It Detects | Limitation |
|---|---|---|
| Distribution monitoring | Broad distribution shifts | Misses targeted entity-level poisoning |
| Entity-level anomaly detection | Individual entity feature changes | High false positive rate for volatile features |
| Consistency monitoring | Online/offline divergence | Misses dual-store poisoning |
| Access logging | Unauthorized write access | Does not detect authorized-but-malicious access |
| Value range checks | Out-of-bounds values | Misses in-range but incorrect values |
Prevention Controls
- Immutable offline store. Use append-only storage for historical features; prevent modification of existing records.
- Write access restriction. Minimize the number of service accounts and users with write access to online and offline stores.
- Feature value signing. Sign feature values at computation time and verify at serving time.
- Real-time anomaly detection. Monitor feature values at serving time for entity-level anomalies.
- Materialization integrity. Verify that materialized values match offline store values.
References
- Goldblum et al., "Dataset Security for Machine Learning" -- Data poisoning survey
- Feast Documentation -- Open-source feature store
- Tecton Security -- Enterprise feature store security
An attacker poisons feature values in the offline store with backdated timestamps that fall within the training window. Current feature values remain clean. A daily distribution monitoring job checks online store features. Will this attack be detected?