mirror of
https://github.com/sagiegurari/duckscript
synced 2024-09-29 20:54:34 +00:00
ls command #9
This commit is contained in:
parent
5fc5a934e0
commit
768a50b502
|
@ -2,6 +2,7 @@
|
|||
|
||||
### v0.1.2
|
||||
|
||||
* New **ls** command #9
|
||||
* New **cp** command #7
|
||||
* New **man** command #16
|
||||
* New **calc** command #10
|
||||
|
|
51
docs/sdk.md
51
docs/sdk.md
|
@ -25,6 +25,7 @@
|
|||
* [sdk::fs::GetCanonicalPath (canonicalize)](#sdk__fs__GetCanonicalPath)
|
||||
* [sdk::fs::GetFileName (basename)](#sdk__fs__GetFileName)
|
||||
* [sdk::fs::GetParentDirectory (dirname)](#sdk__fs__GetParentDirectory)
|
||||
* [sdk::fs::List (ls)](#sdk__fs__List)
|
||||
* [sdk::fs::MovePath (mv)](#sdk__fs__MovePath)
|
||||
* [sdk::fs::Print (cat)](#sdk__fs__Print)
|
||||
* [sdk::fs::Read (readfile)](#sdk__fs__Read)
|
||||
|
@ -973,6 +974,56 @@ directory = dirname ./dir/file.txt
|
|||
#### Aliases:
|
||||
dirname
|
||||
|
||||
<a name="sdk__fs__List"></a>
|
||||
## sdk::fs::List
|
||||
```sh
|
||||
var = ls [flags] [path]
|
||||
```
|
||||
|
||||
Lists the file/directory contents.<br>
|
||||
If no path is provided, the current working directory will be used.<br>
|
||||
The supported flags are:
|
||||
|
||||
* -l - Shows extended information
|
||||
|
||||
#### Parameters
|
||||
|
||||
* Optional flags (currently only -l is supported)
|
||||
* Optional path (if not provided, current working directory is used)
|
||||
|
||||
#### Return Value
|
||||
|
||||
**true** is operation was successful.
|
||||
|
||||
#### Examples
|
||||
|
||||
```sh
|
||||
# prints current directory content
|
||||
ls
|
||||
|
||||
# prints current directory content
|
||||
ls .
|
||||
|
||||
# prints examples directory content
|
||||
ls ./examples
|
||||
|
||||
# prints examples directory content with extended info
|
||||
ls -l ./examples
|
||||
|
||||
# prints current directory content with extended info
|
||||
ls -l
|
||||
|
||||
# prints file name
|
||||
ls ./examples/ls.ds
|
||||
|
||||
# prints file name with extended info
|
||||
ls -l ./examples/ls.ds
|
||||
```
|
||||
|
||||
|
||||
#### Aliases:
|
||||
ls
|
||||
|
||||
<a name="sdk__fs__MovePath"></a>
|
||||
## sdk::fs::MovePath
|
||||
```sh
|
||||
|
|
43
duckscript_sdk/src/sdk/std/fs/list/help.md
Normal file
43
duckscript_sdk/src/sdk/std/fs/list/help.md
Normal file
|
@ -0,0 +1,43 @@
|
|||
```sh
|
||||
var = ls [flags] [path]
|
||||
```
|
||||
|
||||
Lists the file/directory contents.<br>
|
||||
If no path is provided, the current working directory will be used.<br>
|
||||
The supported flags are:
|
||||
|
||||
* -l - Shows extended information
|
||||
|
||||
#### Parameters
|
||||
|
||||
* Optional flags (currently only -l is supported)
|
||||
* Optional path (if not provided, current working directory is used)
|
||||
|
||||
#### Return Value
|
||||
|
||||
**true** is operation was successful.
|
||||
|
||||
#### Examples
|
||||
|
||||
```sh
|
||||
# prints current directory content
|
||||
ls
|
||||
|
||||
# prints current directory content
|
||||
ls .
|
||||
|
||||
# prints examples directory content
|
||||
ls ./examples
|
||||
|
||||
# prints examples directory content with extended info
|
||||
ls -l ./examples
|
||||
|
||||
# prints current directory content with extended info
|
||||
ls -l
|
||||
|
||||
# prints file name
|
||||
ls ./examples/ls.ds
|
||||
|
||||
# prints file name with extended info
|
||||
ls -l ./examples/ls.ds
|
||||
```
|
157
duckscript_sdk/src/sdk/std/fs/list/mod.rs
Executable file
157
duckscript_sdk/src/sdk/std/fs/list/mod.rs
Executable file
|
@ -0,0 +1,157 @@
|
|||
use crate::utils::{flags, io, pckg};
|
||||
use duckscript::types::command::{Command, CommandResult};
|
||||
use fs_extra::dir::{ls, DirEntryAttr, DirEntryValue};
|
||||
use std::collections::{HashMap, HashSet};
|
||||
use std::path::Path;
|
||||
|
||||
#[cfg(test)]
|
||||
#[path = "./mod_test.rs"]
|
||||
mod mod_test;
|
||||
|
||||
fn get_string_value(
|
||||
key: DirEntryAttr,
|
||||
attributes: &HashMap<DirEntryAttr, DirEntryValue>,
|
||||
) -> String {
|
||||
match attributes.get(&key) {
|
||||
Some(ref entry_value) => match entry_value {
|
||||
DirEntryValue::String(value) => value.to_string(),
|
||||
_ => "".to_string(),
|
||||
},
|
||||
None => "".to_string(),
|
||||
}
|
||||
}
|
||||
|
||||
fn get_u64_value(key: DirEntryAttr, attributes: &HashMap<DirEntryAttr, DirEntryValue>) -> String {
|
||||
match attributes.get(&key) {
|
||||
Some(ref entry_value) => match entry_value {
|
||||
DirEntryValue::U64(value) => value.to_string(),
|
||||
_ => "".to_string(),
|
||||
},
|
||||
None => "".to_string(),
|
||||
}
|
||||
}
|
||||
|
||||
fn get_boolean_value(key: DirEntryAttr, attributes: &HashMap<DirEntryAttr, DirEntryValue>) -> bool {
|
||||
match attributes.get(&key) {
|
||||
Some(ref entry_value) => match entry_value {
|
||||
DirEntryValue::Boolean(value) => *value,
|
||||
_ => false,
|
||||
},
|
||||
None => false,
|
||||
}
|
||||
}
|
||||
|
||||
fn print_entry(item: &HashMap<DirEntryAttr, DirEntryValue>, extended_details: bool) {
|
||||
if extended_details {
|
||||
let directory_flag = if get_boolean_value(DirEntryAttr::IsDir, &item) {
|
||||
"<DIR>"
|
||||
} else {
|
||||
""
|
||||
};
|
||||
|
||||
println!(
|
||||
"{}\t{}\t{}",
|
||||
get_u64_value(DirEntryAttr::FileSize, &item),
|
||||
directory_flag,
|
||||
get_string_value(DirEntryAttr::FullName, &item)
|
||||
);
|
||||
} else {
|
||||
println!("{} ", get_string_value(DirEntryAttr::FullName, &item));
|
||||
}
|
||||
}
|
||||
|
||||
struct CommandImpl {
|
||||
package: String,
|
||||
}
|
||||
|
||||
impl Command for CommandImpl {
|
||||
fn name(&self) -> String {
|
||||
pckg::concat(&self.package, "List")
|
||||
}
|
||||
|
||||
fn aliases(&self) -> Vec<String> {
|
||||
vec!["ls".to_string()]
|
||||
}
|
||||
|
||||
fn help(&self) -> String {
|
||||
include_str!("help.md").to_string()
|
||||
}
|
||||
|
||||
fn run(&self, arguments: Vec<String>) -> CommandResult {
|
||||
let (path_str, flags) = if arguments.is_empty() {
|
||||
(".", "")
|
||||
} else if arguments.len() == 1 {
|
||||
if flags::is_unix_flags_argument(&arguments[0]) {
|
||||
(".", arguments[0].as_str())
|
||||
} else {
|
||||
(arguments[0].as_str(), "")
|
||||
}
|
||||
} else if flags::is_unix_flags_argument(&arguments[0]) {
|
||||
(arguments[1].as_str(), arguments[0].as_str())
|
||||
} else {
|
||||
(arguments[0].as_str(), "")
|
||||
};
|
||||
|
||||
let path = Path::new(path_str);
|
||||
|
||||
if !path.exists() {
|
||||
CommandResult::Continue(Some("false".to_string()))
|
||||
} else {
|
||||
let extended_details = flags::is_unix_flag_exists('l', flags);
|
||||
|
||||
let mut config = HashSet::new();
|
||||
config.insert(DirEntryAttr::FullName);
|
||||
|
||||
if extended_details {
|
||||
config.insert(DirEntryAttr::FileSize);
|
||||
config.insert(DirEntryAttr::IsDir);
|
||||
}
|
||||
|
||||
let (is_file, query_path) = if path.is_file() {
|
||||
match io::get_parent_directory_name(path_str) {
|
||||
Some(value) => (true, value),
|
||||
None => return CommandResult::Continue(Some("false".to_string())),
|
||||
}
|
||||
} else {
|
||||
(false, path_str.to_string())
|
||||
};
|
||||
|
||||
let result = ls(&query_path, &config);
|
||||
|
||||
match result {
|
||||
Ok(ls_result) => {
|
||||
let items = ls_result.items;
|
||||
|
||||
if is_file {
|
||||
let file_name = match io::get_base_name(path_str) {
|
||||
Some(value) => value,
|
||||
None => path_str.to_string(),
|
||||
};
|
||||
|
||||
for item in items {
|
||||
let item_name = get_string_value(DirEntryAttr::FullName, &item);
|
||||
|
||||
if item_name == file_name {
|
||||
print_entry(&item, extended_details);
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for item in items {
|
||||
print_entry(&item, extended_details);
|
||||
}
|
||||
}
|
||||
|
||||
CommandResult::Continue(Some("true".to_string()))
|
||||
}
|
||||
Err(_) => CommandResult::Continue(Some("false".to_string())),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn create(package: &str) -> Box<dyn Command> {
|
||||
Box::new(CommandImpl {
|
||||
package: package.to_string(),
|
||||
})
|
||||
}
|
71
duckscript_sdk/src/sdk/std/fs/list/mod_test.rs
Normal file
71
duckscript_sdk/src/sdk/std/fs/list/mod_test.rs
Normal file
|
@ -0,0 +1,71 @@
|
|||
use super::*;
|
||||
use crate::test;
|
||||
use crate::test::CommandValidation;
|
||||
|
||||
#[test]
|
||||
fn common_functions() {
|
||||
test::test_common_command_functions(create(""));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_no_args() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_flag_only() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls -l",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_current_directory() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls .",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_current_directory_and_flags() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls -l .",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_current_directory_does_not_exist() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls ./baddirname",
|
||||
CommandValidation::Match("out".to_string(), "false".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_file() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls ./Cargo.toml",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn run_file_with_flags() {
|
||||
test::run_script_and_validate(
|
||||
vec![create("")],
|
||||
"out = ls -l ./Cargo.toml",
|
||||
CommandValidation::Match("out".to_string(), "true".to_string()),
|
||||
);
|
||||
}
|
|
@ -2,6 +2,7 @@ mod basename;
|
|||
mod canonical;
|
||||
mod cp;
|
||||
mod dirname;
|
||||
mod list;
|
||||
mod mkdir;
|
||||
mod mv;
|
||||
mod print;
|
||||
|
@ -24,6 +25,7 @@ pub(crate) fn load(commands: &mut Commands, parent: &str) -> Result<(), ScriptEr
|
|||
commands.set(canonical::create(&package))?;
|
||||
commands.set(cp::create(&package))?;
|
||||
commands.set(dirname::create(&package))?;
|
||||
commands.set(list::create(&package))?;
|
||||
commands.set(mkdir::create(&package))?;
|
||||
commands.set(mv::create(&package))?;
|
||||
commands.set(print::create(&package))?;
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
use crate::utils::io;
|
||||
use crate::utils::pckg;
|
||||
use crate::utils::{io, pckg};
|
||||
use duckscript::types::command::{Command, CommandResult};
|
||||
|
||||
#[cfg(test)]
|
||||
|
|
21
examples/ls.ds
Normal file
21
examples/ls.ds
Normal file
|
@ -0,0 +1,21 @@
|
|||
|
||||
# prints current directory content
|
||||
ls
|
||||
|
||||
# prints current directory content
|
||||
ls .
|
||||
|
||||
# prints examples directory content
|
||||
ls ./examples
|
||||
|
||||
# prints examples directory content with extended info
|
||||
ls -l ./examples
|
||||
|
||||
# prints current directory content with extended info
|
||||
ls -l
|
||||
|
||||
# prints file name
|
||||
ls ./examples/ls.ds
|
||||
|
||||
# prints file name with extended info
|
||||
ls -l ./examples/ls.ds
|
Loading…
Reference in a new issue