From b191dde06a82c15611cc43be3fcc03e6a2749bd0 Mon Sep 17 00:00:00 2001 From: Evan H Stanton <79367212+EvanHStanton@users.noreply.github.com> Date: Thu, 7 Dec 2023 13:11:56 -0500 Subject: [PATCH 1/9] Add pg_orphaned (#528) Co-authored-by: Evan Stanton Co-authored-by: Steven Miller --- contrib/pg_orphaned/Dockerfile | 11 +++++++++++ contrib/pg_orphaned/Trunk.toml | 19 +++++++++++++++++++ 2 files changed, 30 insertions(+) create mode 100644 contrib/pg_orphaned/Dockerfile create mode 100644 contrib/pg_orphaned/Trunk.toml diff --git a/contrib/pg_orphaned/Dockerfile b/contrib/pg_orphaned/Dockerfile new file mode 100644 index 00000000..1614ec55 --- /dev/null +++ b/contrib/pg_orphaned/Dockerfile @@ -0,0 +1,11 @@ +# Set PostgreSQL version +ARG PG_VERSION=15 +FROM quay.io/coredb/c-builder:pg${PG_VERSION} +USER root + +# Clone repository +RUN git clone https://github.com/bdrouvot/pg_orphaned.git + +# Build extension +RUN cd pg_orphaned && \ + make diff --git a/contrib/pg_orphaned/Trunk.toml b/contrib/pg_orphaned/Trunk.toml new file mode 100644 index 00000000..de2d242b --- /dev/null +++ b/contrib/pg_orphaned/Trunk.toml @@ -0,0 +1,19 @@ +[extension] +name = "pg_orphaned" +version = "1.0.0" +repository = "https://github.com/bdrouvot/pg_orphaned" +license = "PostgreSQL" +description = "Functions relating to orphaned files." +documentation = "https://github.com/bdrouvot/pg_orphaned" +categories = ["data_transformations"] + +[build] +postgres_version = "15" +platform = "linux/amd64" +dockerfile = "Dockerfile" +install_command = """ + cd pg_orphaned && make install + set -x + mv /usr/local/pgsql/share/extension/* /usr/share/postgresql/15/extension + mv /usr/local/pgsql/lib/* /usr/lib/postgresql/15/lib + """ From 24ecc6dcc6f7c8cf39719dfa32d9706a0a926e11 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Fri, 8 Dec 2023 01:32:11 -0300 Subject: [PATCH 2/9] cli: allow setting loadable libraries in Trunk.toml (#549) Co-authored-by: Steven Miller Co-authored-by: Ian Stanton --- cli/Cargo.toml | 2 +- cli/src/commands/build.rs | 21 ++++----- cli/src/commands/containers.rs | 5 +- cli/src/commands/generic_build.rs | 5 +- cli/src/commands/install.rs | 13 +++-- cli/src/commands/pgrx.rs | 5 +- cli/src/commands/publish.rs | 17 ++++--- cli/src/config.rs | 8 ++++ cli/src/manifest.rs | 4 +- cli/src/trunk_toml.rs | 4 +- cli/tests/integration_tests.rs | 47 ++++++------------- .../test_trunk_toml_dirs/pg_cron/Trunk.toml | 6 ++- .../pgrx_with_trunk_toml/Trunk.toml | 5 +- .../test_trunk_toml_dirs/postgis/Dockerfile | 1 - 14 files changed, 75 insertions(+), 68 deletions(-) diff --git a/cli/Cargo.toml b/cli/Cargo.toml index 6b1d395d..ccdde7fd 100644 --- a/cli/Cargo.toml +++ b/cli/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "pg-trunk" -version = "0.11.9" +version = "0.11.10" edition = "2021" authors = ["Steven Miller", "Ian Stanton", "Vinícius Miguel"] description = "A package manager for PostgreSQL extensions" diff --git a/cli/src/commands/build.rs b/cli/src/commands/build.rs index e5fe2a03..6ab5f45b 100644 --- a/cli/src/commands/build.rs +++ b/cli/src/commands/build.rs @@ -1,7 +1,7 @@ use super::SubCommand; use crate::commands::generic_build::build_generic; use crate::commands::pgrx::build_pgrx; -use crate::config; +use crate::config::{self, LoadableLibrary}; use crate::trunk_toml::{cli_or_trunk, cli_or_trunk_opt, SystemDependencies}; use anyhow::anyhow; use async_trait::async_trait; @@ -49,13 +49,13 @@ pub struct BuildSettings { pub name: Option, pub extension_name: Option, pub extension_dependencies: Option>, - pub preload_libraries: Option>, pub system_dependencies: Option, pub glob_patterns_to_include: Vec, pub platform: Option, pub dockerfile_path: Option, pub install_command: Option, pub should_test: bool, + pub loadable_libraries: Option>, } impl BuildCommand { @@ -90,6 +90,11 @@ impl BuildCommand { let name = cli_or_trunk(&self.name, |toml| &toml.extension.name, &trunk_toml); + let loadable_libraries = trunk_toml + .as_ref() + .and_then(|toml| toml.extension.loadable_libraries.as_ref()) + .cloned(); + let extension_name = cli_or_trunk_opt( &self.extension_name, |toml| &toml.extension.extension_name, @@ -102,12 +107,6 @@ impl BuildCommand { &trunk_toml, ); - let preload_libraries = cli_or_trunk_opt( - &self.preload_libraries, - |toml| &toml.extension.preload_libraries, - &trunk_toml, - ); - let version = cli_or_trunk(&self.version, |toml| &toml.extension.version, &trunk_toml); let platform = cli_or_trunk(&self.platform, |toml| &toml.build.platform, &trunk_toml); @@ -157,13 +156,13 @@ impl BuildCommand { name, extension_name, extension_dependencies, - preload_libraries, system_dependencies, glob_patterns_to_include, platform, dockerfile_path, install_command, should_test: self.test, + loadable_libraries, }) } } @@ -232,10 +231,10 @@ impl SubCommand for BuildCommand { &build_settings.output_path, build_settings.extension_name, build_settings.extension_dependencies, - build_settings.preload_libraries, cargo_toml, build_settings.system_dependencies, build_settings.glob_patterns_to_include, + build_settings.loadable_libraries, task, ) .await?; @@ -276,12 +275,12 @@ impl SubCommand for BuildCommand { build_settings.name.clone().unwrap().as_str(), build_settings.extension_name, build_settings.extension_dependencies, - build_settings.preload_libraries, build_settings.system_dependencies, build_settings.version.clone().unwrap().as_str(), build_settings.glob_patterns_to_include, task, build_settings.should_test, + build_settings.loadable_libraries, ) .await?; return Ok(()); diff --git a/cli/src/commands/containers.rs b/cli/src/commands/containers.rs index 7f0b2ef5..0f9c720d 100644 --- a/cli/src/commands/containers.rs +++ b/cli/src/commands/containers.rs @@ -16,6 +16,7 @@ use std::io::Cursor; use std::path::{Path, PathBuf}; use crate::commands::generic_build::GenericBuildError; +use crate::config::LoadableLibrary; use crate::control_file::ControlFile; use crate::manifest::Manifest; use crate::sync_utils::{ByteStreamSyncReceiver, ByteStreamSyncSender}; @@ -399,13 +400,13 @@ pub async fn package_installed_extension_files( docker: Docker, container_id: &str, package_path: &str, - preload_libraries: Option>, system_dependencies: Option, name: &str, mut extension_name: Option, extension_version: &str, extension_dependencies: Option>, inclusion_patterns: Vec, + loadable_libraries: Option>, ) -> Result<(), anyhow::Error> { let name = name.to_owned(); let extension_version = extension_version.to_owned(); @@ -497,11 +498,11 @@ pub async fn package_installed_extension_files( extension_version, extension_dependencies, manifest_version: 2, - preload_libraries, architecture: target_arch, sys: "linux".to_string(), files: None, dependencies: system_dependencies, + loadable_libraries, }; // If the docker copy command starts to stream data println!("Create Trunk bundle:"); diff --git a/cli/src/commands/generic_build.rs b/cli/src/commands/generic_build.rs index d28e77fc..06190aac 100644 --- a/cli/src/commands/generic_build.rs +++ b/cli/src/commands/generic_build.rs @@ -18,6 +18,7 @@ use crate::commands::containers::{ start_postgres, }; use crate::commands::license::{copy_licenses, find_licenses}; +use crate::config::LoadableLibrary; use crate::trunk_toml::SystemDependencies; #[derive(Error, Debug)] @@ -74,12 +75,12 @@ pub async fn build_generic( name: &str, extension_name: Option, extension_dependencies: Option>, - preload_libraries: Option>, system_dependencies: Option, extension_version: &str, inclusion_patterns: Vec, _task: Task, should_test: bool, + loadable_libraries: Option>, ) -> Result<(), GenericBuildError> { println!("Building with name {}", &name); println!("Building with version {}", &extension_version); @@ -149,13 +150,13 @@ pub async fn build_generic( docker.clone(), &temp_container.id, output_path, - preload_libraries, system_dependencies, name, extension_name, extension_version, extension_dependencies, inclusion_patterns, + loadable_libraries, ) .await?; diff --git a/cli/src/commands/install.rs b/cli/src/commands/install.rs index d1ba0304..35deb8bb 100644 --- a/cli/src/commands/install.rs +++ b/cli/src/commands/install.rs @@ -9,6 +9,7 @@ use flate2::read::GzDecoder; use log::{error, info, warn}; use reqwest; use reqwest::Url; +use slicedisplay::SliceDisplay; use std::ffi::OsStr; use std::fs::File; use std::io::{Read, Seek, Write}; @@ -439,10 +440,16 @@ fn print_post_installation_guide(manifest: &Manifest) { } // If the manifest has preload_libraries, then we need to add the extension to preload_libraries // Output will look like preload_libraries = 'spl1,spl2,spl3' - if let Some(preload_libraries) = &manifest.preload_libraries { - let spl = preload_libraries.join(","); + if let Some(preload_libraries) = &manifest.loadable_libraries { + let libraries: Vec<_> = preload_libraries + .iter() + .map(|lib| &lib.library_name) + .collect(); println!("\nAdd the following to your postgresql.conf:"); - println!("\tshared_preload_libraries = '{}'", spl); + println!( + "\tshared_preload_libraries = {}", + libraries.display().terminator('\'', '\'') + ); } println!("\nEnable the extension with:"); diff --git a/cli/src/commands/pgrx.rs b/cli/src/commands/pgrx.rs index db3bcb7c..674a4e6e 100644 --- a/cli/src/commands/pgrx.rs +++ b/cli/src/commands/pgrx.rs @@ -12,6 +12,7 @@ use bollard::Docker; use crate::commands::containers::{ build_image, exec_in_container, package_installed_extension_files, run_temporary_container, }; +use crate::config::LoadableLibrary; use crate::trunk_toml::SystemDependencies; use tokio::sync::mpsc; @@ -105,10 +106,10 @@ pub async fn build_pgrx( output_path: &str, extension_name: Option, extension_dependencies: Option>, - preload_libraries: Option>, cargo_toml: toml::Table, system_dependencies: Option, inclusion_patterns: Vec, + loadable_libraries: Option>, _task: Task, ) -> Result<(), PgrxBuildError> { let cargo_package_info = cargo_toml @@ -231,13 +232,13 @@ pub async fn build_pgrx( docker.clone(), &temp_container.id, output_path, - preload_libraries, system_dependencies, name, extension_name, extension_version, extension_dependencies, inclusion_patterns, + loadable_libraries, ) .await?; diff --git a/cli/src/commands/publish.rs b/cli/src/commands/publish.rs index e83e32fc..6359bd6d 100644 --- a/cli/src/commands/publish.rs +++ b/cli/src/commands/publish.rs @@ -1,7 +1,7 @@ use super::SubCommand; use crate::commands::categories::VALID_CATEGORY_SLUGS; use crate::commands::publish::PublishError::InvalidExtensionName; -use crate::config; +use crate::config::{self, LoadableLibrary}; use crate::manifest::Manifest; use crate::trunk_toml::{cli_or_trunk, cli_or_trunk_opt, SystemDependencies}; use anyhow::{anyhow, Context}; @@ -67,7 +67,6 @@ pub struct PublishSettings { name: String, extension_name: Option, extension_dependencies: Option>, - preload_libraries: Option>, version: String, file: Option, description: Option, @@ -78,6 +77,7 @@ pub struct PublishSettings { repository: Option, system_dependencies: Option, categories: Option>, + loadable_libraries: Option>, } impl PublishCommand { @@ -112,11 +112,10 @@ impl PublishCommand { &trunk_toml, ); - let preload_libraries = cli_or_trunk_opt( - &self.preload_libraries, - |toml| &toml.extension.preload_libraries, - &trunk_toml, - ); + let loadable_libraries = trunk_toml + .as_ref() + .and_then(|toml| toml.extension.loadable_libraries.as_ref()) + .cloned(); let maybe_version = cli_or_trunk(&self.version, |toml| &toml.extension.version, &trunk_toml); @@ -190,7 +189,7 @@ impl PublishCommand { extension_dependencies, system_dependencies, categories, - preload_libraries, + loadable_libraries, }) } } @@ -358,7 +357,7 @@ impl SubCommand for PublishCommand { "repository": publish_settings.repository, "system_dependencies": publish_settings.system_dependencies, "categories": publish_settings.categories, - "libraries": publish_settings.preload_libraries, + "libraries": publish_settings.loadable_libraries, }); let metadata = reqwest::multipart::Part::text(m.to_string()).headers(headers); let form = reqwest::multipart::Form::new() diff --git a/cli/src/config.rs b/cli/src/config.rs index 7b2b31c3..9165584f 100644 --- a/cli/src/config.rs +++ b/cli/src/config.rs @@ -1,4 +1,5 @@ use log::warn; +use serde::{Deserialize, Serialize}; use std::io::Read; use crate::trunk_toml::TrunkToml; @@ -16,6 +17,13 @@ pub fn parse_trunk_toml(mut reader: R) -> Result>, pub sys: String, pub architecture: String, pub files: Option>, + pub loadable_libraries: Option>, } impl Manifest { diff --git a/cli/src/trunk_toml.rs b/cli/src/trunk_toml.rs index 2c338773..f2a31a5f 100644 --- a/cli/src/trunk_toml.rs +++ b/cli/src/trunk_toml.rs @@ -4,6 +4,8 @@ use serde::{Deserialize, Serialize}; use glob::PatternError; +use crate::config::LoadableLibrary; + pub type SystemDependencies = HashMap>; /// The definition/schema of a Trunk.toml file @@ -28,7 +30,7 @@ pub struct TomlExtensionData { pub documentation: Option, pub categories: Vec, pub registry: Option, - pub preload_libraries: Option>, + pub loadable_libraries: Option>, } #[derive(Serialize, Deserialize, Debug)] diff --git a/cli/tests/integration_tests.rs b/cli/tests/integration_tests.rs index f5dc6cfe..6c04a49b 100644 --- a/cli/tests/integration_tests.rs +++ b/cli/tests/integration_tests.rs @@ -135,8 +135,6 @@ fn build_pgrx_extension() -> Result<(), Box> { cmd.arg(extension_path.as_os_str()); cmd.arg("--output-path"); cmd.arg(output_dir.clone()); - cmd.arg("--preload-libraries"); - cmd.arg("test_pgrx_extension_spl"); cmd.assert().code(0); assert!(std::path::Path::new( format!("{output_dir}/test_pgrx_extension-0.0.0.tar.gz").as_str() @@ -151,7 +149,7 @@ fn build_pgrx_extension() -> Result<(), Box> { let stdout = String::from_utf8(output.stdout).unwrap(); assert!(stdout.contains("licenses/LICENSE.txt")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name and loadable_libraries is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/test_pgrx_extension-0.0.0.tar.gz").as_str()) @@ -166,7 +164,6 @@ fn build_pgrx_extension() -> Result<(), Box> { .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"test_pgrx_extension\"")); - assert!(stdout.contains("\"test_pgrx_extension_spl\"")); // assert post installation steps contain correct CREATE EXTENSION command let mut cmd = Command::cargo_bin(CARGO_BIN)?; @@ -178,8 +175,6 @@ fn build_pgrx_extension() -> Result<(), Box> { let stdout = String::from_utf8(output.stdout)?; cmd.assert().code(0); assert!(stdout.contains("CREATE EXTENSION IF NOT EXISTS test_pgrx_extension CASCADE;")); - assert!(stdout.contains("Add the following to your postgresql.conf:")); - assert!(stdout.contains("shared_preload_libraries = 'test_pgrx_extension_spl'")); // delete the temporary file std::fs::remove_dir_all(output_dir)?; @@ -275,8 +270,6 @@ fn build_c_extension() -> Result<(), Box> { cmd.arg("1.0.3"); cmd.arg("--name"); cmd.arg("pg_tle"); - cmd.arg("--preload-libraries"); - cmd.arg("pg_tle_spl"); cmd.assert().code(0); assert!(std::path::Path::new(format!("{output_dir}/pg_tle-1.0.3.tar.gz").as_str()).exists()); // assert any license files are included @@ -289,7 +282,7 @@ fn build_c_extension() -> Result<(), Box> { assert!(stdout.contains("licenses/LICENSE")); assert!(stdout.contains("licenses/NOTICE")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/pg_tle-1.0.3.tar.gz").as_str()) @@ -304,7 +297,6 @@ fn build_c_extension() -> Result<(), Box> { .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"pg_tle\"")); - assert!(stdout.contains("\"pg_tle_spl\"")); // delete the temporary file std::fs::remove_dir_all(output_dir)?; @@ -361,8 +353,6 @@ fn build_extension_custom_dockerfile() -> Result<(), Box> cmd.arg("1.5.0"); cmd.arg("--name"); cmd.arg("pgsql_http"); - cmd.arg("--preload-libraries"); - cmd.arg("pgsql_http_spl"); cmd.assert().code(0); assert!( std::path::Path::new(format!("{output_dir}/pgsql_http-1.5.0.tar.gz").as_str()).exists() @@ -376,7 +366,7 @@ fn build_extension_custom_dockerfile() -> Result<(), Box> let stdout = String::from_utf8(output.stdout).unwrap(); assert!(stdout.contains("licenses/LICENSE.md")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/pgsql_http-1.5.0.tar.gz").as_str()) @@ -393,7 +383,6 @@ fn build_extension_custom_dockerfile() -> Result<(), Box> // Note - name and extension_name are different here assert!(stdout.contains("\"name\": \"pgsql_http\"")); assert!(stdout.contains("\"extension_name\": \"http\"")); - assert!(stdout.contains("\"pgsql_http_spl\"")); // assert post installation steps contain correct CREATE EXTENSION command let mut cmd = Command::cargo_bin(CARGO_BIN)?; @@ -471,8 +460,6 @@ fn build_pg_stat_statements() -> Result<(), Box> { cmd.arg("1.10"); cmd.arg("--name"); cmd.arg("pg_stat_statements"); - cmd.arg("--preload-libraries"); - cmd.arg("pg_stat_statements_spl"); cmd.assert().code(0); assert!( std::path::Path::new(format!("{output_dir}/pg_stat_statements-1.10.tar.gz").as_str()) @@ -488,7 +475,7 @@ fn build_pg_stat_statements() -> Result<(), Box> { assert!(stdout.contains("licenses/COPYRIGHT")); assert!(stdout.contains("licenses/COPYRIGHT.~1~")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/pg_stat_statements-1.10.tar.gz").as_str()) @@ -503,7 +490,6 @@ fn build_pg_stat_statements() -> Result<(), Box> { .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"pg_stat_statements\"")); - assert!(stdout.contains("\"pg_stat_statements_spl\"")); // delete the temporary file std::fs::remove_dir_all(output_dir)?; @@ -538,7 +524,7 @@ fn build_pg_cron_trunk_toml() -> Result<(), Box> { let stdout = String::from_utf8(output.stdout).unwrap(); assert!(stdout.contains("licenses/LICENSE")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name and loadable_libraries is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/pg_cron-1.5.2.tar.gz").as_str()) @@ -553,7 +539,7 @@ fn build_pg_cron_trunk_toml() -> Result<(), Box> { .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"extension_name_from_toml\"")); - assert!(stdout.contains("\"shared_preload_libraries_from_toml\"")); + assert!(stdout.contains("\"loadable_libraries\": [\n {\n \"library_name\": \"shared_preload_libraries_from_toml\",\n \"requires_restart\": true,\n \"priority\": 1\n },\n {\n \"library_name\": \"shared_preload_libraries_from_toml_2\",\n \"requires_restart\": false,\n \"priority\": 2\n }\n ]")); assert!(stdout.contains("\"dependencies\": {\n \"apt\": [\n \"libpq5\"\n ],\n \"dnf\": [\n \"libpq-devel\"\n ]\n }") || stdout.contains("\"dependencies\": {\n \"dnf\": [\n \"libpq-devel\"\n ],\n \"apt\": [\n \"libpq5\"\n ]\n }")); // assert post installation steps contain correct CREATE EXTENSION command @@ -571,6 +557,8 @@ fn build_pg_cron_trunk_toml() -> Result<(), Box> { assert!(stdout.contains("libpq5")); assert!(stdout.contains("On systems using dnf:")); assert!(stdout.contains("libpq-devel")); + assert!(stdout.contains("Add the following to your postgresql.conf:")); + assert!(stdout.contains("shared_preload_libraries = 'shared_preload_libraries_from_toml, shared_preload_libraries_from_toml_2'")); // assert that the dependencies were written to manifest let manifest = Command::new("cat") @@ -621,7 +609,7 @@ fn build_pgrx_with_trunk_toml() -> Result<(), Box> { let stdout = String::from_utf8(output.stdout).unwrap(); assert!(stdout.contains("licenses/LICENSE.txt")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name and loadable_libraries is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/test_pgrx_extension-0.0.0.tar.gz").as_str()) @@ -636,7 +624,7 @@ fn build_pgrx_with_trunk_toml() -> Result<(), Box> { .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"extension_name_from_toml\"")); - assert!(stdout.contains("\"shared_preload_libraries_from_toml\"")); + assert!(stdout.contains("\"loadable_libraries\": [\n {\n \"library_name\": \"shared_preload_libraries_from_toml\",\n \"requires_restart\": true,\n \"priority\": 1\n },\n {\n \"library_name\": \"another_shared_preload_library\",\n \"requires_restart\": false,\n \"priority\": 2\n }\n ]")); assert!(stdout.contains("\"another_shared_preload_library\"")); assert!(stdout.contains("\"libpq5\"")); @@ -669,7 +657,7 @@ fn build_pgrx_with_trunk_toml() -> Result<(), Box> { assert!(stdout.contains("On systems using apt:")); assert!(stdout.contains("libpq5")); assert!(stdout.contains("Add the following to your postgresql.conf:")); - assert!(stdout.contains("shared_preload_libraries = 'shared_preload_libraries_from_toml,another_shared_preload_library'")); + assert!(stdout.contains("shared_preload_libraries = 'shared_preload_libraries_from_toml, another_shared_preload_library'")); // delete the temporary file std::fs::remove_dir_all(output_dir)?; @@ -785,8 +773,6 @@ fn build_auto_explain() -> Result<(), Box> { cmd.arg("15.3.0"); cmd.arg("--name"); cmd.arg("auto_explain"); - cmd.arg("--preload-libraries"); - cmd.arg("auto_explain_spl"); cmd.assert().code(0); assert!( std::path::Path::new(format!("{output_dir}/auto_explain-15.3.0.tar.gz").as_str()).exists() @@ -801,7 +787,7 @@ fn build_auto_explain() -> Result<(), Box> { assert!(stdout.contains("licenses/COPYRIGHT")); assert!(stdout.contains("licenses/COPYRIGHT.~1~")); - // assert extension_name and preload_libraries is in manifest.json + // assert extension_name is in manifest.json let _extract = Command::new("tar") .arg("-xvf") .arg(format!("{output_dir}/auto_explain-15.3.0.tar.gz").as_str()) @@ -815,21 +801,16 @@ fn build_auto_explain() -> Result<(), Box> { .output() .expect("failed to run cat command"); let stdout = String::from_utf8(manifest.stdout).unwrap(); + assert!(stdout.contains("\"extension_name\": \"auto_explain\"")); - assert!(stdout.contains("\"auto_explain_spl\"")); - // assert post installation steps contain correct shared_preload_libraries command let mut cmd = Command::cargo_bin(CARGO_BIN)?; cmd.arg("install"); cmd.arg("--file"); cmd.arg(format!("{output_dir}/auto_explain-15.3.0.tar.gz").as_str()); cmd.arg("auto_explain"); - let output = cmd.output()?; - let stdout = String::from_utf8(output.stdout)?; - cmd.assert().code(0); - assert!(stdout.contains("Add the following to your postgresql.conf:")); - assert!(stdout.contains("shared_preload_libraries = 'auto_explain_spl'")); + cmd.assert().code(0); // delete the temporary file std::fs::remove_dir_all(output_dir)?; diff --git a/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml b/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml index dc7c4bd8..1edca58c 100644 --- a/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml +++ b/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml @@ -2,11 +2,15 @@ name = "pg_cron" extension_name = "extension_name_from_toml" extension_dependencies = ["btree_gin"] -preload_libraries = ["shared_preload_libraries_from_toml"] version = "1.5.2" repository = "https://github.com/tembo-io/trunk" license = "PostgreSQL" categories = [] +loadable_libraries = [ + { library_name = "shared_preload_libraries_from_toml", requires_restart = true, priority = 1 }, + { library_name = "shared_preload_libraries_from_toml_2", requires_restart = false, priority = 2 } +] + [build] dockerfile = "Dockerfile" diff --git a/cli/tests/test_trunk_toml_dirs/pgrx_with_trunk_toml/Trunk.toml b/cli/tests/test_trunk_toml_dirs/pgrx_with_trunk_toml/Trunk.toml index db0c5706..a64cac78 100644 --- a/cli/tests/test_trunk_toml_dirs/pgrx_with_trunk_toml/Trunk.toml +++ b/cli/tests/test_trunk_toml_dirs/pgrx_with_trunk_toml/Trunk.toml @@ -1,11 +1,14 @@ [extension] name = "test_pgrx_extension" extension_name = "extension_name_from_toml" -preload_libraries = ["shared_preload_libraries_from_toml", "another_shared_preload_library"] version = "0.0.0" repository = "https://github.com/tembo-io/trunk" license = "PostgreSQL" categories = [] +loadable_libraries = [ + { library_name = "shared_preload_libraries_from_toml", requires_restart = true, priority = 1 }, + { library_name = "another_shared_preload_library", requires_restart = false, priority = 2 } +] [build] platform = "linux/amd64" diff --git a/cli/tests/test_trunk_toml_dirs/postgis/Dockerfile b/cli/tests/test_trunk_toml_dirs/postgis/Dockerfile index 53112371..2b20d6aa 100644 --- a/cli/tests/test_trunk_toml_dirs/postgis/Dockerfile +++ b/cli/tests/test_trunk_toml_dirs/postgis/Dockerfile @@ -16,7 +16,6 @@ RUN apt-get update && apt-get install -y \ ccache \ libgdal-dev \ libgeos-dev \ - osm2pgsql \ libprotobuf-c-dev \ protobuf-c-compiler From b76e052a0e021c67b013d896de67e37fac40d66c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Fri, 8 Dec 2023 13:00:08 -0300 Subject: [PATCH 3/9] cli: allow setting v1 `configuration` in Trunk.toml (#547) Co-authored-by: Steven Miller --- cli/Cargo.toml | 2 +- cli/src/commands/build.rs | 11 ++++++++++- cli/src/commands/containers.rs | 4 +++- cli/src/commands/generic_build.rs | 4 +++- cli/src/commands/pgrx.rs | 4 +++- cli/src/commands/publish.rs | 12 ++++++++++-- cli/src/config.rs | 11 +++++++++++ cli/src/manifest.rs | 3 ++- cli/src/trunk_toml.rs | 4 +++- cli/tests/integration_tests.rs | 8 ++++++++ cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml | 4 ++++ 11 files changed, 58 insertions(+), 9 deletions(-) diff --git a/cli/Cargo.toml b/cli/Cargo.toml index ccdde7fd..80d5828e 100644 --- a/cli/Cargo.toml +++ b/cli/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "pg-trunk" -version = "0.11.10" +version = "0.11.11" edition = "2021" authors = ["Steven Miller", "Ian Stanton", "Vinícius Miguel"] description = "A package manager for PostgreSQL extensions" diff --git a/cli/src/commands/build.rs b/cli/src/commands/build.rs index 6ab5f45b..2aba2d2d 100644 --- a/cli/src/commands/build.rs +++ b/cli/src/commands/build.rs @@ -1,7 +1,7 @@ use super::SubCommand; use crate::commands::generic_build::build_generic; use crate::commands::pgrx::build_pgrx; -use crate::config::{self, LoadableLibrary}; +use crate::config::{self, ExtensionConfiguration, LoadableLibrary}; use crate::trunk_toml::{cli_or_trunk, cli_or_trunk_opt, SystemDependencies}; use anyhow::anyhow; use async_trait::async_trait; @@ -49,6 +49,7 @@ pub struct BuildSettings { pub name: Option, pub extension_name: Option, pub extension_dependencies: Option>, + pub configurations: Option>, pub system_dependencies: Option, pub glob_patterns_to_include: Vec, pub platform: Option, @@ -128,6 +129,11 @@ impl BuildCommand { glob_patterns_to_include.display() ); + let configurations = trunk_toml + .as_ref() + .and_then(|toml| toml.extension.configurations.as_ref()) + .cloned(); + let system_dependencies = trunk_toml .as_ref() .and_then(|toml| toml.dependencies.as_ref()) @@ -162,6 +168,7 @@ impl BuildCommand { dockerfile_path, install_command, should_test: self.test, + configurations, loadable_libraries, }) } @@ -234,6 +241,7 @@ impl SubCommand for BuildCommand { cargo_toml, build_settings.system_dependencies, build_settings.glob_patterns_to_include, + build_settings.configurations, build_settings.loadable_libraries, task, ) @@ -280,6 +288,7 @@ impl SubCommand for BuildCommand { build_settings.glob_patterns_to_include, task, build_settings.should_test, + build_settings.configurations, build_settings.loadable_libraries, ) .await?; diff --git a/cli/src/commands/containers.rs b/cli/src/commands/containers.rs index 0f9c720d..6ee30480 100644 --- a/cli/src/commands/containers.rs +++ b/cli/src/commands/containers.rs @@ -16,7 +16,7 @@ use std::io::Cursor; use std::path::{Path, PathBuf}; use crate::commands::generic_build::GenericBuildError; -use crate::config::LoadableLibrary; +use crate::config::{ExtensionConfiguration, LoadableLibrary}; use crate::control_file::ControlFile; use crate::manifest::Manifest; use crate::sync_utils::{ByteStreamSyncReceiver, ByteStreamSyncSender}; @@ -406,6 +406,7 @@ pub async fn package_installed_extension_files( extension_version: &str, extension_dependencies: Option>, inclusion_patterns: Vec, + configurations: Option>, loadable_libraries: Option>, ) -> Result<(), anyhow::Error> { let name = name.to_owned(); @@ -502,6 +503,7 @@ pub async fn package_installed_extension_files( sys: "linux".to_string(), files: None, dependencies: system_dependencies, + configurations, loadable_libraries, }; // If the docker copy command starts to stream data diff --git a/cli/src/commands/generic_build.rs b/cli/src/commands/generic_build.rs index 06190aac..1da1ff94 100644 --- a/cli/src/commands/generic_build.rs +++ b/cli/src/commands/generic_build.rs @@ -18,7 +18,7 @@ use crate::commands::containers::{ start_postgres, }; use crate::commands::license::{copy_licenses, find_licenses}; -use crate::config::LoadableLibrary; +use crate::config::{ExtensionConfiguration, LoadableLibrary}; use crate::trunk_toml::SystemDependencies; #[derive(Error, Debug)] @@ -80,6 +80,7 @@ pub async fn build_generic( inclusion_patterns: Vec, _task: Task, should_test: bool, + configurations: Option>, loadable_libraries: Option>, ) -> Result<(), GenericBuildError> { println!("Building with name {}", &name); @@ -156,6 +157,7 @@ pub async fn build_generic( extension_version, extension_dependencies, inclusion_patterns, + configurations, loadable_libraries, ) .await?; diff --git a/cli/src/commands/pgrx.rs b/cli/src/commands/pgrx.rs index 674a4e6e..c89809d4 100644 --- a/cli/src/commands/pgrx.rs +++ b/cli/src/commands/pgrx.rs @@ -12,7 +12,7 @@ use bollard::Docker; use crate::commands::containers::{ build_image, exec_in_container, package_installed_extension_files, run_temporary_container, }; -use crate::config::LoadableLibrary; +use crate::config::{ExtensionConfiguration, LoadableLibrary}; use crate::trunk_toml::SystemDependencies; use tokio::sync::mpsc; @@ -109,6 +109,7 @@ pub async fn build_pgrx( cargo_toml: toml::Table, system_dependencies: Option, inclusion_patterns: Vec, + configurations: Option>, loadable_libraries: Option>, _task: Task, ) -> Result<(), PgrxBuildError> { @@ -238,6 +239,7 @@ pub async fn build_pgrx( extension_version, extension_dependencies, inclusion_patterns, + configurations, loadable_libraries, ) .await?; diff --git a/cli/src/commands/publish.rs b/cli/src/commands/publish.rs index 6359bd6d..33b3f5d1 100644 --- a/cli/src/commands/publish.rs +++ b/cli/src/commands/publish.rs @@ -1,7 +1,7 @@ use super::SubCommand; use crate::commands::categories::VALID_CATEGORY_SLUGS; use crate::commands::publish::PublishError::InvalidExtensionName; -use crate::config::{self, LoadableLibrary}; +use crate::config::{self, ExtensionConfiguration, LoadableLibrary}; use crate::manifest::Manifest; use crate::trunk_toml::{cli_or_trunk, cli_or_trunk_opt, SystemDependencies}; use anyhow::{anyhow, Context}; @@ -77,6 +77,7 @@ pub struct PublishSettings { repository: Option, system_dependencies: Option, categories: Option>, + configurations: Option>, loadable_libraries: Option>, } @@ -175,6 +176,11 @@ impl PublishCommand { .and_then(|toml| toml.dependencies.as_ref()) .cloned(); + let configurations = trunk_toml + .as_ref() + .and_then(|toml| toml.extension.configurations.as_ref()) + .cloned(); + Ok(PublishSettings { version, file, @@ -189,6 +195,7 @@ impl PublishCommand { extension_dependencies, system_dependencies, categories, + configurations, loadable_libraries, }) } @@ -357,7 +364,8 @@ impl SubCommand for PublishCommand { "repository": publish_settings.repository, "system_dependencies": publish_settings.system_dependencies, "categories": publish_settings.categories, - "libraries": publish_settings.loadable_libraries, + "configurations": publish_settings.configurations, + "libraries": publish_settings.loadable_libraries }); let metadata = reqwest::multipart::Part::text(m.to_string()).headers(headers); let form = reqwest::multipart::Form::new() diff --git a/cli/src/config.rs b/cli/src/config.rs index 9165584f..a8780302 100644 --- a/cli/src/config.rs +++ b/cli/src/config.rs @@ -4,6 +4,17 @@ use std::io::Read; use crate::trunk_toml::TrunkToml; +#[derive(Serialize, Deserialize, Debug, Clone)] +pub struct ExtensionConfiguration { + #[serde(alias = "name")] + configuration_name: String, + #[serde(default)] + #[serde(alias = "required")] + is_required: bool, + #[serde(alias = "default")] + recommended_default_value: Option, +} + pub fn parse_trunk_toml(mut reader: R) -> Result { let mut body = String::new(); reader.read_to_string(&mut body)?; diff --git a/cli/src/manifest.rs b/cli/src/manifest.rs index a3b7bb2a..0fe1f933 100644 --- a/cli/src/manifest.rs +++ b/cli/src/manifest.rs @@ -2,7 +2,7 @@ use serde::{Deserialize, Serialize}; use std::collections::HashMap; use std::path::{Path, PathBuf}; -use crate::config::LoadableLibrary; +use crate::config::{ExtensionConfiguration, LoadableLibrary}; /// Packaged file #[derive(Serialize, Deserialize, Debug)] @@ -59,6 +59,7 @@ pub struct Manifest { pub sys: String, pub architecture: String, pub files: Option>, + pub configurations: Option>, pub loadable_libraries: Option>, } diff --git a/cli/src/trunk_toml.rs b/cli/src/trunk_toml.rs index f2a31a5f..23c98617 100644 --- a/cli/src/trunk_toml.rs +++ b/cli/src/trunk_toml.rs @@ -4,7 +4,7 @@ use serde::{Deserialize, Serialize}; use glob::PatternError; -use crate::config::LoadableLibrary; +use crate::config::{ExtensionConfiguration, LoadableLibrary}; pub type SystemDependencies = HashMap>; @@ -30,6 +30,8 @@ pub struct TomlExtensionData { pub documentation: Option, pub categories: Vec, pub registry: Option, + pub preload_libraries: Option>, + pub configurations: Option>, pub loadable_libraries: Option>, } diff --git a/cli/tests/integration_tests.rs b/cli/tests/integration_tests.rs index 6c04a49b..bafa775a 100644 --- a/cli/tests/integration_tests.rs +++ b/cli/tests/integration_tests.rs @@ -540,6 +540,14 @@ fn build_pg_cron_trunk_toml() -> Result<(), Box> { let stdout = String::from_utf8(manifest.stdout).unwrap(); assert!(stdout.contains("\"extension_name\": \"extension_name_from_toml\"")); assert!(stdout.contains("\"loadable_libraries\": [\n {\n \"library_name\": \"shared_preload_libraries_from_toml\",\n \"requires_restart\": true,\n \"priority\": 1\n },\n {\n \"library_name\": \"shared_preload_libraries_from_toml_2\",\n \"requires_restart\": false,\n \"priority\": 2\n }\n ]")); + // Config name + assert!(stdout.contains("ip_address")); + // Is required + assert!(stdout.contains("is_required\": true")); + // Config name + assert!(stdout.contains("port")); + // Recommended default value + assert!(stdout.contains("8801")); assert!(stdout.contains("\"dependencies\": {\n \"apt\": [\n \"libpq5\"\n ],\n \"dnf\": [\n \"libpq-devel\"\n ]\n }") || stdout.contains("\"dependencies\": {\n \"dnf\": [\n \"libpq-devel\"\n ],\n \"apt\": [\n \"libpq5\"\n ]\n }")); // assert post installation steps contain correct CREATE EXTENSION command diff --git a/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml b/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml index 1edca58c..70e33282 100644 --- a/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml +++ b/cli/tests/test_trunk_toml_dirs/pg_cron/Trunk.toml @@ -11,6 +11,10 @@ loadable_libraries = [ { library_name = "shared_preload_libraries_from_toml_2", requires_restart = false, priority = 2 } ] +configurations = [ + { name = "ip_address", required = true }, + { name = "port", recommended_default_value = "8801"} +] [build] dockerfile = "Dockerfile" From d022d84953406c5f1dec7e684c19d3aab2cf4d56 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Fri, 8 Dec 2023 16:26:11 -0300 Subject: [PATCH 4/9] registry(v1): save Configuration and LoadableLibraries on publish (#551) --- registry/sqlx-data.json | 30 +++++------ registry/src/openapi.rs | 9 ++-- registry/src/routes/extensions.rs | 2 +- registry/src/v1/extractor.rs | 11 ++-- registry/src/v1/repository.rs | 72 ++++++++++++++----------- registry/src/views/extension_publish.rs | 20 ++++++- 6 files changed, 85 insertions(+), 59 deletions(-) diff --git a/registry/sqlx-data.json b/registry/sqlx-data.json index 679efef3..69c14aa8 100644 --- a/registry/sqlx-data.json +++ b/registry/sqlx-data.json @@ -1414,21 +1414,6 @@ }, "query": "SELECT * FROM extension_detail_vw" }, - "cff34205e2334651e696df107dac775cff18f102ca67898d9d68303ddfa314c5": { - "describe": { - "columns": [], - "nullable": [], - "parameters": { - "Left": [ - "Int4", - "Text", - "Bool", - "Int4" - ] - } - }, - "query": "INSERT INTO v1.extensions_loadable_libraries (extension_version_id, library_name, requires_restart, priority)\n VALUES ($1, $2, $3, $4)" - }, "e41ccd0b4b07c1761d78d4de2efdba33979114f1b055db3261af653afca8be56": { "describe": { "columns": [], @@ -1480,6 +1465,21 @@ }, "query": "\n UPDATE categories\n SET extension_count = extension_count + 1\n WHERE id = $1\n " }, + "f5c4444586051427aaf351b423d8dba82b213eef6e707a1cf5b54854769ce1b9": { + "describe": { + "columns": [], + "nullable": [], + "parameters": { + "Left": [ + "Int4", + "Text", + "Bool", + "Int4" + ] + } + }, + "query": "INSERT INTO v1.extensions_loadable_libraries (extension_version_id, library_name, requires_restart, priority)\n VALUES ($1, $2, $3, $4)" + }, "f77d6c607d830e7ea1d564c34ec42b998e0c2657f4cdb8a89dd211a29b4a7d65": { "describe": { "columns": [], diff --git a/registry/src/openapi.rs b/registry/src/openapi.rs index 21e719e6..0cca7c43 100644 --- a/registry/src/openapi.rs +++ b/registry/src/openapi.rs @@ -1,10 +1,9 @@ use utoipa::openapi::License; use utoipa::OpenApi; -use crate::v1::repository::{ - ExtensionConfigurationView, ExtensionPreloadLibrariesView, ExtensionView, TrunkProjectView, -}; +use crate::v1::repository::{ExtensionView, TrunkProjectView}; use crate::v1::routes as v1; +use crate::views::extension_publish::{ExtensionConfiguration, LoadableLibrary}; // v1 API documentation #[derive(OpenApi)] @@ -17,8 +16,8 @@ use crate::v1::routes as v1; ), components(schemas( ExtensionView, - ExtensionPreloadLibrariesView, - ExtensionConfigurationView, + LoadableLibrary, + ExtensionConfiguration, TrunkProjectView, )) )] diff --git a/registry/src/routes/extensions.rs b/registry/src/routes/extensions.rs index 2645f59c..3bf85381 100644 --- a/registry/src/routes/extensions.rs +++ b/registry/src/routes/extensions.rs @@ -328,7 +328,7 @@ async fn insert_into_v1( gzipped_archive: &[u8], ) -> anyhow::Result<()> { let extension_views = - crate::v1::extractor::extract_extension_view(gzipped_archive, &new_extension.name)?; + crate::v1::extractor::extract_extension_view(gzipped_archive, &new_extension)?; let trunk_project = TrunkProjectView { name: new_extension.name, diff --git a/registry/src/v1/extractor.rs b/registry/src/v1/extractor.rs index 26d18a64..1b42384a 100644 --- a/registry/src/v1/extractor.rs +++ b/registry/src/v1/extractor.rs @@ -6,6 +6,8 @@ use std::{ }; use tar::EntryType; +use crate::views::extension_publish::ExtensionUpload; + use super::repository::ExtensionView; pub struct ControlFile { @@ -16,7 +18,7 @@ pub struct ControlFile { pub fn extract_extension_view( tar_gz: &[u8], - trunk_project_name: &str, + new_extension: &ExtensionUpload, ) -> anyhow::Result> { let control_files = extract_control_files(tar_gz)?; @@ -25,10 +27,11 @@ pub fn extract_extension_view( .map(|control_file| ExtensionView { extension_name: control_file.extension_name, version: control_file.default_version.unwrap_or_default(), - trunk_project_name: trunk_project_name.to_string(), + trunk_project_name: new_extension.name.to_string(), dependencies_extension_names: control_file.dependencies, - loadable_libraries: None, - configurations: None, + // TODO: should we clone this for every extension in a Trunk project? + loadable_libraries: new_extension.libraries.clone(), + configurations: new_extension.configurations.clone(), }) .collect(); diff --git a/registry/src/v1/repository.rs b/registry/src/v1/repository.rs index 0b008437..7983eb4c 100644 --- a/registry/src/v1/repository.rs +++ b/registry/src/v1/repository.rs @@ -3,6 +3,7 @@ use utoipa::{ToResponse, ToSchema}; use crate::errors::Result; use crate::repository::Registry; +use crate::views::extension_publish::{ExtensionConfiguration, LoadableLibrary}; #[derive(Debug, Clone, Serialize, Deserialize, ToSchema, ToResponse)] pub struct TrunkProjectView { @@ -14,28 +15,14 @@ pub struct TrunkProjectView { pub extensions: Vec, } -#[derive(Default, Debug, Clone, PartialEq, Serialize, Deserialize, ToSchema)] -pub struct ExtensionConfigurationView { - pub name: String, - pub is_required: bool, - pub recommended_default: Option, -} - -#[derive(Debug, Clone, Serialize, Deserialize, ToSchema)] -pub struct ExtensionPreloadLibrariesView { - library_name: String, - requires_restart: bool, - priority: i32, -} - #[derive(Debug, Clone, Serialize, Deserialize, ToSchema)] pub struct ExtensionView { pub extension_name: String, pub version: String, pub trunk_project_name: String, pub dependencies_extension_names: Option>, - pub loadable_libraries: Option>, - pub configurations: Option>, + pub loadable_libraries: Option>, + pub configurations: Option>, } impl Registry { @@ -360,29 +347,50 @@ impl Registry { } // 5. insert extension configurations - for config in configurations { - sqlx::query!( + self.insert_configurations(extension_version_id, configurations) + .await?; + + // 6. insert shared preload libraries + self.insert_loadable_libraries(extension_version_id, loadable_libraries) + .await?; + } + Ok(()) + } + + async fn insert_configurations( + &self, + extension_version_id: i32, + configurations: impl Iterator, + ) -> Result { + for config in configurations { + sqlx::query!( "INSERT INTO v1.extension_configurations (extension_version_id, is_required, configuration_name, recommended_default_value) VALUES ($1, $2, $3, $4)", extension_version_id, config.is_required, - config.name, - config.recommended_default, + config.configuration_name, + config.recommended_default_value, ).execute(&self.pool).await?; - } + } + Ok(()) + } - // 6. insert shared preload libraries - for library in loadable_libraries { - sqlx::query!( - "INSERT INTO v1.extensions_loadable_libraries (extension_version_id, library_name, requires_restart, priority) - VALUES ($1, $2, $3, $4)", - extension_version_id, - library.library_name, - library.requires_restart, - library.priority, - ).execute(&self.pool).await?; - } + async fn insert_loadable_libraries( + &self, + extension_version_id: i32, + loadable_libraries: impl Iterator, + ) -> Result { + for library in loadable_libraries { + sqlx::query!( + "INSERT INTO v1.extensions_loadable_libraries (extension_version_id, library_name, requires_restart, priority) + VALUES ($1, $2, $3, $4)", + extension_version_id, + library.library_name, + library.requires_restart, + library.priority, + ).execute(&self.pool).await?; } + Ok(()) } } diff --git a/registry/src/views/extension_publish.rs b/registry/src/views/extension_publish.rs index 18a70139..ff5c16f4 100644 --- a/registry/src/views/extension_publish.rs +++ b/registry/src/views/extension_publish.rs @@ -1,7 +1,8 @@ //! This module handles the expected information an extension should have use std::collections::HashMap; -use serde::Deserialize; +use serde::{Deserialize, Serialize}; +use utoipa::ToSchema; pub type SystemDependencies = HashMap>; @@ -17,5 +18,20 @@ pub struct ExtensionUpload { pub repository: Option, pub categories: Option>, pub system_dependencies: Option, - pub libraries: Option>, + pub libraries: Option>, + pub configurations: Option>, +} + +#[derive(Debug, Clone, Serialize, Deserialize, ToSchema)] +pub struct LoadableLibrary { + pub library_name: String, + pub requires_restart: bool, + pub priority: i32, +} + +#[derive(Debug, Clone, Serialize, Deserialize, ToSchema)] +pub struct ExtensionConfiguration { + pub configuration_name: String, + pub is_required: bool, + pub recommended_default_value: Option, } From 3d918cfd56806ffa5de7069a66ff985c3791aca7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Mon, 11 Dec 2023 17:26:29 -0300 Subject: [PATCH 5/9] cli(verify): show line summary after tests (#554) --- cli/Cargo.toml | 2 +- cli/src/commands/verify.rs | 30 +++++++++++++++++++++++++++--- 2 files changed, 28 insertions(+), 4 deletions(-) diff --git a/cli/Cargo.toml b/cli/Cargo.toml index 80d5828e..18bfc223 100644 --- a/cli/Cargo.toml +++ b/cli/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "pg-trunk" -version = "0.11.11" +version = "0.11.12" edition = "2021" authors = ["Steven Miller", "Ian Stanton", "Vinícius Miguel"] description = "A package manager for PostgreSQL extensions" diff --git a/cli/src/commands/verify.rs b/cli/src/commands/verify.rs index fbd471db..32649bee 100644 --- a/cli/src/commands/verify.rs +++ b/cli/src/commands/verify.rs @@ -42,6 +42,12 @@ struct ExtractedTestCases { expected_files: Vec, } +#[derive(Default)] +struct TestSummary { + lines_equal: u32, + lines_differed: u32, +} + async fn extract_sql_and_expected_files( tempdir: &TempDir, github_project: GitHubProject<'_>, @@ -143,6 +149,8 @@ impl SubCommand for VerifyCommand { expected_files, } = extract_sql_and_expected_files(&tempdir, github_project).await?; + let mut summary = TestSummary::default(); + // Now, run every test file with psql and compare its output for expected_file in expected_files { let test_stem = expected_file @@ -168,15 +176,31 @@ impl SubCommand for VerifyCommand { for change in diff.iter_all_changes() { let sign = match change.tag() { - ChangeTag::Delete => "-", - ChangeTag::Insert => "+", - ChangeTag::Equal => " ", + ChangeTag::Delete => { + summary.lines_differed += 1; + "-" + } + ChangeTag::Insert => { + summary.lines_differed += 1; + "+" + } + ChangeTag::Equal => { + summary.lines_equal += 1; + " " + } }; print!("{}{}", sign, change); } } } + println!( + "Summary: {} lines equal, {} lines differed, {} lines total.", + summary.lines_equal, + summary.lines_differed, + summary.lines_equal + summary.lines_differed + ); + Ok(()) } } From 81d628b28ca188829dab65f623ffef97b34ad0ab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Mon, 11 Dec 2023 17:44:48 -0300 Subject: [PATCH 6/9] registry: fix aliases in v1 (#557) --- registry/sqlx-data.json | 122 ++++++++++++------------ registry/src/v1/repository.rs | 8 +- registry/src/views/extension_publish.rs | 2 + 3 files changed, 67 insertions(+), 65 deletions(-) diff --git a/registry/sqlx-data.json b/registry/sqlx-data.json index 69c14aa8..5decdd7e 100644 --- a/registry/sqlx-data.json +++ b/registry/sqlx-data.json @@ -410,26 +410,6 @@ }, "query": "UPDATE versions\n SET updated_at = (now() at time zone 'utc'), license = $1, published_by = $2, extension_name = $5, system_dependencies = $6::jsonb, libraries = $7::jsonb\n WHERE extension_id = $3\n AND num = $4" }, - "33dbfeede4d01448246b1c6741efb4655302625534140ec6be0ecf5e1ed43aa1": { - "describe": { - "columns": [ - { - "name": "result", - "ordinal": 0, - "type_info": "Json" - } - ], - "nullable": [ - null - ], - "parameters": { - "Left": [ - "Text" - ] - } - }, - "query": "SELECT\n json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'version', tpv.version,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'recommended_default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n WHERE\n tpv.trunk_project_name = $1" - }, "36bc3613b2f0f2bf8347edc3ddc1c117a164f45f16195ff92c05f2eb764779bd": { "describe": { "columns": [ @@ -542,27 +522,6 @@ }, "query": "SELECT user_name\n FROM api_tokens\n WHERE\n token = $1" }, - "44f8993884a03b9b1bd8b8197a31fadd834fd4d029d40d4c83a13c0e6a48bc28": { - "describe": { - "columns": [ - { - "name": "result", - "ordinal": 0, - "type_info": "Json" - } - ], - "nullable": [ - null - ], - "parameters": { - "Left": [ - "Text", - "Text" - ] - } - }, - "query": "SELECT json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'version', tpv.version,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'recommended_default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n WHERE\n tpv.trunk_project_name = $1\n AND tpv.version = $2" - }, "49a41631cfe21efe58022e6e4026e6f3d388d8bb12ac478dbf30addab78d430e": { "describe": { "columns": [ @@ -1021,6 +980,24 @@ }, "query": "\n INSERT INTO api_tokens(user_id, user_name, token, created_at)\n VALUES ($1, $2, $3, (now() at time zone 'utc'))\n " }, + "825b6399dd7d3709f5538fce33b71fce462db236e77c7767bdbd1acf69223032": { + "describe": { + "columns": [ + { + "name": "result", + "ordinal": 0, + "type_info": "Json" + } + ], + "nullable": [ + null + ], + "parameters": { + "Left": [] + } + }, + "query": "\n SELECT\n json_build_object(\n 'name', tp.name,\n 'description', latest_tpvs.description,\n 'documentation_link', latest_tpvs.documentation_link,\n 'repository_link', latest_tpvs.repository_link,\n 'version', latest_tpvs.version,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tp.name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = latest_tpvs.id\n )\n ) AS result\n FROM\n v1.trunk_project tp\n JOIN (\n SELECT tpv.*\n FROM v1.trunk_project_versions tpv\n JOIN (\n SELECT trunk_project_name, MAX(string_to_array(version, '.')::int[]) as max_version\n FROM v1.trunk_project_versions\n GROUP BY trunk_project_name\n ) sub_tpv\n ON tpv.trunk_project_name = sub_tpv.trunk_project_name\n AND string_to_array(tpv.version, '.')::int[] = sub_tpv.max_version\n ) latest_tpvs\n ON tp.name = latest_tpvs.trunk_project_name\n ORDER BY tp.name" + }, "8937136b4deb49610728a789a022f48c42064d13df598b8c38a90662443f02ae": { "describe": { "columns": [], @@ -1159,24 +1136,6 @@ }, "query": "SELECT id, repository FROM extensions WHERE extensions.name = $1" }, - "a8a9f2cc263abfb2cb9153fd30854c7aaf6977221746b18ebf45af67baf32768": { - "describe": { - "columns": [ - { - "name": "result", - "ordinal": 0, - "type_info": "Json" - } - ], - "nullable": [ - null - ], - "parameters": { - "Left": [] - } - }, - "query": "\n SELECT\n json_build_object(\n 'name', tp.name,\n 'description', latest_tpvs.description,\n 'documentation_link', latest_tpvs.documentation_link,\n 'repository_link', latest_tpvs.repository_link,\n 'version', latest_tpvs.version,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tp.name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'recommended_default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = latest_tpvs.id\n )\n ) AS result\n FROM\n v1.trunk_project tp\n JOIN (\n SELECT tpv.*\n FROM v1.trunk_project_versions tpv\n JOIN (\n SELECT trunk_project_name, MAX(string_to_array(version, '.')::int[]) as max_version\n FROM v1.trunk_project_versions\n GROUP BY trunk_project_name\n ) sub_tpv\n ON tpv.trunk_project_name = sub_tpv.trunk_project_name\n AND string_to_array(tpv.version, '.')::int[] = sub_tpv.max_version\n ) latest_tpvs\n ON tp.name = latest_tpvs.trunk_project_name\n ORDER BY tp.name" - }, "ac75c8170d5f5bc2fa5c48cdec0ec8899a2cfd1fd679e3656fe95c19650e5bd3": { "describe": { "columns": [ @@ -1288,6 +1247,26 @@ }, "query": "SELECT * FROM versions WHERE extension_id = $1 AND num = $2" }, + "b0e7d9787b9eb5b025d3b237f65acb13cc551a7ef0f2ffae7ed06b73525f4b52": { + "describe": { + "columns": [ + { + "name": "result", + "ordinal": 0, + "type_info": "Json" + } + ], + "nullable": [ + null + ], + "parameters": { + "Left": [ + "Text" + ] + } + }, + "query": "SELECT\n json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'version', tpv.version,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n WHERE\n tpv.trunk_project_name = $1" + }, "bd184a09a0f45acc606a45ef90e0e41c500128881c1284374823f53c978b527d": { "describe": { "columns": [], @@ -1414,6 +1393,26 @@ }, "query": "SELECT * FROM extension_detail_vw" }, + "c8876d5fd044e2a447196117983326ec258304fb0892c016e24e4c78de651e33": { + "describe": { + "columns": [ + { + "name": "result", + "ordinal": 0, + "type_info": "Json" + } + ], + "nullable": [ + null + ], + "parameters": { + "Left": [ + "Text" + ] + } + }, + "query": "SELECT\n json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'version', tpv.version,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n JOIN v1.extension_versions ev ON ev.trunk_project_version_id = tpv.id\n JOIN (\n SELECT extension_name, MAX(string_to_array(version, '.')::int[]) as max_version\n FROM v1.extension_versions\n WHERE extension_name = $1\n GROUP BY extension_name\n ) sub_ev ON ev.extension_name = sub_ev.extension_name AND string_to_array(ev.version, '.')::int[] = sub_ev.max_version\n " + }, "e41ccd0b4b07c1761d78d4de2efdba33979114f1b055db3261af653afca8be56": { "describe": { "columns": [], @@ -1433,7 +1432,7 @@ }, "query": "\n INSERT INTO versions(extension_id, num, created_at, yanked, license, published_by, extension_name, system_dependencies, libraries)\n VALUES ($1, $2, (now() at time zone 'utc'), $3, $4, $5, $6, $7::jsonb, $8::jsonb)\n " }, - "e76de020f649e65247b5b4d24346eddbf53fe5d28cb97e4b96ad27caa800550d": { + "e905022dcb31c2a862579c02b53c7b2e17ad34584eb711eb6d149bbcf4760e26": { "describe": { "columns": [ { @@ -1447,11 +1446,12 @@ ], "parameters": { "Left": [ + "Text", "Text" ] } }, - "query": "SELECT\n json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'version', tpv.version,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'recommended_default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n JOIN v1.extension_versions ev ON ev.trunk_project_version_id = tpv.id\n JOIN (\n SELECT extension_name, MAX(string_to_array(version, '.')::int[]) as max_version\n FROM v1.extension_versions\n WHERE extension_name = $1\n GROUP BY extension_name\n ) sub_ev ON ev.extension_name = sub_ev.extension_name AND string_to_array(ev.version, '.')::int[] = sub_ev.max_version\n " + "query": "SELECT json_build_object(\n 'name', tpv.trunk_project_name,\n 'description', tpv.description,\n 'version', tpv.version,\n 'documentation_link', tpv.documentation_link,\n 'repository_link', tpv.repository_link,\n 'extensions', (\n SELECT json_agg(json_build_object(\n 'extension_name', ev.extension_name,\n 'version', ev.version,\n 'trunk_project_name', tpv.trunk_project_name,\n 'dependencies_extension_names', (\n SELECT json_agg(ed.depends_on_extension_name)\n FROM v1.extension_dependency ed\n WHERE ed.extension_version_id = ev.id\n ),\n 'loadable_libraries', (\n SELECT json_agg(json_build_object(\n 'library_name', ell.library_name,\n 'requires_restart', ell.requires_restart,\n 'priority', ell.priority\n ))\n FROM v1.extensions_loadable_libraries ell\n WHERE ell.extension_version_id = ev.id\n ),\n 'configurations', (\n SELECT json_agg(json_build_object(\n 'name', ec.configuration_name,\n 'is_required', ec.is_required,\n 'default', ec.recommended_default_value\n ))\n FROM v1.extension_configurations ec\n WHERE ec.extension_version_id = ev.id\n )\n ))\n FROM v1.extension_versions ev\n WHERE ev.trunk_project_version_id = tpv.id\n )\n ) AS result\n FROM\n v1.trunk_project_versions tpv\n WHERE\n tpv.trunk_project_name = $1\n AND tpv.version = $2" }, "f29a9769c67e94ef0eb534c3ea009496dc13426c6d46f545ada1f9ebc9def26b": { "describe": { diff --git a/registry/src/v1/repository.rs b/registry/src/v1/repository.rs index 7983eb4c..5f56dc6b 100644 --- a/registry/src/v1/repository.rs +++ b/registry/src/v1/repository.rs @@ -58,7 +58,7 @@ impl Registry { SELECT json_agg(json_build_object( 'name', ec.configuration_name, 'is_required', ec.is_required, - 'recommended_default', ec.recommended_default_value + 'default', ec.recommended_default_value )) FROM v1.extension_configurations ec WHERE ec.extension_version_id = ev.id @@ -127,7 +127,7 @@ impl Registry { SELECT json_agg(json_build_object( 'name', ec.configuration_name, 'is_required', ec.is_required, - 'recommended_default', ec.recommended_default_value + 'default', ec.recommended_default_value )) FROM v1.extension_configurations ec WHERE ec.extension_version_id = ev.id @@ -191,7 +191,7 @@ impl Registry { SELECT json_agg(json_build_object( 'name', ec.configuration_name, 'is_required', ec.is_required, - 'recommended_default', ec.recommended_default_value + 'default', ec.recommended_default_value )) FROM v1.extension_configurations ec WHERE ec.extension_version_id = ev.id @@ -252,7 +252,7 @@ impl Registry { SELECT json_agg(json_build_object( 'name', ec.configuration_name, 'is_required', ec.is_required, - 'recommended_default', ec.recommended_default_value + 'default', ec.recommended_default_value )) FROM v1.extension_configurations ec WHERE ec.extension_version_id = ev.id diff --git a/registry/src/views/extension_publish.rs b/registry/src/views/extension_publish.rs index ff5c16f4..ea42e122 100644 --- a/registry/src/views/extension_publish.rs +++ b/registry/src/views/extension_publish.rs @@ -31,7 +31,9 @@ pub struct LoadableLibrary { #[derive(Debug, Clone, Serialize, Deserialize, ToSchema)] pub struct ExtensionConfiguration { + #[serde(alias = "name")] pub configuration_name: String, pub is_required: bool, + #[serde(alias = "default")] pub recommended_default_value: Option, } From 496a744726e163dbb206438dc99e6ae18bb9e6e6 Mon Sep 17 00:00:00 2001 From: Ian Stanton Date: Mon, 11 Dec 2023 15:50:15 -0500 Subject: [PATCH 7/9] Add PGRX Builder 0.11.1 (#556) --- .github/workflows/builder-images.yml | 25 +++++++++++++------------ cli/src/commands/pgrx.rs | 16 +++++++++++++--- 2 files changed, 26 insertions(+), 15 deletions(-) diff --git a/.github/workflows/builder-images.yml b/.github/workflows/builder-images.yml index 709baa8c..e026b3c7 100644 --- a/.github/workflows/builder-images.yml +++ b/.github/workflows/builder-images.yml @@ -29,18 +29,19 @@ jobs: - "14" - "15" pgrx_version: - - "0.7.4" - - "0.8.0" - - "0.8.3" - - "0.8.4" - - "0.9.0" - - "0.9.1" - - "0.9.7" - - "0.9.8" - - "0.10.0" - - "0.10.1" - - "0.10.2" - - "0.11.0" +# - "0.7.4" +# - "0.8.0" +# - "0.8.3" +# - "0.8.4" +# - "0.9.0" +# - "0.9.1" +# - "0.9.7" +# - "0.9.8" +# - "0.10.0" +# - "0.10.1" +# - "0.10.2" +# - "0.11.0" + - "0.11.1" steps: - name: Check out the repo uses: actions/checkout@v3 diff --git a/cli/src/commands/pgrx.rs b/cli/src/commands/pgrx.rs index c89809d4..8fba0403 100644 --- a/cli/src/commands/pgrx.rs +++ b/cli/src/commands/pgrx.rs @@ -58,8 +58,18 @@ pub enum PgrxBuildError { fn semver_from_range(pgrx_range: &str) -> Result { let versions = [ - "0.11.0", "0.10.2", "0.10.1", "0.10.0", "0.9.8", "0.9.7", "0.9.1", "0.9.0", "0.8.4", - "0.8.3", "0.8.0", "0.7.4", + "0.11.1, 0.11.0", + "0.10.2", + "0.10.1", + "0.10.0", + "0.9.8", + "0.9.7", + "0.9.1", + "0.9.0", + "0.8.4", + "0.8.3", + "0.8.0", + "0.7.4", ]; if versions.contains(&pgrx_range) { @@ -277,7 +287,7 @@ mod tests { assert_eq!(result.unwrap(), "0.8.4"); let result = semver_from_range(">=0.9.0, <0.10.0"); assert_eq!(result.unwrap(), "0.9.8"); - let result = semver_from_range(">=0.10.0, <0.11.0"); + let result = semver_from_range(">=0.10.0, <0.11.1"); assert_eq!(result.unwrap(), "0.10.2"); } } From 91125c697b026e76a4c46b9a3c4b991a27ef70ff Mon Sep 17 00:00:00 2001 From: Ian Stanton Date: Tue, 12 Dec 2023 08:47:34 -0500 Subject: [PATCH 8/9] Bump pg_bm25 to 0.3.12 (#555) --- contrib/pg_bm25/Dockerfile | 8 +++++--- contrib/pg_bm25/Trunk.toml | 2 +- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/contrib/pg_bm25/Dockerfile b/contrib/pg_bm25/Dockerfile index 35e22168..cffa1994 100644 --- a/contrib/pg_bm25/Dockerfile +++ b/contrib/pg_bm25/Dockerfile @@ -1,8 +1,8 @@ ARG PG_VERSION=15 -FROM quay.io/coredb/pgrx-builder:pg${PG_VERSION}-pgrx0.9.7 +FROM quay.io/coredb/pgrx-builder:pg${PG_VERSION}-pgrx0.11.1 USER root -ARG RELEASE=v0.2.21 +ARG RELEASE=v0.3.12 # Extension build dependencies RUN apt-get update && apt-get install -y \ @@ -10,9 +10,11 @@ RUN apt-get update && apt-get install -y \ # Install Rust RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y +RUN cargo install cargo-pgrx --version 0.11.0 --locked # Set default Rust version -RUN /root/.cargo/bin/rustup default stable && /root/.cargo/bin/rustup override set 1.72.0 +RUN /root/.cargo/bin/rustup default stable + # Clone repository RUN git clone https://github.com/paradedb/paradedb.git && \ diff --git a/contrib/pg_bm25/Trunk.toml b/contrib/pg_bm25/Trunk.toml index cec5d511..3f9b29c6 100644 --- a/contrib/pg_bm25/Trunk.toml +++ b/contrib/pg_bm25/Trunk.toml @@ -1,6 +1,6 @@ [extension] name = "pg_bm25" -version = "0.4.0" +version = "0.3.12" repository = "https://github.com/paradedb/paradedb/tree/dev/pg_bm25" license = "AGPL-3.0" description = "Full text search over SQL tables using the state-of-the-art BM25 algorithm" From 6105840496c1757cfcdc79fe03b0d660505f5598 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Miguel?= <36349314+vrmiguel@users.noreply.github.com> Date: Wed, 13 Dec 2023 11:52:01 -0300 Subject: [PATCH 9/9] actions: run extensions tests in CI (#558) --- .github/workflows/extensions.yaml | 26 +++++++++++++++++++++++- .github/workflows/trunk-install-test.yml | 2 +- images/trunk-test-tembo/Dockerfile | 2 +- 3 files changed, 27 insertions(+), 3 deletions(-) diff --git a/.github/workflows/extensions.yaml b/.github/workflows/extensions.yaml index 8c6c4efa..b795900a 100644 --- a/.github/workflows/extensions.yaml +++ b/.github/workflows/extensions.yaml @@ -50,6 +50,30 @@ jobs: changed_relative_to_ref: ${{ steps.versions.outputs.changed_relative_to_ref }} ignore_dirs: ".tembo cli" + test: + name: Test extensions + runs-on: + - self-hosted + - dind + - large-8x8 + container: + image: quay.io/tembo/trunk-test-tembo:0.0.27 + options: --user root + needs: + - find_directories + strategy: + fail-fast: false + matrix: ${{ fromJson(needs.find_directories.outputs.directories) }} + steps: + - uses: actions/checkout@v3.5.3 + - name: Install system dependencies + run: | + set -xe + apt-get update + apt-get install -y pkg-config libssl-dev gosu + - name: Test the extension within Docker + run: cd ${{ matrix.path }} && trunk build --test + build: name: Build extensions runs-on: @@ -57,7 +81,7 @@ jobs: - dind - large-8x8 container: - image: quay.io/tembo/trunk-test-tembo:0.0.26 + image: quay.io/tembo/trunk-test-tembo:0.0.27 options: --user root needs: - find_directories diff --git a/.github/workflows/trunk-install-test.yml b/.github/workflows/trunk-install-test.yml index fbb01e3a..067324f0 100644 --- a/.github/workflows/trunk-install-test.yml +++ b/.github/workflows/trunk-install-test.yml @@ -18,7 +18,7 @@ jobs: - dind - large-8x8 container: - image: quay.io/tembo/trunk-test-tembo:0.0.26 + image: quay.io/tembo/trunk-test-tembo:0.0.27 options: --user root env: PGHOST: "localhost" diff --git a/images/trunk-test-tembo/Dockerfile b/images/trunk-test-tembo/Dockerfile index 1aeac4d7..0cf0819f 100644 --- a/images/trunk-test-tembo/Dockerfile +++ b/images/trunk-test-tembo/Dockerfile @@ -1,4 +1,4 @@ -FROM quay.io/tembo/tembo-pg-cnpg:15.3.0-5-57d5ce4 +FROM quay.io/tembo/tembo-pg-cnpg:15.3.0-5-c9fde12 USER root RUN apt-get update && apt-get install -y \