Contacto

Nos puedes enviar un artículo a publicar (si te fue útil, seguro que a otros también).
Nos puedes sugerir temas/profundidad de interés.
correo-e - perfil

Busquedas

linux: ubuntu APT y DPKG, algunos comandos útiles

 apt y dpkg son dos de las herramientas que podemos usar en sistemas linux basados en debian (como ubuntu) para la administración del software.

 apt (ej, apt-get) se usa para bajar e instalar paquetes desde repositorios online (en la wikipedia: http://en.wikipedia.org/wiki/Advanced_Packaging_Tool)
 dpkg se usa con archivos .deb, configurar, instalar y obtener información del software instalado(en la wikipedia: http://en.wikipedia.org/wiki/Dpkg)

Usando APT 
------------------

 Los repositorios a los que se accede cuando usamos apt, se listan en el archivo: /etc/apt/sources.list
 Si necesitamos instalar un paquete desde un repositorio que no se encuentra en sources.list, tenemos que incluir este nuevo repositorio en la lista, editando sources.list, y agregando la ruta del repositorio. Luego es necesario bajar la clave de autenticación para los paquetes de ese repositorio, y agregarlo a nuestra lista de confianza: "sudo apt-key add nombreArchivo.pub" (donde: nombreArchivo.pub es el archivo con la clave de autenticación que bajamos).
 Por último, se actualiza la base de datos de paquetes mediante: "sudo apt-get update".

 Para buscar una aplicación a instalar, podemos usar: apt-cache search, por ejemplo:

  apt-cache search openvpn
   ebox-openvpn - eBox - OpenVPN server module
   network-manager-openvpn - network management framework (OpenVPN plugin)
   openvpn - Virtual Private Network daemon
   ...

 Para saber las dependencias de un paquete con apt.
  ej: apt-cache depends ebox-openvpn

 Para instalar un paquete con apt, usamos apt-get install
  ej: sudo apt-get install ebox-openvpn
 Si el paquete ya esta instalado en el sistema, se actualiza a la ultima versión encontrada.

 Para eliminar un paquete con apt, usamos 'remove'
  sudo apt-get remove ebox-openvpn

Usando dpkg.
------------------

 Usamos dkpg para manejar paquetes bajados previamente.
 Para extraer los archivos dentro de un archivo .deb con dpkg:
    sudo dpkg -x <archivo.deb>  <directorio_destino>

 Para instalar un paquete con dpkg, usamos la opción '-i'
    sudo dpkg -i <archivo.deb>

 Eliminar un paquete con dpkg, usamos la opción -P para eliminar el paquete y sus archivos de configuración.
    sudo dpkg -P <archivo.deb>
 o usamos la opción -r para eliminar solo el paquete.
    sudo dpkg -r <archivo.deb>

 Para imprimir en pantalla la lista de todos los paquetes instalados en el sistema, usamos -l
    dpkg -l
  podemos filtrar de esta lista, los paquetes que nos interesan,
    ej: dpkg -l | grep -i openvpn

 Conocer el paquete al que pertenece un archivo con dpkg, usamos -S
   ej: dpkg -S /usr/sbin/snmptrapd
   R: snmpd: /usr/sbin/snmptrapd 

 Para ver la lista de archivos instalados por un paquete, usamos -L
   ej: dpkg -L snmpd | less

 Un resumen de algunos comandos útiles:
  apt-key add <archivo>: Agrega la clave publica contenida en <archivo> a la lista de confianza de apt.
  apt-key del <keyid>: Elimina <keyid> de la lista de confianza de apt.
  apt-key list:   Imprime la lista de claves
  apt-get update:  Lee el archivo sources.list y actualiza la base de datos de paquetes disponibles. Se tiene que correr este comando toda vez que se modifique sources.list
  apt-get install:  Baja e instala un paquete dado, si este se encuentra en la base de datos
  apt-get auoclean:  Elimina paquetes que se descargaron y son antiguos.
  apt-get upgrade:  Actualiza todos los paquetes.
  apt-get dist-upgrade:  Actualiza la distribución.
  apt-get clean:  Elimina los archivos descargados (almacenados en cache)
  apt-get remove <paquete>: Elimina el paquete.
  apt-get purge:  Elimina y purga paquetes
  apt-get --purge remove <paquete>: Elimina el paquete y elimina sus archivos de configuración.
  apt-get -f install:  Hace un chequeo de los paquetes rotos. Se intenta corregir los menajes de error en las dependencias.
  apt-cache pkgnames:  Imprime la lista de todos los paquetes instalados.
 
  dpkg -x <archivo.deb><directorio>: Extrae los archivos que están contenidos en el archivo .deb, en el directorio indicado.
  dpkg -i <archivo.deb>: Instala en el sistema el archivo .deb.
  dpkg -P <paquete>: Elimina el paquete y sus archivos de configuración.
  dpkg -r <paquete>: Elimina solo el paquete indicado.
  dpkg -l:  Imprime la lista de paquetes instalados en el sistema.
  dpkg -S <nombre archivo>: Muestra los paquetes donde el nombre del archivo es encontrado.
  dpkg -L <paquete>: Muestra la lista de archivos instalados en el sistema que pertenecen al paquete dado.
Leer más...

Crear el primer Custom TagLib

 Cuando las funciones disponibles en JSTL (u otras bibliotecas de tag) no cubren nuestra necesidad, podemos crear nuestras propias funcionalidades.

 Para esto, creamos un archivo conocido como TLD ( Tag Library Descriptor ).
 Es un archivo xml en el cual se define las funciones, los atributos que tienen y cuales son obligatorios, la clase que realiza la tarea cuando se usa el tag, el identificador único del tag ( el URI, que se usa para importar la biblioteca de tag desde las páginas jsp's), etc.
 Este archivo tiene como extensión '.tld', y puede ser copiado en diferentes lugares en el proyecto web, como ser:
  Directamente bajo el directorio "WEB-INF".
  Dentro de un sub-directorio en "WEB-INF".
  Dentro del directorio "META-INF" en un archivo .jar, que está dentro de WEB-INF/lib.
  Dentro de un sub-directorio, dentro del directorio "META-INF" en un archivo .jar, que está dentro de WEB-INF/lib .

 Vamos a crear como ejemplo, un tag que imprime un mensaje (un saludo) en pantalla. El código para nuestro TLD es el siguiente :


  (archivo: primerctl.tld)
<?xml version="1.0" encoding="ISO-8859-1" ?>
<taglib version="2.0" xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee/web-jsptaglibrary_2_0.xsd">

<tlib-version>1.2</tlib-version>
<short-name>MyPrimerTag</short-name>
<uri>MyPrimerTagURI</uri>

<tag>
 <name>saludo</name>
 <tag-class>ejemplos.SaludoTagHandler</tag-class>
 <body-content>empty</body-content>
 <attribute>
  <name>nombre</name>
  <required>true</required>
  <rtexprvalue>true</rtexprvalue>
 </attribute>
 <attribute>
  <name>apellido</name>
  <required>false</required>
  <rtexprvalue>false</rtexprvalue>
 </attribute>
</tag>
</taglib>


 Para cada atributo que soporte la función, se tiene que indicar el nombre del atributo (mediante la propiedad 'name'), si el atributo es obligatorio (required), y si el valor del atributo tiene que ser ingresado de forma explícita, o puede ser el resultado de una expresión (rtexprvalue, si no se define esta propiedad, el efecto es igual a rtexprvalue=false ).

 En el TLD indicamos la clase a usar (por medio de tag-class ), en nuestro caso es:  ejemplos.SaludoTagHandler.
 Una de las formas para realizar esta clase, es extender de SimpleTagSupport, en donde se tiene que implementar el método 'doTag()', donde se realiza el trabajo.
 También se tiene que crear los métodos set para los atributos que usamos, en nuestro ejemplo, setNombre() y setApellido().

 Creamos un proyecto java (java Class Library), un paquete llamado 'ejemplos', y en este paquete, la clase SaludoTagHandler.java con el siguiente código:

package ejemplos;
import java.io.IOException;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.tagext.SimpleTagSupport;

public class SaludoTagHandler extends SimpleTagSupport {
    private String nombre;
    private String apellido;

    @Override
    public void doTag() throws JspException, IOException {
        String aSaludar = apellido == null ? nombre : nombre + " " + apellido ;
        getJspContext().getOut().write("Hola: " + aSaludar + "<br>");
    }

    public void setNombre(String nombre) {
        this.nombre = nombre;
    }
    public void setApellido(String apellido) {
        this.apellido = apellido;
    }   
}


 Tenemos que crear un jar con esta clase, y agregamos en el directorio META-INF del jar, el archivo primerctl.tld que se hizo previamente.

 Por último, incluimos esta biblioteca en un proyecto web (dentro de WEB-INF/lib). De esta forma, ya podemos usarlo en las paginas jsp del proyecto web, por ejemplo, creamos la página: test.jsp

 <%@page contentType="text/html" pageEncoding="UTF-8"%>
 <%@ taglib prefix="pctl" uri="MyPrimerTagURI" %>

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
        <title>JSP Page</title>
    </head>
    <body>
        <pctl:saludo nombre='MiNombre' apellido="Mi-Apellido" />
    </body>
</html>


 La salida en la página es:
   Hola: MiNombre Mi-Apellido

 Tener presente que se indico en el archivo primerctl.tld, que es obligatorio incluir el atributo "nombre", pudiendo ingresar su valor directamente como un String (como se hizo en el ejemplo), o por medio de una expresión (ej. <pctl:saludo nombre='${nmbre}' /> ).
 El atributo "apellido" no es obligatorio, y en caso de incluirlo, el valor tiene que ser un string ingresado directamente en el tag, ya que mediante rtexprvalue=false se indica que no es válido ingresar este valor como una expresión.

 Mediante el desarrollo estos tag reducimos el código java insertado en las páginas, y facilitamos el re-uso sin necesidad de "copiar y pegar".
 Los diseñadores de páginas, acostumbrados a código html/xml pueden usar estos tag's sin conocer java.
Leer más...

Introducción a JSTL - JSP Standard Tag Lib

 En esta  introducción a JSTL, no se explica como crear nuestra propia biblioteca de tag (tag lib).

 JSTL es una colección de funciones de uso común, cuando se desarrolla páginas dinámicas (como ser bucles, bloques condicionales, formateo de textos, internacionalización, etc), prontas para ser usados desde paginas JSP, y con una apariencia similar a tags de xml (ej: <c:out value="se muestra este texto en la pagina" />).
 El uso de estas funcionalidades (JSTL) permiten que las páginas sean mas fáciles de leer y de mantener, evitando agregar gran cantidad de código java insertado en las páginas. Están divididas en diferentes bibliotecas que cubren varias áreas, como ser procesamiento de xml,  Core, internacionalización y formateo de datos, acceso a base de datos relacional (sql).

Para poder usar JSTL en un proyecto web, primero es necesario copiar dos bibliotecas en nuestro proyecto, estos son: jstl.jar y standard.jar (en WEB-INF/lib).
En la aplicación de ejemplo que se baja con tomcat, se puede obtener estas bibliotecas (o podemos bajarlas desde la web).

Para poder usar una tag lib en una página, es necesario importarla usando el identificador asociado al tag (la uri ), y dar un nombre de prefijo, el cual es usado para llamar luego a las funciones disponibles.
 Para esto, en la pagina usamos:

  <%@ taglib uri="uri_taglib" prefix="myPrefix" %>

 A continuación, una lista de las librerias disponibles, con su URI, y el prefijo que se usa normalmente:

 XML    http://java.sun.com/jsp/jstl/xml    x
 Core     http://java.sun.com/jsp/jstl/core  c
 i18n      http://java.sun.com/jsp/jstl/fmt    fmt
 SQL     http://java.sun.com/jsp/jstl/sql     sql

Para poder usar en nuestra página, por ej. la funcionalidades dentro del Core, primero tenemos que importar el tag lib correspondiente:
 <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>

nota: Es posible ver en paginas que usa una versión anterior de jstl, usar una uri diferente (no usa el "jsp" uri="http://java.sun.com/jstl/core" ).

 Sobre el lenguaje de expresión:
  Vamos a ver anotaciones del tipo: ${...}.
  De esta forma se indica que la información ingresada dentro de las llaves, no es leída literalmente, sino que se tiene que evaluar, y usar el resultado de esta evaluación.
  Como ejemplo simple, si tenemos: ${8+2}, el valor usado es "10".

  Si tenemos una expresión como: ${ valorEntero}, se busca en los diferentes alcances de variables disponibles para la jsp, esa variable, en el siguiente orden:
 page -> request -> session -> application. Se retorna el primer valor encontrado.
  En caso de ser necesario obtener el valor desde un alcance en particular, se indica dentro de la expresion:
 ${pageScope.valorEntero} || ${requestScope.valorEntero} ||${sessionScope.valorEntero} || ${applicationScope.valorEntero}

 Para acceder a los parámetros dentro de un request (por ejemplo, los datos desde un formulario), simplemente agregamos "param." antes del nombre del parámetro:  ${param.nombre}.
 En caso de que el parámetro pueda tener varios valores, en lugar de 'param' usamos: 'paramValues.'

 Vamos a crear una pagina para usar con ejemplos, y probar algunas funciones.

 <c:out> => Imprime texto en pantalla
uso: <c:out value="Prueba JSTL" />
------------------------
 Ejemplo: index.jsp
<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
    <head>
        <title>JSP Page</title>
    </head>
    <body>
        <c:out value="Prueba JSTL" />
    </body>
</html>

-----------------

Para recorrer una lista con jstl podemos usar la etiqueta <c:forEach>
<c:forEach> Recorre cada elemento de una colección dada, indicando la colección a recorrer por la propiedad: 'items', el nombre para el item actual lo indicamos por la propiedad 'var'.

 Ej:  En la página anterior podemos agregar un array para probar esta funcionalidad.
  Antes del tag '<html>' agregamos:
  <%
  String[ ] equiposUy = {"Peñarol", "Defensor", "Danubio"};
  request.setAttribute("equiposUy", equiposUy);
  %>


 Luego, dentro del body, agregamos el loop.
 <c:forEach var="equipo" items="${equiposUy}" >
       ${equipo}
 </c:forEach>


A este mismo ejemplo, vamos a agregarle un par de elementos para probar la propiedad "empty" que verifica si una variable existe (y no esta vacía), vamos a usar el alcance de variables (requestScope y sessionScope), y al final, obtener un dato por parámetro.
 El nuevo código completo de la página index.jsp:

<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%
String[] equiposUy = {"Peñarol", "Defensor", "Danubio"};
request.setAttribute("equiposUy", equiposUy);
%>
<html>
    <head>
        <title>JSP Page</title>
    </head>
    <body>
        <c:out value="Prueba de JSTL"/><br/>
        <c:out value="Existe el array equiposUy en la session : ${!empty sessionScope.equiposUy}" /> <br>
        <c:out value="Existe el array equiposUy en el request : ${!empty requestScope.equiposUy}" /> <br>
        <c:forEach var="equipo" items="${requestScope.equiposUy}" varStatus="equipLoopTag">
            ${equipLoopTag.count} : ${equipo} <br/>
        </c:forEach>

        Nombre por parametro: <c:out value='${param.nombre}' default=" No se ingreso el nombre"/>
    </body>
</html>

La llamada a la pagina la hacemos con un parámetro ('nombre') que pasamos en la url, por ejemplo: http://localhost:8080/TestWeb/?nombre=MiNombre
salida:
 Prueba de JSTL
Existe el array equiposUy en la session : false
Existe el array equiposUy en el request : true
1 : Peñarol
2 : Defensor
3 : Danubio
Nombre por parametro: MiNombre


Si no pasamos el parámetro en la llamada a la pagina (por ejemplo, simplemente hacemos: http://localhost:8080/TestWeb), la última linea imprime el valor por defecto dado a <c:out>: "Nombre por parametro: No se ingreso el nombre"

Vamos a ver un par de funciones mas:

<c:if> Bloque condicional. Nota: Este elemento no tiene un equivalente a: 'else'
uso: <c:if test="${ 5 > 3}"> <c:out value="Dentro del if" /> </c:if>
Este tag evalúa la expresión de la propiedad 'test', si es verdadero ('true'), ingresa al bloque del if correspondiente.

Si se necesita un equivalente a "if ... else", tenemos que usar:
<c:choose>
  <c:when> ... </c:when>
  <c:otherwise> ... </c:otherwise>
</c:choose>


Como ejemplo, agregamos el siguiente código a nuestra pagina:
<c:choose>
  <c:when test="${param.nombre == 'dlix' }">
    <c:out value="Hola ${param.nombre}" />
  </c:when>
  <c:when test="${param.nombre == 'd-lix' }">
    <c:out value="Usas otro nick" />
  </c:when>
  <c:otherwise>
    <c:out value="No eres dlix" />
  </c:otherwise>
</c:choose>


Y hacemos las siguientes llamadas a la página, para ver los resultados
http://localhost:8080/TestWeb/?nombre=dlix       (salida: Hola dlix)
http://localhost:8080/TestWeb/?nombre=d-lix      (salida: Usas otro nick)
http://localhost:8080/TestWeb/?nombre=MiNombre   (salida: No eres dlix)

Captura de excepciones
<c:catch> Es similar al uso de try/catch. Si el código dentro de este bloque genera una excepción, es capturado, y en lugar de mostrar el error,  se pasa a la siguiente línea luego del bloque
uso: <c:catch> 
           <%= 10/0 %>
        </c:catch>
Sin el bloque '<c:catch>', al ejecutar <%= 10/0 %> tendríamos el error: java.lang.ArithmeticException: / by zero

 Todo sobre JSTL en su propio lugar: http://java.sun.com/products/jsp/jstl
Leer más...

comenzando con log4j - logs en java

Esto es apenas una pequeña introducción a log4j, no un manual.
Espero ayude para comprender y comenzar a usar.

Suele ser normal cuando programamos, imprimir mensajes (en consola o un archivo), por diferentes motivos, como ser, saber si el programa esta pasando por algún punto en particular, conocer el valor de una variable, un mensaje de error, etc. No es extraño ver en el codigo líneas como: System.out.println("me conecto a la base ...");
También puede ser requerimiento de la aplicación, almacenar información de negocio, como ser datos de alguna transacción, fecha/hora cuentas involucradas y monto de una transferencia bancaria, etc.

Si bien resulta sencillo imprimir mensajes con: System.out.println(...) (sin considerar en esta oportunidad el costo de esa llamada), cuando queremos dejar de ver los mensajes (o activarlos nuevamente), se requiere modificar el código, y compilarlo.
La información de negocio se suele almacenar en un archivo, o en una bd (o en ambos), por lo que println() deja de ser una opción.

Es en estos casos donde log4j entra en acción.
Nos permite configurar en un archivo, los tipos de mensajes queremos imprimir (debug, info, error, etc), donde queremos dirigir los mensajes (consola, un archivo, una base de datos, ...), el formato como queremos mostrar la información.
También es posible realizar la configuración en el programa, con la necesidad de compilar con cada cambio.

Vamos a introducir algunos conceptos que vamos a usar en un ejemplo sencillo al terminar el artículo.

1) Nivel o prioridad de log:
En la configuración, indicamos el nivel de prioridad que se habilita.
Estos niveles son jerárquicos:
ALL < DEBUG < INFO < WARN < ERROR < FATAL < OFF.
ALL significa que se habilita todos los logs, mientras que OFF deshabilita todos los logs.
Como ejemplo, si habilitamos el nivel WARN, se van a guardar los mensajes que pertenecen a: WARN, ERROR y FATAL.

2) Logger: La propiedad Logger es donde se configura el elemento a enviar los mensajes (por ej, las clases dentro de un paquete dado).

3) Appender: Mediante los appenders indicamos el/los destino/s de salida de los mensajes.
Si bien podemos crear nuestros propios appenders, existen varios ya creados que podemos usar, como ser: ConsoleAppender (imprime log en consola), FileAppender o RollingFileAppender (para almacenar los mensajes en un archivo, en el último, se puede indicar, por ejemplo, tamaño máximo del archivo, y cantidad de archivos a almacenar), JDBCAppender (almacenar los mensajes en una base de datos), SyslogAppender (envía la salida al syslog en sistemas linux/unix).

4) Layout: Mediante el objeto Layout se formatea el estilo de la información  que se almacena en el log.

Configuracion log4j:
La configuración de log4j puede hacerse por programación, por medio de un archivo propertie de java, o por medio de un archivo xml.
Para nuestro ejemplo vamos a usar el archivo xml. Por defecto, este se tiene que llamar log4j.xml, y tiene que estar en el claspath usado
para la carga de las clases.

ejemplo log4j.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">
<!-- CONSOLA -->
<appender name="console" class="org.apache.log4j.ConsoleAppender">
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern"
value="[%p] [%d{dd/MM/yyyy HH:mm:ss}] [%c]:%L - %m%n" />
</layout>
</appender>
<!-- ARCHIVO -->

<appender name="logfile" class="org.apache.log4j.RollingFileAppender">
<param name="file" value="/tmp/ejemplol4j/test.log" />
<param name="append" value="true" />
<param name="MaxFileSize" value="512KB"/>
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d %p [%c] - %m%n" />
</layout>
</appender>

<logger name="testl4j" additivity="false">
<level value="info" />
<appender-ref ref="console" />
<appender-ref ref="logfile" />
</logger>

<root>
<priority value="debug" />
<appender-ref ref="console" />
</root>
</log4j:configuration>

Descripción de log4j.xml
1.1) Indicamos un appender para enviar los mensajes a la consola
<appender name="console" class="org.apache.log4j.ConsoleAppender">
1.2) Le damos un formato a los mensajes
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern"
value="[%p] [%d{dd/MM/yyyy HH:mm:ss}] [%c]:%L - %m%n" />
</layout>

%p: muestra la prioridad del log que se imprime
%d: muestra la fecha en que se imprime el log, y en este caso, so formatea como se quiere ver la fecha/hora
%c: muestra el objeto que imprime el log.
%L: el número de línea donde se genera el log.
%m: el mensaje que se quiere imprimir.
%n: imprime un salto de linea.

2.1) Indicamos otro appender, en este caso, para enviar los mensajes a un archivo.
<appender name="logfile" class="org.apache.log4j.RollingFileAppender">
2.2) Configuramos algunos parámetros para este appender:
El archivo donde se almacena el log (en este caso, se usa un equipo con linux)
<param name="file" value="/tmp/ejemplol4j/test.log">
Indicamos que el archivo no se sobrescriba cada vez que comienza la aplicación.
<param name="append" value="true">
Indicamos el tamaño máximo de los archivos de log.
<param name="MaxFileSize" value="512KB">
2.3) El formato en el layout es similar al de consola, pero cambiamos el orden de la información de salida, y a la fecha no se le dio un formato en particular.

3) Configuramos el elemento 'logger'. Indicamos el elemento raíz que va a enviar mensajes (en este caso, objetos en el paquete testl4j)
Con additivity="false" los mensajes se imprimen 1 vez, sino se verá el mensaje por el propio logger, y luego por el "root".
<logger name="testl4j" additivity="false">
Indicamos el nivel de prioridad que se permite

<level value="info"></level>
Indicamos a donde se va a enviar los mensajes, en este caso, se envía a la consola y al archivo.
<appender-ref ref="console"></appender-ref>
<appender-ref ref="logfile"></appender-ref>
obviamente, podemos agregar tantos logger's como nos sea necesario.

4) Indicamos el log por defecto. Si un elemento envía un mensaje de log, y no está indicado ese elemento en el logger, se utiliza la esta configuración.
En nuestro ejemplo, se imprime a partir de la prioridad de debug (no es una buena opción en general, pero sí para nuestro ejemplo), y solo enviamos los mensajes a consola
<root>
<priority value="debug"></priority>
<appender-ref ref="console"></appender-ref>
</root>

La clase para la prueba de log4j.
Creamos la clase: Main, dentro del paquete: testl4j

Main.java
---------
package testl4j;
import org.apache.log4j.Logger;
public class Main {
private static Logger _log = Logger.getLogger(Main.class);
public static void main(String[ ] args) {
_log.info(" Iniciando prueba de log4j");
_log.debug(" Iniciando prueba de log4j");
}
}

En este caso enviamos 2 mensajes de log, uno de nivel "info", y el siguiente de nivel "debug".

1er Ejemplo)
-------------------
Al ejecutar el programa, obtenemos la siguiente salida:
1) Consola
[INFO] [10/01/2010 19:32:52] [testl4j.Main]:24 - Iniciando prueba de log4j
2) Archivo
2010-01-10 19:32:52,880 INFO [testl4j.Main] - Iniciando prueba de log4j

En el logger para "testl4j", indicamos que el nivel de prioridad habilitado es "info", por este motivo, no se muestra el mensaje de "debug".

2do Ejemplo)
-------------------
Para esta prueba, eliminamos del archivo log4.xml, todas las lineas de "logger".
Al hacer esto, no se tiene una configuración específica para el paquete testl4j, por lo que utiliza la configuración por defecto( "root")
Al ejecutar el programa, obtenemos la siguiente salida:
1) Consola
[INFO] [10/01/2010 19:40:51] [testl4j.Main]:24 - Iniciando prueba de log4j
[DEBUG] [10/01/2010 19:40:51] [testl4j.Main]:25 - Iniciando prueba de log4j
2) Archivo


En consola se imprime tanto el mensaje de debug y el de info, ya que el nivel de prioridad por defecto se configuro con "debug".
En el archivo de configuración no se imprime ningún mensaje, ya que solo se configuro un append por defecto, el de consola.

Por mayor información, parámetros, appenders, etc, la pagina de log4j es: http://logging.apache.org/log4j
Leer más...

Buscar un elemento en un array - java Arrays

Para nuestra búsqueda en un array vamos a usar java.util.Arrays.binarySearch(array[], key)
Los elementos del array en el cual queremos buscar, tienen que estar ordenados en modo ascendente.
Si el elemento a buscar existe en el array, retorna un entero positivo, que corresponde con la posición del elemento en el array.
Si el elemento a buscar NO existe en el array, retorna un entero negativo.


Ej.

String arrayTest[] = {"aa", "bb", "cc", "dd", "ee"};
//buscamos un elemento que existe en el array
int idx = Arrays.binarySearch(arrayTest, "dd");
System.out.println( "Elemento encontrado en: "+idx);

//buscamos un elemento que NO existe en el array
idx = Arrays.binarySearch(arrayTest, "zz");
System.out.println( "No se encuentra elemento, resultado: "+idx);

Resultado:
run:
Elemento encontrado en: 3
No se encuentra elemento, resultado: -6

Si el array no esta ordenado, el resultado es indefinido.
En caso que el array pueda estar desordenado, puede usarse otro método de "java.util.Arrays"

Arrays.sort( arrayTest);
int idx = Arrays.binarySearch(arrayTest, "dd");
... Leer más...

inicializar variable static final en java

Las variables estáticas son inicializadas cuando se carga la clase, antes de que pueda ser creado un objeto o se pueda ejecutar algún método estático de esa clase.

Al indicar una variable como "final", estamos diciendo que una vez inicializada, no podemos modificar su valor.

Para inicializar una variable "static final", podemos hacerlo en la propia declaración,

ej: public static final int MAX = 10 ;

También puede inicializarse en un bloque estático:

public static final int MAX ;
static {
MAX = 10 ;
}

Este bloque "static", se ejecuta cuando la clase es cargado, y antes de poder usar una variable o método estático de la clase.
Es posible ejecutar un método de un objeto en este bloque, con la lógica necesaria para inicializar la variable. Leer más...