summaryrefslogtreecommitdiffstats
path: root/src/files.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/files.rs')
-rw-r--r--src/files.rs490
1 files changed, 381 insertions, 109 deletions
diff --git a/src/files.rs b/src/files.rs
index 1a038ac..637b99a 100644
--- a/src/files.rs
+++ b/src/files.rs
@@ -1,14 +1,16 @@
use std::cmp::{Ord, Ordering};
use std::ops::Index;
+use std::fs::Metadata;
use std::os::unix::fs::MetadataExt;
use std::path::{Path, PathBuf};
-use std::sync::{Arc, Mutex};
+use std::sync::{Arc, Mutex, RwLock};
+use std::sync::mpsc::Sender;
use std::hash::{Hash, Hasher};
use std::os::unix::ffi::{OsStringExt, OsStrExt};
use std::ffi::{OsStr, OsString};
use lscolors::LsColors;
-use mime_detective;
+use tree_magic;
use users::{get_current_username,
get_current_groupname,
get_user_by_uid,
@@ -16,24 +18,50 @@ use users::{get_current_username,
use chrono::TimeZone;
use failure::Error;
use notify::DebouncedEvent;
+use rayon::{ThreadPool, ThreadPoolBuilder};
-use crate::fail::{HResult, HError};
-use crate::dirty::{DirtyBit, Dirtyable};
-
-
+use crate::fail::{HResult, HError, ErrorLog};
+use crate::dirty::{AsyncDirtyBit, DirtyBit, Dirtyable};
+use crate::preview::{Async, Stale};
+use crate::widget::Events;
lazy_static! {
static ref COLORS: LsColors = LsColors::from_env().unwrap();
- static ref TAGS: Mutex<(bool, Vec<PathBuf>)> = Mutex::new((false, vec![]));
+ static ref TAGS: RwLock<(bool, Vec<PathBuf>)> = RwLock::new((false, vec![]));
+}
+
+fn make_pool(sender: Option<Sender<Events>>) -> ThreadPool {
+ let sender = Arc::new(Mutex::new(sender));
+ ThreadPoolBuilder::new()
+ .num_threads(8)
+ .exit_handler(move |thread_num| {
+ if thread_num == 0 {
+ if let Ok(lock) = sender.lock() {
+ if let Some(sender) = lock.as_ref() {
+ sender.send(Events::WidgetReady).ok();
+ }
+ }
+ }
+ })
+ .build()
+ .expect("Failed to create thread pool")
}
pub fn load_tags() -> HResult<()> {
std::thread::spawn(|| -> HResult<()> {
let tag_path = crate::paths::tagfile_path()?;
+
+ if !tag_path.exists() {
+ import_tags().log();
+ }
+
let tags = std::fs::read_to_string(tag_path)?;
- let mut tags = tags.lines().map(|f| PathBuf::from(f)).collect::<Vec<PathBuf>>();
- let mut tag_lock = TAGS.lock()?;
+ let mut tags = tags.lines()
+ .map(|f|
+ PathBuf::from(f))
+ .collect::<Vec<PathBuf>>();
+ let mut tag_lock = TAGS.write()?;
tag_lock.0 = true;
tag_lock.1.append(&mut tags);
Ok(())
@@ -41,28 +69,43 @@ pub fn load_tags() -> HResult<()> {
Ok(())
}
+pub fn import_tags() -> HResult<()> {
+ let mut ranger_tags = crate::paths::ranger_path()?;
+ ranger_tags.push("tagged");
+
+ if ranger_tags.exists() {
+ let tag_path = crate::paths::tagfile_path()?;
+ std::fs::copy(ranger_tags, tag_path)?;
+ }
+ Ok(())
+}
+
pub fn check_tag(path: &PathBuf) -> HResult<bool> {
tags_loaded()?;
- let tagged = TAGS.lock()?.1.contains(path);
+ let tagged = TAGS.read()?.1.contains(path);
Ok(tagged)
}
pub fn tags_loaded() -> HResult<()> {
- let loaded = TAGS.lock()?.0;
+ let loaded = TAGS.read()?.0;
if loaded { Ok(()) }
else { HError::tags_not_loaded() }
}
+
#[derive(PartialEq, Eq, Hash, Clone, Debug)]
pub struct Files {
pub directory: File,
pub files: Vec<File>,
+ pub meta_upto: Option<usize>,
+ pub meta_updated: bool,
pub sort: SortBy,
pub dirs_first: bool,
pub reverse: bool,
pub show_hidden: bool,
pub filter: Option<String>,
- pub dirty: DirtyBit
+ pub dirty: DirtyBit,
+ pub dirty_meta: AsyncDirtyBit,
}
impl Index<usize> for Files {
@@ -74,12 +117,16 @@ impl Index<usize> for Files {
impl Dirtyable for Files {
- fn get_bit(&self) -> &DirtyBit {
- &self.dirty
+ fn is_dirty(&self) -> bool {
+ self.dirty.is_dirty()
+ }
+
+ fn set_dirty(&mut self) {
+ self.dirty.set_dirty();
}
- fn get_bit_mut(&mut self) -> &mut DirtyBit {
- &mut self.dirty
+ fn set_clean(&mut self) {
+ self.dirty.set_clean();
}
}
@@ -87,6 +134,8 @@ impl Dirtyable for Files {
impl Files {
pub fn new_from_path(path: &Path) -> Result<Files, Error> {
let direntries: Result<Vec<_>, _> = std::fs::read_dir(&path)?.collect();
+ let dirty = DirtyBit::new();
+ let dirty_meta = AsyncDirtyBit::new();
let files: Vec<_> = direntries?
.iter()
@@ -94,23 +143,30 @@ impl Files {
let name = file.file_name();
let name = name.to_string_lossy();
let path = file.path();
- File::new(&name, path)
+ File::new(&name,
+ path,
+ Some(dirty_meta.clone()))
})
.collect();
let mut files = Files {
- directory: File::new_from_path(&path)?,
+ directory: File::new_from_path(&path, None)?,
files: files,
+ meta_upto: None,
+ meta_updated: false,
sort: SortBy::Name,
dirs_first: true,
reverse: false,
show_hidden: true,
filter: None,
- dirty: DirtyBit::new()
+ dirty: dirty,
+ dirty_meta: dirty_meta,
};
files.sort();
+
+
if files.files.len() == 0 {
files.files = vec![File::new_placeholder(&path)?];
}
@@ -118,8 +174,12 @@ impl Files {
Ok(files)
}
- pub fn new_from_path_cancellable(path: &Path, stale: Arc<Mutex<bool>>) -> Result<Files, Error> {
+ pub fn new_from_path_cancellable(path: &Path,
+ stale: Stale)
+ -> Result<Files, Error> {
let direntries: Result<Vec<_>, _> = std::fs::read_dir(&path)?.collect();
+ let dirty = DirtyBit::new();
+ let dirty_meta = AsyncDirtyBit::new();
let files: Vec<_> = direntries?
.iter()
@@ -130,7 +190,10 @@ impl Files {
let name = file.file_name();
let name = name.to_string_lossy();
let path = file.path();
- Some(File::new(&name, path))
+ Some(File::new_with_stale(&name,
+ path,
+ Some(dirty_meta.clone()),
+ stale.clone()))
}
})
.fuse()
@@ -144,14 +207,17 @@ impl Files {
}
let mut files = Files {
- directory: File::new_from_path(&path)?,
+ directory: File::new_from_path(&path, None)?,
files: files,
+ meta_upto: None,
+ meta_updated: false,
sort: SortBy::Name,
dirs_first: true,
reverse: false,
show_hidden: true,
filter: None,
- dirty: DirtyBit::new()
+ dirty: dirty,
+ dirty_meta: dirty_meta,
};
files.sort();
@@ -163,13 +229,46 @@ impl Files {
Ok(files)
}
+ pub fn get_file_mut(&mut self, index: usize) -> Option<&mut File> {
+ let filter = self.filter.clone();
+ let show_hidden = self.show_hidden;
+
+ let file = self.files
+ .iter_mut()
+ .filter(|f| !(filter.is_some() &&
+ !f.name.contains(filter.as_ref().unwrap())))
+ .filter(|f| !(!show_hidden && f.name.starts_with(".")))
+ .nth(index);
+ file
+ }
+
+ pub fn get_files(&self) -> Vec<&File> {
+ self.files
+ .iter()
+ .filter(|f| !(self.filter.is_some() &&
+ !f.name.contains(self.filter.as_ref().unwrap())))
+ .filter(|f| !(!self.show_hidden && f.name.starts_with(".")))
+ .collect()
+ }
+
+ pub fn get_files_mut(&mut self) -> Vec<&mut File> {
+ let filter = self.filter.clone();
+ let show_hidden = self.show_hidden;
+ self.files
+ .iter_mut()
+ .filter(|f| !(filter.is_some() &&
+ !f.name.contains(filter.as_ref().unwrap())))
+ .filter(|f| !(!show_hidden && f.name.starts_with(".")))
+ .collect()
+ }
+
pub fn sort(&mut self) {
match self.sort {
SortBy::Name => self
.files
.sort_by(|a, b| alphanumeric_sort::compare_str(&a.name, &b.name)),
SortBy::Size => {
- self.meta_all();
+ self.meta_all_sync().log();
self.files.sort_by(|a, b| {
if a.meta().unwrap().size() == b.meta().unwrap().size() {
return alphanumeric_sort::compare_str(&b.name, &a.name);
@@ -178,7 +277,7 @@ impl Files {
});
}
SortBy::MTime => {
- self.meta_all();
+ self.meta_all_sync().log();
self.files.sort_by(|a, b| {
if a.meta().unwrap().mtime() == b.meta().unwrap().mtime() {
return alphanumeric_sort::compare_str(&a.name, &b.name);
@@ -227,25 +326,37 @@ impl Files {
self.show_hidden = !self.show_hidden
}
- pub fn reload_files(&mut self) {
- let dir = self.directory.clone();
- let files = Files::new_from_path(&dir.path()).unwrap();
- let files = files
- .files
- .into_iter()
- .skip_while(|f| f.name.starts_with(".") && !self.show_hidden )
- .collect();
-
- self.files = files;
- self.set_dirty();
+ pub fn replace_file(&mut self,
+ old: Option<&File>,
+ new: Option<File>) -> HResult<()> {
+ let (tag, selected) = if let Some(old) = old {
+ if let Some(old) = self.find_file_with_path(&old.path) {
+ (old.tag, old.selected)
+ } else {
+ (None, false)
+ }
+ } else {
+ (None, false)
+ };
+ old.map(|old| self.files.remove_item(old));
+ new.map(|mut new| {
+ new.tag = tag;
+ new.selected = selected;
+ self.files.push(new);
+ });
+ self.sort();
+ Ok(())
}
- pub fn handle_event(&mut self, event: &DebouncedEvent) -> HResult<()> {
+ pub fn handle_event(&mut self,
+ event: &DebouncedEvent) -> HResult<()> {
match event {
DebouncedEvent::Create(path) => {
self.path_in_here(&path)?;
- let file = File::new_from_path(&path)?;
+ let file = File::new_from_path(&path,
+ Some(self.dirty_meta.clone()))?;
self.files.push(file);
+ self.sort();
},
DebouncedEvent::Write(path) | DebouncedEvent::Chmod(path) => {
self.path_in_here(&path)?;
@@ -262,6 +373,7 @@ impl Files {
let mut file = self.find_file_with_path(&old_path)?;
file.name = new_path.file_name()?.to_string_lossy().to_string();
file.path = new_path.into();
+ file.reload_meta()?;
},
DebouncedEvent::Error(err, path) => {
dbg!(err);
@@ -274,12 +386,12 @@ impl Files {
}
pub fn path_in_here(&self, path: &Path) -> HResult<bool> {
- let dir = self.directory.path();
+ let dir = &self.directory.path;
let path = if path.is_dir() { path } else { path.parent().unwrap() };
if dir == path {
Ok(true)
} else {
- HError::wrong_directory(path.into(), dir)?
+ HError::wrong_directory(path.into(), dir.to_path_buf())?
}
}
@@ -287,17 +399,62 @@ impl Files {
self.files.iter_mut().find(|file| file.path == path)
}
+ pub fn meta_all_sync(&mut self) -> HResult<()> {
+ for file in self.files.iter_mut() {
+ if !file.meta_processed {
+ file.meta_sync().log();
+ }
+ }
+ self.set_dirty();
+ self.meta_updated = true;
+ Ok(())
+ }
+
pub fn meta_all(&mut self) {
- let len = self.files.len();
- self.meta_upto(len);
+ let len = self.len();
+ self.meta_upto(len, None);
}
- pub fn meta_upto(&mut self, to: usize) {
- for file in self.files.iter_mut().take(to) {
- file.get_meta().ok();
+ pub fn meta_upto(&mut self, to: usize, sender: Option<Sender<Events>>) {
+ let meta_files = if self.meta_upto > Some(to) {
+ self.meta_upto.unwrap()
+ } else {
+ if to > self.len() {
+ self.len()
+ } else {
+ to
+ }
+ };
+
+ if self.meta_upto >= Some(meta_files) && !self.dirty_meta.is_dirty() { return }
+
+ self.set_dirty();
+ self.dirty_meta.set_clean();
+
+ let meta_pool = make_pool(sender.clone());
+ let show_hidden = self.show_hidden;
+
+ for file in self.files
+ .iter_mut()
+ .filter(|f| !(!show_hidden && f.name.starts_with(".")))
+ .take(meta_files) {
+ if !file.meta_processed {
+ file.take_meta(&meta_pool, &mut self.meta_updated).ok();
+ }
+ if file.is_dir() {
+ file.take_dirsize(&meta_pool, &mut self.meta_updated).ok();
+ }
}
+
+ self.meta_upto = Some(meta_files);
}
+ pub fn meta_set_fresh(&self) -> HResult<()> {
+ self.files.get(0)?.meta.set_fresh()?;
+ Ok(())
+ }
+
+
pub fn set_filter(&mut self, filter: Option<String>) {
self.filter = filter;
self.set_dirty();
@@ -308,15 +465,7 @@ impl Files {
}
pub fn len(&self) -> usize {
- match &self.filter {
- None => self.files.len(),
- Some(filter) => {
- self.files
- .iter()
- .filter(|f| f.name.contains(filter))
- .count()
- }
- }
+ self.get_files().len()
}
pub fn get_selected(&self) -> Vec<&File> {
@@ -364,86 +513,224 @@ impl Hash for File {
fn hash<H: Hasher>(&self, state: &mut H) {
self.name.hash(state);
self.path.hash(state);
- self.selected.hash(state);
}
}
impl Eq for File {}
-#[derive(Debug, Clone)]
+
+#[derive(Clone, Debug)]
pub struct File {
pub name: String,
pub path: PathBuf,
pub kind: Kind,
+ pub dirsize: Option<Async<usize>>,
pub target: Option<PathBuf>,
pub color: Option<lscolors::Color>,
- pub meta: Option<std::fs::Metadata>,
+ pub meta: Async<Metadata>,
+ pub dirty_meta: Option<AsyncDirtyBit>,
+ pub meta_processed: bool,
pub selected: bool,
pub tag: Option<bool>
- // flags: Option<String>,
}
impl File {
pub fn new(
name: &str,
path: PathBuf,
- ) -> File {
+ dirty_meta: Option<AsyncDirtyBit>) -> File {
let tag = check_tag(&path).ok();
+ let meta = File::make_async_meta(&path, dirty_meta.clone(), None);
+ let dirsize = if path.is_dir() {
+ Some(File::make_async_dirsize(&path, dirty_meta.clone(), None))
+ } else { None };
File {
name: name.to_string(),
kind: if path.is_dir() { Kind::Directory } else { Kind::File },
path: path,
+ dirsize: dirsize,
target: None,
- meta: None,
+ meta: meta,
+ meta_processed: false,
+ dirty_meta: dirty_meta,
color: None,
selected: false,
tag: tag,
}
}
- pub fn new_from_path(path: &Path) -> HResult<File> {
+ pub fn new_with_stale(name: &str,
+ path: PathBuf,
+ dirty_meta: Option<AsyncDirtyBit>,
+ stale: Stale) -> File {
+ let tag = check_tag(&path).ok();
+ let meta = File::make_async_meta(&path,
+ dirty_meta.clone(),
+ Some(stale.clone()));
+ let dirsize = if path.is_dir() {
+ Some(File::make_async_dirsize(&path,
+ dirty_meta.clone(),
+ Some(stale)))
+ } else { None };
+
+ File {
+ name: name.to_string(),
+ kind: if path.is_dir() { Kind::Directory } else { Kind::File },
+ path: path,
+ dirsize: dirsize,
+ target: None,
+ meta: meta,
+ meta_processed: false,
+ dirty_meta: dirty_meta,
+ color: None,
+ selected: false,
+ tag: tag,
+ }
+ }
+
+ pub fn new_from_path(path: &Path,
+ dirty_meta: Option<AsyncDirtyBit>) -> HResult<File> {
let pathbuf = path.to_path_buf();
let name = path
.file_name()
.map(|name| name.to_string_lossy().to_string())
.unwrap_or("/".to_string());
- Ok(File::new(&name, pathbuf))
+ Ok(File::new(&name, pathbuf, dirty_meta))
}
pub fn new_placeholder(path: &Path) -> Result<File, Error> {
- let mut file = File::new_from_path(path)?;
+ let mut file = File::new_from_path(path, None)?;
file.name = "<empty>".to_string();
file.kind = Kind::Placeholder;
Ok(file)
}
- pub fn meta(&self) -> HResult<std::fs::Metadata> {
- match &self.meta {
- Some(meta) => Ok(meta.clone()),
- None => { Ok(std::fs::symlink_metadata(&self.path)?) }
+ pub fn meta_sync(&mut self) -> HResult<()> {
+ let stale = self.meta.get_stale();
+ let meta = std::fs::metadata(&self.path)?;
+ self.meta = Async::new_with_value(meta);
+ self.meta.put_stale(stale);
+ self.process_meta()
+ }
+
+ pub fn make_async_meta(path: &PathBuf,
+ dirty_meta: Option<AsyncDirtyBit>,
+ stale_preview: Option<Stale>) -> Async<Metadata> {
+ let path = path.clone();
+
+ let meta_closure = Box::new(move |stale: Stale| {
+ if stale.is_stale()? { HError::stale()? }
+ Ok(std::fs::symlink_metadata(&path)?)
+ });
+
+ let mut meta = match stale_preview {
+ Some(stale) => Async::new_with_stale(meta_closure, stale),
+ None => Async::new(meta_closure)
+ };
+ if let Some(dirty_meta) = dirty_meta {
+ meta.on_ready(Box::new(move || {
+ let mut dirty_meta = dirty_meta.clone();
+ dirty_meta.set_dirty();
+
+ Ok(())
+ }));
}
+ meta
}
- pub fn get_meta(&mut self) -> HResult<()> {
- if let Some(_) = self.meta { return Ok(()) }
+ pub fn make_async_dirsize(path: &PathBuf,
+ dirty_meta: Option<AsyncDirtyBit>,
+ stale_preview: Option<Stale>) -> Async<usize> {
+ let path = path.clone();
- let meta = std::fs::symlink_metadata(&self.path)?;
- let color = self.get_color(&meta);
- let target = if meta.file_type().is_symlink() {
- self.path.read_link().ok()
- } else { None };
+ let dirsize_closure = Box::new(move |stale: Stale| {
+ if stale.is_stale()? { HError::stale()? }
+ Ok(std::fs::read_dir(&path)?.count())
+ });
- self.meta = Some(meta);
- self.color = color;
- self.target = target;
+ let mut dirsize = match stale_preview {
+ Some(stale) => Async::new_with_stale(dirsize_closure, stale),
+ None => Async::new(dirsize_closure)
+ };
+
+ if let Some(dirty_meta) = dirty_meta {
+ dirsize.on_ready(Box::new(move || {
+ let mut dirty_meta = dirty_meta.clone();
+ dirty_meta.set_dirty();
+
+ Ok(())
+ }));
+ }
+ dirsize
+ }
+
+ pub fn meta(&self) -> HResult<&Metadata> {
+ self.meta.get()
+ }
+
+ fn take_dirsize(&mut self,
+ pool: &ThreadPool,
+ meta_updated: &mut bool) -> HResult<()> {
+ let dirsize = self.dirsize.as_mut()?;
+ if let Ok(_) = dirsize.value { return Ok(()) }
+
+ match dirsize.take_async() {
+ Ok(_) => { *meta_updated = true; },
+ Err(HError::AsyncNotReadyError) => { dirsize.run_pooled(&*pool).ok(); },
+ Err(HError::AsyncAlreadyTakenError) => {},
+ Err(HError::NoneError) => {},
+ err @ Err(_) => { err?; }
+ }
+ Ok(())
+ }
+
+ pub fn take_meta(&mut self,
+ pool: &ThreadPool,
+ meta_updated: &mut bool) -> HResult<()> {
+ if self.meta_processed { return Ok(()) }
+
+ match self.meta.take_async() {
+ Ok(_) => { *meta_updated = true; },
+ Err(HError::AsyncNotReadyError) => { self.meta.run_pooled(&*pool).ok(); },
+ Err(HError::AsyncAlreadyTakenError) => {},
+ Err(HError::NoneError) => {},
+ err @ Err(_) => { err?; }
+ }
+
+ self.process_meta()?;
+
+ Ok(())
+ }
+
+ pub fn process_meta(&mut self) -> HResult<()> {
+ if let Ok(meta) = self.meta.get() {
+ let color = self.get_color(&meta);
+ let target = if meta.file_type().is_symlink() {
+ self.path.read_link().ok()
+ } else { None };
+
+ self.color = color;
+ self.target = target;
+ self.meta_processed = true;
+ }
Ok(())
}
pub fn reload_meta(&mut self) -> HResult<()> {
- self.meta = None;
- self.get_meta()
+ self.meta_processed = false;
+ self.meta = File::make_async_meta(&self.path,
+ self.dirty_meta.clone(),
+ None);
+ self.meta.run().log();
+
+ if self.dirsize.is_some() {
+ self.dirsize
+ = Some(File::make_async_dirsize(&self.path, self.dirty_meta.clone(), None));
+ self.dirsize.as_mut()?.run().log();
+ }
+ Ok(())
}
fn get_color(&self, meta: &std::fs::Metadata) -> Option<lscolors::Color> {
@@ -454,13 +741,8 @@ impl File {
}
pub fn calculate_size(&self) -> HResult<(u64, String)> {
- if self.is_dir() {
- let dir_iterator = std::fs::read_dir(&self.path);
- match dir_iterator {
- Ok(dir_iterator) => return Ok((dir_iterator.count() as u64,
- "".to_string())),
- Err(_) => return Ok((0, "".to_string()))
- }
+ if let Some(ref dirsize) = self.dirsize {
+ return Ok((dirsize.value.clone()? as u64, "".to_string()))
}
@@ -483,10 +765,12 @@ impl File {
Ok((size, unit))
}
- pub fn get_mime(&self) -> Option<String> {
- let detective = mime_detective::MimeDetective::new().ok()?;
- let mime = detective.detect_filepath(&self.path).ok()?;
- Some(mime.type_().as_str().to_string())
+ // pub fn get_mime(&self) -> String {
+ // tree_magic::from_filepath(&self.path)
+ // }
+
+ pub fn is_text(&self) -> bool {
+ tree_magic::match_filepath("text/plain", &self.path)
}
@@ -496,7 +780,7 @@ impl File {
pub fn parent_as_file(&self) -> HResult<File> {
let pathbuf = self.parent()?;
- File::new_from_path(&pathbuf)
+ File::new_from_path(&pathbuf, None)
}
pub fn grand_parent(&self) -> Option<PathBuf> {
@@ -505,7 +789,7 @@ impl File {
pub fn grand_parent_as_file(&self) -> HResult<File> {
let pathbuf = self.grand_parent()?;
- File::new_from_path(&pathbuf)
+ File::new_from_path(&pathbuf, None)
}
pub fn is_dir(&self) -> bool {
@@ -559,8 +843,8 @@ impl File {
self.tag = Some(new_state);
match new_state {
- true => TAGS.lock()?.1.push(self.path.clone()),
- false => { TAGS.lock()?.1.remove_item(&self.path); },
+ true => TAGS.write()?.1.push(self.path.clone()),
+ false => { TAGS.write()?.1.remove_item(&self.path); },
}
self.save_tags()?;
Ok(())
@@ -569,7 +853,7 @@ impl File {
pub fn save_tags(&self) -> HResult<()> {
std::thread::spawn(|| -> HResult<()> {
let tagfile_path = crate::paths::tagfile_path()?;
- let tags = TAGS.lock()?.clone();
+ let tags = TAGS.read()?.clone();
let tags_str = tags.1.iter().map(|p| {
let path = p.to_string_lossy().to_string();
format!("{}\n", path)
@@ -642,7 +926,7 @@ impl File {
if file_user.name() == cur_user {
crate::term::color_green()
} else {
- crate::term::color_yellow() };
+ crate::term::color_red() };
Some(format!("{}{}", color, file_user.name().to_string_lossy()))
}
@@ -655,13 +939,12 @@ impl File {
if file_group.name() == cur_group {
crate::term::color_green()
} else {
- crate::term::color_yellow() };
+ crate::term::color_red() };
Some(format!("{}{}", color, file_group.name().to_string_lossy()))
}
pub fn pretty_mtime(&self) -> Option<String> {
if self.meta().is_err() { return None }
- //let time = chrono::DateTime::from_timestamp(self.mtime, 0);
let time: chrono::DateTime<chrono::Local>
= chrono::Local.timestamp(self.meta().unwrap().mtime(), 0);
Some(time.format("%F %R").to_string())
@@ -719,7 +1002,6 @@ impl PathBufExt for PathBuf {
if let Some(name) = self.file_name() {
let mut name = name.as_bytes().to_vec();
let mut quote = "\"".as_bytes().to_vec();
- //let mut quote_after = "\"".as_bytes().to_vec();
let mut quoted = vec![];
quoted.append(&mut quote.clone());
quoted.append(&mut name);
@@ -761,14 +1043,10 @@ impl OsStrTools for OsStr {
let pat = pat.as_bytes().to_vec();
let pat_len = pat.len();
- dbg!(&self);
-
let split_string = orig_string
.windows(pat_len)
.enumerate()
.fold(Vec::new(), |mut split_pos, (i, chars)| {
- dbg!(&chars);
- dbg!(&split_pos);
if chars == pat.as_slice() {
if split_pos.len() == 0 {
split_pos.push((0, i));
@@ -781,7 +1059,6 @@ impl OsStrTools for OsStr {
split_pos
}).iter()
.map(|(start, end)| {
- //let orig_string = orig_string.clone();
OsString::from_vec(orig_string[*start..*end]
.to_vec()).replace(&OsString::from_vec(pat.clone()),
&OsString::from(""))
@@ -816,8 +1093,6 @@ impl OsStrTools for OsStr {
return vec![OsString::from(self)];
}
- dbg!(&self);
-
let pos = pos.unwrap();
let string = self.as_bytes().to_vec();
let from = from.as_bytes().to_vec();
@@ -826,9 +1101,6 @@ impl OsStrTools for OsStr {
let lpart = OsString::from_vec(string[0..pos].to_vec());
let rpart = OsString::from_vec(string[pos+fromlen..].to_vec());
- dbg!(&lpart);
- dbg!(&rpart);
-
let mut result = vec![
vec![lpart.trim_last_space()],
to,