Fernando Santagata
Fernando Santagata

Reputation: 1487

Best way to check optional module availability

In a module I'm writing there is just one method which requires an additional module, so I wish to make that module optional by not listing it in the depends part of the META6.json file. The method will return a Failure object if the optional module is not available.
I know I can do something like this:

if (try require Optional::Module) !=== Nil {
  # go on
} else {
  # fail
}

Is there any better way to do it?

Upvotes: 5

Views: 134

Answers (2)

Fernando Santagata
Fernando Santagata

Reputation: 1487

I want to thank everyone who answered or commented on this question.
I benchmarked my proposed solution and the two ones given in the comments to my question:

my $pre = now;
for ^10000 {
  $*REPO.repo-chain.map(*.?candidates('Available::Module').Slip).grep(*.defined);
  $*REPO.repo-chain.map(*.?candidates('Unavailable::Module').Slip).grep(*.defined);
}
say now - $pre; # 13.223087

$pre = now;
for ^10000 {
  $*REPO.resolve(CompUnit::DependencySpecification.new(:short-name("Available::Module")));
  $*REPO.resolve(CompUnit::DependencySpecification.new(:short-name("Unavailable::Module")));
}
say now - $pre; # 3.105257

$pre = now;
for ^10000 {
  (try require Available::Module) !=== Nil;
  (try require Unavailable::Module) !=== Nil;
}
say now - $pre; # 4.963793

Change the module names to match one that you have available on your system and one that you don't.
The comments show the results in seconds on my computer.

Upvotes: 5

Scimon Proctor
Scimon Proctor

Reputation: 4558

Something like this?

my $loaded = False;
CATCH {
    default { $loaded = True }
}
require Optional::Module;
if ( ! $loaded ) {
  # Fail
}
# Go on

In this case it will try and load the module and catch the exception at runtime.

Upvotes: 2

Related Questions