mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-29 12:07:46 +00:00
Implemented --indicator-style flag on ls. (#1907)
* Implemented --indicator-style flag on ls. * Rust fmt * Grouped indicator_style args. * Added tests for sockets and pipes. Needed to modify util.rs to add support for pipes (aka FIFOs). * Updated util.rs to remove FIFO operations on Windows * Fixed slight error in specifying (not(windows)) * Fixed style violations and added indicator_style test for non-unix systems
This commit is contained in:
parent
8320b1ec5f
commit
5f17719a59
4 changed files with 290 additions and 34 deletions
|
@ -1,3 +1,5 @@
|
|||
#[cfg(unix)]
|
||||
extern crate unix_socket;
|
||||
use crate::common::util::*;
|
||||
|
||||
extern crate regex;
|
||||
|
@ -11,7 +13,13 @@ extern crate libc;
|
|||
#[cfg(not(windows))]
|
||||
use self::libc::umask;
|
||||
#[cfg(not(windows))]
|
||||
use std::path::PathBuf;
|
||||
#[cfg(not(windows))]
|
||||
use std::sync::Mutex;
|
||||
#[cfg(not(windows))]
|
||||
extern crate tempdir;
|
||||
#[cfg(not(windows))]
|
||||
use self::tempdir::TempDir;
|
||||
|
||||
#[cfg(not(windows))]
|
||||
lazy_static! {
|
||||
|
@ -813,6 +821,112 @@ fn test_ls_inode() {
|
|||
assert_eq!(inode_short, inode_long)
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(not(windows))]
|
||||
fn test_ls_indicator_style() {
|
||||
let scene = TestScenario::new(util_name!());
|
||||
let at = &scene.fixtures;
|
||||
|
||||
// Setup: Directory, Symlink, and Pipes.
|
||||
at.mkdir("directory");
|
||||
assert!(at.dir_exists("directory"));
|
||||
|
||||
at.touch(&at.plus_as_string("link-src"));
|
||||
at.symlink_file("link-src", "link-dest.link");
|
||||
assert!(at.is_symlink("link-dest.link"));
|
||||
|
||||
at.mkfifo("named-pipe.fifo");
|
||||
assert!(at.is_fifo("named-pipe.fifo"));
|
||||
|
||||
// Classify, File-Type, and Slash all contain indicators for directories.
|
||||
let options = vec!["classify", "file-type", "slash"];
|
||||
for opt in options {
|
||||
// Verify that classify and file-type both contain indicators for symlinks.
|
||||
let result = scene.ucmd().arg(format!("--indicator-style={}", opt)).run();
|
||||
println!("stdout = {:?}", result.stdout);
|
||||
assert!(result.stdout.contains("/"));
|
||||
}
|
||||
|
||||
// Same test as above, but with the alternate flags.
|
||||
let options = vec!["--classify", "--file-type", "-p"];
|
||||
for opt in options {
|
||||
let result = scene.ucmd().arg(format!("{}", opt)).run();
|
||||
println!("stdout = {:?}", result.stdout);
|
||||
assert!(result.stdout.contains("/"));
|
||||
}
|
||||
|
||||
// Classify and File-Type all contain indicators for pipes and links.
|
||||
let options = vec!["classify", "file-type"];
|
||||
for opt in options {
|
||||
// Verify that classify and file-type both contain indicators for symlinks.
|
||||
let result = scene.ucmd().arg(format!("--indicator-style={}", opt)).run();
|
||||
println!("stdout = {}", result.stdout);
|
||||
assert!(result.stdout.contains("@"));
|
||||
assert!(result.stdout.contains("|"));
|
||||
}
|
||||
|
||||
// Test sockets. Because the canonical way of making sockets to test is with
|
||||
// TempDir, we need a separate test.
|
||||
{
|
||||
use self::unix_socket::UnixListener;
|
||||
|
||||
let dir = TempDir::new("unix_socket").expect("failed to create dir");
|
||||
let socket_path = dir.path().join("sock");
|
||||
let _listener = UnixListener::bind(&socket_path).expect("failed to create socket");
|
||||
|
||||
new_ucmd!()
|
||||
.args(&[
|
||||
PathBuf::from(dir.path().to_str().unwrap()),
|
||||
PathBuf::from("--indicator-style=classify"),
|
||||
])
|
||||
.succeeds()
|
||||
.stdout_only("sock=\n");
|
||||
}
|
||||
}
|
||||
|
||||
// Essentially the same test as above, but only test symlinks and directories,
|
||||
// not pipes or sockets.
|
||||
#[test]
|
||||
#[cfg(not(unix))]
|
||||
fn test_ls_indicator_style() {
|
||||
let scene = TestScenario::new(util_name!());
|
||||
let at = &scene.fixtures;
|
||||
|
||||
// Setup: Directory, Symlink.
|
||||
at.mkdir("directory");
|
||||
assert!(at.dir_exists("directory"));
|
||||
|
||||
at.touch(&at.plus_as_string("link-src"));
|
||||
at.symlink_file("link-src", "link-dest.link");
|
||||
assert!(at.is_symlink("link-dest.link"));
|
||||
|
||||
// Classify, File-Type, and Slash all contain indicators for directories.
|
||||
let options = vec!["classify", "file-type", "slash"];
|
||||
for opt in options {
|
||||
// Verify that classify and file-type both contain indicators for symlinks.
|
||||
let result = scene.ucmd().arg(format!("--indicator-style={}", opt)).run();
|
||||
println!("stdout = {:?}", result.stdout);
|
||||
assert!(result.stdout.contains("/"));
|
||||
}
|
||||
|
||||
// Same test as above, but with the alternate flags.
|
||||
let options = vec!["--classify", "--file-type", "-p"];
|
||||
for opt in options {
|
||||
let result = scene.ucmd().arg(format!("{}", opt)).run();
|
||||
println!("stdout = {:?}", result.stdout);
|
||||
assert!(result.stdout.contains("/"));
|
||||
}
|
||||
|
||||
// Classify and File-Type all contain indicators for pipes and links.
|
||||
let options = vec!["classify", "file-type"];
|
||||
for opt in options {
|
||||
// Verify that classify and file-type both contain indicators for symlinks.
|
||||
let result = scene.ucmd().arg(format!("--indicator-style={}", opt)).run();
|
||||
println!("stdout = {}", result.stdout);
|
||||
assert!(result.stdout.contains("@"));
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(any(target_vendor = "apple", target_os = "windows")))] // Truncate not available on mac or win
|
||||
#[test]
|
||||
fn test_ls_human_si() {
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
#![allow(dead_code)]
|
||||
|
||||
use libc;
|
||||
use std::env;
|
||||
use std::ffi::OsStr;
|
||||
use std::ffi::{CString, OsStr};
|
||||
use std::fs::{self, File, OpenOptions};
|
||||
use std::io::{Read, Result, Write};
|
||||
#[cfg(unix)]
|
||||
|
@ -290,6 +291,29 @@ impl AtPath {
|
|||
File::create(&self.plus(file)).unwrap();
|
||||
}
|
||||
|
||||
#[cfg(not(windows))]
|
||||
pub fn mkfifo(&self, fifo: &str) {
|
||||
let full_path = self.plus_as_string(fifo);
|
||||
log_info("mkfifo", &full_path);
|
||||
unsafe {
|
||||
let fifo_name: CString = CString::new(full_path).expect("CString creation failed.");
|
||||
libc::mkfifo(fifo_name.as_ptr(), libc::S_IWUSR | libc::S_IRUSR);
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(windows))]
|
||||
pub fn is_fifo(&self, fifo: &str) -> bool {
|
||||
unsafe {
|
||||
let name = CString::new(self.plus_as_string(fifo)).unwrap();
|
||||
let mut stat: libc::stat = std::mem::zeroed();
|
||||
if libc::stat(name.as_ptr(), &mut stat) >= 0 {
|
||||
libc::S_IFIFO & stat.st_mode != 0
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn symlink_file(&self, src: &str, dst: &str) {
|
||||
log_info(
|
||||
"symlink",
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue