Merge branch 'main' into v1.4
Signed-off-by: Lann Martin <lann.martin@fermyon.com>
This commit is contained in:
commit
ffb9b07f24
|
@ -93,12 +93,11 @@ runs:
|
|||
using: "composite"
|
||||
steps:
|
||||
- name: Install latest Rust stable toolchain
|
||||
uses: actions-rs/toolchain@v1
|
||||
shell: bash
|
||||
if: ${{ inputs.rust == 'true' }}
|
||||
with:
|
||||
toolchain: ${{ inputs.rust-version }}
|
||||
default: true
|
||||
components: clippy, rustfmt
|
||||
run: |
|
||||
rustup toolchain install ${{ inputs.rust-version }} --component clippy --component rustfmt
|
||||
rustup default ${{ inputs.rust-version }}
|
||||
|
||||
- name: "Install Wasm Rust target"
|
||||
run: rustup target add wasm32-wasi && rustup target add wasm32-unknown-unknown
|
||||
|
|
|
@ -13,6 +13,12 @@ on:
|
|||
- "README.md"
|
||||
- "tests/README.md"
|
||||
|
||||
# Serialize workflow runs per ref
|
||||
# Cancel any outdated, in-flight runs for refs other than 'main'
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.ref }}
|
||||
cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
|
||||
|
||||
env:
|
||||
CARGO_TERM_COLOR: always
|
||||
jobs:
|
||||
|
@ -150,7 +156,8 @@ jobs:
|
|||
run: make test-sdk-go
|
||||
|
||||
e2e-tests:
|
||||
runs-on: ubuntu-22.04
|
||||
# run on a larger runner for more SSD/resource access
|
||||
runs-on: ubuntu-22.04-4core-spin
|
||||
needs: build-rust-ubuntu
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
|
|
|
@ -6,6 +6,12 @@ on:
|
|||
tags:
|
||||
- "v*"
|
||||
|
||||
# Serialize workflow runs
|
||||
concurrency: ${{ github.workflow }}-${{ github.ref }}
|
||||
|
||||
env:
|
||||
RUST_VERSION: 1.68
|
||||
|
||||
jobs:
|
||||
build-and-sign:
|
||||
name: build and sign release assets
|
||||
|
@ -29,7 +35,7 @@ jobs:
|
|||
targetDir: "target/release",
|
||||
}
|
||||
- {
|
||||
os: "ubuntu-latest",
|
||||
os: "ubuntu-20.04",
|
||||
arch: "aarch64",
|
||||
extension: "",
|
||||
extraArgs: "--features openssl/vendored --target aarch64-unknown-linux-gnu",
|
||||
|
@ -85,14 +91,18 @@ jobs:
|
|||
cosign-release: v2.0.0
|
||||
|
||||
- name: Install Rust toolchain
|
||||
uses: actions-rs/toolchain@v1
|
||||
with:
|
||||
toolchain: 1.68
|
||||
default: true
|
||||
target: ${{ matrix.config.target }}
|
||||
shell: bash
|
||||
run: |
|
||||
rustup toolchain install ${{ env.RUST_VERSION }}
|
||||
rustup default ${{ env.RUST_VERSION }}
|
||||
|
||||
- name: Install target
|
||||
if: matrix.config.target != ''
|
||||
shell: bash
|
||||
run: rustup target add --toolchain ${{ env.RUST_VERSION }} ${{ matrix.config.target }}
|
||||
|
||||
- name: "Install Wasm Rust target"
|
||||
run: rustup target add wasm32-wasi --toolchain 1.68 && rustup target add wasm32-unknown-unknown --toolchain 1.68
|
||||
run: rustup target add wasm32-wasi --toolchain ${{ env.RUST_VERSION }} && rustup target add wasm32-unknown-unknown --toolchain ${{ env.RUST_VERSION }}
|
||||
|
||||
- name: setup for cross-compiled linux aarch64 build
|
||||
if: matrix.config.target == 'aarch64-unknown-linux-gnu'
|
||||
|
@ -103,10 +113,8 @@ jobs:
|
|||
echo 'linker = "aarch64-linux-gnu-gcc"' >> ${HOME}/.cargo/config.toml
|
||||
|
||||
- name: build release
|
||||
uses: actions-rs/cargo@v1
|
||||
with:
|
||||
command: build
|
||||
args: "--all-features --release ${{ matrix.config.extraArgs }}"
|
||||
shell: bash
|
||||
run: cargo build --all-features --release ${{ matrix.config.extraArgs }}
|
||||
|
||||
- name: Sign the binary with GitHub OIDC token
|
||||
shell: bash
|
||||
|
|
|
@ -356,9 +356,9 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
|
|||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "2.2.1"
|
||||
version = "2.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "24a6904aef64d73cf10ab17ebace7befb918b82164785cb89907993be7f83813"
|
||||
checksum = "b4682ae6287fcf752ecaabbfcc7b6f9b72aa33933dc23a554d853aea8eea8635"
|
||||
|
||||
[[package]]
|
||||
name = "bitvec"
|
||||
|
@ -1518,6 +1518,12 @@ dependencies = [
|
|||
"instant",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fastrand"
|
||||
version = "2.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6999dc1837253364c2ebb0704ba97994bd874e8f195d665c50b7548f6ea92764"
|
||||
|
||||
[[package]]
|
||||
name = "fd-lock"
|
||||
version = "3.0.12"
|
||||
|
@ -1688,7 +1694,7 @@ version = "1.13.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "49a9d51ce47660b1e808d3c990b4709f2f415d928835a17dfd16991515c46bce"
|
||||
dependencies = [
|
||||
"fastrand",
|
||||
"fastrand 1.9.0",
|
||||
"futures-core",
|
||||
"futures-io",
|
||||
"memchr",
|
||||
|
@ -1753,7 +1759,7 @@ version = "0.6.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "27d12c0aed7f1e24276a241aadc4cb8ea9f83000f34bc062b7cc2d51e3b0fabd"
|
||||
dependencies = [
|
||||
"bitflags 2.2.1",
|
||||
"bitflags 2.4.0",
|
||||
"debugid",
|
||||
"fxhash",
|
||||
"serde",
|
||||
|
@ -1903,7 +1909,7 @@ version = "5.0.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "41b80172055c5d8017a48ddac5cc7a95421c00211047db0165c97853c4f05194"
|
||||
dependencies = [
|
||||
"fastrand",
|
||||
"fastrand 1.9.0",
|
||||
"gix-tempfile",
|
||||
"thiserror",
|
||||
]
|
||||
|
@ -2773,6 +2779,12 @@ version = "0.3.6"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b64f40e5e03e0d54f03845c8197d0291253cdbedfb1cb46b13c2c117554a9f4c"
|
||||
|
||||
[[package]]
|
||||
name = "linux-raw-sys"
|
||||
version = "0.4.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "57bcfdad1b858c2db7c38303a6d2ad4dfaf5eb53dfeb0910128b2c26d6158503"
|
||||
|
||||
[[package]]
|
||||
name = "liquid"
|
||||
version = "0.23.1"
|
||||
|
@ -3322,9 +3334,9 @@ checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5"
|
|||
|
||||
[[package]]
|
||||
name = "openssl"
|
||||
version = "0.10.48"
|
||||
version = "0.10.55"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "518915b97df115dd36109bfa429a48b8f737bd05508cf9588977b599648926d2"
|
||||
checksum = "345df152bc43501c5eb9e4654ff05f794effb78d4efe3d53abc158baddc0703d"
|
||||
dependencies = [
|
||||
"bitflags 1.3.2",
|
||||
"cfg-if",
|
||||
|
@ -3354,11 +3366,10 @@ checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf"
|
|||
|
||||
[[package]]
|
||||
name = "openssl-sys"
|
||||
version = "0.9.83"
|
||||
version = "0.9.90"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "666416d899cf077260dac8698d60a60b435a46d57e82acb1be3d0dad87284e5b"
|
||||
checksum = "374533b0e45f3a7ced10fcaeccca020e66656bc03dac384f852e4e5a7a8104a6"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"cc",
|
||||
"libc",
|
||||
"pkg-config",
|
||||
|
@ -4166,7 +4177,7 @@ version = "0.29.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "549b9d036d571d42e6e85d1c1425e2ac83491075078ca9a15be021c56b1641f2"
|
||||
dependencies = [
|
||||
"bitflags 2.2.1",
|
||||
"bitflags 2.4.0",
|
||||
"fallible-iterator",
|
||||
"fallible-streaming-iterator",
|
||||
"hashlink",
|
||||
|
@ -4259,6 +4270,19 @@ dependencies = [
|
|||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustix"
|
||||
version = "0.38.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ac5ffa1efe7548069688cd7028f32591853cd7b5b756d41bcffd2353e4fc75b4"
|
||||
dependencies = [
|
||||
"bitflags 2.4.0",
|
||||
"errno 0.3.1",
|
||||
"libc",
|
||||
"linux-raw-sys 0.4.5",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls"
|
||||
version = "0.20.8"
|
||||
|
@ -5467,15 +5491,15 @@ checksum = "8ae9980cab1db3fceee2f6c6f643d5d8de2997c58ee8d25fb0cc8a9e9e7348e5"
|
|||
|
||||
[[package]]
|
||||
name = "tempfile"
|
||||
version = "3.5.0"
|
||||
version = "3.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b9fbec84f381d5795b08656e4912bec604d162bff9291d6189a78f4c8ab87998"
|
||||
checksum = "cb94d2f3cc536af71caac6b6fcebf65860b347e7ce0cc9ebe8f70d3e521054ef"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"fastrand",
|
||||
"fastrand 2.0.0",
|
||||
"redox_syscall 0.3.5",
|
||||
"rustix 0.37.20",
|
||||
"windows-sys 0.45.0",
|
||||
"rustix 0.38.3",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -7013,7 +7037,7 @@ version = "0.8.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "392d16e9e46cc7ca98125bc288dd5e4db469efe8323d3e0dac815ca7f2398522"
|
||||
dependencies = [
|
||||
"bitflags 2.2.1",
|
||||
"bitflags 2.4.0",
|
||||
"wit-bindgen-rust-macro",
|
||||
]
|
||||
|
||||
|
|
|
@ -61,7 +61,7 @@ spin-plugins = { path = "crates/plugins" }
|
|||
spin-redis-engine = { path = "crates/redis" }
|
||||
spin-templates = { path = "crates/templates" }
|
||||
spin-trigger = { path = "crates/trigger" }
|
||||
tempfile = "3.3.0"
|
||||
tempfile = "3.8.0"
|
||||
tokio = { version = "1.23", features = ["full"] }
|
||||
toml = "0.6"
|
||||
tracing = { workspace = true }
|
||||
|
|
47
build.rs
47
build.rs
|
@ -115,7 +115,17 @@ fn has_wasm32_wasi_target() -> bool {
|
|||
|
||||
fn cargo_build(dir: &str) {
|
||||
run(
|
||||
vec!["cargo", "build", "--target", "wasm32-wasi", "--release"],
|
||||
vec![
|
||||
"cargo",
|
||||
"build",
|
||||
"--target",
|
||||
"wasm32-wasi",
|
||||
"--release",
|
||||
// Ensure that even if `CARGO_TARGET_DIR` is set
|
||||
// that we're still building into the right dir.
|
||||
"--target-dir",
|
||||
"./target",
|
||||
],
|
||||
Some(dir),
|
||||
None,
|
||||
);
|
||||
|
@ -130,8 +140,9 @@ fn run<S: Into<String> + AsRef<std::ffi::OsStr>>(
|
|||
cmd.stdout(process::Stdio::piped());
|
||||
cmd.stderr(process::Stdio::piped());
|
||||
|
||||
if let Some(dir) = dir {
|
||||
cmd.current_dir(dir.into());
|
||||
let dir = dir.map(Into::into);
|
||||
if let Some(dir) = &dir {
|
||||
cmd.current_dir(dir);
|
||||
};
|
||||
|
||||
if let Some(env) = env {
|
||||
|
@ -141,20 +152,20 @@ fn run<S: Into<String> + AsRef<std::ffi::OsStr>>(
|
|||
};
|
||||
|
||||
cmd.arg("-c");
|
||||
cmd.arg(
|
||||
args.into_iter()
|
||||
.map(Into::into)
|
||||
.collect::<Vec<String>>()
|
||||
.join(" "),
|
||||
);
|
||||
let c = args
|
||||
.into_iter()
|
||||
.map(Into::into)
|
||||
.collect::<Vec<String>>()
|
||||
.join(" ");
|
||||
cmd.arg(&c);
|
||||
|
||||
let output = cmd.output().unwrap();
|
||||
let code = output.status.code().unwrap();
|
||||
if code != 0 {
|
||||
println!("{:#?}", std::str::from_utf8(&output.stderr).unwrap());
|
||||
println!("{:#?}", std::str::from_utf8(&output.stdout).unwrap());
|
||||
// just fail
|
||||
assert_eq!(0, code);
|
||||
let exit = output.status;
|
||||
if !exit.success() {
|
||||
println!("{}", std::str::from_utf8(&output.stderr).unwrap());
|
||||
println!("{}", std::str::from_utf8(&output.stdout).unwrap());
|
||||
let dir = dir.unwrap_or_else(current_dir);
|
||||
panic!("while running the build script, the command '{c}' failed to run in '{dir}'")
|
||||
}
|
||||
|
||||
output
|
||||
|
@ -167,3 +178,9 @@ fn get_os_process() -> String {
|
|||
String::from("bash")
|
||||
}
|
||||
}
|
||||
|
||||
fn current_dir() -> String {
|
||||
std::env::current_dir()
|
||||
.map(|d| d.display().to_string())
|
||||
.unwrap_or_else(|_| String::from("<CURRENT DIR>"))
|
||||
}
|
||||
|
|
|
@ -174,7 +174,7 @@ impl<'a, L: MaybeLoader> App<'a, L> {
|
|||
&'this self,
|
||||
key: MetadataKey<T>,
|
||||
) -> Result<Option<T>> {
|
||||
self.locked.metadata.get_typed(key)
|
||||
self.locked.get_metadata(key)
|
||||
}
|
||||
|
||||
/// Deserializes typed metadata for this app.
|
||||
|
@ -185,7 +185,7 @@ impl<'a, L: MaybeLoader> App<'a, L> {
|
|||
&'this self,
|
||||
key: MetadataKey<T>,
|
||||
) -> Result<T> {
|
||||
self.locked.metadata.require_typed(key)
|
||||
self.locked.require_metadata(key)
|
||||
}
|
||||
|
||||
/// Returns an iterator of custom config [`Variable`]s defined for this app.
|
||||
|
|
|
@ -5,7 +5,7 @@ use std::path::PathBuf;
|
|||
use serde::{Deserialize, Serialize};
|
||||
use serde_json::Value;
|
||||
|
||||
use crate::values::ValuesMap;
|
||||
use crate::{metadata::MetadataExt, values::ValuesMap};
|
||||
|
||||
/// A String-keyed map with deterministic serialization order.
|
||||
pub type LockedMap<T> = std::collections::BTreeMap<String, T>;
|
||||
|
@ -37,6 +37,29 @@ impl LockedApp {
|
|||
pub fn to_json(&self) -> serde_json::Result<Vec<u8>> {
|
||||
serde_json::to_vec_pretty(&self)
|
||||
}
|
||||
|
||||
/// Deserializes typed metadata for this app.
|
||||
///
|
||||
/// Returns `Ok(None)` if there is no metadata for the given `key` and an
|
||||
/// `Err` only if there _is_ a value for the `key` but the typed
|
||||
/// deserialization failed.
|
||||
pub fn get_metadata<'this, T: Deserialize<'this>>(
|
||||
&'this self,
|
||||
key: crate::MetadataKey<T>,
|
||||
) -> crate::Result<Option<T>> {
|
||||
self.metadata.get_typed(key)
|
||||
}
|
||||
|
||||
/// Deserializes typed metadata for this app.
|
||||
///
|
||||
/// Like [`LockedApp::get_metadata`], but returns an error if there is
|
||||
/// no metadata for the given `key`.
|
||||
pub fn require_metadata<'this, T: Deserialize<'this>>(
|
||||
&'this self,
|
||||
key: crate::MetadataKey<T>,
|
||||
) -> crate::Result<T> {
|
||||
self.metadata.require_typed(key)
|
||||
}
|
||||
}
|
||||
|
||||
/// A LockedComponent represents a "fully resolved" Spin component.
|
||||
|
|
|
@ -153,7 +153,9 @@ impl TestCase {
|
|||
}
|
||||
|
||||
// run spin build
|
||||
let build_output = controller.build_app(&appname).context("building app")?;
|
||||
let build_output = controller
|
||||
.build_app(&appname)
|
||||
.context("failed building app")?;
|
||||
if bail_on_run_failure {
|
||||
utils::assert_success(&build_output);
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
pub mod app_info;
|
||||
pub mod config;
|
||||
pub mod routes;
|
||||
pub mod trigger;
|
||||
pub mod wagi;
|
||||
|
||||
pub const WELL_KNOWN_PREFIX: &str = "/.well-known/spin/";
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
use serde::{Deserialize, Serialize};
|
||||
use spin_app::MetadataKey;
|
||||
|
||||
/// Http trigger metadata key
|
||||
pub const METADATA_KEY: MetadataKey<Metadata> = MetadataKey::new("trigger");
|
||||
|
||||
#[derive(Clone, Debug, Default, Deserialize, Serialize)]
|
||||
#[serde(deny_unknown_fields)]
|
||||
pub struct Metadata {
|
||||
// The type of trigger which should always been "http" in this case
|
||||
pub r#type: String,
|
||||
// The based url
|
||||
pub base: String,
|
||||
}
|
|
@ -23,7 +23,7 @@ impl TryFrom<RawVariable> for Variable {
|
|||
fn try_from(var: RawVariable) -> Result<Self, Self::Error> {
|
||||
ensure!(
|
||||
var.required ^ var.default.is_some(),
|
||||
"variable has both `required` and `default` set"
|
||||
"variable should either have `required` set to true OR have a non-empty default value"
|
||||
);
|
||||
Ok(Variable {
|
||||
default: var.default,
|
||||
|
|
|
@ -167,7 +167,13 @@ async fn prepare(
|
|||
let variables = raw
|
||||
.variables
|
||||
.into_iter()
|
||||
.map(|(key, var)| Ok((key, var.try_into()?)))
|
||||
.map(|(key, var)| {
|
||||
Ok((
|
||||
key.clone(),
|
||||
var.try_into()
|
||||
.map_err(|err| anyhow!("variable '{}': {}", key, err))?,
|
||||
))
|
||||
})
|
||||
.collect::<Result<_>>()?;
|
||||
|
||||
Ok(Application {
|
||||
|
|
|
@ -7,14 +7,14 @@ edition = { workspace = true }
|
|||
[dependencies]
|
||||
anyhow = "1.0"
|
||||
bytes = "1.1"
|
||||
chrono = "0.4"
|
||||
chrono = { version = "0.4", features = ["serde"] }
|
||||
dirs = "4.0"
|
||||
fd-lock = "3.0.12"
|
||||
flate2 = { version = "1.0.17", features = ["zlib-ng"], default-features = false }
|
||||
is-terminal = "0.4"
|
||||
path-absolutize = "3.0.11"
|
||||
reqwest = { version = "0.11", features = ["json"] }
|
||||
semver = "1.0"
|
||||
semver = { version = "1.0", features = ["serde"] }
|
||||
serde = { version = "1.0", features = ["derive"] }
|
||||
serde_json = "1.0"
|
||||
spin-common = { path = "../common" }
|
||||
|
@ -24,4 +24,4 @@ terminal = { path = "../terminal" }
|
|||
thiserror = "1"
|
||||
tokio = { version = "1.23", features = [ "fs", "process", "rt", "macros" ] }
|
||||
tracing = { workspace = true }
|
||||
url = "2.2.2"
|
||||
url = { version = "2.2.2", features = ["serde"] }
|
||||
|
|
|
@ -170,7 +170,7 @@ impl BadgerEvaluator {
|
|||
let latest_version = {
|
||||
let latest_lookup = crate::lookup::PluginLookup::new(&self.plugin_name, None);
|
||||
let latest_manifest = latest_lookup
|
||||
.get_manifest_from_repository(store.get_plugins_directory())
|
||||
.resolve_manifest_exact(store.get_plugins_directory())
|
||||
.await
|
||||
.ok();
|
||||
latest_manifest.and_then(|m| semver::Version::parse(m.version()).ok())
|
||||
|
|
|
@ -14,6 +14,9 @@ pub enum Error {
|
|||
|
||||
#[error("URL parse error {0}")]
|
||||
UrlParseError(#[from] url::ParseError),
|
||||
|
||||
#[error("{0}")]
|
||||
Other(#[from] anyhow::Error),
|
||||
}
|
||||
|
||||
/// Contains error details for when a plugin resource cannot be found at expected location
|
||||
|
|
|
@ -30,7 +30,34 @@ impl PluginLookup {
|
|||
}
|
||||
}
|
||||
|
||||
pub async fn get_manifest_from_repository(
|
||||
pub async fn resolve_manifest(
|
||||
&self,
|
||||
plugins_dir: &Path,
|
||||
skip_compatibility_check: bool,
|
||||
spin_version: &str,
|
||||
) -> PluginLookupResult<PluginManifest> {
|
||||
let exact = self.resolve_manifest_exact(plugins_dir).await?;
|
||||
if skip_compatibility_check
|
||||
|| self.version.is_some()
|
||||
|| exact.is_compatible_spin_version(spin_version)
|
||||
{
|
||||
return Ok(exact);
|
||||
}
|
||||
|
||||
let store = crate::store::PluginStore::new(plugins_dir.to_owned());
|
||||
|
||||
// TODO: This is very similar to some logic in the badger module - look for consolidation opportunities.
|
||||
let manifests = store.catalogue_manifests()?;
|
||||
let relevant_manifests = manifests.into_iter().filter(|m| m.name() == self.name);
|
||||
let compatible_manifests = relevant_manifests
|
||||
.filter(|m| m.has_compatible_package() && m.is_compatible_spin_version(spin_version));
|
||||
let highest_compatible_manifest =
|
||||
compatible_manifests.max_by_key(|m| m.try_version().unwrap_or_else(|_| null_version()));
|
||||
|
||||
Ok(highest_compatible_manifest.unwrap_or(exact))
|
||||
}
|
||||
|
||||
pub async fn resolve_manifest_exact(
|
||||
&self,
|
||||
plugins_dir: &Path,
|
||||
) -> PluginLookupResult<PluginManifest> {
|
||||
|
@ -41,22 +68,48 @@ impl PluginLookup {
|
|||
.map_err(|e| {
|
||||
Error::ConnectionFailed(ConnectionFailedError::new(url.to_string(), e.to_string()))
|
||||
})?;
|
||||
|
||||
self.resolve_manifest_exact_from_good_repo(plugins_dir)
|
||||
}
|
||||
|
||||
// This is split from resolve_manifest_exact because it may recurse (once) and that makes
|
||||
// Rust async sad. So we move the potential recursion to a sync helper.
|
||||
#[allow(clippy::let_and_return)]
|
||||
pub fn resolve_manifest_exact_from_good_repo(
|
||||
&self,
|
||||
plugins_dir: &Path,
|
||||
) -> PluginLookupResult<PluginManifest> {
|
||||
let expected_path = spin_plugins_repo_manifest_path(&self.name, &self.version, plugins_dir);
|
||||
let file = File::open(&expected_path).map_err(|e| {
|
||||
Error::NotFound(NotFoundError::new(
|
||||
|
||||
let not_found = |e: std::io::Error| {
|
||||
Err(Error::NotFound(NotFoundError::new(
|
||||
Some(self.name.clone()),
|
||||
expected_path.display().to_string(),
|
||||
e.to_string(),
|
||||
))
|
||||
})?;
|
||||
let manifest: PluginManifest = serde_json::from_reader(file).map_err(|e| {
|
||||
Error::InvalidManifest(InvalidManifestError::new(
|
||||
Some(self.name.clone()),
|
||||
expected_path.display().to_string(),
|
||||
e.to_string(),
|
||||
))
|
||||
})?;
|
||||
Ok(manifest)
|
||||
)))
|
||||
};
|
||||
|
||||
let manifest = match File::open(&expected_path) {
|
||||
Ok(file) => serde_json::from_reader(file).map_err(|e| {
|
||||
Error::InvalidManifest(InvalidManifestError::new(
|
||||
Some(self.name.clone()),
|
||||
expected_path.display().to_string(),
|
||||
e.to_string(),
|
||||
))
|
||||
}),
|
||||
Err(e) if e.kind() == std::io::ErrorKind::NotFound && self.version.is_some() => {
|
||||
// If a user has asked for a version by number, and the path doesn't exist,
|
||||
// it _might_ be because it's the latest version. This checks for that case.
|
||||
let latest = Self::new(&self.name, None);
|
||||
match latest.resolve_manifest_exact_from_good_repo(plugins_dir) {
|
||||
Ok(manifest) if manifest.try_version().ok() == self.version => Ok(manifest),
|
||||
_ => not_found(e),
|
||||
}
|
||||
}
|
||||
Err(e) => not_found(e),
|
||||
};
|
||||
|
||||
manifest
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -64,6 +117,16 @@ pub fn plugins_repo_url() -> Result<Url, url::ParseError> {
|
|||
Url::parse(SPIN_PLUGINS_REPO)
|
||||
}
|
||||
|
||||
#[cfg(not(test))]
|
||||
fn accept_as_repo(git_root: &Path) -> bool {
|
||||
git_root.join(".git").exists()
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
fn accept_as_repo(git_root: &Path) -> bool {
|
||||
git_root.join(".git").exists() || git_root.join("_spin_test_dot_git").exists()
|
||||
}
|
||||
|
||||
pub async fn fetch_plugins_repo(
|
||||
repo_url: &Url,
|
||||
plugins_dir: &Path,
|
||||
|
@ -71,7 +134,7 @@ pub async fn fetch_plugins_repo(
|
|||
) -> anyhow::Result<()> {
|
||||
let git_root = plugin_manifests_repo_path(plugins_dir);
|
||||
let git_source = GitSource::new(repo_url, None, &git_root);
|
||||
if git_root.join(".git").exists() {
|
||||
if accept_as_repo(&git_root) {
|
||||
if update {
|
||||
git_source.pull().await?;
|
||||
}
|
||||
|
@ -110,3 +173,83 @@ pub fn spin_plugins_repo_manifest_dir(plugins_dir: &Path) -> PathBuf {
|
|||
.join(PLUGINS_REPO_LOCAL_DIRECTORY)
|
||||
.join(PLUGINS_REPO_MANIFESTS_DIRECTORY)
|
||||
}
|
||||
|
||||
fn null_version() -> semver::Version {
|
||||
semver::Version::new(0, 0, 0)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
const TEST_NAME: &str = "some-spin-ver-some-not";
|
||||
const TESTS_STORE_DIR: &str = "tests";
|
||||
|
||||
fn tests_store_dir() -> PathBuf {
|
||||
PathBuf::from(env!("CARGO_MANIFEST_DIR")).join(TESTS_STORE_DIR)
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_no_version_given_and_latest_is_compatible_then_latest() -> PluginLookupResult<()> {
|
||||
let lookup = PluginLookup::new(TEST_NAME, None);
|
||||
let resolved = lookup
|
||||
.resolve_manifest(&tests_store_dir(), false, "99.0.0")
|
||||
.await?;
|
||||
assert_eq!("99.0.1", resolved.version);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_no_version_given_and_latest_is_not_compatible_then_highest_compatible(
|
||||
) -> PluginLookupResult<()> {
|
||||
// NOTE: The setup assumes you are NOT running Windows on aarch64, so as to check 98.1.0 is not
|
||||
// offered. If that assumption fails then this test will fail with actual version being 98.1.0.
|
||||
// (We use this combination because the OS and architecture enums don't allow for fake operating systems!)
|
||||
let lookup = PluginLookup::new(TEST_NAME, None);
|
||||
let resolved = lookup
|
||||
.resolve_manifest(&tests_store_dir(), false, "98.0.0")
|
||||
.await?;
|
||||
assert_eq!("98.0.0", resolved.version);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_version_given_it_gets_used_regardless() -> PluginLookupResult<()> {
|
||||
let lookup = PluginLookup::new(TEST_NAME, Some(semver::Version::parse("99.0.0").unwrap()));
|
||||
let resolved = lookup
|
||||
.resolve_manifest(&tests_store_dir(), false, "98.0.0")
|
||||
.await?;
|
||||
assert_eq!("99.0.0", resolved.version);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_latest_version_given_it_gets_used_regardless() -> PluginLookupResult<()> {
|
||||
let lookup = PluginLookup::new(TEST_NAME, Some(semver::Version::parse("99.0.1").unwrap()));
|
||||
let resolved = lookup
|
||||
.resolve_manifest(&tests_store_dir(), false, "98.0.0")
|
||||
.await?;
|
||||
assert_eq!("99.0.1", resolved.version);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_no_version_given_but_skip_compat_then_highest() -> PluginLookupResult<()> {
|
||||
let lookup = PluginLookup::new(TEST_NAME, None);
|
||||
let resolved = lookup
|
||||
.resolve_manifest(&tests_store_dir(), true, "98.0.0")
|
||||
.await?;
|
||||
assert_eq!("99.0.1", resolved.version);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn if_non_existent_version_given_then_error() -> PluginLookupResult<()> {
|
||||
let lookup = PluginLookup::new(TEST_NAME, Some(semver::Version::parse("177.7.7").unwrap()));
|
||||
lookup
|
||||
.resolve_manifest(&tests_store_dir(), true, "99.0.0")
|
||||
.await
|
||||
.expect_err("Should have errored because plugin v177.7.7 does not exist");
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,7 +6,7 @@ use crate::{
|
|||
SPIN_INTERNAL_COMMANDS,
|
||||
};
|
||||
|
||||
use anyhow::{anyhow, bail, Result};
|
||||
use anyhow::{anyhow, bail, Context, Result};
|
||||
use path_absolutize::Absolutize;
|
||||
use serde::Serialize;
|
||||
use spin_common::sha256;
|
||||
|
@ -93,15 +93,26 @@ impl PluginManager {
|
|||
let target_url = Url::parse(&target)?;
|
||||
let temp_dir = tempdir()?;
|
||||
let plugin_tarball_path = match target_url.scheme() {
|
||||
URL_FILE_SCHEME => target_url
|
||||
.to_file_path()
|
||||
.map_err(|_| anyhow!("Invalid file URL: {target_url:?}"))?,
|
||||
URL_FILE_SCHEME => {
|
||||
let path = target_url
|
||||
.to_file_path()
|
||||
.map_err(|_| anyhow!("Invalid file URL: {target_url:?}"))?;
|
||||
if path.is_file() {
|
||||
path
|
||||
} else {
|
||||
bail!(
|
||||
"Package path {} does not exist or is not a file",
|
||||
path.display()
|
||||
);
|
||||
}
|
||||
}
|
||||
_ => download_plugin(&plugin_manifest.name(), &temp_dir, &target).await?,
|
||||
};
|
||||
verify_checksum(&plugin_tarball_path, &plugin_package.sha256)?;
|
||||
|
||||
self.store
|
||||
.untar_plugin(&plugin_tarball_path, &plugin_manifest.name())?;
|
||||
.untar_plugin(&plugin_tarball_path, &plugin_manifest.name())
|
||||
.with_context(|| format!("Failed to untar {}", plugin_tarball_path.display()))?;
|
||||
|
||||
// Save manifest to installed plugins directory
|
||||
self.store.add_manifest(plugin_manifest)?;
|
||||
|
@ -173,6 +184,8 @@ impl PluginManager {
|
|||
pub async fn get_manifest(
|
||||
&self,
|
||||
manifest_location: &ManifestLocation,
|
||||
skip_compatibility_check: bool,
|
||||
spin_version: &str,
|
||||
) -> PluginLookupResult<PluginManifest> {
|
||||
let plugin_manifest = match manifest_location {
|
||||
ManifestLocation::Remote(url) => {
|
||||
|
@ -221,7 +234,11 @@ impl PluginManager {
|
|||
}
|
||||
ManifestLocation::PluginsRepository(lookup) => {
|
||||
lookup
|
||||
.get_manifest_from_repository(self.store().get_plugins_directory())
|
||||
.resolve_manifest(
|
||||
self.store().get_plugins_directory(),
|
||||
skip_compatibility_check,
|
||||
spin_version,
|
||||
)
|
||||
.await?
|
||||
}
|
||||
};
|
||||
|
@ -338,7 +355,8 @@ async fn download_plugin(name: &str, temp_dir: &TempDir, target_url: &str) -> Re
|
|||
}
|
||||
|
||||
fn verify_checksum(plugin_file: &Path, expected_sha256: &str) -> Result<()> {
|
||||
let actual_sha256 = sha256::hex_digest_from_file(plugin_file)?;
|
||||
let actual_sha256 = sha256::hex_digest_from_file(plugin_file)
|
||||
.with_context(|| format!("Cannot get digest for {}", plugin_file.display()))?;
|
||||
if actual_sha256 == expected_sha256 {
|
||||
log::info!("Package checksum verified successfully");
|
||||
Ok(())
|
||||
|
|
|
@ -64,6 +64,10 @@ impl PluginManifest {
|
|||
Err(_) => false,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn try_version(&self) -> Result<semver::Version, semver::Error> {
|
||||
semver::Version::parse(&self.version)
|
||||
}
|
||||
}
|
||||
|
||||
/// Describes compatibility and location of a plugin source.
|
||||
|
|
|
@ -0,0 +1 @@
|
|||
Fake file for preventing the plugin system from pulling from the production repo into this directory during tests
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "99.0.1",
|
||||
"spinCompatibility": ">=99.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "98.0.0",
|
||||
"spinCompatibility": ">=98.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "98.1.0",
|
||||
"spinCompatibility": ">=98.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "windows",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "99.0.0",
|
||||
"spinCompatibility": ">=99.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "99.0.1",
|
||||
"spinCompatibility": ">=99.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "98.0.0",
|
||||
"spinCompatibility": ">=98.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "98.1.0",
|
||||
"spinCompatibility": ">=98.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "windows",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"name": "some-spin-ver-some-not",
|
||||
"description": "A plugin where only some versions work with the test harness version of Spin.",
|
||||
"version": "99.0.0",
|
||||
"spinCompatibility": ">=99.0",
|
||||
"license": "Apache-2.0",
|
||||
"packages": [
|
||||
{
|
||||
"os": "linux",
|
||||
"arch": "amd64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
},
|
||||
{
|
||||
"os": "macos",
|
||||
"arch": "aarch64",
|
||||
"url": "https://example.com/doesnt-exist",
|
||||
"sha256": "11111111"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -24,3 +24,6 @@ pub use manager::*;
|
|||
pub use run::{Run, RunOptions};
|
||||
pub use source::TemplateSource;
|
||||
pub use template::{Template, TemplateVariantInfo};
|
||||
|
||||
#[cfg(test)]
|
||||
mod test_built_ins;
|
||||
|
|
|
@ -107,7 +107,11 @@ impl TemplateManager {
|
|||
/// Creates a `TemplateManager` for the default install location.
|
||||
pub fn try_default() -> anyhow::Result<Self> {
|
||||
let store = TemplateStore::try_default()?;
|
||||
Ok(Self { store })
|
||||
Ok(Self::new(store))
|
||||
}
|
||||
|
||||
pub(crate) fn new(store: TemplateStore) -> Self {
|
||||
Self { store }
|
||||
}
|
||||
|
||||
/// Installs templates from the specified source.
|
||||
|
|
|
@ -0,0 +1,73 @@
|
|||
#![cfg(test)]
|
||||
|
||||
// Module for unit-testing the built-in templates when a full e2e test would be overkill.
|
||||
// If your test involves invoking the Spin CLI, or builds or runs an application, use
|
||||
// an e2e test.
|
||||
|
||||
use std::{collections::HashMap, path::PathBuf};
|
||||
|
||||
use super::*;
|
||||
|
||||
struct DiscardingReporter;
|
||||
|
||||
impl ProgressReporter for DiscardingReporter {
|
||||
fn report(&self, _: impl AsRef<str>) {}
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn add_fileserver_does_not_create_dir() -> anyhow::Result<()> {
|
||||
let built_ins_dir = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("../..");
|
||||
let built_ins_src = TemplateSource::File(built_ins_dir);
|
||||
|
||||
let store_dir = tempfile::tempdir()?;
|
||||
let store = store::TemplateStore::new(store_dir.path());
|
||||
let manager = TemplateManager::new(store);
|
||||
|
||||
manager
|
||||
.install(
|
||||
&built_ins_src,
|
||||
&InstallOptions::default(),
|
||||
&DiscardingReporter,
|
||||
)
|
||||
.await?;
|
||||
|
||||
let app_dir = tempfile::tempdir()?;
|
||||
|
||||
// Create an app to add the fileserver into
|
||||
let new_empty_options = RunOptions {
|
||||
variant: TemplateVariantInfo::NewApplication,
|
||||
name: "add-fs-dir-test".to_owned(),
|
||||
output_path: app_dir.path().to_owned(),
|
||||
values: HashMap::new(),
|
||||
accept_defaults: true,
|
||||
};
|
||||
manager
|
||||
.get("http-empty")?
|
||||
.expect("http-empty template should exist")
|
||||
.run(new_empty_options)
|
||||
.silent()
|
||||
.await?;
|
||||
|
||||
// Add the fileserver to that app
|
||||
let manifest_path = app_dir.path().join("spin.toml");
|
||||
let add_fs_options = RunOptions {
|
||||
variant: TemplateVariantInfo::AddComponent { manifest_path },
|
||||
name: "fs".to_owned(),
|
||||
output_path: app_dir.path().join("fs"),
|
||||
values: HashMap::new(),
|
||||
accept_defaults: true,
|
||||
};
|
||||
manager
|
||||
.get("static-fileserver")?
|
||||
.expect("static-fileserver template should exist")
|
||||
.run(add_fs_options)
|
||||
.silent()
|
||||
.await?;
|
||||
|
||||
// Finally!
|
||||
assert!(
|
||||
!app_dir.path().join("fs").exists(),
|
||||
"<app_dir>/fs should not have been created"
|
||||
);
|
||||
Ok(())
|
||||
}
|
|
@ -75,7 +75,6 @@ fn color_choice(stream: atty::Stream) -> termcolor::ColorChoice {
|
|||
#[macro_export]
|
||||
macro_rules! step {
|
||||
($step:expr, $($arg:tt)*) => {{
|
||||
|
||||
$crate::cprint!($crate::colors::bold_green(), $step);
|
||||
print!(" ");
|
||||
println!($($arg)*);
|
||||
|
|
|
@ -23,8 +23,7 @@ use hyper::{
|
|||
service::{make_service_fn, service_fn},
|
||||
Body, Request, Response, Server,
|
||||
};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use spin_app::{AppComponent, MetadataKey};
|
||||
use spin_app::AppComponent;
|
||||
use spin_core::Engine;
|
||||
use spin_http::{
|
||||
app_info::AppInfo,
|
||||
|
@ -44,8 +43,6 @@ pub use tls::TlsConfig;
|
|||
pub(crate) type RuntimeData = ();
|
||||
pub(crate) type Store = spin_core::Store<RuntimeData>;
|
||||
|
||||
const TRIGGER_METADATA_KEY: MetadataKey<TriggerMetadata> = MetadataKey::new("trigger");
|
||||
|
||||
/// The Spin HTTP trigger.
|
||||
pub struct HttpTrigger {
|
||||
engine: TriggerAppEngine<Self>,
|
||||
|
@ -84,13 +81,6 @@ impl CliArgs {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, Default, Deserialize, Serialize)]
|
||||
#[serde(deny_unknown_fields)]
|
||||
struct TriggerMetadata {
|
||||
r#type: String,
|
||||
base: String,
|
||||
}
|
||||
|
||||
#[async_trait]
|
||||
impl TriggerExecutor for HttpTrigger {
|
||||
const TRIGGER_TYPE: &'static str = "http";
|
||||
|
@ -99,7 +89,10 @@ impl TriggerExecutor for HttpTrigger {
|
|||
type RunConfig = CliArgs;
|
||||
|
||||
async fn new(engine: TriggerAppEngine<Self>) -> Result<Self> {
|
||||
let base = engine.app().require_metadata(TRIGGER_METADATA_KEY)?.base;
|
||||
let base = engine
|
||||
.app()
|
||||
.require_metadata(spin_http::trigger::METADATA_KEY)?
|
||||
.base;
|
||||
|
||||
let component_routes = engine
|
||||
.trigger_configs()
|
||||
|
@ -174,17 +167,11 @@ impl TriggerExecutor for HttpTrigger {
|
|||
if let Some(HttpExecutorType::Wagi(_)) = &config.executor {
|
||||
let module = component.load_module(engine).await?;
|
||||
Ok(EitherInstancePre::Module(
|
||||
engine
|
||||
.module_instantiate_pre(&module)
|
||||
.map_err(spin_trigger::decode_preinstantiation_error)?,
|
||||
engine.module_instantiate_pre(&module)?,
|
||||
))
|
||||
} else {
|
||||
let comp = component.load_component(engine).await?;
|
||||
Ok(EitherInstancePre::Component(
|
||||
engine
|
||||
.instantiate_pre(&comp)
|
||||
.map_err(spin_trigger::decode_preinstantiation_error)?,
|
||||
))
|
||||
Ok(EitherInstancePre::Component(engine.instantiate_pre(&comp)?))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -465,6 +452,7 @@ mod tests {
|
|||
use std::collections::BTreeMap;
|
||||
|
||||
use anyhow::Result;
|
||||
use serde::Deserialize;
|
||||
use spin_testing::test_socket_addr;
|
||||
|
||||
use super::*;
|
||||
|
|
|
@ -28,7 +28,10 @@ pub const SPIN_WORKING_DIR: &str = "SPIN_WORKING_DIR";
|
|||
|
||||
/// A command that runs a TriggerExecutor.
|
||||
#[derive(Parser, Debug)]
|
||||
#[clap(next_help_heading = "TRIGGER OPTIONS")]
|
||||
#[clap(
|
||||
usage = "spin [COMMAND] [OPTIONS]",
|
||||
next_help_heading = "TRIGGER OPTIONS"
|
||||
)]
|
||||
pub struct TriggerExecutorCommand<Executor: TriggerExecutor>
|
||||
where
|
||||
Executor::RunConfig: Args,
|
||||
|
|
|
@ -56,7 +56,6 @@ pub trait TriggerExecutor: Sized + Send + Sync {
|
|||
Ok(EitherInstancePre::Component(
|
||||
engine
|
||||
.instantiate_pre(&comp)
|
||||
.map_err(decode_preinstantiation_error)
|
||||
.with_context(|| format!("Failed to instantiate component '{}'", component.id()))?,
|
||||
))
|
||||
}
|
||||
|
@ -354,32 +353,3 @@ pub fn parse_file_url(url: &str) -> Result<PathBuf> {
|
|||
.to_file_path()
|
||||
.map_err(|_| anyhow!("Invalid file URL path: {url:?}"))
|
||||
}
|
||||
|
||||
pub fn decode_preinstantiation_error(e: anyhow::Error) -> anyhow::Error {
|
||||
let err_text = e.to_string();
|
||||
|
||||
if err_text.contains("unknown import") && err_text.contains("has not been defined") {
|
||||
// TODO: how to maintain this list?
|
||||
let sdk_imported_interfaces = &[
|
||||
"config",
|
||||
"http",
|
||||
"key-value",
|
||||
"mysql",
|
||||
"postgres",
|
||||
"redis",
|
||||
"sqlite",
|
||||
];
|
||||
|
||||
if sdk_imported_interfaces
|
||||
.iter()
|
||||
.map(|s| format!("{s}::"))
|
||||
.any(|s| err_text.contains(&s))
|
||||
{
|
||||
return anyhow!(
|
||||
"{e}. Check that the component uses a SDK or plugin version that matches the Spin runtime."
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
e
|
||||
}
|
||||
|
|
|
@ -80,6 +80,10 @@ To cut a release of Spin, you will need to do the following:
|
|||
`--certificate-identity` value should match this release, e.g.
|
||||
`https://github.com/fermyon/spin/.github/workflows/release.yml@refs/tags/v1.1.0`.
|
||||
|
||||
1. Create a Pull Request into Fermyon's Hombrew tap repository updating the [Spin
|
||||
formula](https://github.com/fermyon/homebrew-tap/blob/main/Formula/spin.rb). In the formula,
|
||||
update the version, point to the latest release artifacts, and set their correct sha256 digests.
|
||||
|
||||
The release is now complete!
|
||||
|
||||
[release action]: https://github.com/fermyon/spin/actions/workflows/release.yml
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
# Triage Duty Guide
|
||||
|
||||
This guide explains the goals of triage duty and outlines the triage process.
|
||||
|
||||
## Goals
|
||||
|
||||
1. Identify and properly manage critical issues in a timely manner.
|
||||
2. Label and prioritize incoming issues.
|
||||
3. Help move along conversations in issues until they are scoped for the backlog and ready for someone to pick up, closed or resolved.
|
||||
|
||||
## Steps
|
||||
|
||||
1. Add all new issues to the [`Spin Triage` project board](https://github.com/orgs/fermyon/projects/7/) under the `Triage Needed` column.
|
||||
|
||||
To do this:
|
||||
|
||||
- Go to the [project board](https://github.com/orgs/fermyon/projects/7/) and select `+ Add Item` at the bottom of the `Triage Needed` column.
|
||||
- Select `+`
|
||||
- Select `Add items to project`
|
||||
- In the search bar, filter issues by `is:issue is:open`
|
||||
- Select all and push the button `add selected items`
|
||||
|
||||
2. For each issue in the `Triage Needed` column, add appropriate labels and move the issue to another column if the issue is ready for a different column (`Investigating / Open for Comment`, `Backlog`, `In progress`) or close.
|
||||
|
||||
To do this:
|
||||
|
||||
- Determine if the issue is a `bug`, `enhancement`, or `question` and label as such.
|
||||
- If the issue does not clearly fall into one of these buckets, please ask more questions to determine what labels make sense.
|
||||
- Please bubble up and help resolve any critical bugs as you come across them.
|
||||
- If a `question` exposes a need for an improvement in the docs, please open up an issue in the [developer docs repo](https://github.com/fermyon/developer/issues).
|
||||
- If the issue is being currently investigated, move the issue to the `Investigating / Open for Comment` column and assign the issue an owner (the person who is investigating).
|
||||
- If the issue is an enhancement and we do not know yet whether we want to address it or it needs more input and discussion, move the issue to the `Investigating / Open for Comment` column. Please also bring this up in the next Spin maintainer or community meeting.
|
||||
- If the issue is well scoped, we want to resolve it, and it is ready to be picked up, move it to the `Backlog` column.
|
||||
- If the issue is being actively worked on, please ensure there is an owner and move it to the `In Progress` column.
|
||||
- If the issue requires no further action or it is a suggestion we don't plan on working on, add an explanation, link to other relevant issues/comments, add the appropriate labels (`duplicate`, `wontfix`) and then close the issue.
|
||||
|
||||
3. Visit the [Security Vulnerability tab](https://github.com/fermyon/spin/security/dependabot) to see if there are any outstanding dependabot PRs to review or if any vulnerabilities need to be addressed.
|
||||
|
||||
If merging a dependabot PR turns out to be a complicated endevaor and there are reasons for not being able to merge it immediately, leave a comment explaining the situation and where application, link to relevant upstream issues/PRs to watch for progress.
|
||||
|
||||
4. Time permitting, review and help move along issues in the `Investigating / Open for Comment` column.
|
|
@ -14,12 +14,6 @@ version = "1.1.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "1.3.2"
|
||||
|
@ -28,15 +22,15 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
|
|||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "2.3.2"
|
||||
version = "2.3.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6dbe3c979c178231552ecba20214a8272df4e09f232a87aef4320cf06539aded"
|
||||
checksum = "630be753d4e58660abd17930c71b647fe46c27ea6b63cc59e1e3851406972e42"
|
||||
|
||||
[[package]]
|
||||
name = "bytes"
|
||||
version = "1.1.0"
|
||||
version = "1.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c4872d67bab6358e59559027aa3b9157c53d9358c51423c17554809a8858e0f8"
|
||||
checksum = "89b2fd2a0dcf38d7971e2194b6b6eebab45ae01067456a7fd93d5547a61b70be"
|
||||
|
||||
[[package]]
|
||||
name = "fnv"
|
||||
|
@ -46,11 +40,10 @@ checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
|
|||
|
||||
[[package]]
|
||||
name = "form_urlencoded"
|
||||
version = "1.0.1"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5fc25a87fa4fd2094bffb06925852034d90a17f0d1e05197d4956d3555752191"
|
||||
checksum = "a62bc1cf6f830c2ec14a513a9fb124d0a213a629668a4186f329db21fe045652"
|
||||
dependencies = [
|
||||
"matches",
|
||||
"percent-encoding",
|
||||
]
|
||||
|
||||
|
@ -71,9 +64,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "http"
|
||||
version = "0.2.6"
|
||||
version = "0.2.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "31f4c6746584866f0feabcc69893c5b51beef3831656a968ed7ae254cdc4fd03"
|
||||
checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482"
|
||||
dependencies = [
|
||||
"bytes",
|
||||
"fnv",
|
||||
|
@ -98,11 +91,10 @@ checksum = "25a2bc672d1148e28034f176e01fffebb08b35768468cc954630da77a1449005"
|
|||
|
||||
[[package]]
|
||||
name = "idna"
|
||||
version = "0.2.3"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "418a0a6fab821475f634efe3ccc45c013f742efe03d853e8d3355d5cb850ecf8"
|
||||
checksum = "7d20d6b07bfbc108882d88ed8e37d39636dcc260e15e30c45e6ba089610b917c"
|
||||
dependencies = [
|
||||
"matches",
|
||||
"unicode-bidi",
|
||||
"unicode-normalization",
|
||||
]
|
||||
|
@ -120,9 +112,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "itoa"
|
||||
version = "1.0.1"
|
||||
version = "1.0.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1aab8fc367588b89dcee83ab0fd66b72b50b72fa1904d7095045ace2b0c81c35"
|
||||
checksum = "62b02a5381cc465bd3041d84623d0fa3b66738b52b8e2fc3bab8ad63ab032f4a"
|
||||
|
||||
[[package]]
|
||||
name = "leb128"
|
||||
|
@ -136,29 +128,23 @@ version = "0.4.19"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b06a4cde4c0f271a446782e3eff8de789548ce57dbc8eca9292c27f4a42004b4"
|
||||
|
||||
[[package]]
|
||||
name = "matches"
|
||||
version = "0.1.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
|
||||
|
||||
[[package]]
|
||||
name = "memchr"
|
||||
version = "2.4.1"
|
||||
version = "2.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a"
|
||||
checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d"
|
||||
|
||||
[[package]]
|
||||
name = "percent-encoding"
|
||||
version = "2.1.0"
|
||||
version = "2.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e"
|
||||
checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.60"
|
||||
version = "1.0.64"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dec2b086b7a862cf4de201096214fa870344cf922b2b30c167badb3af3195406"
|
||||
checksum = "78803b62cbf1f46fde80d7c0e803111524b9877184cfe7c3033659490ac7a7da"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
@ -176,9 +162,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.28"
|
||||
version = "1.0.29"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1b9ab9c7eadfd8df19006f1cf1a4aed13540ed5cbc047010ece5826e10825488"
|
||||
checksum = "573015e8ab27661678357f27dc26460738fd2b6c86e46f386fde94cb5d913105"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
]
|
||||
|
@ -193,6 +179,32 @@ dependencies = [
|
|||
"smartstring",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "semver"
|
||||
version = "1.0.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bebd363326d05ec3e2f532ab7660680f3b02130d780c299bca73469d521bc0ed"
|
||||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.171"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "30e27d1e4fd7659406c492fd6cfaf2066ba8773de45ca75e855590f856dc34a9"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.171"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "389894603bd18c46fa56231694f8d827779c0951a667087194cf9de94ed24682"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.25",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smartcow"
|
||||
version = "0.2.1"
|
||||
|
@ -222,12 +234,12 @@ dependencies = [
|
|||
"http",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 1.0.109",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "spin-sdk"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bytes",
|
||||
|
@ -247,20 +259,20 @@ checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f"
|
|||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "1.0.85"
|
||||
version = "1.0.109"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a684ac3dcd8913827e18cd09a68384ee66c1de24157e3c556c9ab16d85695fb7"
|
||||
checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-xid",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.18"
|
||||
version = "2.0.25"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "32d41677bcbe24c20c52e7c70b0d8db04134c5d1066bf98662e2871ad200ea3e"
|
||||
checksum = "15e3fc8c0c74267e2df136e5e5fb656a464158aa57624053375eb9c8c6e25ae2"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
|
@ -269,38 +281,38 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "thiserror"
|
||||
version = "1.0.37"
|
||||
version = "1.0.43"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "10deb33631e3c9018b9baf9dcbbc4f737320d2b576bac10f6aefa048fa407e3e"
|
||||
checksum = "a35fc5b8971143ca348fa6df4f024d4d55264f3468c71ad1c2f365b0a4d58c42"
|
||||
dependencies = [
|
||||
"thiserror-impl",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror-impl"
|
||||
version = "1.0.37"
|
||||
version = "1.0.43"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "982d17546b47146b28f7c22e3d08465f6b8903d0ea13c1660d9d84a6e7adcdbb"
|
||||
checksum = "463fe12d7993d3b327787537ce8dd4dfa058de32fc2b195ef3cde03dc4771e8f"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.85",
|
||||
"syn 2.0.25",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tinyvec"
|
||||
version = "1.5.1"
|
||||
version = "1.6.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2c1c1d5a42b6245520c249549ec267180beaffcc0615401ac8e31853d4b6d8d2"
|
||||
checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50"
|
||||
dependencies = [
|
||||
"tinyvec_macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tinyvec_macros"
|
||||
version = "0.1.0"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c"
|
||||
checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20"
|
||||
|
||||
[[package]]
|
||||
name = "unicase"
|
||||
|
@ -319,36 +331,36 @@ checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460"
|
|||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.9"
|
||||
version = "1.0.10"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b15811caf2415fb889178633e7724bad2509101cde276048e013b9def5e51fa0"
|
||||
checksum = "22049a19f4a68748a168c0fc439f9516686aa045927ff767eca0a85101fb6e73"
|
||||
|
||||
[[package]]
|
||||
name = "unicode-normalization"
|
||||
version = "0.1.19"
|
||||
version = "0.1.22"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d54590932941a9e9266f0832deed84ebe1bf2e4c9e4a3554d393d18f5e854bf9"
|
||||
checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921"
|
||||
dependencies = [
|
||||
"tinyvec",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicode-segmentation"
|
||||
version = "1.8.0"
|
||||
version = "1.10.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8895849a949e7845e06bd6dc1aa51731a103c42707010a5b591c0038fb73385b"
|
||||
checksum = "1dd624098567895118886609431a7c3b8f516e41d30e0643f03d94592a147e36"
|
||||
|
||||
[[package]]
|
||||
name = "unicode-xid"
|
||||
version = "0.2.2"
|
||||
version = "0.2.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8ccb82d61f80a663efe1f787a51b16b5a51e3314d6ac365b08639f52387b33f3"
|
||||
checksum = "f962df74c8c05a667b5ee8bcf162993134c104e96440b663c8daa176dc772d8c"
|
||||
|
||||
[[package]]
|
||||
name = "url"
|
||||
version = "2.3.0"
|
||||
version = "2.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "22fe195a4f217c25b25cb5058ced57059824a678474874038dc88d211bf508d3"
|
||||
checksum = "50bff7831e19200a85b17131d085c25d7811bc4e186efdaf54bbd132994a88cb"
|
||||
dependencies = [
|
||||
"form_urlencoded",
|
||||
"idna",
|
||||
|
@ -399,7 +411,7 @@ version = "0.8.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "392d16e9e46cc7ca98125bc288dd5e4db469efe8323d3e0dac815ca7f2398522"
|
||||
dependencies = [
|
||||
"bitflags 2.3.2",
|
||||
"bitflags 2.3.3",
|
||||
"wit-bindgen-rust-macro",
|
||||
]
|
||||
|
||||
|
@ -445,7 +457,7 @@ checksum = "ced38a5e174940c6a41ae587babeadfd2e2c2dc32f3b6488bcdca0e8922cf3f3"
|
|||
dependencies = [
|
||||
"anyhow",
|
||||
"proc-macro2",
|
||||
"syn 2.0.18",
|
||||
"syn 2.0.25",
|
||||
"wit-bindgen-core",
|
||||
"wit-bindgen-rust",
|
||||
"wit-component",
|
||||
|
|
|
@ -87,12 +87,6 @@ version = "1.3.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2d098ff73c1ca148721f37baad5ea6a465a13f9573aba8641fbbbae8164a54e"
|
||||
|
||||
[[package]]
|
||||
name = "arrayvec"
|
||||
version = "0.7.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8da52d66c7071e2e3fa2a1e5c6d088fec47b593032b254f5e980de8ea54454d6"
|
||||
|
||||
[[package]]
|
||||
name = "async-channel"
|
||||
version = "1.8.0"
|
||||
|
@ -215,17 +209,6 @@ dependencies = [
|
|||
"getrandom 0.2.8",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bigdecimal"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6aaf33151a6429fe9211d1b276eafdf70cdff28b071e76c0b0e1503221ea3744"
|
||||
dependencies = [
|
||||
"num-bigint",
|
||||
"num-integer",
|
||||
"num-traits",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bincode"
|
||||
version = "1.3.3"
|
||||
|
@ -349,78 +332,12 @@ dependencies = [
|
|||
"opaque-debug",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "borsh"
|
||||
version = "0.9.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "15bf3650200d8bffa99015595e10f1fbd17de07abbc25bb067da79e769939bfa"
|
||||
dependencies = [
|
||||
"borsh-derive",
|
||||
"hashbrown 0.11.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "borsh-derive"
|
||||
version = "0.9.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6441c552f230375d18e3cc377677914d2ca2b0d36e52129fe15450a2dce46775"
|
||||
dependencies = [
|
||||
"borsh-derive-internal",
|
||||
"borsh-schema-derive-internal",
|
||||
"proc-macro-crate",
|
||||
"proc-macro2",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "borsh-derive-internal"
|
||||
version = "0.9.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5449c28a7b352f2d1e592a8a28bf139bc71afb0764a14f3c02500935d8c44065"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "borsh-schema-derive-internal"
|
||||
version = "0.9.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cdbd5696d8bfa21d53d9fe39a714a18538bad11492a42d066dbbc395fb1951c0"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bumpalo"
|
||||
version = "3.12.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0d261e256854913907f67ed06efbc3338dfe6179796deefc1ff763fc1aee5535"
|
||||
|
||||
[[package]]
|
||||
name = "bytecheck"
|
||||
version = "0.6.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d11cac2c12b5adc6570dad2ee1b87eff4955dac476fe12d81e5fdd352e52406f"
|
||||
dependencies = [
|
||||
"bytecheck_derive",
|
||||
"ptr_meta",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bytecheck_derive"
|
||||
version = "0.6.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "13e576ebe98e605500b3c8041bb888e966653577172df6dd97398714eb30b9bf"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "byteorder"
|
||||
version = "1.4.3"
|
||||
|
@ -1233,7 +1150,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "a8a2db397cb1c8772f31494cb8917e48cd1e64f0fa7efac59fbd741a0a8ce841"
|
||||
dependencies = [
|
||||
"crc32fast",
|
||||
"libz-sys",
|
||||
"libz-ng-sys",
|
||||
"miniz_oxide",
|
||||
]
|
||||
|
||||
|
@ -1267,70 +1184,6 @@ dependencies = [
|
|||
"percent-encoding",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "frunk"
|
||||
version = "0.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a89c703bf50009f383a0873845357cc400a95fc535f836feddfe015d7df6e1e0"
|
||||
dependencies = [
|
||||
"frunk_core",
|
||||
"frunk_derives",
|
||||
"frunk_proc_macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "frunk_core"
|
||||
version = "0.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2a446d01a558301dca28ef43222864a9fa2bd9a2e71370f769d5d5d5ec9f3537"
|
||||
|
||||
[[package]]
|
||||
name = "frunk_derives"
|
||||
version = "0.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b83164912bb4c97cfe0772913c7af7387ee2e00cb6d4636fb65a35b3d0c8f173"
|
||||
dependencies = [
|
||||
"frunk_proc_macro_helpers",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "frunk_proc_macro_helpers"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "015425591bbeb0f5b8a75593340f1789af428e9f887a4f1e36c0c471f067ef50"
|
||||
dependencies = [
|
||||
"frunk_core",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "frunk_proc_macros"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ea01524f285deab48affffb342b97f186e657b119c3f1821ac531780e0fbfae0"
|
||||
dependencies = [
|
||||
"frunk_core",
|
||||
"frunk_proc_macros_impl",
|
||||
"proc-macro-hack",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "frunk_proc_macros_impl"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0a802d974cc18ee7fe1a7868fc9ce31086294fd96ba62f8da64ecb44e92a2653"
|
||||
dependencies = [
|
||||
"frunk_core",
|
||||
"frunk_proc_macro_helpers",
|
||||
"proc-macro-hack",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fs-set-times"
|
||||
version = "0.19.1"
|
||||
|
@ -1560,15 +1413,6 @@ version = "1.8.2"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "eabb4a44450da02c90444cf74558da904edde8fb4e9035a9a6a4e15445af0bd7"
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.11.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e"
|
||||
dependencies = [
|
||||
"ahash 0.7.6",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.12.3"
|
||||
|
@ -1637,9 +1481,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "hrana-client-proto"
|
||||
version = "0.1.2"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26f15d50a607f7f2cb8cb97cad7ae746f861139e8ebc425a8545195a556d6102"
|
||||
checksum = "f16b4e41e289da3fd60e64f245246a97e78fab7b3788c6d8147b3ae7d9f5e533"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"base64 0.21.0",
|
||||
|
@ -2044,18 +1888,20 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "libsql-client"
|
||||
version = "0.24.5"
|
||||
version = "0.31.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8861153820a4228a1261ee92138345f7e08c71e64a75c95217247427172f2ce8"
|
||||
checksum = "e119ff2e259fe776a1340d2cb40baf4d44c32e5a9fd2755e756fc46802c79c70"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
"base64 0.21.0",
|
||||
"fallible-iterator",
|
||||
"futures",
|
||||
"hrana-client-proto",
|
||||
"num-traits",
|
||||
"reqwest",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"sqlite3-parser",
|
||||
"tracing",
|
||||
"url",
|
||||
]
|
||||
|
@ -2072,14 +1918,13 @@ dependencies = [
|
|||
]
|
||||
|
||||
[[package]]
|
||||
name = "libz-sys"
|
||||
version = "1.1.8"
|
||||
name = "libz-ng-sys"
|
||||
version = "1.1.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9702761c3935f8cc2f101793272e202c72b99da8f4224a19ddcf1279a6450bbf"
|
||||
checksum = "2468756f34903b582fe7154dc1ffdebd89d0562c4a43b53c621bb0f1b1043ccb"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"pkg-config",
|
||||
"vcpkg",
|
||||
"cmake",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -2279,7 +2124,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "9006c95034ccf7b903d955f210469119f6c3477fc9c9e7a7845ce38a3e665c2a"
|
||||
dependencies = [
|
||||
"base64 0.13.1",
|
||||
"bigdecimal",
|
||||
"bindgen",
|
||||
"bitflags 1.3.2",
|
||||
"bitvec",
|
||||
|
@ -2289,14 +2133,12 @@ dependencies = [
|
|||
"cmake",
|
||||
"crc32fast",
|
||||
"flate2",
|
||||
"frunk",
|
||||
"lazy_static",
|
||||
"lexical",
|
||||
"num-bigint",
|
||||
"num-traits",
|
||||
"rand 0.8.5",
|
||||
"regex",
|
||||
"rust_decimal",
|
||||
"saturating",
|
||||
"serde",
|
||||
"serde_json",
|
||||
|
@ -2305,8 +2147,6 @@ dependencies = [
|
|||
"smallvec",
|
||||
"subprocess",
|
||||
"thiserror",
|
||||
"time",
|
||||
"uuid",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -2518,7 +2358,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "outbound-http"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"http",
|
||||
|
@ -2532,9 +2372,10 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "outbound-mysql"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"flate2",
|
||||
"mysql_async",
|
||||
"mysql_common",
|
||||
"spin-core",
|
||||
|
@ -2546,7 +2387,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "outbound-pg"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"native-tls",
|
||||
|
@ -2560,7 +2401,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "outbound-redis"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"redis",
|
||||
|
@ -2678,6 +2519,26 @@ dependencies = [
|
|||
"phf_shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "phf_codegen"
|
||||
version = "0.11.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e8d39688d359e6b34654d328e262234662d16cc0f60ec8dcbe5e718709342a5a"
|
||||
dependencies = [
|
||||
"phf_generator",
|
||||
"phf_shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "phf_generator"
|
||||
version = "0.11.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b1181c94580fa345f50f19d738aaa39c0ed30a600d95cb2d3e23f94266f14fbf"
|
||||
dependencies = [
|
||||
"phf_shared",
|
||||
"rand 0.8.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "phf_shared"
|
||||
version = "0.11.1"
|
||||
|
@ -2685,6 +2546,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "e1fb5f6f826b772a8d4c0394209441e7d37cbbb967ae9c7e0e8134365c9ee676"
|
||||
dependencies = [
|
||||
"siphasher",
|
||||
"uncased",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -2773,15 +2635,6 @@ version = "0.2.17"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-crate"
|
||||
version = "0.1.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d6ea3c4595b96363c13943497db34af4460fb474a95c43f4446ad341b8c9785"
|
||||
dependencies = [
|
||||
"toml",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-error"
|
||||
version = "1.0.4"
|
||||
|
@ -2806,12 +2659,6 @@ dependencies = [
|
|||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-hack"
|
||||
version = "0.5.20+deprecated"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc375e1527247fe1a97d8b7156678dfe7c1af2fc075c9a4db3690ecd2a148068"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.54"
|
||||
|
@ -2830,26 +2677,6 @@ dependencies = [
|
|||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ptr_meta"
|
||||
version = "0.1.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0738ccf7ea06b608c10564b31debd4f5bc5e197fc8bfe088f68ae5ce81e7a4f1"
|
||||
dependencies = [
|
||||
"ptr_meta_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ptr_meta_derive"
|
||||
version = "0.1.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "16b845dbfca988fa33db069c0e230574d15a3088f147a87b64c7589eb662c9ac"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pulldown-cmark"
|
||||
version = "0.8.0"
|
||||
|
@ -3050,15 +2877,6 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rend"
|
||||
version = "0.3.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "79af64b4b6362ffba04eef3a4e10829718a4896dac19daa741851c86781edf95"
|
||||
dependencies = [
|
||||
"bytecheck",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "reqwest"
|
||||
version = "0.11.14"
|
||||
|
@ -3119,31 +2937,6 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rkyv"
|
||||
version = "0.7.39"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cec2b3485b07d96ddfd3134767b8a447b45ea4eb91448d0a35180ec0ffd5ed15"
|
||||
dependencies = [
|
||||
"bytecheck",
|
||||
"hashbrown 0.12.3",
|
||||
"ptr_meta",
|
||||
"rend",
|
||||
"rkyv_derive",
|
||||
"seahash",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rkyv_derive"
|
||||
version = "0.7.39"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6eaedadc88b53e36dd32d940ed21ae4d850d5916f2581526921f553a72ac34c4"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.107",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rusqlite"
|
||||
version = "0.29.0"
|
||||
|
@ -3158,24 +2951,6 @@ dependencies = [
|
|||
"smallvec",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rust_decimal"
|
||||
version = "1.28.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7fe32e8c89834541077a5c5bbe5691aa69324361e27e6aeb3552a737db4a70c8"
|
||||
dependencies = [
|
||||
"arrayvec",
|
||||
"borsh",
|
||||
"bytecheck",
|
||||
"byteorder",
|
||||
"bytes",
|
||||
"num-traits",
|
||||
"rand 0.8.5",
|
||||
"rkyv",
|
||||
"serde",
|
||||
"serde_json",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustc-demangle"
|
||||
version = "0.1.21"
|
||||
|
@ -3344,12 +3119,6 @@ dependencies = [
|
|||
"untrusted",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "seahash"
|
||||
version = "4.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1c107b6f4780854c8b126e228ea8869f4d7b71260f962fefb57b996b8959ba6b"
|
||||
|
||||
[[package]]
|
||||
name = "security-framework"
|
||||
version = "2.8.0"
|
||||
|
@ -3617,7 +3386,7 @@ checksum = "6e63cff320ae2c57904679ba7cb63280a3dc4613885beafb148ee7bf9aa9042d"
|
|||
|
||||
[[package]]
|
||||
name = "spin-app"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
|
@ -3630,7 +3399,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-common"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"dirs",
|
||||
|
@ -3652,7 +3421,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-config"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
|
@ -3669,7 +3438,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-core"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
|
@ -3686,7 +3455,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-key-value"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"lru 0.9.0",
|
||||
|
@ -3739,7 +3508,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-loader"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
|
@ -3761,6 +3530,7 @@ dependencies = [
|
|||
"serde_json",
|
||||
"shellexpand 3.1.0",
|
||||
"spin-common",
|
||||
"spin-config",
|
||||
"spin-manifest",
|
||||
"tempfile",
|
||||
"terminal",
|
||||
|
@ -3773,7 +3543,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-manifest"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"indexmap",
|
||||
"serde",
|
||||
|
@ -3783,9 +3553,10 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-sqlite"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
"spin-app",
|
||||
"spin-core",
|
||||
"spin-key-value",
|
||||
|
@ -3795,9 +3566,10 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-sqlite-inproc"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
"once_cell",
|
||||
"rand 0.8.5",
|
||||
"rusqlite",
|
||||
|
@ -3808,9 +3580,10 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-sqlite-libsql"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
"libsql-client",
|
||||
"spin-sqlite",
|
||||
"spin-world",
|
||||
|
@ -3820,7 +3593,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-trigger"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"async-trait",
|
||||
|
@ -3861,7 +3634,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "spin-world"
|
||||
version = "1.4.0-pre0"
|
||||
version = "1.5.0-pre0"
|
||||
dependencies = [
|
||||
"wasmtime",
|
||||
]
|
||||
|
@ -3872,6 +3645,25 @@ version = "0.3.2"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3b9b39299b249ad65f3b7e96443bad61c02ca5cd3589f46cb6d610a0fd6c0d6a"
|
||||
|
||||
[[package]]
|
||||
name = "sqlite3-parser"
|
||||
version = "0.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c3995a6daa13c113217b6ad22154865fb06f9cb939bef398fd04f4a7aaaf5bd7"
|
||||
dependencies = [
|
||||
"bitflags 2.2.1",
|
||||
"cc",
|
||||
"fallible-iterator",
|
||||
"indexmap",
|
||||
"log",
|
||||
"memchr",
|
||||
"phf",
|
||||
"phf_codegen",
|
||||
"phf_shared",
|
||||
"smallvec",
|
||||
"uncased",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "sqlparser"
|
||||
version = "0.34.0"
|
||||
|
@ -4326,6 +4118,15 @@ version = "1.16.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba"
|
||||
|
||||
[[package]]
|
||||
name = "uncased"
|
||||
version = "0.9.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9b9bc53168a4be7402ab86c3aad243a84dd7381d09be0eddc81280c1da95ca68"
|
||||
dependencies = [
|
||||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicase"
|
||||
version = "2.6.0"
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
wit_bindgen::generate!({
|
||||
world: "spin-timer",
|
||||
path: "../spin-timer.wit"
|
||||
path: ".."
|
||||
});
|
||||
|
||||
use fermyon::example::config;
|
||||
use fermyon::spin::config;
|
||||
|
||||
struct MySpinTimer;
|
||||
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
package fermyon:spin
|
||||
|
||||
interface config {
|
||||
// Get a configuration value for the current component.
|
||||
// The config key must match one defined in in the component manifest.
|
||||
get-config: func(key: string) -> result<string, error>
|
||||
|
||||
variant error {
|
||||
provider(string),
|
||||
invalid-key(string),
|
||||
invalid-schema(string),
|
||||
other(string),
|
||||
}
|
||||
}
|
|
@ -1,19 +1,6 @@
|
|||
package fermyon:example
|
||||
|
||||
interface config {
|
||||
// Get a configuration value for the current component.
|
||||
// The config key must match one defined in in the component manifest.
|
||||
get-config: func(key: string) -> result<string, error>
|
||||
|
||||
variant error {
|
||||
provider(string),
|
||||
invalid-key(string),
|
||||
invalid-schema(string),
|
||||
other(string),
|
||||
}
|
||||
}
|
||||
|
||||
world spin-timer {
|
||||
import config
|
||||
import fermyon:spin/config
|
||||
export handle-timer-request: func()
|
||||
}
|
||||
|
|
|
@ -10,7 +10,7 @@ use spin_trigger::{
|
|||
};
|
||||
|
||||
wasmtime::component::bindgen!({
|
||||
path: "spin-timer.wit",
|
||||
path: ".",
|
||||
world: "spin-timer",
|
||||
async: true
|
||||
});
|
||||
|
|
|
@ -47,6 +47,10 @@ SDK_VERSION_SOURCE_FILE = sdk_version/sdk-version-go-template.c
|
|||
SDK_VERSION_DEST_FILES = config/sdk-version-go.c http/sdk-version-go.c \
|
||||
key_value/sdk-version-go.c redis/sdk-version-go.c
|
||||
|
||||
# NOTE: To generate the C bindings you need to install a forked version of wit-bindgen.
|
||||
#
|
||||
# cargo install wit-bindgen-cli --git https://github.com/fermyon/wit-bindgen-backport --rev "b89d5079ba5b07b319631a1b191d2139f126c976"
|
||||
#
|
||||
.PHONY: generate
|
||||
generate: $(GENERATED_OUTBOUND_HTTP) $(GENERATED_SPIN_HTTP)
|
||||
generate: $(GENERATED_OUTBOUND_REDIS) $(GENERATED_SPIN_REDIS)
|
||||
|
|
|
@ -17,14 +17,18 @@ const spinBinary = "../../target/debug/spin"
|
|||
func retryGet(t *testing.T, url string) *http.Response {
|
||||
t.Helper()
|
||||
|
||||
const maxTries = 120 // (10min/5sec)
|
||||
const maxTries = 600 // (10min)
|
||||
for i := 1; i < maxTries; i++ {
|
||||
// Catch call to `Fail` in other goroutine
|
||||
if t.Failed() {
|
||||
t.FailNow()
|
||||
}
|
||||
if res, err := http.Get(url); err != nil {
|
||||
t.Log(err)
|
||||
} else {
|
||||
return res
|
||||
}
|
||||
time.Sleep(5 * time.Second)
|
||||
time.Sleep(1 * time.Second)
|
||||
}
|
||||
t.Fatal("Get request timeout: ", url)
|
||||
return nil
|
||||
|
@ -50,6 +54,15 @@ func startSpin(t *testing.T, spinfile string) *testSpin {
|
|||
t.Fatal(err)
|
||||
}
|
||||
|
||||
go func() {
|
||||
cmd.Wait()
|
||||
if ctx.Err() == nil {
|
||||
t.Log("spin exited before the test finished:", cmd.ProcessState)
|
||||
t.Log("stderr:\n", stderr.String())
|
||||
t.Fail()
|
||||
}
|
||||
}()
|
||||
|
||||
return &testSpin{
|
||||
cancel: cancel,
|
||||
url: fmt.Sprintf("http://%s", url),
|
||||
|
|
|
@ -10,7 +10,7 @@ import (
|
|||
"unsafe"
|
||||
)
|
||||
|
||||
type Store C.key_value_store_t
|
||||
type Store uint32
|
||||
|
||||
const (
|
||||
errorKindStoreTableFull = iota
|
||||
|
|
|
@ -100,7 +100,7 @@ func srem(addr string, key string, values []string) (int64, error) {
|
|||
return int64(cpayload), toErr(err)
|
||||
}
|
||||
|
||||
type RedisParameterKind C.uint8_t
|
||||
type RedisParameterKind uint8
|
||||
|
||||
const (
|
||||
RedisParameterKindInt64 = iota
|
||||
|
@ -112,7 +112,7 @@ type RedisParameter struct {
|
|||
Val interface{}
|
||||
}
|
||||
|
||||
type RedisResultKind C.uint8_t
|
||||
type RedisResultKind uint8
|
||||
|
||||
const (
|
||||
RedisResultKindNil = iota
|
||||
|
|
|
@ -2,7 +2,6 @@ use anyhow::Error;
|
|||
use clap::{CommandFactory, FromArgMatches, Parser, Subcommand};
|
||||
use is_terminal::IsTerminal;
|
||||
use lazy_static::lazy_static;
|
||||
use spin_cli::build_info::*;
|
||||
use spin_cli::commands::external::predefined_externals;
|
||||
use spin_cli::commands::{
|
||||
build::BuildCommand,
|
||||
|
@ -16,6 +15,7 @@ use spin_cli::commands::{
|
|||
up::UpCommand,
|
||||
watch::WatchCommand,
|
||||
};
|
||||
use spin_cli::{build_info::*, subprocess::ExitStatusError};
|
||||
use spin_redis_engine::RedisTrigger;
|
||||
use spin_trigger::cli::help::HelpArgsOnlyTrigger;
|
||||
use spin_trigger::cli::TriggerExecutorCommand;
|
||||
|
@ -24,9 +24,20 @@ use spin_trigger_http::HttpTrigger;
|
|||
#[tokio::main]
|
||||
async fn main() {
|
||||
if let Err(err) = _main().await {
|
||||
terminal::error!("{err}");
|
||||
print_error_chain(err);
|
||||
std::process::exit(1)
|
||||
let code = match err.downcast_ref::<ExitStatusError>() {
|
||||
// If we encounter an `ExitStatusError` it means a subprocess has already
|
||||
// exited unsuccessfully and thus already printed error messages. No need
|
||||
// to print anything additional.
|
||||
Some(e) => e.code(),
|
||||
// Otherwise we print the error chain.
|
||||
None => {
|
||||
terminal::error!("{err}");
|
||||
print_error_chain(err);
|
||||
1
|
||||
}
|
||||
};
|
||||
|
||||
std::process::exit(code)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -114,7 +114,13 @@ impl Install {
|
|||
let manager = PluginManager::try_default()?;
|
||||
// Downgrades are only allowed via the `upgrade` subcommand
|
||||
let downgrade = false;
|
||||
let manifest = manager.get_manifest(&manifest_location).await?;
|
||||
let manifest = manager
|
||||
.get_manifest(
|
||||
&manifest_location,
|
||||
self.override_compatibility_check,
|
||||
SPIN_VERSION,
|
||||
)
|
||||
.await?;
|
||||
try_install(
|
||||
&manifest,
|
||||
&manager,
|
||||
|
@ -250,7 +256,14 @@ impl Upgrade {
|
|||
.to_string();
|
||||
let manifest_location =
|
||||
ManifestLocation::PluginsRepository(PluginLookup::new(&name, None));
|
||||
let manifest = match manager.get_manifest(&manifest_location).await {
|
||||
let manifest = match manager
|
||||
.get_manifest(
|
||||
&manifest_location,
|
||||
self.override_compatibility_check,
|
||||
SPIN_VERSION,
|
||||
)
|
||||
.await
|
||||
{
|
||||
Err(Error::NotFound(e)) => {
|
||||
log::info!("Could not upgrade plugin '{name}': {e:?}");
|
||||
continue;
|
||||
|
@ -283,7 +296,13 @@ impl Upgrade {
|
|||
self.version,
|
||||
)),
|
||||
};
|
||||
let manifest = manager.get_manifest(&manifest_location).await?;
|
||||
let manifest = manager
|
||||
.get_manifest(
|
||||
&manifest_location,
|
||||
self.override_compatibility_check,
|
||||
SPIN_VERSION,
|
||||
)
|
||||
.await?;
|
||||
try_install(
|
||||
&manifest,
|
||||
&manager,
|
||||
|
|
|
@ -126,7 +126,7 @@ impl UpCommand {
|
|||
}
|
||||
|
||||
let working_dir_holder = match &self.tmp {
|
||||
None => WorkingDirectory::Temporary(tempfile::tempdir()?),
|
||||
None => WorkingDirectory::Temporary(TempDir::with_prefix("spinup-")?),
|
||||
Some(d) => WorkingDirectory::Given(d.to_owned()),
|
||||
};
|
||||
let working_dir = working_dir_holder.path().canonicalize()?;
|
||||
|
@ -206,7 +206,7 @@ impl UpCommand {
|
|||
if status.success() {
|
||||
Ok(())
|
||||
} else {
|
||||
bail!(status);
|
||||
Err(crate::subprocess::ExitStatusError::new(status).into())
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
pub mod build_info;
|
||||
pub mod commands;
|
||||
pub(crate) mod opts;
|
||||
pub mod subprocess;
|
||||
mod watch_filter;
|
||||
mod watch_state;
|
||||
|
||||
pub use crate::opts::HELP_ARGS_ONLY_TRIGGER_TYPE;
|
||||
pub use opts::HELP_ARGS_ONLY_TRIGGER_TYPE;
|
||||
|
|
|
@ -0,0 +1,34 @@
|
|||
/// An error representing a subprocess that errored
|
||||
///
|
||||
/// This can be used to propogate a subprocesses exit status.
|
||||
/// When this error is encountered the cli will exit with the status code
|
||||
/// instead of printing an error,
|
||||
#[derive(Debug)]
|
||||
pub struct ExitStatusError {
|
||||
status: Option<i32>,
|
||||
}
|
||||
|
||||
impl ExitStatusError {
|
||||
pub(crate) fn new(status: std::process::ExitStatus) -> Self {
|
||||
Self {
|
||||
status: status.code(),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn code(&self) -> i32 {
|
||||
self.status.unwrap_or(1)
|
||||
}
|
||||
}
|
||||
|
||||
impl std::error::Error for ExitStatusError {}
|
||||
|
||||
impl std::fmt::Display for ExitStatusError {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
let _ = write!(f, "subprocess exited with status: ");
|
||||
if let Some(status) = self.status {
|
||||
writeln!(f, "{}", status)
|
||||
} else {
|
||||
writeln!(f, "unknown")
|
||||
}
|
||||
}
|
||||
}
|
|
@ -6,8 +6,8 @@ trigger = { type = "http", base = "{{http-base}}" }
|
|||
version = "0.1.0"
|
||||
|
||||
[[component]]
|
||||
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.0.2/spin_static_fs.wasm", digest = "sha256:65456bf4e84cf81b62075e761b2b0afaffaef2d0aeda521b245150f76b96421b" }
|
||||
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.0.3/spin_static_fs.wasm", digest = "sha256:38bf971900228222f7f6b2ccee5051f399adca58d71692cdfdea98997965fd0d" }
|
||||
id = "{{ project-name }}"
|
||||
files = [ { source = "{{ files-path }}", destination = "/" } ]
|
||||
files = [{ source = "{{ files-path }}", destination = "/" }]
|
||||
[component.trigger]
|
||||
route = "{{ http-path | http_wildcard }}"
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
[[component]]
|
||||
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.0.2/spin_static_fs.wasm", digest = "sha256:65456bf4e84cf81b62075e761b2b0afaffaef2d0aeda521b245150f76b96421b" }
|
||||
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.0.3/spin_static_fs.wasm", digest = "sha256:38bf971900228222f7f6b2ccee5051f399adca58d71692cdfdea98997965fd0d" }
|
||||
id = "{{ project-name }}"
|
||||
files = [ { source = "{{ files-path }}", destination = "/" } ]
|
||||
[component.trigger]
|
||||
|
|
|
@ -5,7 +5,7 @@ trigger_type = "http"
|
|||
tags = ["http", "file", "static", "asset"]
|
||||
|
||||
[add_component]
|
||||
skip_files = ["spin.toml"]
|
||||
skip_files = ["spin.toml", ".gitignore"]
|
||||
skip_parameters = ["http-base", "project-description"]
|
||||
[add_component.snippets]
|
||||
component = "component.txt"
|
||||
|
|
|
@ -89,8 +89,13 @@ mod spinup_tests {
|
|||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn simple_spin_rust_works() {
|
||||
testcases::simple_spin_rust_works(CONTROLLER).await
|
||||
async fn head_rust_sdk_http() {
|
||||
testcases::head_rust_sdk_http(CONTROLLER).await
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn head_rust_sdk_redis() {
|
||||
testcases::head_rust_sdk_redis(CONTROLLER).await
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
[package]
|
||||
name = "simple-spin-rust-test"
|
||||
name = "head-rust-sdk-http"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
|
@ -17,7 +17,3 @@ http = "0.2"
|
|||
spin-sdk = { path = "../../../sdk/rust" }
|
||||
|
||||
[workspace]
|
||||
|
||||
# Metadata about this component.
|
||||
[package.metadata.component]
|
||||
name = "spinhelloworld"
|
|
@ -1,7 +1,7 @@
|
|||
spin_version = "1"
|
||||
authors = ["Fermyon Engineering <engineering@fermyon.com>"]
|
||||
description = "A simple application that returns hello and goodbye."
|
||||
name = "simple-spin-rust-test"
|
||||
name = "head-rust-sdk-http"
|
||||
trigger = {type = "http", base = "/test"}
|
||||
version = "1.0.0"
|
||||
|
||||
|
@ -10,7 +10,7 @@ object = { default = "teapot" }
|
|||
|
||||
[[component]]
|
||||
id = "hello"
|
||||
source = "target/wasm32-wasi/release/simple_spin_rust_test.wasm"
|
||||
source = "target/wasm32-wasi/release/head_rust_sdk_http.wasm"
|
||||
files = [ { source = "assets", destination = "/" } ]
|
||||
[component.trigger]
|
||||
route = "/hello/..."
|
|
@ -0,0 +1,2 @@
|
|||
[build]
|
||||
target = "wasm32-wasi"
|
|
@ -0,0 +1,15 @@
|
|||
[package]
|
||||
name = "head-rust-sdk-redis"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[lib]
|
||||
crate-type = [ "cdylib" ]
|
||||
|
||||
[dependencies]
|
||||
anyhow = "1"
|
||||
bytes = "1"
|
||||
http = "0.2"
|
||||
spin-sdk = { path = "../../../sdk/rust"}
|
||||
|
||||
[workspace]
|
|
@ -0,0 +1,14 @@
|
|||
spin_version = "1"
|
||||
authors = ["Fermyon Engineering <engineering@fermyon.com>"]
|
||||
description = "A simple redis application that exercises the Rust SDK in the current branch"
|
||||
name = "head-rust-sdk-redis"
|
||||
trigger = {type = "redis", address = "redis://redis:6379"}
|
||||
version = "1.0.0"
|
||||
|
||||
[[component]]
|
||||
id = "hello"
|
||||
source = "target/wasm32-wasi/release/head_rust_sdk_redis.wasm"
|
||||
[component.trigger]
|
||||
channel = "my-channel"
|
||||
[component.build]
|
||||
command = "cargo build --target wasm32-wasi --release"
|
|
@ -0,0 +1,10 @@
|
|||
use spin_sdk::redis_component;
|
||||
|
||||
#[redis_component]
|
||||
fn on_message(message: bytes::Bytes) -> anyhow::Result<()> {
|
||||
println!(
|
||||
"Got message: '{}'",
|
||||
std::str::from_utf8(&*message).unwrap_or("<MESSAGE NOT UTF8>")
|
||||
);
|
||||
Ok(())
|
||||
}
|
|
@ -665,7 +665,8 @@ pub async fn assets_routing_works(controller: &dyn Controller) {
|
|||
tc.run(controller).await.unwrap()
|
||||
}
|
||||
|
||||
pub async fn simple_spin_rust_works(controller: &dyn Controller) {
|
||||
/// Test an http app using the current branch's version of the Rust SDK
|
||||
pub async fn head_rust_sdk_http(controller: &dyn Controller) {
|
||||
async fn checks(
|
||||
metadata: AppMetadata,
|
||||
_: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
|
@ -719,8 +720,42 @@ pub async fn simple_spin_rust_works(controller: &dyn Controller) {
|
|||
}
|
||||
|
||||
let tc = TestCaseBuilder::default()
|
||||
.name("simple-spin-rust-test".to_string())
|
||||
.appname(Some("simple-spin-rust-test".to_string()))
|
||||
.name("head-rust-sdk-http".to_string())
|
||||
.appname(Some("head-rust-sdk-http".to_string()))
|
||||
.assertions(
|
||||
|metadata: AppMetadata,
|
||||
stdout_stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
stderr_stream: Option<Pin<Box<dyn AsyncBufRead>>>| {
|
||||
Box::pin(checks(metadata, stdout_stream, stderr_stream))
|
||||
},
|
||||
)
|
||||
.build()
|
||||
.unwrap();
|
||||
|
||||
tc.run(controller).await.unwrap()
|
||||
}
|
||||
|
||||
/// Test a redis app using the current branch's version of the Rust SDK
|
||||
pub async fn head_rust_sdk_redis(controller: &dyn Controller) {
|
||||
async fn checks(
|
||||
_: AppMetadata,
|
||||
_: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
stderr_stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
) -> Result<()> {
|
||||
wait_for_spin().await;
|
||||
let stderr = get_output_stream(stderr_stream).await?;
|
||||
anyhow::ensure!(
|
||||
stderr.is_empty(),
|
||||
"expected stderr to be empty, but it was not: {}",
|
||||
stderr.join("\n")
|
||||
);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
let tc = TestCaseBuilder::default()
|
||||
.name("head-rust-sdk-redis".to_string())
|
||||
.appname(Some("head-rust-sdk-redis".to_string()))
|
||||
.trigger_type("redis".to_string())
|
||||
.assertions(
|
||||
|metadata: AppMetadata,
|
||||
stdout_stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
|
@ -877,8 +912,7 @@ pub async fn redis_go_works(controller: &dyn Controller) {
|
|||
_: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
stderr_stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
) -> Result<()> {
|
||||
//TODO: wait for spin up to be ready dynamically
|
||||
sleep(Duration::from_secs(10)).await;
|
||||
wait_for_spin().await;
|
||||
|
||||
let output = utils::run(
|
||||
&[
|
||||
|
@ -894,12 +928,13 @@ pub async fn redis_go_works(controller: &dyn Controller) {
|
|||
)?;
|
||||
utils::assert_success(&output);
|
||||
|
||||
let stderr = utils::get_output_stream(stderr_stream, Duration::from_secs(5)).await?;
|
||||
let stderr = get_output_stream(stderr_stream).await?;
|
||||
let expected_logs = vec!["Payload::::", "msg-from-go-channel"];
|
||||
|
||||
assert!(expected_logs
|
||||
.iter()
|
||||
.all(|item| stderr.contains(&item.to_string())));
|
||||
.all(|item| stderr.contains(&item.to_string())),
|
||||
"Expected log lines to contain all of {expected_logs:?} but actual lines were '{stderr:?}'");
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
@ -933,8 +968,7 @@ pub async fn redis_rust_works(controller: &dyn Controller) {
|
|||
_: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
stderr_stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
) -> Result<()> {
|
||||
//TODO: wait for spin up to be ready dynamically
|
||||
sleep(Duration::from_secs(20)).await;
|
||||
wait_for_spin().await;
|
||||
|
||||
utils::run(
|
||||
&[
|
||||
|
@ -949,13 +983,14 @@ pub async fn redis_rust_works(controller: &dyn Controller) {
|
|||
None,
|
||||
)?;
|
||||
|
||||
let stderr = utils::get_output_stream(stderr_stream, Duration::from_secs(5)).await?;
|
||||
let stderr = get_output_stream(stderr_stream).await?;
|
||||
|
||||
let expected_logs = vec!["msg-from-rust-channel"];
|
||||
|
||||
assert!(expected_logs
|
||||
.iter()
|
||||
.all(|item| stderr.contains(&item.to_string())));
|
||||
.all(|item| stderr.contains(&item.to_string())),
|
||||
"Expected log lines to contain all of {expected_logs:?} but actual lines were '{stderr:?}'");
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
@ -1205,3 +1240,14 @@ pub async fn error_messages(controller: &dyn Controller) {
|
|||
|
||||
tc.try_run(controller).await.unwrap();
|
||||
}
|
||||
|
||||
async fn get_output_stream(
|
||||
stream: Option<Pin<Box<dyn AsyncBufRead>>>,
|
||||
) -> anyhow::Result<Vec<String>> {
|
||||
utils::get_output_stream(stream, Duration::from_secs(5)).await
|
||||
}
|
||||
|
||||
async fn wait_for_spin() {
|
||||
//TODO: wait for spin up to be ready dynamically
|
||||
sleep(Duration::from_secs(10)).await;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue