Limpeza de código morto

UCDetector

UCDetector

Trabalhar com manutenção de código não é tarefa fácil.
Depende do local que trabalha, terá tempo para executar testes e melhorar a solução que já existe.
Comecei minha vida de programador Java em 2002, quando aprendi procurando em tutoriais na internet da antiga SUN e trabalhando na área.
Desde lá, Java evolui muito como as IDEs de suporte, exemplo disso é o Eclipse, mas e o código legado? Infelizmente não, porque? Nas empresas onde trabalhei, tempo de refactoring é tempo perdido.
A vantagem de refactoring em código pode ser muito grande, mas o tempo inicial investido pode ser gigantesco. Isso requisita retestar algo que já funciona ou tudo por completo.
O ditado sempre é o mesmo: “Em time que está ganhando não se mexe.”. Será verdade? Ganhando por estar funcionando como planejado inicialmente, mas não tirando o melhor proveito da tecnologia. Evolução é melhoria em meu ponto de vista. Nessa evolução inclui, qualidade, performance, produtividade, dentre outros fatores.
Uma questão da qual eu não vejo muita discussão em refactorings, será que código não utilizado deve ser mantido? N vezes a pessoa que faz manutenção não é a mesma que criou, ou pior, a pessoa criadora daquele código já pode ter abandonado o barco. Comecei então a tirar dos projetos todo código que não é utilizado, tarefa árdua para legados.
No Eclipse achei um plugin que tem me ajudado, o UCDetector. Ele faz a limpeza de código fonte inútil. Busca referências de classe, pacote e até projeto que não possuem nenhuma associação apontando os respectivos problemas ou melhorias.
Sempre que sobra um tempo, executo o UCDector no projeto desejado e realizo a refatoração. Sei muito bem que ela vai me ajudar a não ver código perdido e todos vão ganhar para realizar leitura e manutenções nas aplicações.

Sobre o UCDetector: É um plugin do Eclipse para busca código Java morto. Por exemplo, classe públicas, métodos e propriedade que não tem referência.
Ele cria marcadores para os seguintes melhorias: Código não necessário (morto), código onde a visibilidade por ser alterada (protected, default ou private), métodos ou campos que podem ser final. São apenas sugestões. Tenha certeza das alterações que você irá realizar. As referências ainda podem ser usadas em:
Reflexões, frameworks, código de terceiros, jars, jsp, xml, e outros, alterar visibilidade por causar transtornos e não executar conforme esperado.

Link: http://www.ucdetector.org/

Espero ter ajudado,
André Rezende

Utilizar datasource no log4j

Passei por um perrengue para descobrir como fazer o log ser persistido no banco de um jndi configurado.
Após passar por esse trabalho todo, do qual tive que ler várias documentações, pretendo descrever passo a passo esse processo que não é nada complicado.

Não quero descrever o uso do LOG4J ou sua finalidade, e sim ser compartilhar o uso de um novo appender do qual obtém uma conexão de banco de dados que foi configurado em seu servidor de aplicação.

Crie sua classe appender, pode ser conforme abaixo:

package br.com.rezende.log4j.appender;

import java.sql.Connection;
import java.sql.SQLException;
import javax.faces.context.FacesContext;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.sql.DataSource;
import org.apache.log4j.Logger;
import org.apache.log4j.jdbc.JDBCAppender;
import org.apache.log4j.spi.LoggingEvent;

public class MeuJDBCAppender extends JDBCAppender {

private static Logger LOGGER = Logger.getLogger(NGSAppender.class);
private DataSource dataSource;
private static String dataSourceJNDIName;
private static Context context;

/**
* Inicializa o contexto e o datasource.
*/
static {
   try {
    context = new InitialContext();
    dataSourceJNDIName = "jdbc/DS";
   }catch (NamingException e) {
    LOGGER.error(e.getMessage(), e);
   }
}

/**
* Obtém o nome do datasource configurado no Servidor de aplicações.
*
* @return Connection
*/
public Connection getConnection() throws SQLException {
 if (this.dataSource == null) {
  if (this.getDataSourceJNDIName() == null) {
  LOGGER.error("Nome do datasource está vazio.");
  return null;
 }
 try {
  this.dataSource = (DataSource) context.lookup(this
  .getDataSourceJNDIName());
 } catch (NamingException e) {
  LOGGER.error("Problema em obter o datasource");
  throw new SQLException(e);
 }
}
  try {
    return this.dataSource.getConnection();
  } catch (SQLException e) {
    LOGGER.error("Existe problema em obter um nome de datasource.");
    throw e;
  }
}

  public String getDataSourceJNDIName() {
    return dataSourceJNDIName;
  }

}

Mapeie na sua propriedade seu novo appender dentro do log4j.properties:


log4j.rootCategory=ERROR, JDBC, Console

# Console appender
log4j.appender.Console=org.apache.log4j.ConsoleAppender
log4j.appender.Console.layout=org.apache.log4j.PatternLayout
log4j.appender.Console.layout.ConversionPattern=[%d{ISO8601}]%5p%6.6r[%t]%x - %C.%M(%F:%L) - %m%n
# JDBC Database
log4j.appender.JDBC = br.com.rezende.log4j.appender.MeuJDBCAppender
log4j.appender.JDBC.layout=org.apache.log4j.PatternLayout

Para inserir os valores em seu banco, visualize o próximo post, pois é necessário criar a tabela de log e formatar o seu INSERT para persistir a respectiva informação de stacktrace.

Abraços,
André Rezende