Skip to content

Commit a8eb55b

Browse files
authored
deploy specific models (#1265)
1 parent 4c737b0 commit a8eb55b

File tree

11 files changed

+102
-20
lines changed

11 files changed

+102
-20
lines changed

.github/workflows/ubuntu-packages-and-docker-image.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ on:
44
workflow_dispatch:
55
inputs:
66
packageVersion:
7-
default: "2.8.1"
7+
default: "2.8.2"
88
jobs:
99
#
1010
# PostgresML extension.

.github/workflows/ubuntu-postgresml-python-package.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ on:
44
workflow_dispatch:
55
inputs:
66
packageVersion:
7-
default: "2.8.1"
7+
default: "2.8.2"
88

99
jobs:
1010
postgresml-python:

pgml-cms/docs/SUMMARY.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@
3636
* [pgml.tune()](introduction/apis/sql-extensions/pgml.tune.md)
3737
* [Client SDKs](introduction/apis/client-sdks/README.md)
3838
* [Overview](introduction/apis/client-sdks/getting-started.md)
39-
* [Collections](../../pgml-docs/docs/guides/sdks/collections.md)
39+
* [Collections](introduction/apis/client-sdks/collections.md)
4040
* [Pipelines](introduction/apis/client-sdks/pipelines.md)
4141
* [Search](introduction/apis/client-sdks/search.md)
4242
* [Tutorials](introduction/apis/client-sdks/tutorials/README.md)
File renamed without changes.

pgml-cms/docs/introduction/apis/sql-extensions/pgml.deploy.md

Lines changed: 28 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,11 @@ pgml.deploy(
2626

2727
There are 3 different deployment strategies available:
2828

29-
| Strategy | Description |
30-
| ------------- | --------------------------------------------------------------------------------------------------------------------- |
31-
| `most_recent` | The most recently trained model for this project is immediately deployed, regardless of metrics. |
32-
| `best_score` | The model that achieved the best key metric score is immediately deployed. |
33-
| `rollback` | The model that was last deployed for this project is immediately redeployed, overriding the currently deployed model. |
29+
| Strategy | Description |
30+
| ------------- |--------------------------------------------------------------------------------------------------|
31+
| `most_recent` | The most recently trained model for this project is immediately deployed, regardless of metrics. |
32+
| `best_score` | The model that achieved the best key metric score is immediately deployed. |
33+
| `rollback` | The model that was deployed before to the current one is deployed. |
3434

3535
The default deployment behavior allows any algorithm to qualify. It's automatically used during training, but can be manually executed as well:
3636

@@ -40,11 +40,12 @@ The default deployment behavior allows any algorithm to qualify. It's automatica
4040

4141
#### SQL
4242

43-
<pre class="language-sql"><code class="lang-sql"><strong>SELECT * FROM pgml.deploy(
44-
</strong> 'Handwritten Digit Image Classifier',
43+
```sql
44+
SELECT * FROM pgml.deploy(
45+
'Handwritten Digit Image Classifier',
4546
strategy => 'best_score'
4647
);
47-
</code></pre>
48+
```
4849

4950
#### Output
5051

@@ -121,3 +122,22 @@ SELECT * FROM pgml.deploy(
121122
Handwritten Digit Image Classifier | rollback | xgboost
122123
(1 row)
123124
```
125+
126+
### Specific Model IDs
127+
128+
In the case you need to deploy an exact model that is not the `most_recent` or `best_score`, you may deploy a model by id. Model id's can be found in the `pgml.models` table.
129+
130+
#### SQL
131+
132+
```sql
133+
SELECT * FROM pgml.deploy(12);
134+
```
135+
136+
#### Output
137+
138+
```sql
139+
project | strategy | algorithm
140+
------------------------------------+----------+-----------
141+
Handwritten Digit Image Classifier | specific | xgboost
142+
(1 row)
143+
```

pgml-extension/Cargo.lock

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pgml-extension/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "pgml"
3-
version = "2.8.1"
3+
version = "2.8.2"
44
edition = "2021"
55

66
[lib]
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
-- src/api.rs:317
2+
-- pgml::api::deploy
3+
DROP FUNCTION IF EXISTS pgml."deploy"(BIGINT);
4+
CREATE FUNCTION pgml."deploy"(
5+
"model_id" BIGINT /* i64 */
6+
) RETURNS TABLE (
7+
"project" TEXT, /* alloc::string::String */
8+
"strategy" TEXT, /* alloc::string::String */
9+
"algorithm" TEXT /* alloc::string::String */
10+
)
11+
LANGUAGE c /* Rust */
12+
AS 'MODULE_PATHNAME', 'deploy_model_wrapper';
13+
14+
DROP FUNCTION IF EXISTS pgml."deploy"(text, pgml.Strategy, pgml.Algorithm);
15+
CREATE FUNCTION pgml."deploy"(
16+
"project_name" TEXT, /* &str */
17+
"strategy" pgml.Strategy, /* pgml::orm::strategy::Strategy */
18+
"algorithm" pgml.Algorithm DEFAULT NULL /* core::option::Option<pgml::orm::algorithm::Algorithm> */
19+
) RETURNS TABLE (
20+
"project" TEXT, /* alloc::string::String */
21+
"strategy" TEXT, /* alloc::string::String */
22+
"algorithm" TEXT /* alloc::string::String */
23+
)
24+
LANGUAGE c /* Rust */
25+
AS 'MODULE_PATHNAME', 'deploy_strategy_wrapper';
26+
27+
ALTER TYPE pgml.strategy ADD VALUE 'specific';

pgml-extension/src/api.rs

Lines changed: 37 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -287,7 +287,7 @@ fn train_joint(
287287
};
288288

289289
if deploy {
290-
project.deploy(model.id);
290+
project.deploy(model.id, Strategy::new_score);
291291
} else {
292292
warning!("Not deploying newly trained model.");
293293
}
@@ -300,8 +300,40 @@ fn train_joint(
300300
)])
301301
}
302302

303-
#[pg_extern]
304-
fn deploy(
303+
#[pg_extern(name = "deploy")]
304+
fn deploy_model(
305+
model_id: i64
306+
) -> TableIterator<
307+
'static,
308+
(
309+
name!(project, String),
310+
name!(strategy, String),
311+
name!(algorithm, String),
312+
),
313+
> {
314+
let model = unwrap_or_error!(Model::find_cached(model_id));
315+
316+
let project_id = Spi::get_one_with_args::<i64>(
317+
"SELECT projects.id from pgml.projects JOIN pgml.models ON models.project_id = projects.id WHERE models.id = $1",
318+
vec![(PgBuiltInOids::INT8OID.oid(), model_id.into_datum())],
319+
)
320+
.unwrap();
321+
322+
let project_id =
323+
project_id.unwrap_or_else(|| error!("Project does not exist."));
324+
325+
let project = Project::find(project_id).unwrap();
326+
project.deploy(model_id, Strategy::specific);
327+
328+
TableIterator::new(vec![(
329+
project.name,
330+
Strategy::specific.to_string(),
331+
model.algorithm.to_string(),
332+
)])
333+
}
334+
335+
#[pg_extern(name = "deploy")]
336+
fn deploy_strategy(
305337
project_name: &str,
306338
strategy: Strategy,
307339
algorithm: default!(Option<Algorithm>, "NULL"),
@@ -378,7 +410,7 @@ fn deploy(
378410
let algorithm = algorithm.expect("No qualified models exist for this deployment.");
379411

380412
let project = Project::find(project_id).unwrap();
381-
project.deploy(model_id);
413+
project.deploy(model_id, strategy);
382414

383415
TableIterator::new(vec![(
384416
project_name.to_string(),
@@ -922,7 +954,7 @@ fn tune(
922954
};
923955

924956
if deploy {
925-
project.deploy(model.id);
957+
project.deploy(model.id, Strategy::new_score);
926958
}
927959

928960
TableIterator::new(vec![(

pgml-extension/src/orm/project.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -89,14 +89,14 @@ impl Project {
8989
.unwrap()
9090
}
9191

92-
pub fn deploy(&self, model_id: i64) {
92+
pub fn deploy(&self, model_id: i64, strategy: Strategy) {
9393
info!("Deploying model id: {:?}", model_id);
9494
Spi::get_one_with_args::<i64>(
9595
"INSERT INTO pgml.deployments (project_id, model_id, strategy) VALUES ($1, $2, $3::pgml.strategy) RETURNING id",
9696
vec![
9797
(PgBuiltInOids::INT8OID.oid(), self.id.into_datum()),
9898
(PgBuiltInOids::INT8OID.oid(), model_id.into_datum()),
99-
(PgBuiltInOids::TEXTOID.oid(), Strategy::most_recent.to_string().into_datum()),
99+
(PgBuiltInOids::TEXTOID.oid(), strategy.to_string().into_datum()),
100100
],
101101
).unwrap();
102102
let mut projects = PROJECT_ID_TO_DEPLOYED_MODEL_ID.exclusive();

0 commit comments

Comments
 (0)