Imported Upstream version 7.48.0
[platform/upstream/curl.git] / scripts / zsh.pl
1 #!/usr/bin/perl
2
3 # Generate ZSH completion
4
5 use strict;
6 use warnings;
7
8 my $curl = $ARGV[0] || 'curl';
9
10 my $regex = '\s+(?:(-[^\s]+),\s)?(--[^\s]+)\s([^\s.]+)?\s+(.*)';
11 my @opts = parse_main_opts('--help', $regex);
12
13 my $opts_str;
14
15 $opts_str .= qq{  $_ \\\n} foreach (@opts);
16 chomp $opts_str;
17
18 my $tmpl = <<"EOS";
19 #compdef curl
20
21 # curl zsh completion
22
23 local curcontext="\$curcontext" state state_descr line
24 typeset -A opt_args
25
26 local rc=1
27
28 _arguments -C -S \\
29 $opts_str
30   '*:URL:_urls' && rc=0
31
32 return rc
33 EOS
34
35 print $tmpl;
36
37 sub parse_main_opts {
38     my ($cmd, $regex) = @_;
39
40     my @list;
41     my @lines = call_curl($cmd);
42
43     foreach my $line (@lines) {
44         my ($short, $long, $arg, $desc) = ($line =~ /^$regex/) or next;
45
46         my $option = '';
47
48         $desc =~ s/'/'\\''/g if defined $desc;
49         $desc =~ s/\[/\\\[/g if defined $desc;
50         $desc =~ s/\]/\\\]/g if defined $desc;
51
52         $option .= '{' . trim($short) . ',' if defined $short;
53         $option .= trim($long)  if defined $long;
54         $option .= '}' if defined $short;
55         $option .= '\'[' . trim($desc) . ']\'' if defined $desc;
56
57         $option .= ":$arg" if defined $arg;
58
59         $option .= ':_files'
60             if defined $arg and ($arg eq 'FILE' || $arg eq 'DIR');
61
62         push @list, $option;
63     }
64
65     # Sort longest first, because zsh won't complete an option listed
66     # after one that's a prefix of it.
67     @list = sort {
68         $a =~ /([^=]*)/; my $ma = $1;
69         $b =~ /([^=]*)/; my $mb = $1;
70
71         length($mb) <=> length($ma)
72     } @list;
73
74     return @list;
75 }
76
77 sub trim { my $s = shift; $s =~ s/^\s+|\s+$//g; return $s };
78
79 sub call_curl {
80     my ($cmd) = @_;
81     my $output = `"$curl" $cmd`;
82     if ($? == -1) {
83         die "Could not run curl: $!";
84     } elsif ((my $exit_code = $? >> 8) != 0) {
85         die "curl returned $exit_code with output:\n$output";
86     }
87     return split /\n/, $output;
88 }