Tags:
create new tag
, view all tags

Velocity

Tecnologia de geração baseada em template mantida pela comunidade Apache. Proposta inicialmente para geração de conteúdo HTML dinâmico, passou a ser usada como uma solução de template de propósito geral.

Geração de código com Velocity

Esse exemplo consiste em adaptar um avaliador de expressões de acordo com:

  • o tipo da expressão (int ou double)
  • suporte opcional a geração de uma representação String das expressões
  • suporte alternativo a expressões básicas (soma e subtração) ou avançada (que inclui divisão e multiplicação)

Para usar o velocity, usamos a tarefa texen do ANT, específica para geração de conteúdo texto exportado para arquivos. Para isso, é necessário adicionar duas bibliotecas velocity ao classpath do ANT (isso pode ser feito via eclipse, nas página de preferências do ANT). As bibliotecas (arquivos jars), estão disponíveis no arquivo: velocity-1.5.zip

Abaixo, é apresentado um exemplo de arquivo build.xml que pode ser usado para fazer a geração de código fonte.

<project name="HtmlGenerator" default="main" basedir=".">
   <taskdef name="texen" classname="org.apache.velocity.texen.ant.TexenTask" />
   
   
   <!-- ============================================================= -->
   <!-- G E N E R A T E JAVA SOURCE CODE-->
   <!-- ============================================================= -->
   <!-- This target will generate a set of Java source code pages     -->
   <!-- based on the information in our control context.              -->
   <!-- ============================================================= -->
   
   <target name="main">
      <echo message="+------------------------------------------+" />
      <echo message="| |" />
      <echo message="| Generating JAVA source code! |" />
      <echo message="| |" />
      <echo message="+------------------------------------------+" />
      <texen controlTemplate="ExpressionControl.vm" outputDirectory="./target" templatePath="." outputFile="generation.report" />
   </target>

</project>

O processo de geração é customizado com o arquivo ExpressionControl.vm, que pode ser adaptado para gerar diferentes membros da linha de produtos. Optamos por disponibilizar a forma mais simples de implementar esse tipo de adaptação: as propriedades são definidas no próprio arquivo ExpressionControl.vm. Usa solução mais flexível seria a utilização de arquivos de propriedades para definir as propriedades de uma instância. Abaixo um exemplo do arquivo ExpressionControl.vm. Esse exemplo define um produto com as seguintes features:

  • int como tipo base das expressões (type=int)
  • sem suporte a representacao string das expressoes (print=false)
  • sem suporte a operações complementares (extended=false)

#set ($type = "int")
#set ($print = true)
#set ($extended = true)

$generator.parse("Expression.vm", "Expression.java", "type", $type) 
$generator.parse("Value.vm", "Value.java", "type", $type) 
$generator.parse("BinaryExp.vm", "BinaryExp.java", "type", $type) 
$generator.parse("AddExp.vm", "AddExp.java", "type", $type) 
$generator.parse("SubExp.vm", "SubExp.java", "type", $type)

#if($extended == true)
 $generator.parse("MultExp.vm", "MultExp.java", "type", $type) 
 $generator.parse("DivisionExp.vm", "DivisionExp.java", "type", $type) 
#end

Por fim, criamos templates velocity para cada classe ou interface que varia na linha de produtos. Esses arquivos são referenciados, ou processados, pelas chamadas $generator.parse do arquivo de controle.

Arquivo Expression.vm

package br.ufpe.cin.lps.base.expression;

public interface Expression {
   public $type eval();
#if($print)
   public String print();
#end

Arquivo Value.vm

package br.ufpe.expression;

public class Value implements AbstractExpression {
   private $type value;

   public Value($type value) {
      this.value = value;
   }
   
   public $type eval() {
      return value;
   }

#if($print)
   public String print() {
      return "" + value;
   }
#end
}

Arquivo Binary.vm

package br.ufpe.cin.lps.elp.base.expression;
   
public abstract class BinaryExp implements Expression {

   private Expression left;

   private Expression right;

   private String operator;

   public BinaryExp(Expression left, Expression right, String operator) {
      this.left = left;
      this.right = right;
      this.operator = operator;
   }

   public Expression getLeft() {
      return left;
   }

   public Expression getRight() {
      return right;
   }

   public String getOperator() {
      return operator;
   }
   
#if($print)
   public String print() {
      return left.print() + operator + right.print();
   }
#end
}

Arquivo AddExp.vm

package br.ufpe.cin.lps.elp.base.expression;

public class AddExp extends BinaryExp {
   
   public AddExp(Expression left, Expression right) {
      super(left, right, "+");
   }
   
   public $type eval() {
      return left.eval() + right.eval();
   }
}

Exercício

Criar templates do velocity para as expressões de subtração, multiplicação e divisão. Note que o exemplo de arquivo de controle faz referência a esses templates. O processo de build só funciona com os mesmos. Executar gerações para diferentes configurações dos produtos e analisar os resultados.

-- RodrigoBonifacio - 26 Aug 2008

Topic revision: r3 - 2008-08-28 - RodrigoBonifacio
 
This site is powered by the TWiki collaboration platformCopyright © 2008-2021 by the contributing authors. All material on this collaboration platform is the property of the contributing authors.
Ideas, requests, problems regarding TWiki? Send feedback

mersin escort bayan adana escort bayan izmit escort ankara escort bursa escort