Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement substitutions using the deploy.toml #1670

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion crates/argument_parsers/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ pub fn parse_network(network: &str) -> Result<Network> {
}
}

#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq, PartialOrd, Ord)]
pub struct NaoAddress {
pub ip: Ipv4Addr,
}
Expand Down
3 changes: 3 additions & 0 deletions deploy.toml.example
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@ branches = [
assignments = [
"33:1",
]
substitutions = [
# "34:1",
]
with_communication = false

[recording_intervals]
Expand Down
2 changes: 1 addition & 1 deletion tools/pepsi/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "pepsi"
version = "5.1.0"
version = "6.0.0"
edition.workspace = true
license.workspace = true
homepage.workspace = true
Expand Down
83 changes: 64 additions & 19 deletions tools/pepsi/src/deploy_config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,17 @@ use std::{collections::HashMap, str::FromStr};
use chrono::Utc;
use color_eyre::{eyre::WrapErr, Result};
use serde::{de::Error as DeserializeError, Deserialize, Deserializer};
use spl_network_messages::PlayerNumber;
use tokio::fs::read_to_string;
use toml::from_str;

use argument_parsers::{parse_network, NaoAddress, NaoAddressPlayerAssignment};
use argument_parsers::{
parse_network, NaoAddress, NaoAddressPlayerAssignment, NaoNumberPlayerAssignment,
};
use nao::Network;
use repository::Repository;

use crate::player_number::{player_number, Arguments};
use crate::player_number::{check_for_duplication, player_number, Arguments};

#[derive(Deserialize)]
pub struct DeployConfig {
Expand All @@ -23,6 +26,8 @@ pub struct DeployConfig {
pub branches: Vec<Branch>,
#[serde(deserialize_with = "deserialize_assignments")]
pub assignments: Vec<NaoAddressPlayerAssignment>,
#[serde(deserialize_with = "deserialize_assignments")]
pub substitutions: Vec<NaoAddressPlayerAssignment>,
pub with_communication: bool,
pub recording_intervals: HashMap<String, usize>,
}
Expand Down Expand Up @@ -57,14 +62,46 @@ impl DeployConfig {
branch_name
}

pub fn naos(&self) -> Vec<NaoAddress> {
self.assignments
pub fn playing_naos(&self) -> Result<Vec<NaoAddress>> {
Ok(self.assignments()?.into_values().collect())
}

pub fn all_naos(&self) -> Vec<NaoAddress> {
let mut naos: Vec<_> = self
.assignments
.iter()
.chain(&self.substitutions)
.map(|assignment| assignment.nao_address)
.collect()
.collect();

naos.sort_unstable();
naos.dedup();

naos
}

pub async fn configure_repository(self, repository: &Repository) -> Result<()> {
player_number(
Arguments {
assignments: self
.assignments()?
.into_iter()
.map(|(player_number, nao_address)| {
nao_address
.try_into()
.map(|nao_number| NaoNumberPlayerAssignment {
nao_number,
player_number,
})
})
.collect::<Result<Vec<_>, _>>()
.wrap_err("failed to convert NAO addresses to NAO numbers")?,
},
repository,
)
.await
.wrap_err("failed to set player numbers")?;

repository
.configure_recording_intervals(self.recording_intervals)
.await
Expand All @@ -80,22 +117,30 @@ impl DeployConfig {
.await
.wrap_err("failed to set communication")?;

player_number(
Arguments {
assignments: self
.assignments
.iter()
.copied()
.map(TryFrom::try_from)
.collect::<Result<Vec<_>, _>>()?,
},
repository,
)
.await
.wrap_err("failed to set player numbers")?;

Ok(())
}

fn assignments(&self) -> Result<HashMap<PlayerNumber, NaoAddress>> {
let inital_assignments = self
.assignments
.iter()
.copied()
.map(TryInto::try_into)
.collect::<Result<Vec<_>, _>>()?;
check_for_duplication(&inital_assignments)?;

let mut assignments: HashMap<_, _> = self
.assignments
.iter()
.map(|assignment| (assignment.player_number, assignment.nao_address))
.collect();

for substitution in &self.substitutions {
assignments.insert(substitution.player_number, substitution.nao_address);
}

Ok(assignments)
}
}

fn deserialize_network<'de, D, E>(deserializer: D) -> Result<Network, E>
Expand Down
6 changes: 3 additions & 3 deletions tools/pepsi/src/player_number.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,9 @@ pub async fn player_number(arguments: Arguments, repository: &Repository) -> Res
Ok(())
}

fn check_for_duplication(assignments: &[NaoNumberPlayerAssignment]) -> Result<()> {
// Check if two NaoNumbers are assigned to the same PlayerNumber
// or if a NaoNumber is assigned to multiple PlayerNumbers
/// Check if two NaoNumbers are assigned to the same PlayerNumber
/// or if a NaoNumber is assigned to multiple PlayerNumbers
pub fn check_for_duplication(assignments: &[NaoNumberPlayerAssignment]) -> Result<()> {
let mut existing_player_numbers = HashSet::new();
let mut existing_nao_numbers = HashSet::new();

Expand Down
20 changes: 17 additions & 3 deletions tools/pepsi/src/post_game.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,10 @@ use std::{

use argument_parsers::NaoAddress;
use clap::{Args, ValueEnum};
use color_eyre::{eyre::WrapErr, Result};
use color_eyre::{
eyre::{bail, WrapErr},
Result,
};

use nao::{Nao, Network, SystemctlAction};
use repository::Repository;
Expand Down Expand Up @@ -48,7 +51,18 @@ pub async fn post_game(arguments: Arguments, repository: &Repository) -> Result<
let config = DeployConfig::read_from_file(repository)
.await
.wrap_err("failed to read deploy config from file")?;
let naos = arguments.naos.unwrap_or_else(|| config.naos());

let all_naos = config.all_naos();
let naos = if let Some(naos) = &arguments.naos {
for nao in naos {
if !all_naos.contains(nao) {
bail!("NAO with IP {nao} is not specified in the deploy.toml");
}
}
naos
} else {
&all_naos
};

let log_directory = &arguments.log_directory.unwrap_or_else(|| {
let log_directory_name = config.log_directory_name();
Expand All @@ -57,7 +71,7 @@ pub async fn post_game(arguments: Arguments, repository: &Repository) -> Result<
});

ProgressIndicator::map_tasks(
&naos,
naos,
"Executing postgame tasks...",
|nao_address, progress_bar| async move {
let nao = Nao::try_new_with_ping(nao_address.ip).await?;
Expand Down
8 changes: 4 additions & 4 deletions tools/pepsi/src/pre_game.rs
Original file line number Diff line number Diff line change
Expand Up @@ -72,16 +72,16 @@ pub async fn pre_game(arguments: Arguments, repository: &Repository) -> Result<(
config.recording_intervals = HashMap::from_iter(recording_intervals.iter().cloned());
}

let config_naos = config.naos();
let playing_naos = config.playing_naos()?;
let naos = if let Some(naos) = &arguments.pre_game.naos {
for nao in naos {
if !config_naos.contains(nao) {
bail!("NAO {nao} is not present in deploy.toml");
if !playing_naos.contains(nao) {
bail!("NAO with IP {nao} is not one of the playing NAOs in the deploy.toml");
}
}
naos
} else {
&config_naos
&playing_naos
};
let wifi = config.wifi;

Expand Down