LeetLLM
My PlanLearnGlossaryTracksPracticeBlog
LeetLLM

Your go-to resource for mastering AI & LLM systems.

Product

  • Learn
  • Glossary
  • Tracks
  • Practice
  • Blog
  • RSS

Legal

  • Terms of Service
  • Privacy Policy

© 2026 LeetLLM. All rights reserved.

All Topics
Your Progress
0%

0 of 177 articles completed

🛠️Computing Foundations0/9
Git, Shell, Linux for AIDocker for Reproducible AIPython for AI EngineeringNumPy and Tensor ShapesCUDA for ML TrainingMPS & Metal for ML on MacData Structures for AISQL and Data ModelingAlgorithms for ML Engineers
📊Math & Statistics0/8
Gradients and BackpropVectors, Matrices & TensorsLinear Algebra for MLAdam, Momentum, SchedulersProbability for Machine LearningStatistics and UncertaintyDistributions and SamplingHypothesis Tests, Intervals, and pass@k
📚Preparation & Prerequisites0/13
Neural Networks from ScratchCNNs from ScratchTraining & BackpropagationSoftmax, Cross-Entropy & OptimizationRNNs, LSTMs, GRUs, and Sequence ModelingAutoencoders and VAEsThe Transformer Architecture End-to-EndLanguage Modeling & Next TokensFrom GPT to Modern LLMsPrompt Engineering FundamentalsCalling LLM APIs in ProductionFirst AI App End-to-EndThe LLM Lifecycle
🧮ML Algorithms & Evaluation0/11
Linear Regression from ScratchLogistic Regression and MetricsDecision Trees, Forests, and BoostingReinforcement Learning BasicsValidation and LeakageClustering and PCACore Retrieval AlgorithmsDecoding AlgorithmsExperiment Design and A/B TestingPyTorch Training LoopsDataset Pipelines and Data Quality
📦Production ML Systems0/6
Feature Engineering for Production MLBatch and Streaming Feature PipelinesGradient Boosted Trees in ProductionRanking and Recommendation SystemsForecasting and Anomaly DetectionMonitoring Predictive Models
🧪Core LLM Foundations0/8
The Bitter Lesson & ComputeBPE, WordPiece, and SentencePieceStatic to Contextual EmbeddingsPerplexity & Model EvaluationFile Ingestion for AIChunking StrategiesLLM Benchmarks & LimitationsInstruction Tuning & Chat Templates
🧰Applied LLM Engineering0/24
Dimensionality Reduction for EmbeddingsCoT, ToT & Self-Consistency PromptingFunction Calling & Tool UseMCP & Tool Protocol StandardsContext EngineeringPrompt Injection DefenseResponsible AI GovernanceData Labeling and Human FeedbackEvaluating AI AgentsProduction RAG PipelinesHybrid Search: Dense + SparseReranking and Cross-Encoders for RAGRAG Evaluation for Reliable AnswersLLM-as-a-Judge EvaluationBias & Fairness in LLMsHallucination Detection & MitigationLLM Observability & MonitoringExperiment Tracking with MLflow and W&BPrompt Optimization with DSPyModel Versioning & DeploymentSemantic Caching & Cost OptimizationLLM Cost Engineering & Token EconomicsModel Gateways, Routing, and FallbacksDesign an Automated Support Agent
🎓Portfolio Capstones0/9
Capstone: Delivery ETA PredictionCapstone: Product RankingCapstone: Demand ForecastingCapstone: Image Damage ClassifierCapstone: Production ML PipelineCapstone: Document QACapstone: Eval DashboardCapstone: Fine-Tuned ClassifierCapstone: Reproducible ML Study
🧠Transformer Deep Dives0/8
Sentence Embeddings & Contrastive LossEmbedding Similarity & QuantizationScaled Dot-Product AttentionVision Transformers and Image EncodersPositional Encoding: RoPE & ALiBiLayer Normalization: Pre-LN vs Post-LNMechanistic InterpretabilityDecoding Strategies: Greedy to Nucleus
🧬Advanced Training & Adaptation0/16
Scaling Laws & Compute-Optimal TrainingPre-training Data at ScaleBuild GPT from Scratch LabJAX for PyTorch ResearchersContinued Pretraining for Domain ShiftSynthetic Data PipelinesSupervised Fine-Tuning PipelineMixed Precision TrainingDistributed Training: FSDP & ZeROLoRA & Parameter-Efficient TuningReward Modeling from Preference DataRLHF & DPO AlignmentConstitutional AI & Red TeamingRLVR & Verifiable RewardsKnowledge Distillation for LLMsModel Merging and Weight Interpolation
🤖Advanced Agents & Retrieval0/16
Vector DB Internals: HNSW & IVFAdvanced RAG: HyDE & Self-RAGGraphRAG & Knowledge GraphsRAG Security & Access ControlStructured Output GenerationReAct & Plan-and-ExecuteGuardrails & Safety FiltersCode Generation & SandboxingComputer-Use / GUI / Browser AgentsHuman-in-the-Loop Agent ArchitectureAI Coding Workflow with AgentsAgent Memory & PersistenceAgent Failure & RecoveryRecursive Language Models (RLM)Multi-Agent OrchestrationCapstone: Production Agent
⚡Inference & Production Scale0/19
Inference: TTFT, TPS & KV CacheMulti-Query & Grouped-Query AttentionKV Cache & PagedAttentionPrefix Caching and Prompt CachingFlashAttention & Memory EfficiencyContinuous Batching & SchedulingScaling LLM InferenceModel Parallelism for LLM InferenceModel Quantization: GPTQ, AWQ & GGUFLocal LLM DeploymentSLM Specialization & Edge DeploymentSpeculative DecodingLong Context Window ManagementMixture of Experts ArchitectureMamba & State Space ModelsReasoning & Test-Time ComputeAdvanced MLOps & DevOps for AIGPU Serving & AutoscalingA/B Testing for LLMs
🏗️System Design Capstones0/9
Content Moderation SystemCode Completion SystemMulti-Tenant LLM PlatformLLM-Powered Search EngineVision-Language Models & CLIPMultimodal LLM ArchitectureDiffusion Models: Images & TextReal-Time Voice AI AgentReasoning Agent System Design
🎤AI Lab Interviewing0/4
AI Lab Coding Interview: Python SystemsAI Lab System Design InterviewAI Lab Behavioral InterviewAI Lab Technical Presentation
🔬Project Deep Dives0/17
Deep Dive - vLLMDeep Dive - SkyRLDeep Dive - FlashAttentionDeep Dive - FlashInferDeep Dive - DeepGEMMDeep Dive - NCCLDeep Dive - MegatronDeep Dive - DeepSpeedDeep Dive - RayDeep Dive - MLflowDeep Dive - PyTorchDeep Dive - TransformersDeep Dive - SGLangDeep Dive - slimeDeep Dive - DeepEPDeep Dive - TinkerDeep Dive - Light-PEFT
Back to Topics
LearnProduction ML SystemsFeature Engineering for Production ML
⚙️MediumMLOps & Deployment

Feature Engineering for Production ML

Turn training-job events into stable prediction inputs while preventing leakage and training-serving mismatch.

9 min read
Learning path
Step 42 of 177 in the full curriculum
Dataset Pipelines and Data QualityBatch and Streaming Feature Pipelines

Personalize this lesson

Adapt explanations and teaching visuals to your background and preferred voice.

Versioned datasets with clean splits still aren't model-ready by themselves. A prediction model can't consume a raw event log directly. To predict whether a training job will miss its SLA, it needs a fixed row of measurements available at the moment the promise is made.

Those measurements are features. A feature such as hours_since_last_heartbeat compresses many scheduler events into one input value. Inventing columns is easy compared with making sure each value means the same thing during training and while serving live requests.

Job J-204 event timeline cut at the 09:00 prediction timestamp: heartbeats at 01:00 and 08:30 are visible, the latest at 08:30 yields a six-slot feature vector with 0.5-hour heartbeat age, while a 12:00 heartbeat, finished timestamp, and post-SLA escalation remain in the future-only region outside model inputs.
At 09:00, the contract emits the exact six-field row [a100-pool, 42.0, 0.5, 18.0, 0, 0]. The noon heartbeat, finished timestamp, and post-SLA escalation remain beyond the cutoff and can't enter the model input.

Start With a Prediction Timestamp

Suppose the product asks at 2026-05-01 09:00: will job J-204 miss its SLA? Job heartbeats after that timestamp aren't available to the prediction service and can't appear in its training row.

Candidate fieldKnown at prediction time?Use as feature?
runner poolyesyes, categorical
queued minutesyesyes, numeric
minutes since most recent heartbeatyesyes, numeric
cluster queue backlogyesyes, numeric
finished timestampnono, it defines the eventual label
post-SLA escalationnono, it leaks the outcome

The label may be computed later as missed_sla = 1. A feature must be computed from history ending at the prediction timestamp. If a training row contains the post-SLA escalation, feature leakage rewards the model for reading the answer.

Sculley et al. describe production ML systems as networks of data and configuration dependencies where hidden feedback and undeclared consumers create technical debt.[1]Reference 1Hidden Technical Debt in Machine Learning Systems.https://research.google/pubs/hidden-technical-debt-in-machine-learning-systems/ Feature definitions are one of those dependencies: when their time boundary is unclear, the model's impressive score doesn't survive deployment.

Diagram showing Job events through prediction time, Feature contract types + missing policy, Training snapshot label joins later, and Online request same computation.
Job events through prediction time, Feature contract types + missing policy, Training snapshot label joins later, and Online request same computation.

Why must a feature definition begin with a prediction timestamp?

Answer

The timestamp defines which source facts were knowable when the prediction was made. Without it, a training row can silently include future outcomes or later updates that live serving couldn't access.

Define one row before training

Build a small contract for job-SLA prediction:

FeatureTypeMissing ruleWhy it can help
queued_minutesnumericreject if absentlonger queue waits expose more scheduling risk
hours_since_last_heartbeatnumericcap at 180stale heartbeats signal job risk
queue_backlognumericuse measured queue onlyqueue pressure affects scheduling and preemption
runner_poolcategoricalreject if absent; map unseen to otherrunner pools have different networks
priority_jobbooleandefault false only when source guarantees itpriority changes SLA and retry policy

A missing value is a product decision. Filling missing queue_backlog with zero says "unknown congestion means no congestion," which is rarely defensible. Store an additional queue_backlog_missing indicator or stop scoring until the feed recovers.

Categorical values need a policy too. If a new runner pool appears after training, the online encoder can't invent a new model column. An other bucket provides stable behavior while a new model candidate is evaluated. Missing runner pool data is different: it may signal a broken source feed, so don't silently fold it into other.

Prove the Time Boundary

A feature job should make the prediction timestamp explicit, then discard later events before aggregation. This first lab keeps only heartbeats whose event timestamps aren't later than the prediction. It deliberately assumes heartbeats arrive immediately. The next lesson adds a separate ingestion timestamp so a replay can't use an earlier heartbeat that arrived late.

keep-visible-events.py
1from datetime import datetime 2 3prediction_time = datetime.fromisoformat("2026-05-01T09:00:00") 4heartbeats = [ 5 datetime.fromisoformat("2026-05-01T01:00:00"), 6 datetime.fromisoformat("2026-05-01T08:30:00"), 7 datetime.fromisoformat("2026-05-01T12:00:00"), 8] 9 10visible_heartbeats = [heartbeat for heartbeat in heartbeats if heartbeat <= prediction_time] 11print("visible heartbeats:", len(visible_heartbeats)) 12print("latest visible:", max(visible_heartbeats).isoformat())
Output
1visible heartbeats: 2 2latest visible: 2026-05-01T08:30:00

Filtering source history is necessary but not sufficient. The row contract must also enforce output keys, types, missing-value meaning, fitted category mappings, and numeric bounds. In this example:

  • queue_backlog=0 means a measured empty queue; missing backlog emits queue_backlog_missing=1.
  • an unseen but valid runner pool maps to fitted category other; an absent pool is rejected.
  • heartbeat age is capped at the fitted 180-hour limit, while a future heartbeat is rejected.
  • an output allowlist blocks future-only keys such as finished_at.

The integrated row builder below exercises these rules together. Source filtering proves values were available at the cutoff; the allowlist proves only declared keys leave the transform. Neither check replaces offline/online parity.

Build one trustworthy row

Now assemble those policies. The source record may contain post-job-SLA fields because labels need them later. The returned model row may contain only allowlisted feature keys.

build-feature-row.py
1from datetime import datetime 2from math import isfinite 3 4allowed_feature_keys = { 5 "runner_pool", 6 "queued_minutes", 7 "hours_since_last_heartbeat", 8 "queue_backlog", 9 "queue_backlog_missing", 10 "priority_job", 11} 12known_runner_pools = {"a100-pool", "h100-pool"} 13future_only_keys = {"finished_at", "post_sla_escalation"} 14 15def make_features(row, prediction_time): 16 required_keys = {"queued_minutes", "last_heartbeat_at", "priority_job"} 17 missing_keys = sorted(required_keys - row.keys()) 18 if missing_keys: 19 raise ValueError(f"missing required fields: {missing_keys}") 20 21 queued_minutes = float(row["queued_minutes"]) 22 if not isfinite(queued_minutes) or queued_minutes <= 0: 23 raise ValueError("queued_minutes must be finite and positive") 24 25 runner_pool = row.get("runner_pool") 26 if not isinstance(runner_pool, str) or not runner_pool.strip(): 27 raise ValueError("runner_pool is missing") 28 runner_pool = runner_pool.strip().casefold() 29 30 if not isinstance(row["priority_job"], bool): 31 raise ValueError("priority_job must be boolean") 32 33 last_heartbeat = datetime.fromisoformat(row["last_heartbeat_at"]) 34 if last_heartbeat > prediction_time: 35 raise ValueError("last_heartbeat_at is after prediction_time") 36 heartbeat_age = min((prediction_time - last_heartbeat).total_seconds() / 3600, 180.0) 37 38 queue_backlog = row.get("queue_backlog") 39 if queue_backlog is not None: 40 queue_backlog = float(queue_backlog) 41 if not isfinite(queue_backlog) or queue_backlog < 0: 42 raise ValueError("queue_backlog must be finite and nonnegative") 43 features = { 44 "runner_pool": runner_pool if runner_pool in known_runner_pools else "other", 45 "queued_minutes": queued_minutes, 46 "hours_since_last_heartbeat": heartbeat_age, 47 "queue_backlog": 0.0 if queue_backlog is None else queue_backlog, 48 "queue_backlog_missing": int(queue_backlog is None), 49 "priority_job": int(row["priority_job"]), 50 } 51 52 blocked_fields = sorted(features.keys() - allowed_feature_keys) 53 if blocked_fields: 54 raise ValueError(f"unexpected feature fields: {blocked_fields}") 55 return features 56 57prediction_time = datetime.fromisoformat("2026-05-01T09:00:00") 58job = { 59 "job_id": "J-204", 60 "runner_pool": "a100-pool", 61 "queued_minutes": 42, 62 "queue_backlog": 18, 63 "priority_job": False, 64 "last_heartbeat_at": "2026-05-01T08:30:00", 65 "finished_at": "2026-05-03T14:00:00", 66 "post_sla_escalation": True, 67} 68 69features = make_features(job, prediction_time) 70print(features) 71print("future fields leaked:", sorted(features.keys() & future_only_keys))
Output
1{'runner_pool': 'a100-pool', 'queued_minutes': 42.0, 'hours_since_last_heartbeat': 0.5, 'queue_backlog': 18.0, 'queue_backlog_missing': 0, 'priority_job': 0} 2future fields leaked: []

Probe the contract's highest-risk branches directly:

preserve-missing-backlog.py
1missing_backlog = make_features({**job, "queue_backlog": None}, prediction_time) 2assert missing_backlog["queue_backlog"] == 0.0 3assert missing_backlog["queue_backlog_missing"] == 1
map-unseen-runner-pool.py
1unseen_pool = make_features({**job, "runner_pool": "l4-pool"}, prediction_time) 2assert unseen_pool["runner_pool"] == "other"
reject-missing-runner-pool.py
1try: 2 make_features({**job, "runner_pool": None}, prediction_time) 3except ValueError as error: 4 assert str(error) == "runner_pool is missing" 5else: 6 raise AssertionError("missing runner_pool was accepted")
reject-future-heartbeat.py
1try: 2 make_features({**job, "last_heartbeat_at": "2026-05-01T12:00:00"}, prediction_time) 3except ValueError as error: 4 assert str(error) == "last_heartbeat_at is after prediction_time" 5else: 6 raise AssertionError("future heartbeat was accepted")
reject-invalid-queue-time.py
1try: 2 make_features({**job, "queued_minutes": 0}, prediction_time) 3except ValueError as error: 4 assert str(error) == "queued_minutes must be finite and positive" 5else: 6 raise AssertionError("zero queued_minutes was accepted")

A model still needs a fixed vector order and fitted categorical mapping. Version both beside the model artifact.

vectorize-features.py
1runner_pool_code = {"a100-pool": 0, "h100-pool": 1, "other": 2} 2feature_order = ( 3 "runner_pool_code", 4 "queued_minutes", 5 "hours_since_last_heartbeat", 6 "queue_backlog", 7 "queue_backlog_missing", 8 "priority_job", 9) 10features = { 11 "runner_pool": "other", 12 "queued_minutes": 42.0, 13 "hours_since_last_heartbeat": 8.0, 14 "queue_backlog": 0.0, 15 "queue_backlog_missing": 1, 16 "priority_job": 0, 17} 18 19vector = [ 20 runner_pool_code[features["runner_pool"]], 21 features["queued_minutes"], 22 features["hours_since_last_heartbeat"], 23 features["queue_backlog"], 24 features["queue_backlog_missing"], 25 features["priority_job"], 26] 27print("order:", feature_order) 28print("vector:", vector)
Output
1order: ('runner_pool_code', 'queued_minutes', 'hours_since_last_heartbeat', 'queue_backlog', 'queue_backlog_missing', 'priority_job') 2vector: [2, 42.0, 8.0, 0.0, 1, 0]

Why keep both queue_backlog=0 and queue_backlog_missing=1 when the source value is absent?

Answer

Measured zero and unknown congestion aren't the same fact. The indicator preserves that distinction instead of teaching the model that a broken feed means an empty queue.

Test parity before release

An offline notebook might compute queue backlog by scanning a completed daily table. The service might read an hourly cache. Even when both columns are named queue_backlog, differences in freshness or aggregation can change predictions. This failure is training-serving skew.

Feast documents point-in-time joins that reproduce feature state at each historical entity timestamp, scanning backward only within the configured TTL.[2]Reference 2Point-in-time Joinshttps://docs.feast.dev/getting-started/concepts/point-in-time-joins It also documents online stores for low-latency serving, where only the latest feature values for each entity key are stored.[3]Reference 3Online Storehttps://docs.feast.dev/getting-started/components/online-store A model release must identify the feature definition and snapshot that produced its score.

Sample offline and online paths on the same entities before promoting a model. Compare both a matching row and a stale-cache failure.

check-parity.py
1def mismatches(offline, online): 2 keys = offline.keys() | online.keys() 3 return {key: (offline.get(key), online.get(key)) for key in keys if offline.get(key) != online.get(key)} 4 5offline = {"runner_pool": "a100-pool", "queue_backlog": 18.0, "priority_job": 0} 6online_rows = { 7 "matching": {"runner_pool": "a100-pool", "queue_backlog": 18.0, "priority_job": 0}, 8 "stale cache": {"runner_pool": "a100-pool", "queue_backlog": 0.0, "priority_job": 0}, 9} 10 11for name, online in online_rows.items(): 12 differences = mismatches(offline, online) 13 print(name, "mismatches:", differences, "release allowed:", not differences)
Output
1matching mismatches: {} release allowed: True 2stale cache mismatches: {'queue_backlog': (18.0, 0.0)} release allowed: False

Monitor the contract before monitoring accuracy:

Production checkFailure it catchesAction
null rate by featureupstream feed disappearedfail closed or fallback
unseen-category raterunner-pool catalog changedcollect labels and retrain
freshness lagonline values are stalepause promotions
offline/online parity sampletransformations disagreerepair feature path

Parity strategy also depends on where the feature is computed:

Feature kindProduction pathParity strategy
request-timecomputed on the serving path from the live request and request-local contextlog raw request fields and recompute the training transform offline
precomputed storewritten to an online feature store ahead of the requestdual-write or dual-read the store path, plus point-in-time replay for training rows

Request-path fields need log-and-recompute. Precomputed store fields need dual-write (or dual-read) plus PIT replay. Both still require a shared transformation contract; only the evidence path differs.

Freshness failures need an explicit product policy. This policy tries normal scoring, fallback, then abstention. The 15 / 45 minute cutoffs here are a local product policy, not a universal constant; other lessons may choose different numbers for the same idea. Thresholds depend on product tolerance and must be versioned with the serving path.

apply-freshness-policy.py
1def scoring_policy(freshness_lag_minutes): 2 if freshness_lag_minutes <= 15: 3 return "normal scoring" 4 if freshness_lag_minutes <= 45: 5 return "fallback model" 6 return "abstain and alert" 7 8for lag in [8, 30, 90]: 9 print(f"{lag} minutes -> {scoring_policy(lag)}")
Output
18 minutes -> normal scoring 230 minutes -> fallback model 390 minutes -> abstain and alert

Offline and online transforms return different queue_backlog values for the same entity and cutoff. What should the release check do?

Answer

Block release and inspect freshness, aggregation, and feature-definition versions. Matching column names don't establish training-serving parity.

Complete the lesson

Mastery Check

Answer every question, then check your score. Score 75% or higher to mark this lesson complete.

1.A job-SLA feature row is built from a source record that also contains finished_at for later label construction. The output allowlist contains only runner_pool, queued_minutes, hours_since_last_heartbeat, queue_backlog, queue_backlog_missing, and priority_job. Which statement describes the correct gate?

Correct answer: Block unexpected output keys like finished_at, but still use timestamp filtering to prove allowed values are cutoff-safe.

A job-SLA outcome can be joined later to create the label, but it must not enter the model input for an earlier prediction. An output allowlist is useful because it fails when an unexpected key actually appears, but it only checks keys; timestamp filtering must still confirm allowed fields were computed from visible history.

2.During a scheduler telemetry feed outage, queue_backlog is unavailable. A feature job writes queue_backlog = 0.0 and does not emit queue_backlog_missing. What is the main contract problem?

Correct answer: The model cannot distinguish an unavailable measurement from a measured empty queue, so an outage can look like no congestion.

A measured queue backlog of zero means the queue was observed to be empty. A missing queue backlog means the measurement failed or was unavailable. The contract preserves that difference with queue_backlog_missing or abstains instead of silently treating unknown congestion as no congestion.

3.Serving will load trained weights for job-SLA prediction. Engineers also want to rebuild the runner-pool mapping from today's runner-pool catalog and change the heartbeat-age cap from 180 to 360 hours while keeping feature names unchanged. What package avoids changing the input meaning?

Correct answer: The fitted feature contract, runner_pool mapping with other, heartbeat-age cap, fixed vector order, training snapshot, and parity evidence.

The trained weights interpret each vector position according to the transformations used during training. Regenerating the runner_pool mapping or changing the heartbeat-age cap can change the meaning of the same feature names, so fitted contracts and parity evidence must travel with the model.

4.At 2026-05-01T09:00:00, heartbeats are at 2026-05-01T01:00:00, 2026-05-01T08:30:00, and 2026-05-01T12:00:00. Which feature-construction result respects the prediction timestamp?

Correct answer: Two heartbeats are visible, the latest visible heartbeat is 08:30, and the 12:00 heartbeat is excluded.

Feature history must end at the prediction timestamp. Events at or before 09:00 are visible, while the 12:00 heartbeat is future information for that prediction and must be excluded rather than converted into a negative age.

5.An encoder was fitted with known_runner_pools = {'a100-pool', 'h100-pool'} and a reserved other bucket. How should it handle runner_pool='l4-pool' and runner_pool=None?

Correct answer: l4-pool maps to other; None is rejected as missing runner_pool data.

A well-formed unseen category can use the reserved other representation until retraining evaluates it. A missing runner_pool is different: it may indicate a broken source feed, so silently folding it into other would hide a data-quality failure.

6.For the same entity and cutoff, the offline path produces {'runner_pool': 'a100-pool', 'queue_backlog': 18.0, 'priority_job': 0} and the online path produces {'runner_pool': 'a100-pool', 'queue_backlog': 0.0, 'priority_job': 0}. What should the release gate do?

Correct answer: Block release and investigate training-serving skew in queue_backlog.

A parity sample compares the actual values produced by offline and online feature paths for the same entity and cutoff. The different queue_backlog values show that the paths disagree, so the model should not be promoted until the feature path is repaired.

7.An online feature cache has freshness lag of 90 minutes. The serving path's versioned policy is: up to 15 minutes use normal scoring, up to 45 minutes use a fallback model, and above 45 minutes abstain and alert. What should happen?

Correct answer: Abstain and alert because the lag is outside the fallback window.

Freshness is part of the production feature contract. Under the stated policy, 90 minutes is beyond both the normal-scoring and fallback ranges, so the service should stop using the stale path and alert rather than silently score with stale values.

8.Assume the required timestamps and runner_pool are valid and present. Which input combination satisfies the row contract?

Correct answer: queued_minutes=42, priority_job=False, and measured queue_backlog=0.

The contract requires a finite positive queued minutes, a true Boolean for priority_job, and a finite nonnegative queue backlog. A measured queue backlog of zero is valid. Zero queued minutes, a string that merely spells false, and a negative queue backlog must each cause rejection.

8 questions remaining.

Next Step
Continue to Batch and Streaming Feature Pipelines

You can now define one trustworthy prediction row. Next you'll construct those rows from event history without joining future information or serving stale features.

PreviousDataset Pipelines and Data Quality
Share this article
XFacebookLinkedInBlueskyRedditHacker NewsEmail
References

Hidden Technical Debt in Machine Learning Systems.

Sculley et al. · 2015

https://research.google/pubs/hidden-technical-debt-in-machine-learning-systems/

Point-in-time Joins

Feast Contributors · 2026 · Official documentation

https://docs.feast.dev/getting-started/concepts/point-in-time-joins

Online Store

Feast Contributors · 2026 · Official documentation

https://docs.feast.dev/getting-started/components/online-store

Discussion

Questions and insights from fellow learners.

Discussion loads when you reach this section.