aboutsummaryrefslogtreecommitdiff
path: root/cmd.ha
blob: ff37c79e7d7438240abee54d6d7b1b4d79aed690 (plain)
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
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
use fmt;
use strings;
use getopt;
use os;
use io;
use path;
use os::exec;
use strconv;

type error = !(io::error | path::error | exec::error);

type func = fn(tasks: []task, args: str...) (void | task | error);

type command = struct {
	names: []str,
	func: *func,
};

const PADDING: size = 30z;

const commands: [_]command = [
	command {
		names = ["f", "filter"],
		func = &filter,
	},
	command {
		names = ["s", "show"],
		func = &show,
	},
	command {
		names = ["w", "write"],
		func = &write,
	},
];

fn execcommand(name: str, tasks: []task, args: str...) (void | error) = {
	for (const c .. commands) {
		for (const n .. c.names) {
			if (n == name) {
				c.func(tasks, args...)?;
			};
		};
	};
};

fn write(tasks: []task, args: str...) (void | task | error) = {
	const cmdname = "task write";
	const cmdhelp: []getopt::help = ["write a task", "<name>"];
	if (len(args) == 0z) {
		getopt::printhelp(os::stderr, cmdname, cmdhelp)?;
		return;
	};
	const cmd = getopt::parse(args,
		cmdname: getopt::help,
		cmdhelp[0],
		cmdhelp[1],
	);
	defer getopt::finish(&cmd);

	if (len(args) != 1z) {
		getopt::printhelp(os::stderr, cmdname, cmdhelp)?;
		return;
	};

	let buf = path::init()?;
	const p = path::push(&buf, "tasks", args[0])?;
	const c = exec::cmd("vim", p)?;
	exec::exec(&c);
};

fn show(tasks: []task, args: str...) (void | task | error) = {
	for (const t .. tasks) {
		for (const s .. args) {
			if (t.name == s) {
				fmt::println(t.content)!;
			};
		};
	};
};

fn printtask(t: task) (void | error) = {
	const pad = PADDING - len(t.name) + len(strconv::utos(t.priority));
	fmt::printfln("{}{%}", t.name, t.priority, &fmt::mods {
		pad = ' ',
		width = pad, ...
	})!;
};

fn filter(tasks: []task, args: str...) (void | task | error) = {
	const headpad = PADDING - len("name") + len("priority");
	fmt::printfln("name{%}", "priority", &fmt::mods {
		pad = ' ',
		width = headpad,
		...
	})!;
	for (const t .. tasks) {
		if (len(args) == 0z) {
			printtask(t)?;
		};
		for (const s .. args) {
			if (strings::contains(t.name, s)) {
				printtask(t)?;
			};
		};
	};
};