sábado, 31 de diciembre de 2011

Lector de comics para mobiles (java j2me)

El día de hoy voy a hablar de un pequeño proyecto que inicié.

La idea es simple: Poder ver el cómic diario de Garfield desde mi celular. Me gusta mucho leer dicha tira cómica y me resulta más simple y cómodo cargarla diariamente en mi celular ya que es una imagen pequeña por lo general.

El proyecto está en sus inicios y un poco abandonado pues he tenido mucho trabajo estos últimos meses pero pueden verlo en el repositorio público aquí (BitBucket.org).

Lo desarrollé usando NetBeans y J2ME. Para ejecutarlo necesitamos un dispositivo movil con soporte para MIDP 2.0. Yo lo probé en un Sony Ericsson Satio que tengo.

En un futuro planeo arreglar varias cosas entre ellas:

  • Soporte para varios dispositivos, posiblemente migrarlo a PhoneGap.
  • Actualizar el código fuente para que esté bajo GPL.
  • Mejorar la interfaz de usuario.
Hasta la próxima.

Convertir de SQL a Linq


Recientemente he estado trabajando mucho con .Net y aunque ya lo he dicho antes lo vuelvo a repetir ¡La gran mayoría de las cosas no me gustan! sin embargo eh estado encontrando buenas técnologias que valen la pena aprenderlas, entre ellas el muy conocido Linq.

Una de las principales razones para usar Linq es el hecho de que es independiente de la tecnología de almacenamiento de datos que está debajo, por ejemplo les dejo una lista de los Proveedores que actualmente existen para linq aquí y aquí una página donde explican en más detalle porque linq es mejor que usar SQL directamente.

Hoy escribo este post para dejar una pequeña documentación de como transformar consultas SQL a Linq usando Linqer.

Linqer me ayudó mucho con la conversión de SQL a Linq y la recomiendo en especial cuando quieren hacer el trabajo rápidamente además que es muy buena para aprender linq aunque lastimosamente no es libre: http://www.sqltolinq.com/


Para los efectos de mis ejemplos crearé una base de datos llamada sample1 con las siguientes tablas: table_1, table_2 y table_3 y a continuación el script sql, más simple que me es posible crear con lo que tengo a mano, es muy probable que si lo desean usar tengan que hacer algunos cambios para que funcione en su DBMS (MySQL, MS SQL Server, Oracle, etc)


Bueno manos a la obra:
1. Select simple
  • SQL: SELECT * FROM table_1
  • Linq: from table_1 in context.Table_1
    select new {
      table_1.Col_1,
      table_1.Col_2,
      table_1.Col_3
    }

2. Select con condicional:
  • SQL: SELECT * FROM table_2 WHERE col_1 <= 10 and col_2 = 'something'
  • Linq: from table_2 in context.Table_2
    where
      table_2.Col_1 <= 10 &&
      table_2.Col_2 == "something"
    select new {
      table_2.Col_1,
      table_2.Table_1_col_1,
      table_2.Col_2,
      table_2.Col_3
    }

3. Select con un group by simple:
  • SQL: SELECT SUM(col_3) sumatory, col_2 FROM Table_1 GROUP BY col_2
  • Linq: from table_1 in context.Table_1
    group table_1 by new { 
       table_1.Col_2
    } into g
    select new {
      sumatory = (System.Decimal?)g.Sum(p => p.Col_3),
      g.Key.Col_2
    }
En este punto es donde Linq se pone algo complicado por la sintaxis del group by


4. Join (old style):
  • SQL: SELECT t1.col_2, t1.col_3, t2.col_3, t3.col_1
    FROM Table_1 t1, Table_2 t2, Table_3 t3
    WHERE t1.col_1 = t2.table_1_col_1 and t2.col_1 = t3.table_2_col_1

    and t1.col_1 = t3.table_1_col_1
  • Linq: from t1 in context.Table_1
    from t2 in context.Table_2

    from t3 in context.Table_3
    where
         t1.Col_1 == t2.Table_1_col_1 &&
         t2.Col_1 == t3.Table_2_col_1 &&
         t1.Col_1 == t3.Table_1_col_1
    select new {
         t1.Col_2,
         t1.Col_3,
         Column1 = t2.Col_3,
         t3.Col_1
    }

5. Inner Join (ansi join), alternativa al ejemplo anterior
  • SQL: SELECT t1.col_2, t1.col_3, t2.col_3, t3.col_1
             FROM  Table_1 t1 inner join Table_2 t2 on t1.col_1 = t2.table_1_col_1
                inner join Table_3 t3 on t2.col_1 = t3.table_2_col_1 
                    and t1.col_1 = t3.table_1_col_1
  • Linq: from t1 in context.Table_1
    join t2 in context.Table_2
          on new { Col_1 = t1.Col_1 } equals new { Col_1 = t2.Table_1_col_1 }
    join t3 in context.Table_3
          on new { t2.Col_1, Column1 = t1.Col_1 } equals new { Col_1 = t3.Table_2_col_1, Column1 = t3.Table_1_col_1 }
    select new {
      t1.Col_2,
      t1.Col_3,
      Column1 = t2.Col_3,
      t3.Col_1
    }
6. Como ultimo ejemplo un join old style que además tiene un group by
  • SQL: SELECT t1.col_2, t3.col_1, SUM(t1.col_3) sumatory
    FROM Table_1 t1, Table_2 t2, Table_3 t3
    WHERE t1.col_1 = t2.table_1_col_1
    and t2.col_1 = t3.table_2_col_1
    and t1.col_1 = t3.table_1_col_1
    GROUP BY
    t1.col_2, t3.col_1
  • Linq: from t1 in context.Table_1
    from t2 in context.Table_2
    from t3 in context.Table_3
    where
      t1.Col_1 == t2.Table_1_col_1 &&
      t2.Col_1 == t3.Table_2_col_1 &&
      t1.Col_1 == t3.Table_1_col_1
    group new {t1, t3} by new { t1.Col_2, t3.Col_1 } into g
    select new {
      g.Key.Col_2,
      Col_1 = (System.Int32?)g.Key.Col_1,
      sumatory = (System.Decimal?)g.Sum(p => p.t1.Col_3)
    }

Hay muchas otras combinaciones que podría poner pero haría este post demasiado extenso, creo que con esto tenemos suficiente para hacernos una idea de como convertir de SQL a Linq.

No puedo dejar de mencionar LinqPad que es una buena herramienta para practicar Linq y mejorar nuestro conocimiento del mismo.

Hasta la próxima.

    miércoles, 7 de diciembre de 2011

    Internacionalizacion en asp.net con gettext

    Desde hace algún tiempo que estoy buscando una forma de usar gettext en mis proyectos asp.net para soportar internacionalización también abreviada como i18n ¿por qué?, hay muchas razones pero las principales para mi son:
    1. Es software libre.
    2. Hay muy buenas herramientas tanto para GNU/Linux como para otros OS.
    3. Es muy popular y muchos proyectos lo usan, lo cual hace más simple que los traductores puedan ayudar con los muchos lenguajes que yo no domino.
    4. Es mucho más simple que la forma soportada por asp.net.

    Ya tengo un proyecto asp.net creado en github, así que lo usaré para los ejemplos.

    Estoy basandome en este artículo publicado por Jason Kester.

    A continuación los pasos a seguir:

    1. Agregar gettext al proyecto. Para esto descargamos la librería FairlyLocal y colocamos los dll en algún lugar accesible para nuestra aplicación y copiamos las clases de ejemplo Internationalization, Localization y Message dentro del proyecto.

    2. Creamos una interfaz que define el helper para soportar i18n (esta interfaz y su implementación están basadas en los ejemplos de la librería FairyLocal):


    3. Ahora modificamos la interfaz IPage, de mi post anterior, para poder insertar el recurso de i18n:


    4.Mediante inyección de dependencias (DI por sus siglas en ingles) proveemos un helper que manejará la lógica de acceso gettext. La forma como implementé la DI la explico en un post anterior. Esto significa que debemos modificar la clase SimpleInjectorPageHandlerFactory.

    5. Modificamos nuestra aplicación para que use la función "_" donde haga falta.


    6. Y el ultimo paso es agregar un script de post construcción (post-build) para que gestione la creación de los archivos .po (a menos claro que prefieran hacerlo manualmente).
    Aqui cabe señalar que existen dos tipos de aplicación web en asp.net, a saber: WSP (web site project) y WAP (web application project); más aquí. Esto es importante porque solo en los WAP existe la posibilidad de crear post-build scripts, pero si tenemos una aplicación WSP lo que debemos hacer es crear un proyecto extra y agregarlo a la solución, por simplicidad recomiendo que sea una librería pero cualquier tipo de proyecto que soporte este tipo de scripts funciona.
    A continuación les dejo mi script


    Cabe señalar que este post-build script tiene que incluir todos los tipos de archivos fuente que nuestro proyecto tiene para que pueda crear correctamente todas las cadenas que requieren una traducción.

    Lo que sigue es traducir o solicitar a nuestros amigos, colegas, traductores pagados, etc que nos den una mano.

    Hasta la próxima.

    martes, 6 de diciembre de 2011

    Dependency Injection sencillo en asp.net

    Siguiendo un poco el hilo de mi post anterior Seguridad Flexible en asp.net usando módulos hago este donde veremos como implementar nuestro propia y muy simple Inyección de Dependencias (Dependency Injection, DI) que es una forma de inversión de control.

    Antes de seguir es bueno comentar que si alguna vez necesitan hacer algo como esto, pueden considerar usar SpringNet el cual no sólo ofrece DI sino muchas otras funcionalidades, aunque no lo he probado en .Net sí lo he usado mucho la versión en Java y me ha sido de gran utilidad.

    Bueno manos a la obra:
    Primero que nada vamos  necesitar definir la forma como se injectaran las dependencias y quien será el responsable:
    1. La forma, haré que todas mis páginas implementen una interfaz la cual el objeto responsable de inyectar las dependencias reconocerá, recuerden que esta es una versión simplificada de un DI
    2. El responsable de inyectar las dependencias necesarias a las páginas será una clase que implemente la interfaz IHttpHandlerFactory llamada SimpleInjectorPageHandlerFactory, en dicha clase extenderemos al PageHandlerFactory que define asp.net para que la implementación sea más simple.
    Para que la inyección funcione necesitamos configurar que los requests que soliciten páginas aspx sean procesados por nuestra clase, en la sección httpHandlers creamos una entrada nueva de la siguiente forma: 
    <add verb="*" path="*.aspx" type="lib.ioc.di.SimpleInjectorPageHandlerFactory"/>
    a continuación un ejemplo de como luce el web.config:



    Aquí solo demostraré como hacer funcionar todo el mecanismo de inyección y en un post siguiente hablaré de como usar este mecanismo para soportar internacionalización en asp.net usando gettext.

    Todo el código está en la misma aplicación de ejemplo del post anterior y la pueden encontrar aquí. Allí puse una interfaz IResource con una implementación sencilla solo para demostrar que funciona.


    Hasta la próxima.