|
| 1 | +use log; |
| 2 | +use log::{debug, info}; |
| 3 | +use serde::{Deserialize, Serialize}; |
| 4 | +use simple_logger; |
1 | 5 | use std::fs;
|
| 6 | +use std::io::Write; |
2 | 7 | use structopt::StructOpt;
|
| 8 | +use tinytemplate::TinyTemplate; |
| 9 | +use toml; |
3 | 10 |
|
4 |
| -// Search for a pattern in a file and display the lines that contain it. |
5 | 11 | #[derive(Debug, StructOpt)]
|
| 12 | +#[structopt(about = "A script to generate the master pre-receive hook file.")] |
6 | 13 | struct Cli {
|
7 |
| - // The path to the file to read |
8 |
| - #[structopt(parse(from_os_str))] |
| 14 | + #[structopt(parse(from_os_str), help = "Path to game config file to read")] |
9 | 15 | game_config_path: std::path::PathBuf,
|
| 16 | + |
| 17 | + #[structopt(parse(from_os_str), help = "Path to template file to read")] |
| 18 | + template_path: std::path::PathBuf, |
| 19 | + |
| 20 | + #[structopt( |
| 21 | + parse(from_os_str), |
| 22 | + default_value = "output/pre-receive", |
| 23 | + help = "Path to output file (creates if doesn't exist)" |
| 24 | + )] |
| 25 | + output_path: std::path::PathBuf, |
| 26 | + |
| 27 | + #[structopt( |
| 28 | + short = "v", |
| 29 | + long = "verbose", |
| 30 | + help = "Show more information about the actions taken" |
| 31 | + )] |
| 32 | + verbose: bool, |
10 | 33 | }
|
11 | 34 |
|
| 35 | +#[derive(Debug, Clone, Deserialize, Serialize)] |
12 | 36 | struct Level {
|
13 | 37 | title: String,
|
14 | 38 | branch: String,
|
15 |
| - solution_checke: String, |
| 39 | + solution_checker: String, |
16 | 40 | flags: Vec<String>,
|
17 | 41 | }
|
18 | 42 |
|
| 43 | +#[derive(Debug, Deserialize, Serialize)] |
19 | 44 | struct GameConfig {
|
20 | 45 | levels: Vec<Level>,
|
21 | 46 | }
|
22 | 47 |
|
| 48 | +fn replace_flags_with_branch_names(game_config: &mut GameConfig) { |
| 49 | + let levels_info = game_config.levels.clone(); |
| 50 | + |
| 51 | + for mut level in &mut game_config.levels { |
| 52 | + let mut new_flags = Vec::new(); |
| 53 | + for flag in &level.flags { |
| 54 | + debug!("level {} flag {}", level.title, flag); |
| 55 | + let mut levels_iterator = levels_info.iter(); |
| 56 | + let found = levels_iterator.find(|&x| &x.title == flag); |
| 57 | + match found { |
| 58 | + Some(x) => { |
| 59 | + debug!("replacing {} with {}", flag, x.branch); |
| 60 | + new_flags.push(String::from(&x.branch)); |
| 61 | + } |
| 62 | + None => { |
| 63 | + debug!("flag {} is final", flag); |
| 64 | + new_flags.push(flag.to_string()); |
| 65 | + } |
| 66 | + } |
| 67 | + } |
| 68 | + level.flags = new_flags; |
| 69 | + } |
| 70 | +} |
| 71 | + |
23 | 72 | fn main() {
|
24 | 73 | let args = Cli::from_args();
|
25 |
| - println!("Loading script from {:?}", args); |
26 | 74 |
|
27 |
| - let game_config_file_contents = |
28 |
| - fs::read_to_string(args.game_config_path).expect("Couldn't read the config file!"); |
| 75 | + if args.verbose { |
| 76 | + simple_logger::init_with_level(log::Level::Debug).unwrap(); |
| 77 | + } else { |
| 78 | + simple_logger::init_with_level(log::Level::Info).unwrap(); |
| 79 | + }; |
| 80 | + |
| 81 | + info!("Reading script from {:?}", args.game_config_path); |
| 82 | + let game_config_file_contents = fs::read_to_string(args.game_config_path).unwrap(); |
| 83 | + |
| 84 | + let mut game_config: GameConfig = toml::from_str(&game_config_file_contents).unwrap(); |
| 85 | + debug!("Game config before editing: {:?}\n", game_config); |
| 86 | + |
| 87 | + replace_flags_with_branch_names(&mut game_config); |
| 88 | + |
| 89 | + debug!("Game config after editing: {:?}\n", game_config); |
| 90 | + |
| 91 | + info!("Reading template from {:?}", args.template_path); |
| 92 | + let template_file_contents = fs::read_to_string(args.template_path).unwrap(); |
| 93 | + |
| 94 | + let mut tt = TinyTemplate::new(); |
| 95 | + let template_name = "switch_case"; |
| 96 | + tt.add_template(template_name, &template_file_contents) |
| 97 | + .unwrap(); |
| 98 | + let rendered = tt.render(template_name, &game_config).unwrap(); |
| 99 | + |
| 100 | + debug!("########## RENDERED TEMPLATE ##########"); |
| 101 | + debug!("{}\n", rendered); |
| 102 | + |
| 103 | + let mut output_dir = args.output_path.clone(); |
| 104 | + output_dir.pop(); |
| 105 | + fs::create_dir_all(&output_dir).expect("Failed to create parent dir"); |
| 106 | + let mut output_file = fs::File::create(&args.output_path).expect("Couldn't create file!"); |
| 107 | + output_file.write_all(&rendered.as_bytes()).unwrap(); |
29 | 108 |
|
30 |
| - println!("{}", game_config_file_contents); |
| 109 | + info!("Wrote rendered file to {:?}", args.output_path); |
31 | 110 | }
|
0 commit comments