Skip to content

Commit c4d23ad

Browse files
committed
db: Fix incorrect Upsert for num_versions
This fixes the misused 'EXCLUDED' which would cause the `num_versions` to remain at 2 during conflicts.
1 parent 8c532da commit c4d23ad

File tree

3 files changed

+48
-20
lines changed

3 files changed

+48
-20
lines changed
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
DROP FUNCTION IF EXISTS update_num_versions_from_versions CASCADE;
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
CREATE OR REPLACE FUNCTION update_num_versions_from_versions() RETURNS TRIGGER AS $$
2+
BEGIN
3+
IF (TG_OP = 'INSERT') THEN
4+
INSERT INTO default_versions (crate_id, version_id, num_versions)
5+
VALUES (NEW.crate_id, NEW.id, 1)
6+
ON CONFLICT (crate_id) DO UPDATE
7+
SET num_versions = default_versions.num_versions + 1;
8+
RETURN NEW;
9+
ELSIF (TG_OP = 'DELETE') THEN
10+
UPDATE default_versions
11+
SET num_versions = num_versions - 1
12+
WHERE crate_id = OLD.crate_id;
13+
RETURN OLD;
14+
END IF;
15+
END
16+
$$ LANGUAGE plpgsql;

src/tests/krate/publish/basics.rs

Lines changed: 31 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ use crate::schema::versions_published_by;
22
use crate::tests::builders::{CrateBuilder, PublishBuilder};
33
use crate::tests::util::{RequestHelper, TestApp};
44
use diesel::QueryDsl;
5-
use diesel_async::RunQueryDsl;
5+
use diesel_async::{AsyncPgConnection, RunQueryDsl};
66
use googletest::prelude::*;
77
use http::StatusCode;
88
use insta::{assert_json_snapshot, assert_snapshot};
@@ -116,23 +116,12 @@ async fn new_krate_twice() {
116116
// The primary purpose is to verify that the `default_version` we provide is as expected.
117117
#[tokio::test(flavor = "multi_thread")]
118118
async fn new_krate_twice_alt() {
119-
use crate::schema::default_versions;
120-
121119
let (app, _, _, token) = TestApp::full().with_token().await;
122-
let mut conn = app.db_conn().await;
123120

124121
let crate_to_publish =
125122
PublishBuilder::new("foo_twice", "2.0.0").description("2.0.0 description");
126123
token.publish_crate(crate_to_publish).await.good();
127124

128-
let num_versions = default_versions::table
129-
.select(default_versions::num_versions)
130-
.load::<Option<i32>>(&mut conn)
131-
.await
132-
.unwrap();
133-
assert_eq!(num_versions.len(), 1);
134-
assert_eq!(num_versions[0], Some(1));
135-
136125
let crate_to_publish = PublishBuilder::new("foo_twice", "0.99.0");
137126
let response = token.publish_crate(crate_to_publish).await;
138127
assert_eq!(response.status(), StatusCode::OK);
@@ -141,14 +130,6 @@ async fn new_krate_twice_alt() {
141130
".crate.updated_at" => "[datetime]",
142131
});
143132

144-
let num_versions = default_versions::table
145-
.select(default_versions::num_versions)
146-
.load::<Option<i32>>(&mut conn)
147-
.await
148-
.unwrap();
149-
assert_eq!(num_versions.len(), 1);
150-
assert_eq!(num_versions[0], Some(2));
151-
152133
let crates = app.crates_from_index_head("foo_twice");
153134
assert_json_snapshot!(crates);
154135

@@ -180,3 +161,33 @@ async fn new_krate_duplicate_version() {
180161

181162
assert_that!(app.stored_files().await, empty());
182163
}
164+
165+
#[tokio::test(flavor = "multi_thread")]
166+
async fn new_krate_advance_num_versions() {
167+
use crate::schema::default_versions;
168+
169+
let (app, _, _, token) = TestApp::full().with_token().await;
170+
let mut conn = app.db_conn().await;
171+
172+
async fn assert_num_versions(conn: &mut AsyncPgConnection, expected: i32) {
173+
let num_versions = default_versions::table
174+
.select(default_versions::num_versions)
175+
.load::<Option<i32>>(conn)
176+
.await
177+
.unwrap();
178+
assert_eq!(num_versions.len(), 1);
179+
assert_eq!(num_versions[0], Some(expected));
180+
}
181+
182+
let crate_to_publish = PublishBuilder::new("foo", "2.0.0").description("2.0.0 description");
183+
token.publish_crate(crate_to_publish).await.good();
184+
assert_num_versions(&mut conn, 1).await;
185+
186+
let crate_to_publish = PublishBuilder::new("foo", "2.0.1").description("2.0.1 description");
187+
token.publish_crate(crate_to_publish).await.good();
188+
assert_num_versions(&mut conn, 2).await;
189+
190+
let crate_to_publish = PublishBuilder::new("foo", "2.0.2").description("2.0.2 description");
191+
token.publish_crate(crate_to_publish).await.good();
192+
assert_num_versions(&mut conn, 3).await;
193+
}

0 commit comments

Comments
 (0)