Creative Commons License
Excepto donde se indique otra cosa, todo el contenido de este lugar está bajo una licencia de Creative Commons.
Taquiones > perl > Recetas de archivos make

Recetas de archivos make

Me gusta utilizar un archivo Makefile en todos los proyectos en los que trabajo. make no es una de mis herramientas favoritas, desde luego, pero con los años he terminado acostumbrándome a ella, y no quiero emplear más atención en las herramientas que en cómo usarlas.

Plantilla base para un módulo

Esta es una de las plantillas que utilizo cada vez que tengo un proyecto nuevo:

    1 #
    2 # Global values
    3 MODULE=
    4 DEBIAN_PACKAGE=
    5 DESTDIR ?= /tmp
    6 
    7 #
    8 # Source modules (all .pm files under the lib directory)
    9 MODULES=$(shell find lib -name "*.pm")
   10 BINARIES=$(wildcard bin/*.pl)
   11 EXAMPLES=$(wildcard examples/*.p[lm])
   12 CHECK_SOURCES=$(MODULES) $(BINARIES) $(EXAMPLES)
   13 
   14 #
   15 # Test program
   16 DEBUG=
   17 ARGS=
   18 
   19 #
   20 # External tools
   21 PERL ?= perl -Ilib
   22 PERL_CHECK ?= $(PERL) -cw
   23 PERL_DEBUG ?= $(PERL) -d:ptkdb
   24 PROVE=$(shell which prove)
   25 INSTALL=$(shell which install)
   26 
   27 #
   28 # Do nothing for default
   29 all:
   30 
   31 #
   32 # Check syntax
   33 .PHONY: check $(CHECK_SOURCES)
   34 
   35 check:   $(CHECK_SOURCES)
   36 
   37 $(CHECK_SOURCES):
   38     $(PERL_CHECK) $@
   39 
   40 #
   41 # Test programs
   42 test:
   43     $(PROVE) -v t/
   44 
   45 #
   46 # Debug program
   47 debug:     check $(DEBUG)
   48     $(PERL_DEBUG) $(DEBUG) $(ARGS)
   49 
   50 #
   51 # Build the perl package
   52 build:     Build
   53 
   54 Build:     Build.PL
   55     $(PERL) Build.PL installdirs=vendor
   56 
   57 binary:        build
   58     $(PERL) Build
   59 
   60 #
   61 # Install the perl package
   62 install:  test binary
   63     $(PERL) Build install destdir=$(DESTDIR)
   64 
   65 #
   66 # Debian package
   67 deb:   install
   68     $(DEBUILD)

Me basta con copiarla y completar los campos MODULE y DEBIAN_PACKAGE, así como los nombres de los programas, que veremos en la otra versión del archivo, para que funcione inmediatamente.

Verificando todos los fuentes de un proyecto

Si observamos las siguientes estrofas

    1 #
    2 # Source modules (all .pm files under the lib directory)
    3 MODULES=$(shell find lib -name "*.pm")
    4 BINARIES=$(wildcard bin/*.pl)
    5 EXAMPLES=$(wildcard examples/*.p[lm])
    6 CHECK_SOURCES=$(MODULES) $(BINARIES) $(EXAMPLES)
    7 
    8 #
    9 # Check syntax
   10 .PHONY: check $(CHECK_SOURCES)
   11 
   12 check:   $(CHECK_SOURCES)
   13 
   14 $(CHECK_SOURCES):
   15     $(PERL_CHECK) $@

veremos otro truco en acción. Queremos tener un destino especial que verifique la síntaxis de todos los fuentes del proyecto y sabemos que el intérprete Perl no admite más que un único parámetro; necesitamos dos características de make:

  • Destinos múltiples
  • Destinos falsos

Con el primero indicamos en el lado izquierdo de la regla que los destinos son varios, y que debe expandir la ejecución por cada uno de ellos. La variable $@ sirve precisamente para indicárselo como en

    1 examples/example_csv.pm examples/example.pl:  examples/datasource.pm
    2     $(SPECIAL_COMMAND) $@

que lo convierte en los siguientes

    1 examples/example_csv.pm:  examples/datasource.pm
    2     $(SPECIAL_COMMAND) examples/example_csv.pm
    3 
    4 examples/example.pl:  examples/datasource.pm
    5     $(SPECIAL_COMMAND) examples/example.pl

Por otra parte nos encontramos con una acción que queremos que realice siempre (al menos en este caso), y que consiste en comprobar la síntaxis de todos los archivos del proyecto. Para ello, y una vez reunidos todos en una misma variable como $CHECK_SOURCES, indicamos que el destino clean sobre ella es falso con la expresión .PHONY, de tal manera que make no comprobará las dependencias y lo ejecutará siempre.