mirror of
https://github.com/gtritchie/bulk-properties.git
synced 2026-07-22 14:10:30 +00:00
* Add metadata cache warning modal for large bulk operations When a bulk operation modifies more than 75 notes, show a modal explaining that Obsidian's metadata cache may take several minutes to re-index. Includes a "Don't show again" toggle persisted via a new showLargeOperationWarning setting, re-enableable from the settings tab. Covers bulk update, bulk delete, deselect all, and remove selection property entry points. Also simplifies deselectAll and removeSelectionProperty signatures to take the plugin instance, deriving app and selectionProperty from it. * Pass captured selectionProperty through to doRemove Restore the original data flow where selectionProperty is captured once at command start and threaded through, rather than re-read from plugin.settings inside doRemove. The signature simplification in the prior commit introduced a subtle re-read that could mismatch if the setting changed between confirmation and execution. * Remove cache warning from file deletion, lower threshold to 25 File deletion reconciles in the metadata cache much faster than property edits (entry removal vs YAML re-parse), so the warning would be misleading. Also lower LARGE_OPERATION_THRESHOLD from 75 to 25. * Document scale expectations and cache warning in README * Avoid hardcoding threshold number in README
54 lines
1.5 KiB
TypeScript
54 lines
1.5 KiB
TypeScript
import {Notice} from "obsidian";
|
|
import type BulkPropertiesPlugin from "./main";
|
|
import {confirmDeselectAll} from "./confirm-modal";
|
|
import {getSelectedFiles} from "./files";
|
|
import {
|
|
shouldWarnLargeOperation,
|
|
showLargeOperationNotice,
|
|
} from "./large-operation-notice";
|
|
import {withProgress} from "./progress";
|
|
|
|
export async function deselectAll(
|
|
plugin: BulkPropertiesPlugin,
|
|
): Promise<void> {
|
|
const {app} = plugin;
|
|
const selectionProperty = plugin.settings.selectionProperty;
|
|
const files = getSelectedFiles(app, selectionProperty);
|
|
|
|
if (files.length === 0) {
|
|
new Notice("No notes are selected");
|
|
return;
|
|
}
|
|
|
|
const confirmed = await confirmDeselectAll(app, files.length);
|
|
if (!confirmed) return;
|
|
|
|
const result = await withProgress(
|
|
files,
|
|
"Deselecting",
|
|
async (file) => {
|
|
await app.fileManager.processFrontMatter(
|
|
file,
|
|
(fm: Record<string, unknown>) => {
|
|
fm[selectionProperty] = false;
|
|
},
|
|
);
|
|
},
|
|
);
|
|
|
|
const {succeeded, failed, cancelled, total} = result;
|
|
let msg: string;
|
|
if (cancelled) {
|
|
msg = `Deselected ${succeeded} of ${total} note${total === 1 ? "" : "s"} (cancelled)`;
|
|
} else if (failed.length === 0) {
|
|
msg = `Deselected ${succeeded} note${succeeded === 1 ? "" : "s"}`;
|
|
} else {
|
|
msg = `Deselected ${succeeded} note${succeeded === 1 ? "" : "s"}, failed on ${failed.length}: ${failed.join(", ")}`;
|
|
}
|
|
|
|
if (shouldWarnLargeOperation(plugin, succeeded)) {
|
|
showLargeOperationNotice(plugin, succeeded, msg);
|
|
} else {
|
|
new Notice(msg);
|
|
}
|
|
}
|