Skip to content

Commit d7b2b4b

Browse files
author
黄顽强
committed
Merge branch 'issues/78-support-sparse-checkout-dirs' into 'master'
Resolve "#PEGE-3141 配置文件支持 sparse-checkout-dirs 字段" Closes #78 See merge request devtools/mgit!87
2 parents 6c53fbf + dc6a7ac commit d7b2b4b

File tree

7 files changed

+121
-2
lines changed

7 files changed

+121
-2
lines changed

Cargo.toml

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ members = [
77
resolver = "2"
88

99
[workspace.package]
10-
version = "1.2.2"
10+
version = "1.2.3"
1111
edition = "2021"
1212
rust-version = "1.74.0"
1313
repository = "https://github.com/funny/mgit"

core/src/core/git.rs

+17
Original file line numberDiff line numberDiff line change
@@ -273,3 +273,20 @@ pub fn log_current(path: impl AsRef<Path>) -> Result<String, anyhow::Error> {
273273
];
274274
exec_cmd(path, "git", &args)
275275
}
276+
277+
pub fn sparse_checkout_set(
278+
path: impl AsRef<Path>,
279+
dirs: &Vec<String>,
280+
) -> Result<(), anyhow::Error> {
281+
let mut args = vec!["sparse-checkout", "set", "--no-cone"];
282+
for dir in dirs {
283+
args.push(dir)
284+
}
285+
286+
exec_cmd(path, "git", &args).map(|_| ())
287+
}
288+
289+
pub fn sparse_checkout_disable(path: impl AsRef<Path>) -> Result<(), anyhow::Error> {
290+
let args = vec!["sparse-checkout", "disable"];
291+
exec_cmd(path, "git", &args).map(|_| ())
292+
}

core/src/core/repo.rs

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ pub struct TomlRepo {
2222
pub branch: Option<String>,
2323
pub tag: Option<String>,
2424
pub commit: Option<String>,
25+
pub sparse_checkout_dirs: Option<Vec<String>>,
2526
}
2627

2728
impl RepoId {

core/src/ops/snapshot.rs

+1
Original file line numberDiff line numberDiff line change
@@ -154,6 +154,7 @@ pub fn snapshot_repo(options: SnapshotOptions) -> MgitResult {
154154
branch,
155155
tag: None,
156156
commit,
157+
sparse_checkout_dirs: None,
157158
};
158159
repos.push(toml_repo);
159160
logger::info(format!(" + {}", norm_str));

core/src/ops/sync.rs

+7-1
Original file line numberDiff line numberDiff line change
@@ -365,6 +365,11 @@ fn inner_exec(
365365
// reset --hard
366366
exec_reset(input_path, repo_info, progress, ResetType::Hard)
367367
}
368+
}?;
369+
370+
match repo_info.toml_repo.sparse_checkout_dirs.as_ref() {
371+
Some(dirs) => git::sparse_checkout_set(&full_path, dirs),
372+
None => git::sparse_checkout_disable(&full_path),
368373
}
369374
}
370375

@@ -420,7 +425,8 @@ fn exec_reset(
420425
ResetType::Mixed => "--mixed",
421426
ResetType::Hard => "--hard",
422427
};
423-
git::reset(full_path, reset_type, remote_ref_str)
428+
429+
git::reset(&full_path, reset_type, remote_ref_str)
424430
}
425431

426432
fn exec_stash(

core/tests/common.rs

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ pub mod failed_message {
2222
pub const GIT_FETCH: &str = "git fetch failed";
2323
pub const GIT_CONFIG: &str = "git config failed";
2424
pub const GIT_REV_LIST: &str = "git rev-list failed";
25+
pub const GIT_SPARSE_CHECKOUT: &str = "git sparse-checkout failed";
2526

2627
pub const WRITE_FILE: &str = "write file failed";
2728
}

core/tests/sync_test.rs

+93
Original file line numberDiff line numberDiff line change
@@ -1707,3 +1707,96 @@ fn cli_sync_new_remote_url() -> MgitResult<()> {
17071707
std::fs::remove_dir_all(&path).unwrap();
17081708
Ok(())
17091709
}
1710+
1711+
/// 测试内容:
1712+
/// 1、运行命令 mgit sync <path> --no-checkout
1713+
/// 2、检查配置的稀疏检出是否和预期匹配
1714+
/// 3、根目录是仓库
1715+
///
1716+
/// 测试目录结构:
1717+
/// cli_sync_with_sparse_checkout_dirs(.git)
1718+
/// ├─Doc
1719+
/// ├─img
1720+
/// └─README.md
1721+
#[test]
1722+
fn cli_sync_with_sparse_checkout_dirs() -> MgitResult<()> {
1723+
let path = env::current_dir()
1724+
.unwrap()
1725+
.join("target")
1726+
.join("tmp")
1727+
.join("cli_sync_with_sparse_checkout_dirs");
1728+
let input_path = path.to_str().unwrap();
1729+
1730+
let _ = std::fs::remove_dir_all(&path);
1731+
std::fs::create_dir_all(&path).unwrap();
1732+
1733+
let mut toml_string = TomlBuilder::default()
1734+
.default_branch("develop")
1735+
.join_repo(".", &CSBOOKS_REPO, Some("master"), None, None)
1736+
.build();
1737+
let sparse_checkout_dirs = r#"sparse-checkout-dirs = ["Doc", "/*.md"]"#;
1738+
toml_string.push_str(sparse_checkout_dirs);
1739+
1740+
let config_file = path.join(".gitrepos");
1741+
std::fs::write(&config_file, toml_string.trim()).expect(failed_message::WRITE_FILE);
1742+
1743+
// initialize the repositories tree
1744+
ops::sync_repo(
1745+
SyncOptions::new(
1746+
Some(input_path),
1747+
None::<PathBuf>,
1748+
None,
1749+
None,
1750+
None,
1751+
None,
1752+
Some(true),
1753+
None,
1754+
Some(true),
1755+
None,
1756+
),
1757+
TestProgress,
1758+
)?;
1759+
1760+
// compaire sparse-checkout list
1761+
if let Ok(output) = exec_cmd(&path, "git", &["sparse-checkout", "list"]) {
1762+
assert_eq!(output.contains("Doc"), true);
1763+
assert_eq!(output.contains("img"), false);
1764+
assert_eq!(output.contains("/*.md"), true);
1765+
1766+
assert_eq!(path.join("Doc").exists(), true);
1767+
assert_eq!(path.join("img").exists(), false);
1768+
assert_eq!(path.join("README.md").exists(), true);
1769+
} else {
1770+
panic!("{}", failed_message::GIT_SPARSE_CHECKOUT);
1771+
}
1772+
1773+
toml_string = toml_string.replace(sparse_checkout_dirs, "");
1774+
std::fs::write(&config_file, toml_string.trim()).expect(failed_message::WRITE_FILE);
1775+
// excute sync
1776+
ops::sync_repo(
1777+
SyncOptions::new(
1778+
Some(input_path),
1779+
None::<PathBuf>,
1780+
None,
1781+
None,
1782+
None,
1783+
None,
1784+
None,
1785+
None,
1786+
None,
1787+
Some(true),
1788+
),
1789+
TestProgress,
1790+
)?;
1791+
1792+
// compaire sparse-checkout list
1793+
let res = exec_cmd(&path, "git", &["sparse-checkout", "list"]);
1794+
assert!(res.is_err());
1795+
assert_eq!(path.join("Doc").exists(), true);
1796+
assert_eq!(path.join("img").exists(), true);
1797+
assert_eq!(path.join("README.md").exists(), true);
1798+
1799+
// clean-up
1800+
std::fs::remove_dir_all(&path).unwrap();
1801+
Ok(())
1802+
}

0 commit comments

Comments
 (0)