Skip to content

Commit b1ce939

Browse files
authored
Reference directories in CLI (#1364)
* Test * Debug * Hellow * Randoms * Renaming
1 parent b4d4cc7 commit b1ce939

26 files changed

+295
-60
lines changed

.github/workflows/linux_cli.yml

+4-1
Original file line numberDiff line numberDiff line change
@@ -32,14 +32,17 @@ jobs:
3232
name: czkawka_cli-${{ runner.os }}
3333
path: target/release/czkawka_cli
3434

35+
- name: Build test version
36+
run: cargo build --profile test --bin czkawka_cli
37+
3538
- name: Linux Regression Test
3639
run: |
3740
wget https://github.com/qarmin/czkawka/releases/download/6.0.0/TestFiles.zip
3841
cd ci_tester
3942
cargo build --release
4043
cd ..
4144
42-
ci_tester/target/release/ci_tester target/release/czkawka_cli
45+
ci_tester/target/release/ci_tester target/debug/czkawka_cli
4346
4447
- name: Prepare files to release
4548
run: |

Cargo.toml

+6-1
Original file line numberDiff line numberDiff line change
@@ -28,4 +28,9 @@ overflow-checks = true
2828

2929
# Optimize all dependencies except application/workspaces, even in debug builds
3030
[profile.dev.package."*"]
31-
opt-level = 3
31+
opt-level = 3
32+
33+
[profile.test]
34+
debug-assertions = true # Forces to crash when there is duplicated item in cli
35+
overflow-checks = true
36+
opt-level = 3

Changelog.md

+4
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
- Due to the removal image_type from image struct, old cache files are incompatible with new version and should be
66
regenerated
77
from scratch(it uses new name)
8+
- Some CLI arguments could change short name, due fixing ambiguous names
89

910
### Known regressions
1011

@@ -15,6 +16,7 @@
1516

1617
- Providing nightly
1718
builds - [#1360](https://github.com/qarmin/czkawka/pull/1360) - https://github.com/qarmin/czkawka/releases/tag/Nightly
19+
- Added finding duplicated options in CLI -[#1364](https://github.com/qarmin/czkawka/pull/1364)
1820

1921
### Core
2022

@@ -53,6 +55,7 @@
5355
- Added ability to show preview of referenced folders - [#1359](https://github.com/qarmin/czkawka/pull/1359)
5456
- Enable selecting with space and jumping over entries with
5557
arrows and opening with enter - [#1359](https://github.com/qarmin/czkawka/pull/1359)
58+
- Added button to rename files with invalid extension -[#1364](https://github.com/qarmin/czkawka/pull/1364)
5659

5760
### GTK GUI
5861

@@ -68,6 +71,7 @@
6871
- Fixed and added more input parameters to the application - [#1354](https://github.com/qarmin/czkawka/pull/1354)
6972
- Fixed crash when stopping scan multiple times - [#1355](https://github.com/qarmin/czkawka/pull/1355)
7073
- Print results also in debug build - [#1355](https://github.com/qarmin/czkawka/pull/1355)
74+
- Added support for selecting reference directories -[#1364](https://github.com/qarmin/czkawka/pull/1364)
7175

7276
## Version 7.0.0 - 19.02.2024r
7377

ci_tester/Cargo.toml

+5
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,11 @@ edition = "2021"
55

66
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
77

8+
9+
[profile.release]
10+
debug-assertions = true
11+
overflow-checks = true
12+
813
[dependencies]
914
state = "0.6.0"
1015
handsome_logger = "0.8.0"

ci_tester/src/main.rs

+13
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,25 @@ static COLLECTED_FILES: state::InitCell<CollectedFiles> = state::InitCell::new()
1717
const ATTEMPTS: u32 = 10;
1818
const PRINT_MESSAGES_CZKAWKA: bool = true;
1919

20+
fn test_args() {
21+
let modes = ["dup", "big", "empty-folders", "empty-files", "temp", "image", "symlinks", "broken", "ext", "video", "music"];
22+
for mode in modes {
23+
println!("Testing mode {}", mode);
24+
let _ = fs::remove_dir_all("RandomDirWithoutContent");
25+
fs::create_dir_all("RandomDirWithoutContent").expect("Should not fail in tests");
26+
run_with_good_status(&[CZKAWKA_PATH.get().as_str(), mode, "-d", "RandomDirWithoutContent"], true);
27+
}
28+
}
29+
2030
// App runs - ./ci_tester PATH_TO_CZKAWKA
2131
fn main() {
2232
handsome_logger::init().expect("Should not fail in tests");
2333
let args: Vec<String> = std::env::args().collect();
2434
let path_to_czkawka = args[1].clone();
2535
CZKAWKA_PATH.set(path_to_czkawka);
36+
37+
test_args();
38+
return;
2639
remove_test_dir();
2740
run_with_good_status(&["ls"], false);
2841
unzip_files();

czkawka_cli/README.md

-8
Original file line numberDiff line numberDiff line change
@@ -47,14 +47,6 @@ cd ..
4747
cargo build --release --bin czkawka_cli
4848
```
4949

50-
## Limitations
51-
52-
Not all available features in core are available in CLI.
53-
54-
List of not available features:
55-
56-
- Ability to use/choose referenced directories
57-
5850
## LICENSE
5951

6052
MIT

czkawka_cli/src/commands.rs

+24-5
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ pub enum Commands {
2525
#[clap(
2626
name = "dup",
2727
about = "Finds duplicate files",
28-
after_help = "EXAMPLE:\n czkawka dup -d /home/rafal -e /home/rafal/Obrazy -m 25 -x 7z rar IMAGE -s hash -f results.txt -D aeo"
28+
after_help = "EXAMPLE:\n czkawka dup -d /home/rafal - -e /home/rafal/Obrazy -m 25 -x 7z rar IMAGE -s hash -f results.txt -D aeo"
2929
)]
3030
Duplicates(DuplicatesArgs),
3131
#[clap(
@@ -88,8 +88,10 @@ pub enum Commands {
8888
pub struct DuplicatesArgs {
8989
#[clap(flatten)]
9090
pub common_cli_items: CommonCliItems,
91+
#[clap(flatten)]
92+
pub reference_directories: ReferenceDirectories,
9193
#[clap(
92-
short = 'p',
94+
short = 'Z',
9395
long,
9496
value_parser = parse_minimal_file_size,
9597
default_value = "257144",
@@ -198,6 +200,8 @@ pub struct TemporaryArgs {
198200
pub struct SimilarImagesArgs {
199201
#[clap(flatten)]
200202
pub common_cli_items: CommonCliItems,
203+
#[clap(flatten)]
204+
pub reference_directories: ReferenceDirectories,
201205
#[clap(
202206
short,
203207
long,
@@ -264,6 +268,8 @@ pub struct SameMusicArgs {
264268
#[clap(flatten)]
265269
pub common_cli_items: CommonCliItems,
266270
#[clap(flatten)]
271+
pub reference_directories: ReferenceDirectories,
272+
#[clap(flatten)]
267273
pub delete_method: DMethod,
268274
#[clap(flatten)]
269275
pub dry_run: DryRun,
@@ -317,7 +323,7 @@ pub struct SameMusicArgs {
317323
)]
318324
pub minimum_segment_duration: f32,
319325
#[clap(
320-
short = 'd',
326+
short = 'Y',
321327
long,
322328
value_parser = parse_maximum_difference,
323329
default_value = "2.0",
@@ -386,6 +392,8 @@ pub struct SimilarVideosArgs {
386392
#[clap(flatten)]
387393
pub common_cli_items: CommonCliItems,
388394
#[clap(flatten)]
395+
pub reference_directories: ReferenceDirectories,
396+
#[clap(flatten)]
389397
pub delete_method: DMethod,
390398
#[clap(flatten)]
391399
pub allow_hard_links: AllowHardLinks,
@@ -437,7 +445,7 @@ pub struct CommonCliItems {
437445
long,
438446
required = true,
439447
help = "Directorie(s) to search",
440-
long_help = "List of directorie(s) which will be searched(absolute path)"
448+
long_help = "List of directorie(s) which will be searched(absolute path) - this directories are not set as reference folders"
441449
)]
442450
pub directories: Vec<PathBuf>,
443451
#[clap(
@@ -495,6 +503,17 @@ pub struct FileToSave {
495503
pub file_to_save: Option<PathBuf>,
496504
}
497505

506+
#[derive(Debug, clap::Args)]
507+
pub struct ReferenceDirectories {
508+
#[clap(
509+
short,
510+
long,
511+
help = "Reference directorie(s) to search",
512+
long_help = "List of directorie(s) which will be searched(absolute path) - this directories are set as reference folders, so will not be visible in the results"
513+
)]
514+
pub reference_directories: Vec<PathBuf>,
515+
}
516+
498517
#[derive(Debug, clap::Args)]
499518
pub struct JsonCompactFileToSave {
500519
#[clap(short = 'C', long, value_name = "json-file-name", help = "Saves the results into the compact json file")]
@@ -527,7 +546,7 @@ pub struct DryRun {
527546

528547
#[derive(Debug, clap::Args)]
529548
pub struct IgnoreSameSize {
530-
#[clap(short, long, help = "Ignore files with the same size, leaving only one file of each size")]
549+
#[clap(short = 'J', long, help = "Ignore files with the same size, leaving only one file of each size")]
531550
pub ignore_same_size: bool,
532551
}
533552

czkawka_cli/src/main.rs

+24-13
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
#![allow(clippy::needless_late_init)]
22
#![warn(clippy::unwrap_used)]
33

4+
use std::path::PathBuf;
45
use std::thread;
56

67
use clap::Parser;
@@ -79,6 +80,7 @@ fn main() {
7980
fn duplicates(duplicates: DuplicatesArgs, stop_receiver: &Receiver<()>, progress_sender: &Sender<ProgressData>) {
8081
let DuplicatesArgs {
8182
common_cli_items,
83+
reference_directories,
8284
minimal_file_size,
8385
maximal_file_size,
8486
minimal_cached_file_size,
@@ -103,7 +105,7 @@ fn duplicates(duplicates: DuplicatesArgs, stop_receiver: &Receiver<()>, progress
103105
);
104106
let mut item = DuplicateFinder::new(params);
105107

106-
set_common_settings(&mut item, &common_cli_items);
108+
set_common_settings(&mut item, &common_cli_items, Some(reference_directories.reference_directories.as_ref()));
107109
item.set_minimal_file_size(minimal_file_size);
108110
item.set_maximal_file_size(maximal_file_size);
109111
item.set_delete_method(delete_method.delete_method);
@@ -119,7 +121,7 @@ fn empty_folders(empty_folders: EmptyFoldersArgs, stop_receiver: &Receiver<()>,
119121

120122
let mut item = EmptyFolder::new();
121123

122-
set_common_settings(&mut item, &common_cli_items);
124+
set_common_settings(&mut item, &common_cli_items, None);
123125
if delete_folders {
124126
item.set_delete_method(DeleteMethod::Delete);
125127
}
@@ -141,7 +143,7 @@ fn biggest_files(biggest_files: BiggestFilesArgs, stop_receiver: &Receiver<()>,
141143
let params = BigFileParameters::new(number_of_files, big_files_mode);
142144
let mut item = BigFile::new(params);
143145

144-
set_common_settings(&mut item, &common_cli_items);
146+
set_common_settings(&mut item, &common_cli_items, None);
145147
if delete_files {
146148
item.set_delete_method(DeleteMethod::Delete);
147149
}
@@ -156,7 +158,7 @@ fn empty_files(empty_files: EmptyFilesArgs, stop_receiver: &Receiver<()>, progre
156158

157159
let mut item = EmptyFiles::new();
158160

159-
set_common_settings(&mut item, &common_cli_items);
161+
set_common_settings(&mut item, &common_cli_items, None);
160162
if delete_files {
161163
item.set_delete_method(DeleteMethod::Delete);
162164
}
@@ -171,7 +173,7 @@ fn temporary(temporary: TemporaryArgs, stop_receiver: &Receiver<()>, progress_se
171173

172174
let mut item = Temporary::new();
173175

174-
set_common_settings(&mut item, &common_cli_items);
176+
set_common_settings(&mut item, &common_cli_items, None);
175177
if delete_files {
176178
item.set_delete_method(DeleteMethod::Delete);
177179
}
@@ -184,6 +186,7 @@ fn temporary(temporary: TemporaryArgs, stop_receiver: &Receiver<()>, progress_se
184186
fn similar_images(similar_images: SimilarImagesArgs, stop_receiver: &Receiver<()>, progress_sender: &Sender<ProgressData>) {
185187
let SimilarImagesArgs {
186188
common_cli_items,
189+
reference_directories,
187190
minimal_file_size,
188191
maximal_file_size,
189192
similarity_preset,
@@ -207,7 +210,7 @@ fn similar_images(similar_images: SimilarImagesArgs, stop_receiver: &Receiver<()
207210
);
208211
let mut item = SimilarImages::new(params);
209212

210-
set_common_settings(&mut item, &common_cli_items);
213+
set_common_settings(&mut item, &common_cli_items, Some(reference_directories.reference_directories.as_ref()));
211214
item.set_minimal_file_size(minimal_file_size);
212215
item.set_maximal_file_size(maximal_file_size);
213216
item.set_delete_method(delete_method.delete_method);
@@ -221,6 +224,7 @@ fn similar_images(similar_images: SimilarImagesArgs, stop_receiver: &Receiver<()
221224
fn same_music(same_music: SameMusicArgs, stop_receiver: &Receiver<()>, progress_sender: &Sender<ProgressData>) {
222225
let SameMusicArgs {
223226
common_cli_items,
227+
reference_directories,
224228
delete_method,
225229
minimal_file_size,
226230
maximal_file_size,
@@ -243,7 +247,7 @@ fn same_music(same_music: SameMusicArgs, stop_receiver: &Receiver<()>, progress_
243247
);
244248
let mut item = SameMusic::new(params);
245249

246-
set_common_settings(&mut item, &common_cli_items);
250+
set_common_settings(&mut item, &common_cli_items, Some(reference_directories.reference_directories.as_ref()));
247251
item.set_minimal_file_size(minimal_file_size);
248252
item.set_maximal_file_size(maximal_file_size);
249253
item.set_delete_method(delete_method.delete_method);
@@ -259,7 +263,7 @@ fn invalid_symlinks(invalid_symlinks: InvalidSymlinksArgs, stop_receiver: &Recei
259263

260264
let mut item = InvalidSymlinks::new();
261265

262-
set_common_settings(&mut item, &common_cli_items);
266+
set_common_settings(&mut item, &common_cli_items, None);
263267
if delete_files {
264268
item.set_delete_method(DeleteMethod::Delete);
265269
}
@@ -283,7 +287,7 @@ fn broken_files(broken_files: BrokenFilesArgs, stop_receiver: &Receiver<()>, pro
283287
let params = BrokenFilesParameters::new(checked_type);
284288
let mut item = BrokenFiles::new(params);
285289

286-
set_common_settings(&mut item, &common_cli_items);
290+
set_common_settings(&mut item, &common_cli_items, None);
287291
if delete_files {
288292
item.set_delete_method(DeleteMethod::Delete);
289293
}
@@ -295,6 +299,7 @@ fn broken_files(broken_files: BrokenFilesArgs, stop_receiver: &Receiver<()>, pro
295299

296300
fn similar_videos(similar_videos: SimilarVideosArgs, stop_receiver: &Receiver<()>, progress_sender: &Sender<ProgressData>) {
297301
let SimilarVideosArgs {
302+
reference_directories,
298303
common_cli_items,
299304
tolerance,
300305
minimal_file_size,
@@ -308,7 +313,7 @@ fn similar_videos(similar_videos: SimilarVideosArgs, stop_receiver: &Receiver<()
308313
let params = SimilarVideosParameters::new(tolerance, ignore_same_size.ignore_same_size, !allow_hard_links.allow_hard_links);
309314
let mut item = SimilarVideos::new(params);
310315

311-
set_common_settings(&mut item, &common_cli_items);
316+
set_common_settings(&mut item, &common_cli_items, Some(reference_directories.reference_directories.as_ref()));
312317
item.set_minimal_file_size(minimal_file_size);
313318
item.set_maximal_file_size(maximal_file_size);
314319
item.set_delete_method(delete_method.delete_method);
@@ -325,7 +330,7 @@ fn bad_extensions(bad_extensions: BadExtensionsArgs, stop_receiver: &Receiver<()
325330
let params = BadExtensionsParameters::new();
326331
let mut item = BadExtensions::new(params);
327332

328-
set_common_settings(&mut item, &common_cli_items);
333+
set_common_settings(&mut item, &common_cli_items, None);
329334

330335
item.find_bad_extensions_files(Some(stop_receiver), Some(progress_sender));
331336

@@ -354,13 +359,19 @@ fn save_and_print_results<T: CommonData + PrintResults>(component: &mut T, commo
354359
component.get_text_messages().print_messages();
355360
}
356361

357-
fn set_common_settings<T>(component: &mut T, common_cli_items: &CommonCliItems)
362+
fn set_common_settings<T>(component: &mut T, common_cli_items: &CommonCliItems, reference_directories: Option<&Vec<PathBuf>>)
358363
where
359364
T: CommonData + PrintResults,
360365
{
361366
set_number_of_threads(common_cli_items.thread_number);
362367

363-
component.set_included_directory(common_cli_items.directories.clone());
368+
let mut included_directories = common_cli_items.directories.clone();
369+
if let Some(reference_directories) = reference_directories {
370+
included_directories.extend_from_slice(reference_directories);
371+
component.set_reference_directory(reference_directories.clone());
372+
}
373+
374+
component.set_included_directory(included_directories);
364375
component.set_excluded_directory(common_cli_items.excluded_directories.clone());
365376
component.set_excluded_items(common_cli_items.excluded_items.clone());
366377
component.set_recursive_search(!common_cli_items.not_recursive);

0 commit comments

Comments
 (0)