Alien-Base-ModuleBuild

 view release on metacpan or  search on metacpan

lib/Alien/Base/ModuleBuild/FAQ.pod  view on Meta::CPAN

 
 Alien::Base::ModuleBuild->new(
   ...
   alien_bin_requires => {
     'Alien::gmake' => 0.11, # needed for %{gmake} helper
   },
   alien_build_commands => [
     "%{gmake}",
   ],
   alien_install_commands => [
     "%{gmake} install",
   ],
   ...
 )->create_build_script;

=head2 When debugging my package build, I get different results!

If you get results from running the commands in your shell different to what happens when your C<Alien::>
distribution attempts to build, it may be because your environment is different than the one that your
distribution is using.  For example, if you use L<Alien::CMake> or L<Alien::gmake> to build with specific tools
that are provided by your operating system, L<Alien::Base::ModuleBuild> will adjust the path before executing
build and install commands.

In the alien build directory (usually C<_alien>) you will find environment files that you can source
into your shell (C<env.csh> for tcsh and C<env.sh> for bourne based shells), which should provide the
identical environment used by the build process in order to troubleshoot the build manually.

 % source _alien/env.sh

=head2 Can/Should I write a tool oriented Alien module using C<Alien::Base> that provides executables instead of a library?

Certainly.  The original intent was to provide libraries, but tools are also quite doable using the
C<Alien::Base> tool set.  A simple minded example of this which is fairly easy to replicate is L<Alien::m4>.

In general, this means specifying a subclass in your C<Build.PL> and bundling it in your distribution C<inc> directory.

C<Build.PL>:

 ...
 use lib 'inc';
 use My::ModuleBuild;
 
 My::ModuleBuild->new(
   ...
 )->create_build_script;

C<inc/My/ModuleBuild.pm>:

 package My::ModuleBuild;
 
 use strict;
 use warnings;
 use parent 'Alien::Base::ModuleBuild';
 use Capture::Tiny qw( capture );
 
 sub alien_check_installed_version
 {
   # see Alien::Base::ModuleBuild#alien_check_installed_version for details
 
   my($self) = @_;
   my($stdout, $stderr) = capture { system 'mytool', '--version' };
 
   # return empty list if the tool is unavailable on the system,
   # or unacceptable.
   return if $! || ...;
 
   # parse from stdout or stderr
   my $version = ...;
   return $version;
 }
 
 sub alien_check_built_version
 {
   # see Alien::Base::ModuleBuild#alien_check_built_version for details
 
   # return empty list if the tool version cannot be found, or if it
   # is unacceptable.  Note that this will cause a failure, so "unknown"
   # may be reasonable if the tool version cannot be determined.
   return if ...;
 
   # determine from the tool itself, or the current directory.
   my $version = ...;
   return $version;
 }
 
 1;

As usual your C<Alien::MyTool> class will simply be a subclass of L<Alien::Base>.
If you tool is installed in a C<bin> directory, you are done, the default C<bin_dir>
implementation should work for you.  Otherwise you may need to provide an alternate
implementation:

 package Alien::MyTool;
 
 use strict;
 use warnings;
 use parent 'Alien::Base';
 
 sub bin_dir
 {
   # see Alien::Base#bin_dir for details
   # You only need to override the default implementation if your tool
   # does not install into the standard "bin" directory.
 
   my($class) = @_;
 
   # normally for system installs the tool should already be in your
   # PATH, so return an empty list.
   return if $class->install_type eq 'system';
 
   # install_type = share
   my $dist_dir = $class->dist_dir;
   return ("$dist_dir/some/bin", "$dist_dir/some/other/bin");
 }
 
 1;

Now once your tool based Alien is installed you can use the C<bin_dir> method to
update the C<PATH> as necessary:

 use Alien::MyTool;
 use Env qw( @PATH );
 
 unshift @PATH, Alien::MyTool->bin_dir;
 system 'mytool';

=head2 How do I use C<Alien::Base> from C<Dist::Zilla>



( run in 0.476 second using v1.01-cache-2.11-cpan-fa01517f264 )