aboutsummaryrefslogtreecommitdiff
path: root/.local/bin/gittab
blob: 5ffd5f99319cc285b4ac0a44d4603ae58f73cb0b (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
#! /usr/bin/env perl6

use v6.d;

constant TABDIR = $*HOME.add('.local/etc/gittab/tabs');
constant TABCONF = $*HOME.add('.local/etc/gittab/basedirs');

#| Update managed git repositories
multi sub MAIN (
	#| A list of targets to update.
	*@targets,
) {
	@targets = TABDIR.dir.map(*.basename) unless @targets;

	for @targets -> $target {
		my $tab = find-tab($target);

		note "No gittab for target '$target'" unless $tab;

		my $basedir = get-basedir($target);

		mkdir($basedir) unless $basedir.d;

		for $tab.lines.grep(!*.starts-with("#")) {
			my ($name, $repo, $branch) = $_.words;

			if (!$basedir.add($name).d) {
				chdir $basedir;
				run « git clone --single-branch --branch "$branch" --depth 1 "$repo" "$name" »;
			}

			chdir $basedir.add($name);
			run « git checkout "$branch" »;
			run « git pull "$repo" "$branch" »;
		}
	}
}

#| List managed git repositories
multi sub MAIN (
	Bool:D :$list!,
) {
	my @tabs = TABDIR.dir.map(*.basename).sort;
	my $longest = @tabs.map(*.chars).sort.tail;

	for @tabs {
		"%-{$longest}s %s\n".printf($_, get-basedir($_));
	}
}

sub find-tab (
	Str:D $name,
) {
	my @attempts =
		$name,
		$name ~ 'tab',
	;

	for @attempts {
		my $fh = TABDIR.add($_);

		return $fh if $fh.f;
	}

	Nil;
}

sub get-basedir (
	Str:D $tab,
) {
	state %basedirs;

	if (!%basedirs && TABCONF.e) {
		TABCONF
			.lines
			.grep(!*.starts-with('#'))
			.map({
				my ($tab, $basedir) = $_.words;

				%basedirs{$tab} = $basedir.IO;
			})
	}

	return $*HOME unless %basedirs{$tab}:exists;

	$*HOME.add(%basedirs{$tab});
}