feat: add support for executables and symlinks highlight

This commit is contained in:
Akmadan23 2024-01-12 21:53:09 +01:00 committed by sxyazi
parent 876419a6c4
commit a765d23fc9
No known key found for this signature in database

View file

@ -9,13 +9,33 @@ use crate::Pattern;
pub struct Filetype { pub struct Filetype {
pub name: Option<Pattern>, pub name: Option<Pattern>,
pub mime: Option<Pattern>, pub mime: Option<Pattern>,
pub typ: Option<String>,
pub style: Style, pub style: Style,
} }
impl Filetype { impl Filetype {
pub fn matches(&self, path: &Path, mime: Option<&str>) -> bool { pub fn matches(&self, path: &Path, mime: Option<&str>) -> bool {
let is_dir = mime == Some(MIME_DIR); let is_dir = mime == Some(MIME_DIR);
self.name.as_ref().is_some_and(|n| n.match_path(path, is_dir)) let special_types = self.typ.as_ref().is_some_and(|t| match t.as_str() {
"symlink" => path.is_symlink(),
#[cfg(unix)]
"executable" => {
use std::os::unix::fs::PermissionsExt;
let Ok(metadata) = path.metadata() else {
return false;
};
let mode_bin = format!("{:b}", metadata.permissions().mode());
return mode_bin.len() == 16 && match *mode_bin.as_bytes() {
[.., _, _, a, _, _, b, _, _, c] => a == b'1' || b == b'1' || c == b'1',
_ => false,
}
},
_ => false
});
special_types
|| self.name.as_ref().is_some_and(|n| n.match_path(path, is_dir))
|| self.mime.as_ref().zip(mime).map_or(false, |(m, s)| m.matches(s)) || self.mime.as_ref().zip(mime).map_or(false, |(m, s)| m.matches(s))
} }
} }
@ -33,6 +53,8 @@ impl Filetype {
struct FiletypeRule { struct FiletypeRule {
name: Option<Pattern>, name: Option<Pattern>,
mime: Option<Pattern>, mime: Option<Pattern>,
#[serde(rename = "type")]
typ: Option<String>,
fg: Option<Color>, fg: Option<Color>,
bg: Option<Color>, bg: Option<Color>,
@ -63,6 +85,7 @@ impl Filetype {
.map(|r| Filetype { .map(|r| Filetype {
name: r.name, name: r.name,
mime: r.mime, mime: r.mime,
typ: r.typ,
style: StyleShadow { style: StyleShadow {
fg: r.fg, fg: r.fg,
bg: r.bg, bg: r.bg,