mirror of
https://github.com/kata-containers/kata-containers.git
synced 2025-04-28 03:42:09 +00:00
Merge pull request #5388 from jodh-intel/kata-ctl
kata-ctl: Move development to main branch
This commit is contained in:
commit
d3ee8d9f1b
5
Makefile
5
Makefile
@ -16,9 +16,10 @@ COMPONENTS += runtime-rs
|
||||
TOOLS =
|
||||
|
||||
TOOLS += agent-ctl
|
||||
TOOLS += trace-forwarder
|
||||
TOOLS += runk
|
||||
TOOLS += kata-ctl
|
||||
TOOLS += log-parser
|
||||
TOOLS += runk
|
||||
TOOLS += trace-forwarder
|
||||
|
||||
STANDARD_TARGETS = build check clean install test vendor
|
||||
|
||||
|
@ -133,6 +133,7 @@ The table below lists the remaining parts of the project:
|
||||
| [kernel](https://www.kernel.org) | kernel | Linux kernel used by the hypervisor to boot the guest image. Patches are stored [here](tools/packaging/kernel). |
|
||||
| [osbuilder](tools/osbuilder) | infrastructure | Tool to create "mini O/S" rootfs and initrd images and kernel for the hypervisor. |
|
||||
| [`agent-ctl`](src/tools/agent-ctl) | utility | Tool that provides low-level access for testing the agent. |
|
||||
| [`kata-ctl`](src/tools/kata-ctl) | utility | Tool that provides advanced commands and debug facilities. |
|
||||
| [`trace-forwarder`](src/tools/trace-forwarder) | utility | Agent tracing helper. |
|
||||
| [`runk`](src/tools/runk) | utility | Standard OCI container runtime based on the agent. |
|
||||
| [`ci`](https://github.com/kata-containers/ci) | CI | Continuous Integration configuration files and scripts. |
|
||||
|
1
src/tools/kata-ctl/.gitignore
vendored
Normal file
1
src/tools/kata-ctl/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/vendor/
|
20
src/tools/kata-ctl/Cargo.toml
Normal file
20
src/tools/kata-ctl/Cargo.toml
Normal file
@ -0,0 +1,20 @@
|
||||
# Copyright (c) 2022 Intel Corporation
|
||||
#
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
|
||||
[package]
|
||||
name = "kata-ctl"
|
||||
version = "0.0.1"
|
||||
authors = ["The Kata Containers community <kata-dev@lists.katacontainers.io>"]
|
||||
edition = "2018"
|
||||
|
||||
[dependencies]
|
||||
anyhow = "1.0.31"
|
||||
clap = { version = "3.2.20", features = ["derive", "cargo"] }
|
||||
reqwest = { version = "0.11", default-features = false, features = ["json", "blocking", "rustls-tls"] }
|
||||
serde_json = "1.0.85"
|
||||
thiserror = "1.0.35"
|
||||
|
||||
[dev-dependencies]
|
||||
semver = "1.0.12"
|
64
src/tools/kata-ctl/Makefile
Normal file
64
src/tools/kata-ctl/Makefile
Normal file
@ -0,0 +1,64 @@
|
||||
# Copyright (c) 2022 Intel Corporation
|
||||
#
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
|
||||
include ../../../utils.mk
|
||||
|
||||
PROJECT_NAME = Kata Containers
|
||||
PROJECT_URL = https://github.com/kata-containers
|
||||
PROJECT_COMPONENT = kata-ctl
|
||||
|
||||
TARGET = $(PROJECT_COMPONENT)
|
||||
|
||||
VERSION_FILE := ./VERSION
|
||||
VERSION := $(shell grep -v ^\# $(VERSION_FILE))
|
||||
COMMIT_NO := $(shell git rev-parse HEAD 2>/dev/null || true)
|
||||
COMMIT_NO_SHORT := $(shell git rev-parse --short HEAD 2>/dev/null || true)
|
||||
COMMIT := $(if $(shell git status --porcelain --untracked-files=no 2>/dev/null || true),${COMMIT_NO}-dirty,${COMMIT_NO})
|
||||
|
||||
# Exported to allow cargo to see it
|
||||
export KATA_CTL_VERSION := $(if $(COMMIT),$(VERSION)-$(COMMIT),$(VERSION))
|
||||
|
||||
GENERATED_CODE = src/ops/version.rs
|
||||
|
||||
GENERATED_REPLACEMENTS= \
|
||||
KATA_CTL_VERSION
|
||||
|
||||
GENERATED_FILES := $(GENERATED_CODE)
|
||||
|
||||
.DEFAULT_GOAL := default
|
||||
|
||||
default: $(TARGET) build
|
||||
|
||||
$(TARGET): $(GENERATED_CODE)
|
||||
|
||||
build:
|
||||
@RUSTFLAGS="$(EXTRA_RUSTFLAGS) --deny warnings" cargo build --target $(TRIPLE) $(if $(findstring release,$(BUILD_TYPE)),--release) $(EXTRA_RUSTFEATURES)
|
||||
|
||||
$(GENERATED_FILES): %: %.in
|
||||
@sed $(foreach r,$(GENERATED_REPLACEMENTS),-e 's|@$r@|$($r)|g') "$<" > "$@"
|
||||
|
||||
|
||||
clean:
|
||||
@cargo clean
|
||||
@rm -f $(GENERATED_FILES)
|
||||
|
||||
vendor:
|
||||
cargo vendor
|
||||
|
||||
test:
|
||||
@RUSTFLAGS="$(EXTRA_RUSTFLAGS) --deny warnings" cargo test --target $(TRIPLE) $(if $(findstring release,$(BUILD_TYPE)),--release) $(EXTRA_RUSTFEATURES)
|
||||
|
||||
install:
|
||||
@RUSTFLAGS="$(EXTRA_RUSTFLAGS) --deny warnings" cargo install --target $(TRIPLE) --path .
|
||||
|
||||
check: standard_rust_check
|
||||
|
||||
.PHONY: \
|
||||
build \
|
||||
check \
|
||||
clean \
|
||||
install \
|
||||
test \
|
||||
vendor
|
49
src/tools/kata-ctl/README.md
Normal file
49
src/tools/kata-ctl/README.md
Normal file
@ -0,0 +1,49 @@
|
||||
# Kata Containers control tool
|
||||
|
||||
## Overview
|
||||
|
||||
The `kata-ctl` tool is a rust rewrite of the
|
||||
[`kata-runtime`](../../runtime/cmd/kata-runtime)
|
||||
[utility program](../../../docs/design/architecture/README.md#utility-program).
|
||||
|
||||
The program provides a number of utility commands for:
|
||||
|
||||
- Using advanced Kata Containers features.
|
||||
- Problem determination and debugging.
|
||||
|
||||
## Audience and environment
|
||||
|
||||
Users and administrators.
|
||||
|
||||
## Build the tool
|
||||
|
||||
```bash
|
||||
$ make
|
||||
```
|
||||
|
||||
## Install the tool
|
||||
|
||||
```bash
|
||||
$ make install
|
||||
```
|
||||
|
||||
## Run the tool
|
||||
|
||||
```bash
|
||||
$ kata-ctl ...
|
||||
```
|
||||
|
||||
For example, to determine if your system is capable of running Kata
|
||||
Containers, run:
|
||||
|
||||
```bash
|
||||
$ kata-ctl check all
|
||||
```
|
||||
|
||||
### Full details
|
||||
|
||||
For a usage statement, run:
|
||||
|
||||
```bash
|
||||
$ kata-ctl --help
|
||||
```
|
1
src/tools/kata-ctl/VERSION
Symbolic link
1
src/tools/kata-ctl/VERSION
Symbolic link
@ -0,0 +1 @@
|
||||
../../../VERSION
|
15
src/tools/kata-ctl/src/arch/aarch64/mod.rs
Normal file
15
src/tools/kata-ctl/src/arch/aarch64/mod.rs
Normal file
@ -0,0 +1,15 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#[cfg(target_arch = "aarch64")]
|
||||
pub use arch_specific::*;
|
||||
|
||||
mod arch_specific {
|
||||
use anyhow::Result;
|
||||
|
||||
pub fn check() -> Result<()> {
|
||||
unimplemented!("Check not implemented in aarch64")
|
||||
}
|
||||
}
|
42
src/tools/kata-ctl/src/arch/mod.rs
Normal file
42
src/tools/kata-ctl/src/arch/mod.rs
Normal file
@ -0,0 +1,42 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
use anyhow::Result;
|
||||
|
||||
#[cfg(target_arch = "aarch64")]
|
||||
pub mod aarch64;
|
||||
|
||||
#[cfg(target_arch = "powerpc64le")]
|
||||
pub mod powerpc64le;
|
||||
|
||||
#[cfg(target_arch = "s390x")]
|
||||
pub mod s390x;
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
pub mod x86_64;
|
||||
|
||||
pub fn check() -> Result<()> {
|
||||
#[cfg(target_arch = "aarch64")]
|
||||
let result = aarch64::check();
|
||||
|
||||
#[cfg(target_arch = "powerpc64le")]
|
||||
let result = powerpc64le::check();
|
||||
|
||||
#[cfg(target_arch = "s390x")]
|
||||
let result = s390x::check();
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
let result = x86_64::check();
|
||||
|
||||
#[cfg(not(any(
|
||||
target_arch = "aarch64",
|
||||
target_arch = "powerpc64le",
|
||||
target_arch = "s390x",
|
||||
target_arch = "x86_64"
|
||||
)))]
|
||||
compile_error!("unknown architecture");
|
||||
|
||||
result
|
||||
}
|
15
src/tools/kata-ctl/src/arch/powerpc64le/mod.rs
Normal file
15
src/tools/kata-ctl/src/arch/powerpc64le/mod.rs
Normal file
@ -0,0 +1,15 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#[cfg(target_arch = "powerpc64le")]
|
||||
pub use arch_specific::*;
|
||||
|
||||
mod arch_specific {
|
||||
use anyhow::Result;
|
||||
|
||||
pub fn check() -> Result<()> {
|
||||
unimplemented!("Check not implemented in powerpc64le");
|
||||
}
|
||||
}
|
15
src/tools/kata-ctl/src/arch/s390x/mod.rs
Normal file
15
src/tools/kata-ctl/src/arch/s390x/mod.rs
Normal file
@ -0,0 +1,15 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#[cfg(target_arch = "s390x")]
|
||||
pub use arch_specific::*;
|
||||
|
||||
mod arch_specific {
|
||||
use anyhow::Result;
|
||||
|
||||
pub fn check() -> Result<()> {
|
||||
unimplemented!("Check not implemented in s390x");
|
||||
}
|
||||
}
|
55
src/tools/kata-ctl/src/arch/x86_64/mod.rs
Normal file
55
src/tools/kata-ctl/src/arch/x86_64/mod.rs
Normal file
@ -0,0 +1,55 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#[cfg(target_arch = "x86_64")]
|
||||
pub use arch_specific::*;
|
||||
|
||||
mod arch_specific {
|
||||
use crate::check;
|
||||
use anyhow::{anyhow, Result};
|
||||
|
||||
const PROC_CPUINFO: &str = "/proc/cpuinfo";
|
||||
const CPUINFO_DELIMITER: &str = "\nprocessor";
|
||||
const CPUINFO_FLAGS_TAG: &str = "flags";
|
||||
const CPU_FLAGS_INTEL: &[&str] = &["lm", "sse4_1", "vmx"];
|
||||
const CPU_ATTRIBS_INTEL: &[&str] = &["GenuineIntel"];
|
||||
|
||||
// check cpu
|
||||
fn check_cpu() -> Result<()> {
|
||||
println!("INFO: check CPU: x86_64");
|
||||
|
||||
let cpu_info = check::get_single_cpu_info(PROC_CPUINFO, CPUINFO_DELIMITER)?;
|
||||
|
||||
let cpu_flags = check::get_cpu_flags(&cpu_info, CPUINFO_FLAGS_TAG)
|
||||
.map_err(|e| anyhow!("Error parsing CPU flags, file {:?}, {:?}", PROC_CPUINFO, e))?;
|
||||
|
||||
// perform checks
|
||||
// TODO: Perform checks based on hypervisor type
|
||||
// TODO: Add more information to output (see kata-check in go tool); adjust formatting
|
||||
let missing_cpu_attributes = check::check_cpu_attribs(&cpu_info, CPU_ATTRIBS_INTEL)?;
|
||||
if !missing_cpu_attributes.is_empty() {
|
||||
eprintln!(
|
||||
"WARNING: Missing CPU attributes {:?}",
|
||||
missing_cpu_attributes
|
||||
);
|
||||
}
|
||||
let missing_cpu_flags = check::check_cpu_flags(&cpu_flags, CPU_FLAGS_INTEL)?;
|
||||
if !missing_cpu_flags.is_empty() {
|
||||
eprintln!("WARNING: Missing CPU flags {:?}", missing_cpu_flags);
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn check() -> Result<()> {
|
||||
println!("INFO: check: x86_64");
|
||||
|
||||
let _cpu_result = check_cpu();
|
||||
|
||||
// TODO: collect outcome of tests to determine if checks pass or not
|
||||
|
||||
Ok(())
|
||||
}
|
||||
}
|
86
src/tools/kata-ctl/src/args.rs
Normal file
86
src/tools/kata-ctl/src/args.rs
Normal file
@ -0,0 +1,86 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
use clap::{Args, Parser, Subcommand};
|
||||
|
||||
use thiserror::Error;
|
||||
|
||||
#[derive(Parser, Debug)]
|
||||
#[clap(name = "kata-ctl", author, about = "Kata Containers control tool")]
|
||||
pub struct KataCtlCli {
|
||||
#[clap(subcommand)]
|
||||
pub command: Commands,
|
||||
}
|
||||
|
||||
#[derive(Debug, Subcommand)]
|
||||
pub enum Commands {
|
||||
/// Tests if system can run Kata Containers
|
||||
Check(CheckArgument),
|
||||
|
||||
/// Directly assign a volume to Kata Containers to manage
|
||||
DirectVolume,
|
||||
|
||||
/// Display settings
|
||||
Env,
|
||||
|
||||
/// Enter into guest by debug console
|
||||
Exec,
|
||||
|
||||
/// Manage vm factory
|
||||
Factory,
|
||||
|
||||
/// Manages iptables
|
||||
Iptables(IptablesCommand),
|
||||
|
||||
/// Gather metrics associated with infrastructure used to run a sandbox
|
||||
Metrics(MetricsCommand),
|
||||
|
||||
/// Display version details
|
||||
Version,
|
||||
}
|
||||
|
||||
#[derive(Debug, Args, Error)]
|
||||
#[error("Argument is not valid")]
|
||||
pub struct CheckArgument {
|
||||
#[clap(subcommand)]
|
||||
pub command: CheckSubCommand,
|
||||
}
|
||||
|
||||
#[derive(Debug, Subcommand)]
|
||||
pub enum CheckSubCommand {
|
||||
/// Runs all checks
|
||||
All,
|
||||
|
||||
/// Runs all checks but excluding network checks.
|
||||
NoNetworkChecks,
|
||||
|
||||
/// Only compare the current and latest available versions
|
||||
CheckVersionOnly,
|
||||
}
|
||||
|
||||
#[derive(Debug, Args)]
|
||||
pub struct MetricsCommand {
|
||||
#[clap(subcommand)]
|
||||
pub metrics_cmd: MetricsSubCommand,
|
||||
}
|
||||
|
||||
#[derive(Debug, Subcommand)]
|
||||
pub enum MetricsSubCommand {
|
||||
/// Arguments for metrics
|
||||
MetricsArgs,
|
||||
}
|
||||
|
||||
// #[derive(Parser, Debug)]
|
||||
#[derive(Debug, Args)]
|
||||
pub struct IptablesCommand {
|
||||
#[clap(subcommand)]
|
||||
pub iptables: IpTablesArguments,
|
||||
}
|
||||
|
||||
#[derive(Debug, Subcommand)]
|
||||
pub enum IpTablesArguments {
|
||||
/// Configure iptables
|
||||
Metrics,
|
||||
}
|
200
src/tools/kata-ctl/src/check.rs
Normal file
200
src/tools/kata-ctl/src/check.rs
Normal file
@ -0,0 +1,200 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
// Contains checks that are not architecture-specific
|
||||
|
||||
use anyhow::{anyhow, Result};
|
||||
use reqwest::header::{CONTENT_TYPE, USER_AGENT};
|
||||
use serde_json::Value;
|
||||
use std::collections::HashMap;
|
||||
use std::fs;
|
||||
|
||||
const KATA_GITHUB_URL: &str =
|
||||
"https://api.github.com/repos/kata-containers/kata-containers/releases/latest";
|
||||
|
||||
fn get_cpu_info(cpu_info_file: &str) -> Result<String> {
|
||||
let contents = fs::read_to_string(cpu_info_file)?;
|
||||
Ok(contents)
|
||||
}
|
||||
|
||||
// get_single_cpu_info returns the contents of the first cpu from
|
||||
// the specified cpuinfo file by parsing based on a specified delimiter
|
||||
pub fn get_single_cpu_info(cpu_info_file: &str, substring: &str) -> Result<String> {
|
||||
let contents = get_cpu_info(cpu_info_file)?;
|
||||
|
||||
if contents.is_empty() {
|
||||
return Err(anyhow!("cpu_info string is empty"))?;
|
||||
}
|
||||
|
||||
let subcontents: Vec<&str> = contents.split(substring).collect();
|
||||
let result = subcontents
|
||||
.first()
|
||||
.ok_or("error splitting contents of cpuinfo")
|
||||
.map_err(|e| anyhow!(e))?
|
||||
.to_string();
|
||||
|
||||
Ok(result)
|
||||
}
|
||||
|
||||
// get_cpu_flags returns a string of cpu flags from cpuinfo, passed in
|
||||
// as a string
|
||||
pub fn get_cpu_flags(cpu_info: &str, cpu_flags_tag: &str) -> Result<String> {
|
||||
if cpu_info.is_empty() {
|
||||
return Err(anyhow!("cpu_info string is empty"))?;
|
||||
}
|
||||
|
||||
let subcontents: Vec<&str> = cpu_info.split('\n').collect();
|
||||
for line in subcontents {
|
||||
if line.starts_with(cpu_flags_tag) {
|
||||
let line_data: Vec<&str> = line.split(':').collect();
|
||||
let flags = line_data
|
||||
.last()
|
||||
.ok_or("error splitting flags in cpuinfo")
|
||||
.map_err(|e| anyhow!(e))?
|
||||
.to_string();
|
||||
return Ok(flags);
|
||||
}
|
||||
}
|
||||
|
||||
Ok("".to_string())
|
||||
}
|
||||
|
||||
// get_missing_strings searches for required (strings) in data and returns
|
||||
// a vector containing the missing strings
|
||||
fn get_missing_strings(data: &str, required: &'static [&'static str]) -> Result<Vec<String>> {
|
||||
let mut missing: Vec<String> = Vec::new();
|
||||
|
||||
for item in required {
|
||||
if !data.split_whitespace().any(|x| x == *item) {
|
||||
missing.push(item.to_string());
|
||||
}
|
||||
}
|
||||
|
||||
Ok(missing)
|
||||
}
|
||||
|
||||
pub fn check_cpu_flags(
|
||||
retrieved_flags: &str,
|
||||
required_flags: &'static [&'static str],
|
||||
) -> Result<Vec<String>> {
|
||||
let missing_flags = get_missing_strings(retrieved_flags, required_flags)?;
|
||||
|
||||
Ok(missing_flags)
|
||||
}
|
||||
|
||||
pub fn check_cpu_attribs(
|
||||
cpu_info: &str,
|
||||
required_attribs: &'static [&'static str],
|
||||
) -> Result<Vec<String>> {
|
||||
let mut cpu_info_processed = cpu_info.replace('\t', "");
|
||||
cpu_info_processed = cpu_info_processed.replace('\n', " ");
|
||||
|
||||
let missing_attribs = get_missing_strings(&cpu_info_processed, required_attribs)?;
|
||||
Ok(missing_attribs)
|
||||
}
|
||||
|
||||
pub fn run_network_checks() -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn get_kata_version_by_url(url: &str) -> std::result::Result<String, reqwest::Error> {
|
||||
let content = reqwest::blocking::Client::new()
|
||||
.get(url)
|
||||
.header(CONTENT_TYPE, "application/json")
|
||||
.header(USER_AGENT, "kata")
|
||||
.send()?
|
||||
.json::<HashMap<String, Value>>()?;
|
||||
|
||||
let version = content["tag_name"].as_str().unwrap();
|
||||
Ok(version.to_string())
|
||||
}
|
||||
|
||||
fn handle_reqwest_error(e: reqwest::Error) -> anyhow::Error {
|
||||
if e.is_connect() {
|
||||
return anyhow!(e).context("http connection failure: connection refused");
|
||||
}
|
||||
|
||||
if e.is_timeout() {
|
||||
return anyhow!(e).context("http connection failure: connection timeout");
|
||||
}
|
||||
|
||||
if e.is_builder() {
|
||||
return anyhow!(e).context("http connection failure: url malformed");
|
||||
}
|
||||
|
||||
if e.is_decode() {
|
||||
return anyhow!(e).context("http connection failure: unable to decode response body");
|
||||
}
|
||||
|
||||
anyhow!(e).context("unknown http connection failure: {:?}")
|
||||
}
|
||||
|
||||
pub fn check_version() -> Result<()> {
|
||||
let version = get_kata_version_by_url(KATA_GITHUB_URL).map_err(handle_reqwest_error)?;
|
||||
|
||||
println!("Version: {}", version);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use semver::Version;
|
||||
|
||||
#[test]
|
||||
fn test_get_cpu_info_empty_input() {
|
||||
let expected = "No such file or directory (os error 2)";
|
||||
let actual = get_cpu_info("").err().unwrap().to_string();
|
||||
assert_eq!(expected, actual);
|
||||
|
||||
let actual = get_single_cpu_info("", "\nprocessor")
|
||||
.err()
|
||||
.unwrap()
|
||||
.to_string();
|
||||
assert_eq!(expected, actual);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_get_cpu_flags_empty_input() {
|
||||
let expected = "cpu_info string is empty";
|
||||
let actual = get_cpu_flags("", "").err().unwrap().to_string();
|
||||
assert_eq!(expected, actual);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn check_version_by_empty_url() {
|
||||
const TEST_URL: &str = "http:";
|
||||
let expected = "builder error: empty host";
|
||||
let actual = get_kata_version_by_url(TEST_URL).err().unwrap().to_string();
|
||||
assert_eq!(expected, actual);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn check_version_by_garbage_url() {
|
||||
const TEST_URL: &str = "_localhost_";
|
||||
let expected = "builder error: relative URL without a base";
|
||||
let actual = get_kata_version_by_url(TEST_URL).err().unwrap().to_string();
|
||||
assert_eq!(expected, actual);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn check_version_by_invalid_url() {
|
||||
const TEST_URL: &str = "http://localhost :80";
|
||||
let expected = "builder error: invalid domain character";
|
||||
let actual = get_kata_version_by_url(TEST_URL).err().unwrap().to_string();
|
||||
assert_eq!(expected, actual);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn check_latest_version() {
|
||||
let version = get_kata_version_by_url(KATA_GITHUB_URL).unwrap();
|
||||
|
||||
let v = Version::parse(&version).unwrap();
|
||||
assert!(!v.major.to_string().is_empty());
|
||||
assert!(!v.minor.to_string().is_empty());
|
||||
assert!(!v.patch.to_string().is_empty());
|
||||
}
|
||||
}
|
42
src/tools/kata-ctl/src/main.rs
Normal file
42
src/tools/kata-ctl/src/main.rs
Normal file
@ -0,0 +1,42 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
mod arch;
|
||||
mod args;
|
||||
mod check;
|
||||
mod ops;
|
||||
|
||||
use anyhow::Result;
|
||||
use clap::Parser;
|
||||
use std::process::exit;
|
||||
|
||||
use args::{Commands, KataCtlCli};
|
||||
|
||||
use ops::check_ops::{
|
||||
handle_check, handle_check_volume, handle_env, handle_exec, handle_factory, handle_iptables,
|
||||
handle_metrics, handle_version,
|
||||
};
|
||||
|
||||
fn real_main() -> Result<()> {
|
||||
let args = KataCtlCli::parse();
|
||||
|
||||
match args.command {
|
||||
Commands::Check(args) => handle_check(args),
|
||||
Commands::DirectVolume => handle_check_volume(),
|
||||
Commands::Env => handle_env(),
|
||||
Commands::Exec => handle_exec(),
|
||||
Commands::Factory => handle_factory(),
|
||||
Commands::Iptables(args) => handle_iptables(args),
|
||||
Commands::Metrics(args) => handle_metrics(args),
|
||||
Commands::Version => handle_version(),
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
if let Err(e) = real_main() {
|
||||
eprintln!("ERROR: {:#?}", e);
|
||||
exit(1);
|
||||
}
|
||||
}
|
7
src/tools/kata-ctl/src/ops.rs
Normal file
7
src/tools/kata-ctl/src/ops.rs
Normal file
@ -0,0 +1,7 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
pub mod check_ops;
|
||||
pub mod version;
|
70
src/tools/kata-ctl/src/ops/check_ops.rs
Normal file
70
src/tools/kata-ctl/src/ops/check_ops.rs
Normal file
@ -0,0 +1,70 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
use crate::arch;
|
||||
use crate::check;
|
||||
use crate::ops::version;
|
||||
|
||||
use crate::args::{CheckArgument, CheckSubCommand, IptablesCommand, MetricsCommand};
|
||||
|
||||
use anyhow::Result;
|
||||
|
||||
const NAME: &str = "kata-ctl";
|
||||
|
||||
pub fn handle_check(checkcmd: CheckArgument) -> Result<()> {
|
||||
let command = checkcmd.command;
|
||||
|
||||
match command {
|
||||
CheckSubCommand::All => {
|
||||
// run architecture-specific tests
|
||||
arch::check()?;
|
||||
|
||||
// run code that uses network checks
|
||||
check::run_network_checks()?;
|
||||
}
|
||||
|
||||
CheckSubCommand::NoNetworkChecks => {
|
||||
// run architecture-specific tests
|
||||
arch::check()?;
|
||||
}
|
||||
|
||||
CheckSubCommand::CheckVersionOnly => {
|
||||
// retrieve latest release
|
||||
check::check_version()?;
|
||||
}
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_check_volume() -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_env() -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_exec() -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_factory() -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_iptables(_args: IptablesCommand) -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_metrics(_args: MetricsCommand) -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn handle_version() -> Result<()> {
|
||||
let version = version::get().unwrap();
|
||||
println!("{} version {:?} (type: rust)", NAME, version);
|
||||
Ok(())
|
||||
}
|
39
src/tools/kata-ctl/src/ops/version.rs.in
Normal file
39
src/tools/kata-ctl/src/ops/version.rs.in
Normal file
@ -0,0 +1,39 @@
|
||||
// Copyright (c) 2022 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
//
|
||||
// WARNING: This file is auto-generated - DO NOT EDIT!
|
||||
//
|
||||
|
||||
use clap::crate_version;
|
||||
|
||||
const KATA_CTL_VERSION: &str = "@KATA_CTL_VERSION@";
|
||||
|
||||
pub fn get() -> Result<String, String> {
|
||||
if KATA_CTL_VERSION.trim().is_empty() {
|
||||
Err("Unable to retrieve kata Version. Check that Kata is properly installed".to_string())
|
||||
} else {
|
||||
let version = format!("{}-{}", KATA_CTL_VERSION, crate_version!());
|
||||
|
||||
Ok(version)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use semver::Version;
|
||||
|
||||
#[test]
|
||||
fn test_get() {
|
||||
let version = get().unwrap();
|
||||
let v = Version::parse(&version).unwrap();
|
||||
|
||||
assert!(!v.major.to_string().is_empty());
|
||||
assert!(!v.minor.to_string().is_empty());
|
||||
assert!(!v.patch.to_string().is_empty());
|
||||
assert!(!v.pre.to_string().is_empty());
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user