diff --git a/helix-stdx/src/faccess.rs b/helix-stdx/src/faccess.rs index 11083baf..8be9df1b 100644 --- a/helix-stdx/src/faccess.rs +++ b/helix-stdx/src/faccess.rs @@ -547,10 +547,7 @@ pub fn copy_xattr(src: &Path, dst: &Path) -> io::Result<()> { } let mut attr_buf = vec![0u8; max_val_len]; - for key in key_list[..size] - .split(|&b| b == 0) - .filter(|v| !v.is_empty()) - { + for key in key_list[..size].split_inclusive(|&b| b == 0) { // Needed on macos #[allow(clippy::unnecessary_cast)] let conv = unsafe { std::slice::from_raw_parts(key.as_ptr() as *const u8, key.len()) }; diff --git a/helix-term/tests/test/commands/write.rs b/helix-term/tests/test/commands/write.rs index 336ab2ab..0be0298e 100644 --- a/helix-term/tests/test/commands/write.rs +++ b/helix-term/tests/test/commands/write.rs @@ -687,6 +687,36 @@ async fn test_hardlink_write() -> anyhow::Result<()> { Ok(()) } +#[tokio::test(flavor = "multi_thread")] +#[cfg(unix)] +async fn test_write_ownership() -> anyhow::Result<()> { + // GH CI does not possess CAP_CHOWN + if option_env!("GITHUB_ACTIONS").is_some() { + return Ok(()); + } + use std::os::unix::fs::MetadataExt; + + let mut file = tempfile::NamedTempFile::new()?; + let mut app = helpers::AppBuilder::new() + .with_file(file.path(), None) + .build()?; + + let nobody_uid = 9999; + let nogroup_gid = 9999; + + helix_stdx::faccess::fchown(&file.as_file_mut(), Some(nobody_uid), Some(nogroup_gid))?; + + let old_meta = file.as_file().metadata()?; + + test_key_sequence(&mut app, Some("hello:w"), None, false).await?; + reload_file(&mut file).unwrap(); + + let new_meta = file.as_file().metadata()?; + assert!(old_meta.uid() == new_meta.uid() && old_meta.gid() == new_meta.gid()); + + Ok(()) +} + async fn edit_file_with_content(file_content: &[u8]) -> anyhow::Result<()> { let mut file = tempfile::NamedTempFile::new()?;