generated from obsidianmd/obsidian-sample-plugin
-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.ts
83 lines (76 loc) · 2.57 KB
/
main.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
import { Plugin } from 'obsidian';
const BRACKETS_REGEX = /\[+|\]+/g;
const DATE_REGEX = /\[\[\d{4}-\d{2}-\d{2}\]\]/g;
const OVERDUE_REGEX = /\[\[Overdue\]\]/i;
const TODO_REGEX = /- \[ \]/;
export default class Overdue extends Plugin {
interval: number;
async markOverdue() {
console.log('Searching for overdue items');
// Compare against the start of the day in the local timezone
const now = new Date();
now.setHours(0,0,0,0);
for (const file of this.app.vault.getMarkdownFiles()) {
// Check if the note itself is dated
const fileDate = new Date(`${file.basename}T00:00`);
// Invalid dates always evaluate to false in comparisons so there's no need to check
// validity here.
const isPastDailyNote = (fileDate < now);
let hasChange = false;
const newLines = [];
const content = await this.app.vault.cachedRead(file);
// Check all lines in the note
for(let line of content.split('\n')) {
// Only consider lines that are todo-like and not already marked overdue
if(line.match(TODO_REGEX) && !line.match(OVERDUE_REGEX)) {
if(isPastDailyNote) {
// Mark all todo-like lines as overdue in a note that is overdue
line = `${line} [[Overdue]]`;
hasChange = true;
} else {
// Check all dates in a line
for(const dateLink of line.match(DATE_REGEX) || []) {
const dateString = dateLink.replace(BRACKETS_REGEX, '');
const lineDate = new Date(`${dateString}T00:00`);
if(lineDate < now) {
// Mark the todo-like line as overdue if it has a date in the past
line = `${line} [[Overdue]]`;
hasChange = true;
break;
}
}
}
}
newLines.push(line);
}
if(hasChange) {
console.log(`Marking overdue item(s) in ${file.path}`)
await this.app.vault.modify(file, newLines.join('\n'));
}
}
console.log('Finished marking overdue items');
}
async onload() {
// Add a command to mark overdue items
this.addCommand({
id: 'overdue-mark',
name: 'Mark overdue items',
callback: () => {
this.markOverdue();
}
});
// Add an interval that marks overdue items during the local midnight hour.
// The function is idempotent so it can run safely multiple times in the hour.
this.interval = window.setInterval(() => {
const now = new Date();
// Run right after midnight.
if(now.getHours() == 0) {
this.markOverdue();
}
}, 20 * 60 * 1000);
this.registerInterval(this.interval);
}
onunload() {
window.clearInterval(this.interval);
}
}