


package       com.pkg.services;


import        java.io.File;
import        java.io.FileOutputStream;
import        java.util.List;

import        org.mule.umo.UMOEventContext;


public class SWFCompiler extends Service {
  // *** Symbolic constants ***

  private static final String     COMPILER     = "build";

  
  // *** Private and protected members ***

  private String   sourceDir,
                   sourceFile,
                   objectDir,
                   objectFile,
                   cacheDir,
                   dirLPSHome;
  
  
  private void dumpBytesToFile(byte[]  bySource,
                               String  fileName) throws Exception {
    FileOutputStream    output = new FileOutputStream(fileName);

    log.info(fileName+" written to disk");

    output.write(bySource);
    output.close();
  } // dumpBytesToFile


  // "File" in the UNIX sense, meaning file or directory.
  private boolean validateFile(String  fileName,
                               boolean bFileSystem) {
    File           aFile;

    if (fileName == null) return false;

    log.info("Validating: "+fileName);
    if (fileName.length() < 1) return false;

    if (bFileSystem)
      try {
        aFile = new File(fileName);
        if (!aFile.exists()) {
          log.error("File or directory "+fileName+" not present.");
          return false;
        }
      }
      catch (Exception e) {
        log.error(fileName+" validation error: "+e.toString());
  
        return false;
      }

    return true;
  } // validateFile

  
  private boolean validateEnvironment() {
    if (!this.validateFile(sourceDir, true))
      return false;

    if (!this.validateFile(objectDir, true))
      return false;

    if (!this.validateFile(sourceFile, false))
      return false;

    if (!this.validateFile(objectFile, false))
      return false;

    if (!this.validateFile(cacheDir, true))
      return false;

    if (!this.validateFile(dirLPSHome, true))
      return false;

    return true;
  } // validateEnvironment


  private void compile(String     fileName,
                       String     objectFile) throws Exception {
    Compiler       compiler;
    int            nRetCode;
    List<String>   errors;

    log.info("Compile: "+fileName);
    compiler = new OpenLaszloCompiler(dirLPSHome, cacheDir);
    compiler.sourcesAt(sourceDir).outputAt(objectDir);
    nRetCode = compiler.compile(fileName, objectFile);
    if (nRetCode != Compiler.COMPILER_OK) {
      errors = compiler.errors();
      for (String message : errors)
        log.error(message);
    }
  } // compile


  private void packageSWF() {
    File           targetFile,
                   sourceDir = new File(this.sourceDir);
    File[]         files     = sourceDir.listFiles();
    String[]       parts;
    String         targetFileName;

    log.info("Packaging the executable.");
    for (File aFile : files)
      if (aFile.toString().contains(".swf")) {
        parts          = aFile.toString().split("=");
        targetFileName = parts[0x00].replaceAll("lzr", "swf");
        log.info("Found: "+aFile);
        log.info("File name: "+parts[0x00]);
        log.info("Rename to: "+targetFileName);
        aFile.renameTo(new File(targetFileName));
      }
  } // packageSWF


  // *** Public methods ***

  public Object service(UMOEventContext     eventContext) {
    String         sourceFileName = this.sourceDir+"/"+sourceFile;
    byte[]         byLaszloSource;
    
    if (this.validateEnvironment())
      try {
        byLaszloSource = eventContext.getMessageAsBytes();
        this.dumpBytesToFile(byLaszloSource, sourceFileName);
        this.compile(sourceFile, objectFile);
        this.packageSWF();
      }
      catch (Exception e) {
        log.error(e.toString());
      }
    else
      log.error("Invalid compiler environment.  Check SWFCompiler options in the configuration file.");

    return "";
  } // service


  public void setSourceDir(String sourceDir) {
    this.sourceDir = sourceDir;
  } // setSourceDir

  public void setSourceFile(String sourceFile) {
    this.sourceFile = sourceFile;
  } // setSourceFile

  public void setObjectFile(String objectFile) {
    this.objectFile = objectFile;
  } // setObjectFile

  public void setObjectDir(String objectDir) {
    this.objectDir = objectDir;
  } // setObjectDir

  public void setCacheDir(String cacheDir) {
    this.cacheDir = cacheDir;
  } // ssetCacheDir

  public void setLPSHome(String     LPSHome) {
    this.dirLPSHome = LPSHome;
  } //
} // SWFCompiler

