optimierung-v1.1.0-prerelease
This commit is contained in:
parent
f80f6ac707
commit
1e52d11971
2
Cargo.lock
generated
2
Cargo.lock
generated
@ -458,7 +458,7 @@ checksum = "bfb942dfe1d8e29a7ee7fcbde5bd2b9a25fb89aa70caea2eba3bee836ff41076"
|
||||
|
||||
[[package]]
|
||||
name = "treescanner"
|
||||
version = "1.0.1"
|
||||
version = "1.1.0"
|
||||
dependencies = [
|
||||
"clap",
|
||||
"dirs",
|
||||
|
@ -1,7 +1,9 @@
|
||||
[package]
|
||||
name = "treescanner"
|
||||
version = "1.0.1"
|
||||
edition = "2024"
|
||||
version = "1.1.0" # Buildversion
|
||||
edition = "2024" # Sprachstandard von Crate
|
||||
#author wird in args.rs gesetzt
|
||||
documentation = "https://github.com/realAscot/treeScanner/blob/main/README.md"
|
||||
|
||||
[package.metadata.winres]
|
||||
subsystem = "console"
|
||||
@ -10,7 +12,7 @@ subsystem = "console"
|
||||
embed-resource = "2.4"
|
||||
|
||||
[dependencies]
|
||||
clap = { version = "4.5", features = ["derive"] }
|
||||
clap = { version = "4.5", features = ["derive", "cargo"] }
|
||||
serde = { version = "1.0", features = ["derive"] }
|
||||
toml = "0.8"
|
||||
dirs = "5"
|
||||
|
@ -183,6 +183,11 @@ align_comments = false
|
||||
|
||||
## Build
|
||||
|
||||
Du benötigst zum selbst kompilieren eine funktionierende Toolchain.
|
||||
Das Makefile steht Dir als anhalt zur Verfügung.
|
||||
|
||||
1. npm installieren ->
|
||||
|
||||
---
|
||||
|
||||
## Lizenz
|
||||
|
@ -3,22 +3,33 @@ use std::path::PathBuf;
|
||||
|
||||
/// CLI-Argumente für TreeScanner
|
||||
#[derive(Parser, Debug)]
|
||||
#[command( author ="Adam Skotarczak <adam@skotarczak.net>",
|
||||
version= "0.2.0",
|
||||
#[command( author = "Adam Skotarczak <adam@skotarczak.net>",
|
||||
// holt sich Version aus der Cargo.toml
|
||||
version,
|
||||
about = "TreeScanner: Verzeichnisse als ASCII-Baum visualisieren.",
|
||||
|
||||
long_about = r#"
|
||||
TreeScanner ist ein leichtgewichtiges CLI-Tool zur strukturierten Darstellung von Verzeichnisinhalten.
|
||||
Dokumentation [DE]: https://github.com/realAscot/treeScanner/blob/main/README.md
|
||||
|
||||
Funktionen:
|
||||
- Ausgabe als ASCII-Baum
|
||||
- Ausgabe als ASCII-Baum mit
|
||||
- Optionen für Tiefe, Datei-Limit und Ignorierlisten
|
||||
- Fortschrittsanzeige im Terminal
|
||||
- Unterstützung für Konfigurationsdateien und CLI
|
||||
|
||||
Beispiel:
|
||||
treescanner.exe --max-depth 3 --ignore .git,target
|
||||
"#
|
||||
"#,
|
||||
// hier stellen wir das alte Format wieder her:
|
||||
help_template = "\
|
||||
{name} {version}
|
||||
{author-section}{about-section}
|
||||
USAGE:
|
||||
{usage}
|
||||
|
||||
ARGS:
|
||||
{all-args}{after-help}"
|
||||
)]
|
||||
pub struct CliArgs {
|
||||
/// Root-Verzeichnis für den Scan (Standard: aktuelles Verzeichnis)
|
||||
@ -26,11 +37,11 @@ pub struct CliArgs {
|
||||
pub root_path: PathBuf,
|
||||
|
||||
/// Maximale Scan-Tiefe
|
||||
#[arg(long)]
|
||||
#[arg(short = 'f', long)]
|
||||
pub max_depth: Option<usize>,
|
||||
|
||||
/// Maximale Dateianzahl pro Verzeichnis
|
||||
#[arg(long, default_value_t = 100)]
|
||||
#[arg(short = 'e', long, default_value_t = 100)]
|
||||
pub max_files_per_dir: usize,
|
||||
|
||||
/// Verzeichnisse ignorieren (z. B. .git,target) durch Komma getrennt, ohne Leerzeichen.
|
||||
|
62
src/main.rs
62
src/main.rs
@ -1,22 +1,31 @@
|
||||
mod config;
|
||||
mod app;
|
||||
mod utils;
|
||||
//! Ein kleines CLI-Tool, das ein Verzeichnis einliest und
|
||||
//! eine ASCII-Baumstruktur ausgibt.
|
||||
//! (C) 2025 - Adam Skotarczak <adam@skotarczak.net>
|
||||
|
||||
mod config; // Enthält CLI-Argument-Parsing und Konfigurations-Loader
|
||||
mod app; // Business-Logik: TreeBuilder
|
||||
mod utils; // Hilfsfunktionen: Spinner, Logger, …
|
||||
|
||||
|
||||
use app::treebuilder::{TreeBuilder, TreeBuilderConfig};
|
||||
use config::args::CliArgs;
|
||||
use config::loader::load_config_from_home;
|
||||
use utils::ascii_spinner::start_spinner;
|
||||
use clap::Parser;
|
||||
use config::args::CliArgs; // Definition der CLI-Argumente
|
||||
use config::loader::load_config_from_home; // Lädt optionale Datei-Konfiguration
|
||||
use utils::ascii_spinner::start_spinner; // Zeigt einen Lade-Spinner
|
||||
use clap::Parser; // CLI-Parsing mit Clap
|
||||
use std::fs;
|
||||
use std::time::Instant;
|
||||
use utils::logger::init_logger;
|
||||
use utils::logger::init_logger; // Initialisiert den Logger
|
||||
|
||||
|
||||
/// Gibt die verstrichene Zeit seit `timer` aus.
|
||||
fn view_timer(timer: &Instant) {
|
||||
// `elapsed()` liefert eine Duration, hier formatiert mit (2) Nachkommastellen
|
||||
println!("\n⏱️ Gesamtlaufzeit des Scans: {:.2?}", timer.elapsed());
|
||||
}
|
||||
|
||||
// Hilfsfunktion zur Pfad-Normalisierung
|
||||
|
||||
/// Normalisiert einen Pfad-Eintrag für `--ignore`,
|
||||
/// entfernt führende "./" bzw. ".\" und schließende Slashes.
|
||||
fn normalize_ignore_entry(s: &str) -> String {
|
||||
s.trim_start_matches("./")
|
||||
.trim_start_matches(".\\")
|
||||
@ -25,17 +34,29 @@ fn normalize_ignore_entry(s: &str) -> String {
|
||||
.to_string()
|
||||
}
|
||||
|
||||
|
||||
fn main() {
|
||||
// 1. Logger konfigurieren (z.B. env_logger)
|
||||
init_logger();
|
||||
|
||||
|
||||
// 2. CLI-Argumente parsen: root_path, output, ignore, etc
|
||||
let args = CliArgs::parse();
|
||||
|
||||
// 3. Optional: Konfigurationsdatei aus ~/.config/... laden
|
||||
let file_config = load_config_from_home().unwrap_or_default();
|
||||
|
||||
// 4. Timer starten, um Laufzeit zu messen
|
||||
let timer = Instant::now();
|
||||
|
||||
// 5. Validierung: root_path muss ein Verzeichnis sein
|
||||
if !args.root_path.is_dir() {
|
||||
eprintln!("⚠️ Fehler: '{}' ist kein gültiges Verzeichnis.", args.root_path.display());
|
||||
std::process::exit(1);
|
||||
}
|
||||
|
||||
|
||||
// 6. Falls ein Ausgabepfad angegeben ist, erstelle ggf. das Elternverzeichnis
|
||||
if let Some(parent) = args.output.as_ref().and_then(|p| p.parent()) {
|
||||
if let Err(e) = fs::create_dir_all(parent) {
|
||||
eprintln!("⚠️ Fehler beim Erstellen des Zielordners: {e}");
|
||||
@ -43,28 +64,34 @@ fn main() {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// 7. Ignored-Dirs: CLI hat Vorrang, sonst Datei-Konfig, sonst leer
|
||||
let ignored_dirs: Vec<String> = match (!args.ignore.is_empty(), file_config.ignore) {
|
||||
(true, _) => args.ignore.iter().map(|s| normalize_ignore_entry(s)).collect(),
|
||||
(false, Some(set)) => set.into_iter().map(|s| normalize_ignore_entry(&s)).collect(),
|
||||
(false, None) => vec![],
|
||||
};
|
||||
|
||||
|
||||
// 8. TreeBuilder-Konfiguration zusammenstellen
|
||||
let config = TreeBuilderConfig {
|
||||
root_path: args.root_path.clone(),
|
||||
max_depth: args.max_depth.or(file_config.max_depth),
|
||||
max_depth: args.max_depth.or(file_config.max_depth), // CLI oder Datei
|
||||
max_files_per_dir: if args.max_files_per_dir != 100 {
|
||||
args.max_files_per_dir
|
||||
args.max_files_per_dir // CLI-Wert, wenn abweichend
|
||||
} else {
|
||||
file_config.max_files_per_dir.unwrap_or(100)
|
||||
file_config.max_files_per_dir.unwrap_or(100) // sonst Datei oder Default
|
||||
},
|
||||
ignored_dirs,
|
||||
folder_icon: "📁".to_string(),
|
||||
file_icon: "📄".to_string(),
|
||||
folder_icon: "📁".to_string(), // Alt: ▭
|
||||
file_icon: "📄".to_string(), // Alt:
|
||||
align_comments: args.align_comments,
|
||||
};
|
||||
|
||||
// 9. TreeBuilder initialisieren
|
||||
let mut builder = TreeBuilder::new(config);
|
||||
|
||||
// 10. Optional: Spinner starten, wenn nicht `--quiet
|
||||
let (stop_spinner, spinner_handle) = if !args.quiet {
|
||||
let (s, h) = start_spinner(8);
|
||||
(Some(s), Some(h))
|
||||
@ -72,13 +99,16 @@ fn main() {
|
||||
(None, None)
|
||||
};
|
||||
|
||||
// 11. Baumstruktur bauen und zu einem String zusammenfügen
|
||||
let mut output = builder.build_tree().join("\n");
|
||||
|
||||
// 12. Kommentare in den Zeilen ausrichten (wenn gewünscht)
|
||||
if builder.config.align_comments {
|
||||
let lines = output.lines().map(String::from).collect::<Vec<_>>();
|
||||
output = builder.align_lines_with_comments(&lines).join("\n");
|
||||
}
|
||||
|
||||
// 13. Spinner stoppen und Thread beenden
|
||||
if let Some(stop) = stop_spinner {
|
||||
let _ = stop.send(());
|
||||
}
|
||||
@ -86,15 +116,18 @@ fn main() {
|
||||
let _ = handle.join();
|
||||
}
|
||||
|
||||
// 14. Ausgabemodus: in Datei schreiben oder nur anzeigen
|
||||
let viewonly = args.viewonly || file_config.viewonly.unwrap_or(false);
|
||||
let output_path = args.output.clone().or_else(|| file_config.output.map(Into::into)).unwrap_or_else(|| "tree.txt".into());
|
||||
|
||||
if !viewonly {
|
||||
// 15a. Schreibe Ergebnis in Datei
|
||||
if let Err(e) = fs::write(&output_path, &output) {
|
||||
eprintln!("Fehler beim Schreiben der Datei: {e}");
|
||||
std::process::exit(1);
|
||||
}
|
||||
if !args.quiet {
|
||||
// 16a. Statistik ausgeben
|
||||
let (folders, files) = builder.stats();
|
||||
println!(
|
||||
"Erfasst wurden {} Ordner und {} Dateien. Ergebnis in {} gespeichert.",
|
||||
@ -105,6 +138,7 @@ fn main() {
|
||||
view_timer(&timer);
|
||||
}
|
||||
} else {
|
||||
// 15b. Nur auf stdout ausgeben
|
||||
println!("{}", output);
|
||||
view_timer(&timer);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user