DECLARATIVE ML · SQL-FIRST MACHINE LEARNING

Describe the result. Let the system plan the work.

Declarative ML brings training, prediction and governance closer to data. It does not remove Python; it makes analytical intent visible, reviewable and repeatable through SQL.

INTENT, NOT PROCEDURE
CREATE MODEL churn_model
FROM customer_features
PREDICT churned;

SELECT customer_id,
       churn_model.*
FROM customer_features
JOIN churn_model;

THE IMPORTANT DISTINCTION

SQL around ML is not always SQL-native ML.

Ask where training executes, where the model artifact lives and whether prediction participates in the query plan. That architectural boundary matters more than SQL-looking syntax.

1 · SQL-native lifecycle

SQL expresses training and prediction; the engine owns model state and execution.

2 · SQL-callable ML

SQL calls an extension or function; computation may run in another runtime.

3 · SQL-first pipeline

SQL owns features and snapshots; Python, Spark or another framework owns training.

REFERENCE ARCHITECTURE

One statement may hide five responsibilities.

Keep every boundary observable: snapshot time, feature contract, training configuration, model version and scoring output.

01 · SOURCEevents · labels
02 · FEATURE SQLpoint-in-time relation
03 · TRAINalgorithm · split
04 · REGISTRYartifact · metric · version
05 · PREDICTbatch · online SQL

OPEN-SOURCE DEEP DIVES

Learn through systems you can inspect and run.

Every example uses one customer_features relation so syntax and execution boundaries can be compared directly. Production work still needs temporal splits, access control, monitoring and rollback.

Apache MADlib

APACHE 2.0 · POSTGRESQL / GREENPLUM

A mature in-database library. Training writes a model table and prediction uses coefficients through SQL functions, showing that a model can be relational state.

A mature in-database library. Training writes a model table and prediction uses coefficients through SQL functions, showing that a model can be relational state.

TRAIN / TRANSFORM / PREDICT
SELECT madlib.logregr_train(
  'customer_features', 'churn_model_madlib',
  'churned',
  'ARRAY[1, recency_days, orders_90d, spend_90d]'
);

SELECT f.customer_id,
       madlib.logregr_predict_prob(
         m.coef,
         ARRAY[1, f.recency_days, f.orders_90d, f.spend_90d]
       ) AS churn_probability
FROM customer_features f, churn_model_madlib m;
What this teaches

Feature-array order must remain identical between training and scoring—an explicit data contract.

Architecture question

Where do rows move, which process computes, and what object represents the model?

PostgresML

OPEN SOURCE · POSTGRES EXTENSION

An end-to-end PostgreSQL extension exposing training, deployment and prediction as pgml functions, organized by projects and snapshots.

An end-to-end PostgreSQL extension exposing training, deployment and prediction as pgml functions, organized by projects and snapshots.

TRAIN / TRANSFORM / PREDICT
SELECT * FROM pgml.train(
  project_name  => 'customer_churn',
  task          => 'classification',
  relation_name => 'customer_features',
  y_column_name => 'churned',
  algorithm     => 'xgboost',
  test_size     => 0.20
);

SELECT customer_id,
       pgml.predict(
         'customer_churn',
         ARRAY[recency_days, orders_90d, spend_90d]
       ) AS prediction
FROM customer_features;
What this teaches

Projects compare algorithms on one snapshot and track deployment, but temporal splitting still requires deliberate design.

Architecture question

Where do rows move, which process computes, and what object represents the model?

MindsDB

OPEN SOURCE · SQL AI LAYER

A SQL-facing layer connecting data sources and AI/ML engines. Models become queryable objects, useful for teaching federation and execution boundaries.

A SQL-facing layer connecting data sources and AI/ML engines. Models become queryable objects, useful for teaching federation and execution boundaries.

TRAIN / TRANSFORM / PREDICT
CREATE MODEL churn_model
FROM analytics_db
  (SELECT recency_days, orders_90d,
          spend_90d, churned
   FROM customer_features)
PREDICT churned;

SELECT d.customer_id,
       m.churned AS predicted_churn,
       m.churned_confidence
FROM analytics_db.customer_features AS d
JOIN churn_model AS m;
What this teaches

The SQL surface is unified, but computation may occur in another handler or service. Trace where data moves.

Architecture question

Where do rows move, which process computes, and what object represents the model?

ClickHouse

APACHE 2.0 · COLUMNAR SQL

Trains linear/logistic models as aggregate-function state, stores that state, and applies it in analytical queries.

Trains linear/logistic models as aggregate-function state, stores that state, and applies it in analytical queries.

TRAIN / TRANSFORM / PREDICT
CREATE TABLE churn_models
(
  name String,
  model AggregateFunction(
    stochasticLogisticRegression(0.01,0.0,10,'Adam'),
    UInt8, Float64, Float64, Float64)
) ENGINE=AggregatingMergeTree ORDER BY name;

INSERT INTO churn_models
SELECT 'churn_v1',
  stochasticLogisticRegressionState(0.01,0.0,10,'Adam')(
    churned, recency_days, orders_90d, spend_90d)
FROM customer_features;

WITH (SELECT model FROM churn_models WHERE name='churn_v1') AS m
SELECT customer_id,
  evalMLMethod(m, recency_days, orders_90d, spend_90d) AS score
FROM customer_features;
What this teaches

Excellent near large analytical tables, but built-in training is narrow; complex ML still uses external frameworks.

Architecture question

Where do rows move, which process computes, and what object represents the model?

DuckDB + dbt

MIT / APACHE 2.0 · SQL-FIRST PIPELINE

Not a full SQL-native trainer. DuckDB excels at local feature computation and reproducible datasets; dbt adds tests, documentation and lineage.

Not a full SQL-native trainer. DuckDB excels at local feature computation and reproducible datasets; dbt adds tests, documentation and lineage.

TRAIN / TRANSFORM / PREDICT
CREATE OR REPLACE TABLE train_snapshot AS
SELECT customer_id,
 date_diff('day',max(order_at),DATE '2026-08-31') AS recency_days,
 count(*) FILTER(WHERE order_at>=DATE '2026-06-01') AS orders_90d,
 sum(amount) FILTER(WHERE order_at>=DATE '2026-06-01') AS spend_90d,
 max(churned)::INTEGER AS churned
FROM read_parquet('orders/*.parquet')
GROUP BY customer_id;

COPY train_snapshot TO 'train_snapshot.parquet'
(FORMAT PARQUET, COMPRESSION ZSTD);
What this teaches

Call this a SQL-first feature pipeline, not in-database ML, because an external framework still owns training.

Architecture question

Where do rows move, which process computes, and what object represents the model?

SIDE-BY-SIDE

Choose by computation boundary, not fashionable syntax.

Free can mean open-source code, a free local runtime, a limited cloud tier or proprietary software bundled with a database. This page separates those meanings.

SystemCategoryTrain SQLPredict SQLLearning value
Apache MADlibIn-database libraryYesYesModel table · feature array
PostgresMLPostgres extensionYesYesProject · snapshot · deployment
MindsDBSQL AI layerYesYesQueryable model · federation
ClickHouseColumnar databaseSelected modelsYesAggregate state as model
DuckDB + dbtSQL-first pipelineNoUDF / integrationSnapshot · test · lineage

COMMERCIAL AWARENESS

Know the vocabulary. Learn transferable ideas.

These proprietary or paid-cloud platforms are a map for reading job descriptions and architecture documents, not the core hands-on lab.

Snowflake ML

ML functions และ Model workflow ใกล้ข้อมูลใน Warehouse

Official overview ↗

Amazon Redshift ML

CREATE MODEL เชื่อมข้อมูล Redshift กับ Managed Training

Official overview ↗

Oracle ML for SQL

In-database algorithms, model objects และ SQL prediction functions

Official overview ↗

SQL Server ML Services

T-SQL เรียก Python/R runtime จึงต่างจาก Pure SQL-native Training

Official overview ↗

Databricks SQL AI

SQL AI functions บน Lakehouse; Platform เป็นบริการเชิงพาณิชย์

Official overview ↗

TEACHING LAB SEQUENCE

Do one problem four ways—then explain the boundary.

The outcome is not memorizing syntax. Students should explain where data moves, how versions are controlled and what invalidates evaluation.

Define prediction time

State observation cutoff, horizon, entity key and label availability before features.

Create a shared feature contract

Fix names, types, units, null policy, feature order and a versioned snapshot.

Train in MADlib

Inspect output tables, coefficients, convergence diagnostics and scoring functions.

Compare project lifecycle

Use PostgresML to compare algorithms on one snapshot and observe deployment state.

Model as relation and state

Compare MindsDB joins with ClickHouse aggregate state and trace physical execution.

Build the SQL-first boundary

Create a DuckDB/dbt snapshot for Python and document where declarative control ends.

Audit evaluation

Check leakage, class imbalance, calibration, subgroup error and reproducibility.

Plan rollback and retraining

Record query hash, data snapshot, parameters, metrics, owner and deployment decision.

Short SQL can still create long technical debt.

  • Do not use random splits for time-dependent outcomes without justification.
  • Persist feature schema, cutoff, query hash, parameters and model version.
  • Measure data movement: SQL may still call an external runtime.
  • Evaluate business cost; false positives and false negatives rarely cost the same.

CONTINUE LEARNING

From one engine to a transferable systems view.

Run the MADlib lab, then compare model state, execution placement and governance across engines.