19

I am migrating an old toolchain to a new system and now I get plenty of notifications given is experimental or when is experimental.

$ perl -e 'use v5.10; given (12) { when (12) { print "Hello World" }}'
given is experimental at -e line 1.
when is experimental at -e line 1.
Hello World

I would like my new system to be fully compatible with the old one. By this I mean the exact same output.

Is there a way to mute these notifications without touching the oneliners nor the scripts?

nowox
  • 25,978
  • 39
  • 143
  • 293

2 Answers2

26

First of all, note that smartmatching will be removed or changed in a backwards incompatible manner. This may affect your given statements.


To use given+when without warnings, one needs the following:

# 5.10+
use feature qw( switch );
no if $] >= 5.018, warnings => qw( experimental::smartmatch );

or

# 5.18+
use feature qw( switch );
no warnings qw( experimental::smartmatch );

experimental provides a shortcut for those two statements.

use experimental qw( switch );

Finally, you ask how to add this to your programs without changing them (and presumably without changing Perl). That leaves monkeypatching.

I wouldn't recommend it. It's far easier to write a couple of one-liners to automatically fix up your programs that rewritting Perl's behaviour on the fly.

But if you want to go in that direction, the simplest solution is probably to write a $SIG{__WARN__} handler that filters out the undesired warnings.

$SIG{__WARN__} = sub {
   warn($_[0]) if $_[0] !~ /^(?:given|when) is experimental at /;
};

(Of course, that won't work if your program makes use of $SIG{__WARN__} already.)

To get it loaded without changing your programs or one-liners, all you have to do is place the patch in a module, and tell Perl to load the module as follows:

export PERL5OPT=-MMonkey::SilenceSwitchWarning

$ cat Monkey/SilenceSwitchWarning.pm
package Monkey::SilenceSwitchWarning;

use strict;
use warnings;

$SIG{__WARN__} = sub {
    warn($_[0]) if $_[0] !~ /^(?:given|when) is experimental at /;
};

1;

$ perl -e 'use v5.10; given (12) { when (12) { print "Hello World\n" }}'
given is experimental at -e line 1.
when is experimental at -e line 1.
Hello World

$ export PERL5OPT=-MMonkey::SilenceSwitchWarning

$ perl -e 'use v5.10; given (12) { when (12) { print "Hello World\n" }}'
Hello World
ikegami
  • 367,544
  • 15
  • 269
  • 518
  • Updated my answer with a practical solution – ikegami Apr 12 '17 at 19:06
  • Arf! With this `perl -e '$SIG{__WARN__} = sub { warn("oops?") };` it doesn't work :( Do you know why? – nowox Apr 13 '17 at 06:42
  • What do you mean? It works for me (does absolutely nothing). – ikegami Apr 13 '17 at 06:46
  • Sorry, use this instead: `$ perl -e '$SIG{__WARN__} = sub { warn("oops?") }; use v5.10; given(1) { when(1) {}}' given is experimental at -e line 1. when is experimental at -e line 1.` – nowox Apr 13 '17 at 06:58
  • 1
    It's a compile time warning, but you're only setting up the handler at runtime. Use `BEGIN` – ikegami Apr 13 '17 at 14:03
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/141654/discussion-between-nowox-and-ikegami). – nowox Apr 13 '17 at 14:11
6
no warnings 'experimental';

...works in version 5.22 at least.

Kjetil S.
  • 3,468
  • 20
  • 22
  • Thanks. It's weird though that eclipse was showing it as an error not a warning. Neverthess, this worked for me. – shawn1874 Apr 27 '22 at 22:34