File Coverage

bin/whojobs
Criterion Covered Total %
statement 34 115 29.5
branch 2 30 6.6
condition 0 6 0.0
subroutine 11 17 64.7
pod n/a
total 47 168 27.9


line stmt bran cond sub pod time code
1             #!/usr/bin/env perl
2             #ABSTRACT: List the users with active jobs, and the number of jobs in the cluster
3             #PODNAME: whojobs
4              
5 1     1   5511 use v5.12;
  1         4  
6 1     1   6 use warnings;
  1         2  
  1         57  
7 1     1   783 use Getopt::Long;
  1         19090  
  1         8  
8 1     1   751 use FindBin qw($RealBin);
  1         1556  
  1         137  
9 1     1   741 use Data::Dumper;
  1         11999  
  1         92  
10 1     1   765 use Term::ANSIColor qw(:constants);
  1         14154  
  1         1331  
11 1     1   10 use Cwd;
  1         2  
  1         177  
12 1         70553 $Data::Dumper::Sortkeys = 1;
13 1 50       47 if (-e "$RealBin/../dist.ini") {
  0         0  
14 1 50       7 say STDERR "[dev mode] Using local lib" if ($ENV{"DEBUG"});
15 1     1   590 use lib "$RealBin/../lib";
  1         896  
  1         8  
16             }
17              
18              
19 1         3 my ($opt_color, $opt_no_color, $opt_min_jobs, $opt_verbose, $opt_scramble);
20             GetOptions(
21             'n|no-color' => \$opt_no_color,
22             'm|min-jobs=i' => \$opt_min_jobs,
23             'v|verbose' => \$opt_verbose,
24             's|scramble' => \$opt_scramble,
25 1     1   1391 'version' => sub { say "whojobs v", $NBI::Slurm::VERSION; exit },
  1         114  
26 0     0   0 'h|help' => sub { usage() },
27 1         17 );
28 0         0 my $opt_pattern = shift;
29 1     1   911 use NBI::Slurm;
  1         4  
  1         100290  
30              
31 0         0 our $user_max = 14;
32 0         0 my $unix_users = unix_users();
33 0         0 my $slurm_users = slurm_users();
34 0         0 my $all_users = {};
35              
36 0         0 for my $user (@{$unix_users}) {
  0         0  
37 0         0 $slurm_users->{$user} = 0;
38             }
39 0         0 my $opt_user = $ENV{USER};
40              
41 0         0 my $c = 0;
42 0         0 my $p = 0;
43 0         0 for my $user (sort {$$slurm_users{$a} <=> $$slurm_users{$b}}keys %{$slurm_users}) {
  0         0  
  0         0  
44 0         0 $c++;
45 0 0       0 my $star = ($user eq $opt_user) ? '*' : '';
46 0 0 0     0 if ($opt_pattern && $user !~ /$opt_pattern/i) {
47 0         0 next;
48             }
49 0 0 0     0 if ($opt_min_jobs && $slurm_users->{$user} < $opt_min_jobs) {
50 0         0 next;
51             }
52             # Dedicate 40 chars to user, 10 to jobs, 10 to star
53 0 0       0 if ($c % 2 == 0) {
54 0 0       0 if ( !$opt_no_color) {
55 0         0 print GREEN BOLD;
56             } else {
57 0         0 print RESET;
58             }
59             } else {
60 0         0 print RESET;
61             }
62 0         0 $p++;
63 0 0       0 my $user_string = $opt_scramble ? scramble_string($user, [$opt_user]) : "$user";
64            
65 0         0 printf "%4s %-${user_max}s %5s %2s\n", $c, $user_string, $slurm_users->{$user}, $star;
66             }
67              
68             # END
69              
70 0         0 print STDERR RESET "\n";
71 0 0       0 if ($opt_verbose) {
72 0 0       0 unless ($opt_no_color) {
73 0         0 print STDERR CYAN;
74             }
75 0         0 print STDERR "Total users with jobs: ", scalar(keys %{$slurm_users}), "\n";
  0         0  
76 0         0 print STDERR "Total users logged: ", scalar(@{$unix_users}), "\n";
  0         0  
77 0         0 print STDERR "Printed users: $p\n", RESET;
78             }
79              
80             END {
81 1     1   12 print RESET "";
82             }
83             sub unix_users {
84 0     0     my $cmd = "who | cut -d' ' -f1";
85 0           my @users = `$cmd`;
86 0           chomp @users;
87             # Remove 'USER'
88 0           shift @users;
89             # Sort uniq
90 0           @users = sort { $a cmp $b } @users;
  0            
91 0           my %seen = ();
92 0           @users = grep { ! $seen{ $_ }++ } @users;
  0            
93              
94 0           return \@users;
95             }
96             sub slurm_users {
97 0 0   0     if (not NBI::Slurm::has_squeue()) {
98 0           say STDERR RED, "[WARNING]", RESET, " `squeue` not found, are you in the cluster?";
99 0           say STDERR "Will just print some logged users...";
100 0           return {};
101             }
102 0           my $cmd = "squeue --format='%u'";
103 0           my @users = `$cmd`;
104 0           chomp @users;
105             # Remove 'USER'
106 0           shift @users;
107             # Sort uniq
108 0           @users = sort { $a cmp $b } @users;
  0            
109            
110              
111             # Return a hash user -> times seen
112 0           my %seen = ();
113 0           @users = grep { ! $seen{ $_ }++ } @users;
  0            
114            
115 0           return \%seen;
116             }
117              
118             sub scramble_string {
119             # change odd chars to random chars
120 0     0     my $string = shift;
121 0           my $whitelist = shift;
122 0 0         return "" unless ($string);
123 0           my @chars = split(//, $string);
124 0           my $scrambled = '';
125 0 0         return $string if (grep { $string eq $_ } @{$whitelist});
  0            
  0            
126 0           for my $char (@chars) {
127 0 0         if (rand() > 0.5) {
128 0           $scrambled .= $char;
129             } else {
130 0           $scrambled .= chr(int(rand(26)) + 97);
131             }
132             }
133 0           return $scrambled;
134             }
135             sub get_terminal_width {
136 0     0     my $terminal_width = `tput cols`;
137 0           chomp($terminal_width);
138 0 0         return $terminal_width > 20 ? $terminal_width : 80;
139             }
140              
141             sub usage {
142 0     0     print STDERR <
143             -------------------------------------------------------------------------
144             whojobs - List the users with jobs, and the number of jobs in the cluster
145             -------------------------------------------------------------------------
146             Usage: whojobs [options] [pattern]
147              
148             Options:
149             -n, --no-color Do not use colors
150             -m, --min-jobs INT Only show users with at least one job
151             -v, --verbose Verbose output
152              
153             END
154              
155 0           exit 0;
156             }
157              
158             __END__