Skip to content

Commit 12de52b

Browse files
committed
add coverage on config include logic
Signed-off-by: onur-ozkan <[email protected]>
1 parent 8270478 commit 12de52b

File tree

1 file changed

+208
-2
lines changed

1 file changed

+208
-2
lines changed

Diff for: src/bootstrap/src/core/config/tests.rs

+208-2
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
use std::collections::BTreeSet;
2-
use std::env;
32
use std::fs::{File, remove_file};
43
use std::io::Write;
5-
use std::path::Path;
4+
use std::path::{Path, PathBuf};
5+
use std::{env, fs};
66

77
use build_helper::ci::CiEnv;
88
use clap::CommandFactory;
@@ -23,6 +23,27 @@ pub(crate) fn parse(config: &str) -> Config {
2323
)
2424
}
2525

26+
fn get_toml(file: &Path) -> Result<TomlConfig, toml::de::Error> {
27+
let contents = std::fs::read_to_string(file).unwrap();
28+
toml::from_str(&contents).and_then(|table: toml::Value| TomlConfig::deserialize(table))
29+
}
30+
31+
/// Helps with debugging by using consistent test-specific directories instead of
32+
/// random temporary directories.
33+
fn prepare_test_specific_dir() -> PathBuf {
34+
let current = std::thread::current();
35+
// Replace "::" with "_" to make it safe for directory names on Windows systems
36+
let test_path = current.name().unwrap().replace("::", "_");
37+
38+
let testdir = parse("").tempdir().join(test_path);
39+
40+
// clean up any old test files
41+
let _ = fs::remove_dir_all(&testdir);
42+
let _ = fs::create_dir_all(&testdir);
43+
44+
testdir
45+
}
46+
2647
#[test]
2748
fn download_ci_llvm() {
2849
let config = parse("llvm.download-ci-llvm = false");
@@ -539,3 +560,188 @@ fn test_ci_flag() {
539560
let config = Config::parse_inner(Flags::parse(&["check".into()]), |&_| toml::from_str(""));
540561
assert_eq!(config.is_running_on_ci, CiEnv::is_ci());
541562
}
563+
564+
#[test]
565+
fn test_precedence_of_includes() {
566+
let testdir = prepare_test_specific_dir();
567+
568+
let root_config = testdir.join("config.toml");
569+
let root_config_content = br#"
570+
include = ["./extension.toml"]
571+
572+
[llvm]
573+
link-jobs = 2
574+
"#;
575+
File::create(&root_config).unwrap().write_all(root_config_content).unwrap();
576+
577+
let extension = testdir.join("extension.toml");
578+
let extension_content = br#"
579+
change-id=543
580+
include = ["./extension2.toml"]
581+
"#;
582+
File::create(extension).unwrap().write_all(extension_content).unwrap();
583+
584+
let extension = testdir.join("extension2.toml");
585+
let extension_content = br#"
586+
change-id=742
587+
588+
[llvm]
589+
link-jobs = 10
590+
591+
[build]
592+
description = "Some creative description"
593+
"#;
594+
File::create(extension).unwrap().write_all(extension_content).unwrap();
595+
596+
let config = Config::parse_inner(
597+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
598+
get_toml,
599+
);
600+
601+
assert_eq!(config.change_id.unwrap(), ChangeId::Id(543));
602+
assert_eq!(config.llvm_link_jobs.unwrap(), 2);
603+
assert_eq!(config.description.unwrap(), "Some creative description");
604+
}
605+
606+
#[test]
607+
#[should_panic(expected = "Cyclic inclusion detected")]
608+
fn test_cyclic_include_direct() {
609+
let testdir = prepare_test_specific_dir();
610+
611+
let root_config = testdir.join("config.toml");
612+
let root_config_content = br#"
613+
include = ["./extension.toml"]
614+
"#;
615+
File::create(&root_config).unwrap().write_all(root_config_content).unwrap();
616+
617+
let extension = testdir.join("extension.toml");
618+
let extension_content = br#"
619+
include = ["./config.toml"]
620+
"#;
621+
File::create(extension).unwrap().write_all(extension_content).unwrap();
622+
623+
let config = Config::parse_inner(
624+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
625+
get_toml,
626+
);
627+
}
628+
629+
#[test]
630+
#[should_panic(expected = "Cyclic inclusion detected")]
631+
fn test_cyclic_include_indirect() {
632+
let testdir = prepare_test_specific_dir();
633+
634+
let root_config = testdir.join("config.toml");
635+
let root_config_content = br#"
636+
include = ["./extension.toml"]
637+
"#;
638+
File::create(&root_config).unwrap().write_all(root_config_content).unwrap();
639+
640+
let extension = testdir.join("extension.toml");
641+
let extension_content = br#"
642+
include = ["./extension2.toml"]
643+
"#;
644+
File::create(extension).unwrap().write_all(extension_content).unwrap();
645+
646+
let extension = testdir.join("extension2.toml");
647+
let extension_content = br#"
648+
include = ["./extension3.toml"]
649+
"#;
650+
File::create(extension).unwrap().write_all(extension_content).unwrap();
651+
652+
let extension = testdir.join("extension3.toml");
653+
let extension_content = br#"
654+
include = ["./extension.toml"]
655+
"#;
656+
File::create(extension).unwrap().write_all(extension_content).unwrap();
657+
658+
let config = Config::parse_inner(
659+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
660+
get_toml,
661+
);
662+
}
663+
664+
#[test]
665+
fn test_include_absolute_paths() {
666+
let testdir = prepare_test_specific_dir();
667+
668+
let extension = testdir.join("extension.toml");
669+
File::create(&extension).unwrap().write_all(&[]).unwrap();
670+
671+
let root_config = testdir.join("config.toml");
672+
let root_config_content =
673+
format!(r#"include = ["{}"]"#, extension.canonicalize().unwrap().to_str().unwrap());
674+
File::create(&root_config).unwrap().write_all(root_config_content.as_bytes()).unwrap();
675+
676+
let config = Config::parse_inner(
677+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
678+
get_toml,
679+
);
680+
}
681+
682+
#[test]
683+
fn test_include_relative_paths() {
684+
let testdir = prepare_test_specific_dir();
685+
686+
let _ = fs::create_dir_all(&testdir.join("subdir/another_subdir"));
687+
688+
let root_config = testdir.join("config.toml");
689+
let root_config_content = br#"
690+
include = ["./subdir/extension.toml"]
691+
"#;
692+
File::create(&root_config).unwrap().write_all(root_config_content).unwrap();
693+
694+
let extension = testdir.join("subdir/extension.toml");
695+
let extension_content = br#"
696+
include = ["../extension2.toml"]
697+
"#;
698+
File::create(extension).unwrap().write_all(extension_content).unwrap();
699+
700+
let extension = testdir.join("extension2.toml");
701+
let extension_content = br#"
702+
include = ["./subdir/another_subdir/extension3.toml"]
703+
"#;
704+
File::create(extension).unwrap().write_all(extension_content).unwrap();
705+
706+
let extension = testdir.join("subdir/another_subdir/extension3.toml");
707+
let extension_content = br#"
708+
include = ["../../extension4.toml"]
709+
"#;
710+
File::create(extension).unwrap().write_all(extension_content).unwrap();
711+
712+
let extension = testdir.join("extension4.toml");
713+
File::create(extension).unwrap().write_all(&[]).unwrap();
714+
715+
let config = Config::parse_inner(
716+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
717+
get_toml,
718+
);
719+
}
720+
721+
#[test]
722+
fn test_include_precedence_over_profile() {
723+
let testdir = prepare_test_specific_dir();
724+
725+
let root_config = testdir.join("config.toml");
726+
let root_config_content = br#"
727+
profile = "dist"
728+
include = ["./extension.toml"]
729+
"#;
730+
File::create(&root_config).unwrap().write_all(root_config_content).unwrap();
731+
732+
let extension = testdir.join("extension.toml");
733+
let extension_content = br#"
734+
[rust]
735+
channel = "dev"
736+
"#;
737+
File::create(extension).unwrap().write_all(extension_content).unwrap();
738+
739+
let config = Config::parse_inner(
740+
Flags::parse(&["check".to_owned(), format!("--config={}", root_config.to_str().unwrap())]),
741+
get_toml,
742+
);
743+
744+
// "dist" profile would normally set the channel to "auto-detect", but includes should
745+
// override profile settings, so we expect this to be "dev" here.
746+
assert_eq!(config.channel, "dev");
747+
}

0 commit comments

Comments
 (0)