It started with an idle question to Twitter.

Why are command-line arguments called “flags”?

They’re also called arguments or switches and parameters and, in my language community, options, with Getopt::Long being my tool of choice to get them from ARGV to where they can be of use to the rest of the programs.

An awful lot of people liked and retweeted and replied to that tweet. Common opinions include that they’re flags or switches because of the dash being the switch handle or flagpole, that only the ones that are independent and don’t set a variable are flags or switches ( -p is a flag, -p office_inkjet is not), and that flag comes from communication semaphores and/or registers in the hardware.

This is followed by a friend having an idea I was considering at the same time.

Now I need to create a unicode getopt module that accepts actual flags… 🇹🇴🇸🇾🇱🇰🇰🇷🇻🇺🇵🇷

And right now, I’m 40/60 on whether that Unicode will translate to flags when I push it up to GitHub.

I can get … somewhere with this idea.

#!/usr/bin/env perl
use strict;
use warnings;
use utf8;
use feature qw{ postderef say signatures state switch };
no warnings
    qw{ experimental::postderef experimental::smartmatch experimental::signatures };

use Encode qw{decode_utf8};
use Getopt::Long;

@ARGV = map { decode_utf8( $_, 1 ) } @ARGV;

my $help = 0;
my $flag = undef;

my $flags = {
    '🏴'   => 'Anarchy!',
    '🏳️'   => 'Surrender!',
    '🏴‍☠️'  => 'Ahoy!',
    '🇫🇷'   => 'Bonjour!',
    '🇦🇶' => 'SO COLD!',
};

GetOptions(
    'help'   => \$help,
    'flag=s' => \$flag,
);

if ($help) {
    say 'HELP!';
    exit;
}
elsif ( defined $flag && defined $flags->{$flag} ) {
    say $flags->{$flag};
}

else { say 'Hello' }

$ ./hello.pl -h && ./hello.pl --flag 🏴 && ./hello.pl -f 🇫🇷 && ./hello.pl -f 🏴‍☠️ && ./hello.pl
HELP!
Anarchy!
Bonjour!
Ahoy!
Hello

So, that gets us somewhere, and I know that, for some subset of Unicode, variable names are fine. For example, works. But…

#!/usr/bin/env perl
use strict;
use warnings;
use utf8;
use feature qw{ postderef say signatures state switch };
no warnings
    qw{ experimental::postderef experimental::smartmatch experimental::signatures };

my $🏴 => 'Anarchy!';

say $🏴;
$ ./crash.pl
Unrecognized character \x{1f3f4}; marked by <-- HERE after my $<-- HERE near column 5 at ./crash.pl line 9.

So, that doesn’t work. Let’s try it with a more established Unicode character.

#!/usr/bin/env perl
use strict;
use warnings;
use utf8;
use feature qw{ postderef say signatures state switch };
no warnings
    qw{ experimental::postderef experimental::smartmatch experimental::signatures };

use Encode qw{decode_utf8};
use Getopt::Long;

@ARGV = map { decode_utf8( $_, 1 ) } @ARGV;

my $help = 0;
my $poo = 0 ;

GetOptions(
    '💩' => \$poo,
    'help'   => \$help,
);
if ($help) { say 'HELP!'; exit; }
elsif ( $poo != 0 ) { say '💩' }
else { say 'No 💩' }
$ ./crash.pl -💩
Error in option spec: "SCALAR(0xce2200)"

But if we comment out the 💩 option, we get this.

$ ./crash.pl -💩
Unknown option: 💩
No 💩

But replace Poo with Pi and we get this

#!/usr/bin/env perl
use strict;
use warnings;
use utf8;
use feature qw{ postderef say signatures state switch };
no warnings
    qw{ experimental::postderef experimental::smartmatch experimental::signatures };

use Encode qw{decode_utf8};
use Getopt::Long;

@ARGV = map { decode_utf8( $_, 1 ) } @ARGV;

my $help = 0;
my  = 0 ;

GetOptions(
    'π' => \,
    'help'   => \$help,
);
if ($help) { say 'HELP!'; exit; }
elsif (  != 0 ) { say 'π' }
else { say 'No π' }
$ ./crash.pl -π && ./crash.pl
π
No π

I believe that, with expanded Unicode support, I can run programs with the Jolly Roger flag on Talk Like A Pirate Day and get my output to give me no quarter, etc., but I don’t think I could do that now.

If you have any questions or comments, I would be glad to hear it. Ask me on Twitter or make an issue on my blog repo.