Skip to content

Commit

Permalink
Update compatibility.rs to check for IBC-go dependency (informalsyste…
Browse files Browse the repository at this point in the history
…ms#1431)

* Update compat to check IBC-go dependency

* Updated ibc-go vers to match the ibc-go repo releases

* Added lost changelog entry for issue informalsystems#1433

* Lower log level of health check to warning

* Relax compatibility check from patch version to minor version

* Relax compat versions to `>=0.41, <0.45` for SDK and `>=1.1, <1.2` for IBC-Go

* Add .changelog entry

* Comment fix

Co-authored-by: Romain Ruetschi <[email protected]>
  • Loading branch information
adizere and romac authored Oct 19, 2021
1 parent 4b2a89e commit c088a22
Show file tree
Hide file tree
Showing 5 changed files with 87 additions and 16 deletions.
3 changes: 3 additions & 0 deletions .changelog/unreleased/features/1433-memo-field.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
- Add support for the `tx.memo` field ([#1433])

[#1433]: https://github.com/informalsystems/ibc-rs/issues/1433
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
- Update compatibility check for IBC-Go dependency
([#1464](https://github.com/informalsystems/ibc-rs/issues/1464))
2 changes: 1 addition & 1 deletion relayer-cli/src/commands/health.rs
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ impl Runnable for HealthCheckCmd {
Ok(Unhealthy(_)) => {
// No need to print the error here as it's already printed in `Chain::health_check`
// TODO(romac): Move the printing code here and in the supervisor/registry
error!("[{}] chain is unhealthy", ch.id)
warn!("[{}] chain is unhealthy", ch.id)
}
Err(e) => error!(
"[{}] failed to perform health check, reason: {}",
Expand Down
94 changes: 80 additions & 14 deletions relayer/src/chain/cosmos/compatibility.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@ use thiserror::Error;

use ibc_proto::cosmos::base::tendermint::v1beta1::VersionInfo;

/// Specifies the SDK module path, as it is expected to appear
/// in the application version information.
/// Specifies the SDK & IBC-go modules path, as it is expected
/// to appear in the application version information.
///
/// The module identification is captured in a [`Module`]
/// with the following structure as an example:
Expand All @@ -17,13 +17,24 @@ use ibc_proto::cosmos::base::tendermint::v1beta1::VersionInfo;
/// },
/// ```
const SDK_MODULE_NAME: &str = "cosmos/cosmos-sdk";
const IBC_GO_MODULE_NAME: &str = "cosmos/ibc-go";

/// Specifies the SDK module version requirement.
///
/// # Note: Should be consistent with [features] guide page.
///
/// [features]: https://hermes.informal.systems/features.html
const SDK_MODULE_VERSION_REQ: &str = ">=0.41.3, <=0.44.1";
const SDK_MODULE_VERSION_REQ: &str = ">=0.41, <0.45";

/// Specifies the IBC-go module version requirement.
/// At the moment, we support both chains with and without
/// the standalone ibc-go module, i.e., it's not an error
/// if the chain binary does not build with this module.
///
/// # Note: Should be consistent with [features] guide page.
///
/// [features]: https://hermes.informal.systems/features.html
const IBC_GO_MODULE_VERSION_REQ: &str = ">=1.1, <1.2";

/// Helper struct to capture all the reported information of an
/// IBC application, e.g., `gaiad`.
Expand Down Expand Up @@ -79,38 +90,51 @@ pub enum Diagnostic {
found: String,
app: AppInfo,
},

#[error("Ibc-Go module at version '{found}' does not meet compatibility requirements {requirements} for application {app}")]
MismatchingIbcGoModuleVersion {
requirements: String,
found: String,
app: AppInfo,
},
}

/// Runs a diagnostic check on the provided [`VersionInfo`]
/// to ensure that the Sdk module version matches the
/// predefined requirements.
/// to ensure that the Sdk & IBC-go modules version match
/// the predefined requirements.
///
/// Returns `None` upon success, or a [`Diagnostic`] upon
/// an error.
///
/// Relies on the constant [`SDK_MODULE_NAME`] to find the
/// Sdk module by name, as well as the constant
/// [`SDK_MODULE_VERSION_REQ`] for version compatibility
/// requirements.
pub(crate) fn run_diagnostic(version_info: VersionInfo) -> Result<(), Diagnostic> {
// Parse the requirements into a semver
let reqs = semver::VersionReq::parse(SDK_MODULE_VERSION_REQ)
/// Sdk module by name, as well as the constants
/// [`SDK_MODULE_VERSION_REQ`] and [`IBC_GO_MODULE_VERSION_REQ`]
/// for establishing compatibility requirements.
pub(crate) fn run_diagnostic(v: VersionInfo) -> Result<(), Diagnostic> {
sdk_diagnostic(v.clone())?;
ibc_go_diagnostic(v)?;
Ok(())
}

fn sdk_diagnostic(v: VersionInfo) -> Result<(), Diagnostic> {
// Parse the SDK requirements into a semver
let sdk_reqs = semver::VersionReq::parse(SDK_MODULE_VERSION_REQ)
.expect("parsing the SDK module requirements into semver");

// Get the Cosmos SDK version
let mut version = get_sdk_version(&version_info)?;
let mut version = get_sdk_version(&v)?;

// Remove the pre-release version to ensure we treat pre-releases of the SDK
// as their normal version, eg. 0.42.0-rc2 should satisfy >=0.41.3, <= 0.42.6.
version.pre = semver::Prerelease::EMPTY;

// Finally, check the version requirements
match reqs.matches(&version) {
match sdk_reqs.matches(&version) {
true => Ok(()),
false => Err(Diagnostic::MismatchingSdkModuleVersion {
requirements: SDK_MODULE_VERSION_REQ.to_string(),
found: version.to_string(),
app: AppInfo::from(version_info),
app: AppInfo::from(v),
}),
}
}
Expand Down Expand Up @@ -139,3 +163,45 @@ fn get_sdk_version(version_info: &VersionInfo) -> Result<semver::Version, Diagno

Ok(version)
}

fn ibc_go_diagnostic(version_info: VersionInfo) -> Result<(), Diagnostic> {
// Parse the IBC-go module requirements into a semver
let ibc_reqs = semver::VersionReq::parse(IBC_GO_MODULE_VERSION_REQ)
.expect("parsing the IBC-Go module requirements into semver");

// Find the Ibc-Go module
match version_info
.build_deps
.iter()
.find(|&m| m.path.contains(IBC_GO_MODULE_NAME))
{
// If binary lacks the ibc-go dependency it is _not_ an error,
// we support chains without the standalone ibc-go module.
None => Ok(()),
Some(ibc_module) => {
// The raw version number has a leading 'v', trim it out;
let plain_version = ibc_module.version.trim_start_matches('v');

// Parse the module version
match semver::Version::parse(plain_version).map_err(|e| {
Diagnostic::VersionParsingFailed {
module_path: ibc_module.path.clone(),
raw_version: ibc_module.version.clone(),
cause: e.to_string(),
app: AppInfo::from(version_info.clone()),
}
}) {
// Check the IBC-Go version requirements
Ok(v) => match ibc_reqs.matches(&v) {
true => Ok(()),
false => Err(Diagnostic::MismatchingIbcGoModuleVersion {
requirements: IBC_GO_MODULE_VERSION_REQ.to_string(),
found: v.to_string(),
app: AppInfo::from(version_info),
}),
},
Err(d) => Err(d),
}
}
}
}
2 changes: 1 addition & 1 deletion relayer/src/supervisor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -368,7 +368,7 @@ impl<Chain: ChainHandle + 'static> Supervisor<Chain> {
match chain {
Ok(chain) => match chain.health_check() {
Ok(Healthy) => info!("[{}] chain is healthy", id),
Ok(Unhealthy(e)) => error!("[{}] chain is unhealthy: {}", id, e),
Ok(Unhealthy(e)) => warn!("[{}] chain is unhealthy: {}", id, e),
Err(e) => error!("[{}] failed to perform health check: {}", id, e),
},
Err(e) => {
Expand Down

0 comments on commit c088a22

Please sign in to comment.