Search code examples
phing

Import all build files in a directory - phing


I need to include all xml files inside a directory (I dont know the name, and count of files) in my current build.xml using ImportTask.

This is my build.xml file:

<?xml version="1.0" encoding="utf-8"?>
<project name="New Project" basedir="." default="myimport">
    <target name="myimport" description="dummy to import other build files">
        <if>
            <isset property="file" />
            <then>
                <echo msg="Importing ${file}" />
                <import file="${file}" />
            </then>
        </if>
    </target>

    <if>
        <not>
            <isset property="dummy.property" />
        </not>
        <then>
            <echo msg="Now include all files in ./dev/build directory" />
            <property name="dummy.property" value="true" />
            <foreach param="msg" absparam="file" target="myimport">
                <fileset dir="./dev/build/">
                    <include name="*.xml"/>
                </fileset>
            </foreach>
        </then>
    </if>
</project>

and an example file in target directory:

<?xml version="1.0" encoding="utf-8"?>
<project name="test" basedir="." default="dummy">
    <target name="dummy" description="Dummy task">
        <echo msg="Dummy task, just for test" />
    </target>

    <echo msg="Imported!" />
</project>

when I run phing -l the result is:

Buildfile: /home/f0rud/workspace/s/build.xml
     [echo] Now include all files in ./dev/build directory
  [foreach] Calling Buildfile '/home/f0rud/workspace/s/build.xml' with target 'myimport'

New Project > myimport:

     [echo] Importing ./dev/build/test.xml
     [echo] Imported!
Default target:
----------------------------------------------------------------------------
 myimport  dummy to import other build files

Main targets:
----------------------------------------------------------------------------
 myimport  dummy to import other build files

But there is no dummy (or test.dummy) target, why?

Note : There is a funny bug, if I remove the if part, I get Maximum function nesting level of '100' reached, aborting! error but thats not my problem (the if solve that problem.)


Solution

  • The problem is import work on global context.

    When I call it inside a target, its not available in global context.

    So I've written a simple Phing task to load all files of a fileset like so:

    class ImportDirTask extends Task {
    
        /** Array of filesets */
        private $filesets = array();
    
        /**
         * Nested creator, adds a set of files (nested fileset attribute).
         */
        function createFileSet() {
            $num = array_push($this->filesets, new FileSet());
            return $this->filesets[$num-1];
        }
    
      /**
       * Parse a Phing build file and copy the properties, tasks, data types and 
       * targets it defines into the current project.
       *
       * @return void
       */
      public function main () {
        // filesets
        foreach ($this->filesets as $fs) {
            $ds       = $fs->getDirectoryScanner($this->project);
            $srcFiles = $ds->getIncludedFiles();
            $srcDirs  = $ds->getIncludedDirectories();
            foreach ($srcFiles as $f)
            {
                $task = new ImportTask();
                $task->setProject($this->project);
                $task->init();
                $task->setFile($this->file = $fs->getDir($this->project) . FileSystem::getFileSystem()->getSeparator() . $f);
                $task->main();
            }
    
         }
      } //end main
    
    } //end ImportDirTask
    

    It just work.