From cbcb5d74b8567f9e0a491778f68173bce481db3d Mon Sep 17 00:00:00 2001 From: Thomas Herden Date: Sat, 21 May 2022 14:36:27 -0400 Subject: [PATCH] Address issues identified by @liamcain (https://github.com/obsidianmd/obsidian-releases/pull/960#issuecomment-1131082567); miscellaneous refactorings; bump version --- README.md | 22 +++--- main.ts | 187 +++++++++++++++++++++++++------------------------- manifest.json | 2 +- package.json | 6 +- versions.json | 2 +- 5 files changed, 108 insertions(+), 111 deletions(-) diff --git a/README.md b/README.md index 5876890..9137620 100644 --- a/README.md +++ b/README.md @@ -18,8 +18,8 @@ The above behavior is "alright"; but *completed instances of recurring tasks* te After some reflection, I realized that my completed recurring tasks fall into three categories: 1. those that I don't care to keep -- they can be deleted -2. those that I want to retain in their original note file -- but moved to the end/bottom -3. those that I want to move to a separate archival note file) +2. those that I want to retain within their original note file, but relocated at the end/bottom +3. those that I want to move to a separate archival note file By including within your recurring tasks a 'trigger' that identifies which of the above actions you want to apply to your completed instances, we can automate those actions. @@ -35,31 +35,27 @@ The *default* "trigger" for each **Packrat** action takes the form of an *html c I chose to use *comments* because they aren't displayed in **Obsidian**'s Preview mode, and also to keep them out of its *Tag* pane. -However, you can change the trigger values within **Packrat**'s settings -- to #tags, or @values, or any other string (including Unicode characters) that is supported by **Obsidian**. +However, you can change the trigger values within **Packrat**'s settings -- to #tags, or @values, or any other string (including Unicode characters) that **Obsidian** supports. ## Using **Packrat** -**Packrat** adds a single command to the *Command Palette*. +**Packrat** adds a single command to Obsidian. -Assuming that your active note contains one or more completed instances of recurring tasks, open the *Command Palette* and select "Packrat: Process completed recurring Tasks within the active note". +Assuming that you have a markdown file open as your active note, invoke the *Command Palette* and select "Packrat: Process completed recurring Tasks within the active note". -When that command is issued, **Packrat** will scan the file for completed instances of recurring tasks and act upon each based upon any trigger value contained within it. +When that command is issued, **Packrat** will scan the file for completed instances of recurring tasks and act on each depending on the trigger value(s) it contains. ## Default 'archive file' -By default, **Packrat** appends completed recurring tasks that you want to archive to a file named `archive.md` located in the root directory of the vault -- it will create the file if it doesn't already exist. +By default, **Packrat** appends completed recurring tasks that you want to archive to a file named `archive.md` located in the root directory of the vault. It will create the file if it doesn't already exist. -Both the location and name of this "archive file" can be changed in **Packrat**'s settings; the only requirement is that the file have an ".md" extension. +Both the location and name of this "archive file" can be changed in **Packrat**'s settings; the only requirements are that the filepath must exist and the filename must have an ".md" extension. ## Installation **Packrat** has not yet been reviewed and accepted as a Community Plugin. -Until it is... - -(*if* it ever is: because I don't really know Typescript/Javascript, I pretty much hacked this together -- it probably doesn't meet code quality standards, and I may not be capable of doing much about that) - -...this plugin can be installed manually as follows: +Until it is, it can be installed manually as follows: 1. Create the following subidirectory of your **Obsidian** vault: `.obsidian/plugins/packrat/` 2. From the most recent Release for the repo, copy the files `main.js`, `styles.css`, `manifest.json` to that subdirectory diff --git a/main.ts b/main.ts index 4131999..9b5b92e 100644 --- a/main.ts +++ b/main.ts @@ -1,16 +1,16 @@ -import { App, TFile, Notice, Plugin, PluginSettingTab, Setting } from 'obsidian'; +import { App, Notice, Plugin, PluginSettingTab, Setting, TFile } from 'obsidian'; export interface PackratSettings { - deletion_signifier: string; - bottom_signifier: string; - archive_signifier: string; + deletion_trigger: string; + bottom_trigger: string; + archive_trigger: string; archive_filepath: string; } export const DEFAULT_SETTINGS: PackratSettings = { - deletion_signifier: '%%done_del%%', - bottom_signifier: '%%done_end%%', - archive_signifier: '%%done_log%%', + deletion_trigger: '%%done_del%%', + bottom_trigger: '%%done_end%%', + archive_trigger: '%%done_log%%', archive_filepath: 'archive.md', } @@ -22,25 +22,25 @@ export default class PackratPlugin extends Plugin { await this.loadSettings(); - // This adds a settings tab so the user can configure various aspects of the plugin this.addSettingTab(new PackratSettingTab(this.app, this)); - // This adds a Command to the Command Palette - this.addCommand({ - id: 'tasks-run-packrat', + this.addCommand({ // (to the Command Palette) + id: 'run', name: 'Process completed recurring Tasks within the active note', checkCallback: (checking: boolean) => { // Packrat only works on an open markdown (.md) note file const { workspace } = this.app; const activeFile = workspace.getActiveFile(); - if (!activeFile || activeFile.extension !== "md") { - } else { - if (!checking) { - this.ProcessCompletedRecurringTasks(activeFile); + // Include in Command Palette only when function returns true + if (activeFile && activeFile.extension == "md") { + if (checking) { + return true; } - // Command Palette will only display this command when the check function returns true - return true; + // Actually execute command + this.ProcessCompletedRecurringTasks(activeFile); + } else { + return false; } } }); @@ -59,89 +59,90 @@ export default class PackratPlugin extends Plugin { } async ProcessCompletedRecurringTasks(activeFile): Promise { - const { vault } = this.app; - - const rruleSignifier = "🔁".normalize(); - const deleteSignifier = this.settings.deletion_signifier; - const archiveSignifier = this.settings.archive_signifier; - const bottomSignifier = this.settings.bottom_signifier; - const archiveFilename = this.settings.archive_filepath; - - let deletedTaskCount = 0; - let movedTaskCount = 0; - let archivedTaskCount = 0; - let thisLine = ""; - let writebackLines = []; - let appendLines = []; - let archiveLines = []; - let results = []; - - let fileContents = await vault.read(activeFile); - fileContents = fileContents.split("\n"); - - for (let i = 0; i < fileContents.length; i++) { - thisLine = fileContents[i]; - let firstFive = thisLine.substring(0, 5).toUpperCase() - // test if this is a completed task - if (firstFive == "- [X]") { - // test if line includes Tasks' recurrence signifier 🔁 - if (0 < thisLine.indexOf(rruleSignifier)) { - // test for 'delete' signifier - if (0 < thisLine.indexOf(deleteSignifier)) { + + try { + const { vault } = this.app; + const rruleSignifier = "🔁".normalize(); + const deleteTrigger = this.settings.deletion_trigger; + const archiveTrigger = this.settings.archive_trigger; + const bottomTrigger = this.settings.bottom_trigger; + const archiveFilename = this.settings.archive_filepath; + const archiveFile = + (vault.getAbstractFileByPath(archiveFilename)) || + (await vault.create(archiveFilename, "")); + + let deletedTaskCount = 0; + let movedTaskCount = 0; + let archivedTaskCount = 0; + let thisLine = ""; + let writebackLines = []; + let appendLines = []; + let archiveLines = []; + let results = []; + + let fileContents = await vault.read(activeFile); + fileContents = fileContents.split("\n"); + + for (let i = 0; i < fileContents.length; i++) { + thisLine = fileContents[i]; + let firstFive = thisLine.substring(0, 5).toUpperCase() + // test if this is a completed instance of recurring Task + if (firstFive === "- [X]" && thisLine.indexOf(rruleSignifier) != -1) { + // test for 'delete' trigger + if (0 < thisLine.indexOf(deleteTrigger)) { deletedTaskCount += 1; continue; } - // test for 'archive' signifier - if (0 < thisLine.indexOf(archiveSignifier)) { + // test for 'archive' trigger + if (0 < thisLine.indexOf(archiveTrigger)) { archiveLines.push(thisLine); archivedTaskCount += 1; continue; } - // test for 'move' signifier - if (0 < thisLine.indexOf(bottomSignifier)) { + // test for 'move' trigger + if (0 < thisLine.indexOf(bottomTrigger)) { appendLines.push(thisLine); movedTaskCount += 1; continue; } - // no matching signifier + // completed recurring Task with no Packrat triggers + writebackLines.push(thisLine); + } + else { + // not a completed recurring Task writebackLines.push(thisLine); } - } else { - writebackLines.push(thisLine); } - } - // write designated Tasks to archive file - const archiveFile = - vault.getAbstractFileByPath(archiveFilename) || - (await vault.create(archiveFilename, "")); - - if (!(archiveFile instanceof TFile)) { - new Notice(`${archiveFilename} is not a valid markdown file`); - } else { - let archiveFileContents = await vault.read(archiveFile); - archiveFileContents = archiveFileContents.split("\n"); - archiveFileContents = archiveFileContents.concat(archiveLines); - vault.modify(archiveFile, archiveFileContents.join("\n")); - } + if (archivedTaskCount > 0) { // otherwise needn't modify archiveFile + let archiveFileContents = await vault.read(archiveFile); + archiveFileContents = archiveFileContents.split("\n"); + archiveFileContents = archiveFileContents.concat(archiveLines); + vault.modify(archiveFile, archiveFileContents.join("\n")); + } - // rewrite active Note file with designated Tasks at bottom and Deleted and Archived tasks removed - results = writebackLines.concat(appendLines); - vault.modify(activeFile, results.join("\n")); - var tdMsg = `${deletedTaskCount} tasks deleted\n`; - var tmMsg = `${movedTaskCount} tasks moved to end of note\n`; - var taMsg = `${archivedTaskCount} tasks archived\n`; - const noticeText = tdMsg + tmMsg + taMsg; - new Notice(noticeText); + // rewrite active Note file with designated Tasks at bottom and Deleted and Archived tasks removed + results = writebackLines.concat(appendLines); + vault.modify(activeFile, results.join("\n")); + var tdMsg = `${deletedTaskCount} tasks deleted\n`; + var tmMsg = `${movedTaskCount} tasks moved to end of note\n`; + var taMsg = `${archivedTaskCount} tasks archived\n`; + const noticeText = tdMsg + tmMsg + taMsg; + new Notice(noticeText); + } catch (err) { + new Notice(err); + console.log(err); + return; + } } } class PackratSettingTab extends PluginSettingTab { plugin: PackratPlugin; - public defaultDeletionsignifier = "%%done_del%%"; - public defaultBottomsignifier = "%%done_move%%"; - public defaultArchivesignifier = "%%done_log%%"; + public defaultDeletionTrigger = "%%done_del%%"; + public defaultBottomTrigger = "%%done_move%%"; + public defaultArchiveTrigger = "%%done_log%%"; public defaultArchiveFilepath = "logfile.md"; constructor(app: App, plugin: PackratPlugin) { @@ -155,38 +156,38 @@ class PackratSettingTab extends PluginSettingTab { containerEl.createEl('h2', { text: 'Packrat plugin settings' }); new Setting(containerEl) - .setName('Deletion signifier') + .setName('Deletion trigger') .setDesc('Text to trigger deletion of completed recurring Task instance') .addText(text => text - .setPlaceholder(this.defaultDeletionsignifier) - .setValue(this.plugin.settings.deletion_signifier) + .setPlaceholder(this.defaultDeletionTrigger) + .setValue(this.plugin.settings.deletion_trigger) .onChange(async (value) => { - console.log('deletion_signifier: ' + value); - this.plugin.settings.deletion_signifier = value; + console.log('deletion_trigger: ' + value); + this.plugin.settings.deletion_trigger = value; await this.plugin.saveSettings(); })); new Setting(containerEl) - .setName('"Move to end of file" signifier') + .setName('"Move to end of file" trigger') .setDesc('Text to trigger moving completed recurring Task instance to bottom of Active note') .addText(text => text - .setPlaceholder(this.defaultBottomsignifier) - .setValue(this.plugin.settings.bottom_signifier) + .setPlaceholder(this.defaultbottomTrigger) + .setValue(this.plugin.settings.bottom_trigger) .onChange(async (value) => { - console.log('bottom_signifier: ' + value); - this.plugin.settings.bottom_signifier = value; + console.log('bottom_trigger: ' + value); + this.plugin.settings.bottom_trigger = value; await this.plugin.saveSettings(); })); new Setting(containerEl) - .setName('Archive signifier') + .setName('Archive trigger') .setDesc('Text to trigger moving completed recurring Task instance to archive note') .addText(text => text - .setPlaceholder(this.defaultArchivesignifier) - .setValue(this.plugin.settings.archive_signifier) + .setPlaceholder(this.defaultarchiveTrigger) + .setValue(this.plugin.settings.archive_trigger) .onChange(async (value) => { - console.log('archive_signifier: ' + value); - this.plugin.settings.archive_signifier = value; + console.log('archive_trigger: ' + value); + this.plugin.settings.archive_trigger = value; await this.plugin.saveSettings(); })); diff --git a/manifest.json b/manifest.json index bc46b78..da5fb4d 100644 --- a/manifest.json +++ b/manifest.json @@ -1,7 +1,7 @@ { "id": "tasks-packrat-plugin", "name": "Packrat", - "version": "1.0.0", + "version": "1.1.0", "minAppVersion": "0.12.0", "description": "Process completed recurring Tasks", "author": "Thomas Herden", diff --git a/package.json b/package.json index dced590..6eab981 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "Packrat Plugin", - "version": "1.0.0", - "description": "Process completed recurring Tasks", + "version": "1.1.0", + "description": "Process completed recurring Tasks based on in-line triggers", "main": "main.js", "scripts": { "dev": "node esbuild.config.mjs", @@ -10,7 +10,7 @@ }, "keywords": [ "Obsidian.md", - "Tasks plugin", + "Obsidian Tasks plugin extension", "completed recurring tasks" ], "author": "therden", diff --git a/versions.json b/versions.json index 2aee4c5..fd440b5 100644 --- a/versions.json +++ b/versions.json @@ -1,3 +1,3 @@ { - "1.0.0": "0.14.2" + "1.1.0": "0.14.2" } \ No newline at end of file