Insertar codigo fuente (code snippets) con estilo en Blogger

Vamos a ver cómo insertar código con estilo en Blogger, también llamados code snippets o syntax highlighting, instalando la librería Highlight.js.

Hace tiempo que la librería SyntaxHighlighter de Alex Gorbatchev's, que en su tiempo era la más famosa en los blogs de blogger no es compatible y no ha sido actualizada. Os dejo el enlace por si alguien tiene interés en echarle un ojo: SyntaxHighlighter.

Como consecuencia, me he visto obligado a buscar alguna alternativa, y tras algunas horas (para encontrarla más que para usarla) he encontrado una muy buena opción que es Highlight.js. Así que me tomo nota y os dejo explicado cómo se configura y se usa.

Qué es Highlight.js

Highlight.js es una librería JavaScript que nos pone "bonito" el código fuente (en inglés a los trozos de código se les llama code snippets), con los colores de cada lenguaje de programación, resaltando las palabras clave, constantes, etc.

La librería puede usarse en cualquier proyecto web, y yo la he aprovechado para mis aportaciones de código fuente en mi blog de Blogger.

Guía paso a paso:

  1. Lo primero que yo haría es una copia de seguridad del tema o plantilla de Blogger, por si la liáis parda. Para ello, vamos al menú de Blogger -> Tema y arriba a la derecha tenemos un botón que pone "Crear/Restablecer copia de seguridad". Le damos a "Descargar Tema" y listo.
  2. Vamos a editar el tema, que para eso lo hemos salvado. En la misma pantalla de Temas, le damos al botón "Editar Html".  Nos saldrá el editor feo de blogger.
  3. En el editor incluimos entre las etiquetas <head> </head>, el siguiente código fuente:
  4. <!-- Syntax Highligting -->
    <script src='https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.12.0/languages/go.min.js'/>
    <link href='//cdnjs.cloudflare.com/ajax/libs/highlight.js/9.13.1/styles/vs.min.css' rel='stylesheet'/>
    <script src='//cdnjs.cloudflare.com/ajax/libs/highlight.js/9.13.1/highlight.min.js'/>
    <script>hljs.initHighlightingOnLoad();</script>
    <!-- FIN Syntax Highligting -->
    Básicamente, lo que hemos hecho es incluir las librerías de highlight.js en nuestro blogger para poder usarla.
  5. Por tanto, ya podemos usarla, es tan sencillo como meter nuestro código fuente entre las etiquetas siguientes:
  6.  <pre>  
     <code class="html">   
     Nuestro código va aquí  
     </code>  
     </pre>  
    
    En el atributo "class" de la etiqueta <code> debemos especificar el lenguaje de programación de nuestro code snippet. En nuestro caso era html.
Los lenguajes que por defecto soporta highlight.js con el include del CDN que estamos usando son los que se muestran en la siguiente imagen, sin embargo se pueden usar muchos más que son descargable para incluirlos en la cabecera de nuestro blog. Os dejo después de la imagen en enlace de descarga para otros lenguajes de programación.


Puedes configurar Highlight.js con otros lenguajes de programación.

Eso es todo, espero que os sea útil, a mí seguro, para otros blogs o si cambio el tema.

Hasta pronto! 
spacer

Crear una tabla de objetos en Oracle

Vamos a ver en éste post cómo crear una tabla de objetos en Oracle. Para ello, vamos a crear primero un objeto y sobre ése objeto construiremos una tabla que contendrá en unos de sus campos al citado objeto.
Crear una tabla de objetos en Oracle

Tomaremos como ejemplo el objeto "direccionOBJ" que es una dirección postal:
CREATE OR REPLACE TYPE direccionOBJ as OBJECT
(
   calle VARCHAR2(20),
   ciudad VARCHAR2(20),
   codProvincia CHAR(2),
   cPostal CHAR(5)
);
Ahora creamos una tabla de empleado, que contiene al objeto direccion (de tipo direccionOBJ):
CREATE TABLE empleado 
(
  numEmpleado   NUMBER(3),
  nombre VARCHAR2(20),
  direccion direccionOBJ
);
Vamos a crear ahora una fila para nuestra tabla de empleados:
INSERT INTO empleado VALUES 
(139, 'Antonio', direccionOBJ('Calle Sierpes','Sevilla','41','41001'));

Crear una tabla a partir de un objeto Oracle 

A continuación vamos a crear una tabla oracle con los objetos direccionOBJ y vamos a copiar todas las direcciones de nuestra tabla de empleados a ésta tabla:
CREATE TABLE tabla_direcciones OF direccionOBJ;
Insertamos las direcciones:
INSERT INTO tabla_direcciones 
    SELECT e.direccion
    FROM empleados e;
Así hemos transformado el objeto direccionesOBJ en una tabla que podemos consultar. Vamos a hacer un "select" de nuestra tabla:
SELECT ciudad FROM tabla_direcciones
Ya ésta, así de simple... (o de difícil) ;)
spacer

Crear y recorrer un cursor de Oracle

Crear y recorrer un cursor de oracle
Dejo en este post cómo crear un cursor oracle sobre una consulta para recorrerlo después:

-- Zona de declaración 
declare
-- Declaramos el cursor sobre una consulta de una supuesta tabla usuarios.

cursor usuarios is 
    select * 
    from usuarios
    where edad > 20;

-- Fin declaración. Comenzamos el procedimento:

begin

-- Recorremos el cursor con un bucle for - loop
    for u in usuarios loop
        dbms_output.put_line(u.apellidos||' '||u.nombre);
    end loop; 
-- Fin bucle

end; 
-- Fin procedimiento



La función dbms_output.put_line muestra por pantalla el resultado en la variable "u" con la que recorremos el cursor. El operador || es de concatenación de cadenas.

Quizás te interese...

spacer

JNDI (Java Naming Directory Interface). Configurando recursos en Tomcat.

La Java Naming and Directory Interface (JNDI) es una interfaz de programación (API) que proporciona funcionalidades de nombrado y directorio a las aplicaciones escritas usando Java. Está definido para ser independiente de cualquier implementación de servicio de directorio. Así se puede acceder a una gran variedad de directorios de una forma común.

Sirve para configurar recursos compartidos para aplicaciones java organizándolos por directorio con nombres únicos. Es un servicio de nombres que permite:
  • Asociar nombres con objetos.
  • Permitir la búsqueda de un objeto por su nombre.
En el mercado existen diferentes servicios de directorios, por ejemplo:
  • LDAP (Lightweight Directory Access Protocol)
  • NDS (Novell Directory Service)
  • NIS (Network Information Service)
Cada servicio tiene una forma de acceso diferente, lo que implica que si se cambia de fabricante hay que reescribir los clientes. Es por eso que se usa JNDI como capa por encima pues ofrece un acceso común a los recursos configurados.

La API JNDI  permite escribir código Java que realice operaciones sobre directorios. Es una API uniforme a todos los tipos de servicios de directorios. Es similar a JDBC.

Service Provider Interface (SPI) permite acceder al servicio de directorio específico de cada fabricante. Mapea código JNDI en operaciones específicas de directorios. Es un driver JNDI.

 Arquitectura JNDI

Un ejemplo sencillo

Vamos a configurar un pool de conexiones para una base de datos en el lado del servidor. A continuación se muestra cómo se usaría el API JNDI:

String jndiName = "jdbc/<alias>";
//Obtenemos el contexto inicial (dónde comienza el directorio de nombres)
InitialContext ctx = new InitialContext();
//Asignamos el recurso a un objeto de tipo DataSource (Binding)
DataSource ds = (DataSource) ctx.lookup(jndiName);
Connection conn = ds.getConnection();
// hacer algo con la conexión
conn.close();
ctx.close();


El código anterior funcionaría en todas las aplicaciones que tengamos desplegada en nuestro servidor web (en nuestro caso lo que es Tomcat) o servidor de aplicaciones. Se usa en todas las aplicaciones del servidor y solo lo configuramos una vez.

La configuración que hay que realizar en Tomcat es la siguiente: 
  1.  Modificar el fichero ../conf/server.xml  de Tomcat entre las etiquetas <GlobalNamingResources> y </GlobalNamingResources>
  2. <GlobalNamingResources>
    …
    <Resource name="jdbc/<alias>"
       auth="Container"
       type="oracle.jdbc.pool.OracleDataSource"
       driverClassName="oracle.jdbc.driver.OracleDriver"
       factory="oracle.jdbc.pool.OracleDataSourceFactory"
       url="jdbc:oracle:thin:@<host>:<port>:<sid>"
       [user=<user>]
       [password=<password>]
       maxActive="20"
       maxIdle="10"
       maxWait="-1" />
    …
    </GlobalNamingResources> 
    
    
    Estamos configurando una fuente de datos (dataSource) para poder acceder a una base de datos Oracle. Indicando al servidor que tenemos un recurso. A continuación indicamos a nuestras aplicaciones que pueden hacer uso del recurso definido en el servidor:
  3. Modificar el fichero /conf/context.xml entre las etiquetas <Context> y </Context> con lo siguiente:
  4. <Context>
    …
    <ResourceLink global="jdbc/<alias>" name="jdbc/<alias>" 
    type="oracle.jdbc.pool.OracleDataSource"/>
    …
    </Context> 
    
  5. Incluir el jar del conector jdbc a la base de datos en la carpeta lib del servidor Tomcat, no del proyecto. Y, muy importante, reiniciar el servidor.
spacer

Paquetes (package) en Oracle

Los paquetes en Oracle sirven para agrupar y organizar funcionalidades en una base de datos. Son estructuras que agrupan objetos PL/SQL (funciones, procedimientos, tipos, etc.). Ello nos va a permitir tener programas estructurados agrupados por funcionalidades.
Un paquete de Oracle se compone de dos elementos: 
  • La especificación (cabecera) y
  • El cuerpo
La especificación es la interfaz de las funciones y procedimientos que se van a implmentar en el cuerpo, es algo parecido a las cabeceras en el lenguaje de programación C. La sintaxis general es la siguiente:
CREATE [OR REPLACE] PACKAGE <nombre_del_paquete> is 

  -- Declaración de tipos:
  TYPE <nombreTipo> IS <tipo>;

  -- Declaracion de variables y constantes
  <nombreConstante> CONSTANT <tipo> := <valor>;
  <nombreVariable> <tipo>;

  -- Declaraciones de funciones y procedimientos
  FUNCTION <nombreFuncion>(<parametro> <tipo>,...) RETURN <tipo>;
  PROCEDURE <nombreProcedimiento>(<parametro> <tipo>, ...);

END <nombre_del_paquete>


El cuerpo no es más que la implementación de la especificación que hemos realizado. Por tanto, el cuerpo del paquete debe implementar lo que se ha declarado en la especificación. La sintaxis del cuerpo es parecida a la de la especificación, con la diferencia de que incluimos la implementación de cada procedimiento y función. Declaramos el cuerpo con la palabra clave BODY. La sintaxis general es la siguiente:
CREATE [OR REPLACE] PACKAGE BODY <nombre_del_paquete> IS
   
  -- Declaraciones de tipos y registros privados
  TYPE <TypeName> IS <tipo>;
  
  -- Declaraciones de variables y constantes privadas
  <nombreConstante> CONSTANT <tipo> := <valor>;
  <nombreVariable> <tipo>;

  -- Implementacion de procedimientos y funciones 
  FUNCTION <nombreFuncion>(<parametro> <tipo>,...) RETURN <tipo> IS
    -- Variables locales de la funcion
  BEGIN
    -- Implementación de la función
    return <resultado>;
  [EXCEPTION]
    -- Control de excepciones
  END;
  
  PROCEDURE <nombreProcedimiento>(<parametro> <tipo>, ...) IS 
   -- Variables locales del procedimiento
  BEGIN
    -- Implementacion de procedimiento
  [EXCEPTION]
    -- Control de excepciones
  END;

END <nombre_del_paquete>;


Espero que os sirva, próximamente escribiré sobre procedimientos y funciones con algunos ejemplos.

Un saludo!
spacer

Zend Framework Apache PHP TimeOut (Error 200)

Muy buenas gente! ¿Quien no se ha encontrado con el típico error de timeout en un script php?...

Cuando estamos intentando ejecutar un script que excede un poco del tiempo por defecto de Apache (que creo recordar que son 30 segundos), nos encontramos con un error de timeout. Como muchos de vosotros ya sabreis se puede solucionar cambiando directivas en el php.ini del servidor Apache, en este caso es el máximo tiempo de ejecución del script (en segundos, en el ejemplo 30 segundos):

max_execution_time = 30

Vaaaale, puede que ni siquiera tengas que editar el php.ini y reiniciar el servidor, también puedes usar la función:

set_time_limit(30); 

en el propio script que dura algo más de tiempo, por ejemplo, si son dos minutos:

set_time_limit(120);

Qué fácil!... ya, pero usando Zend Framework... OMFG... no es suficiente, y encontrar la solución requiere saber buscar bien y perder el tiempo en ello. Este es el "super-descriptivo" error que nos lanza Zend:

200 OK
The server is temporarily unable to service your
request due to maintenance downtime or capacity
problems. Please try again later.

Gracias Zend!!!  Eres muy descriptivo, con eso entiendo que lo que me quieres decir es que el tiempo de script no era suficiente y has petado, ¿no?. Vale, vale.

Os dejo un esquemita de cómo funciona el servidor al procesar las peticiones (sin entrar en detalles) y después os doy la solución de dónde y qué hay que tocar.


Como se ve en el esquema anterior, hay un ficherito de Zend que interviene en el requestTimeout. El ficherito en cuestión es ZendEnablerConf.xml y se suele encontrar en Windows en la ruta C:\Program Files\Zend\ZendServer\etc

Bueno, pues en ese fichero tenemos que cambiar la siguiente directiva, aumentando el tiempo de ejecución:

<Timeouts connectionTimeout="120" requestTimeout="600" />

Lo que hay que hacer es aumentar ambos parámetros, pero fundamentalmente el segundo. Yo lo he configurado a 600 segundos (10 minutillos), pues tengo que lazar un parser de un XML kilométrico y el script muere.

Eso es todo, espero que a alguien le sirva, y no haya tardado en encontrar mi blog lo que yo he tardado en solucionar el TimeOut del script. ;)

Un saludo!!!
spacer

Configurar Zend Framework en wamp, xammp, lamp o mamp


Os dejo en este post cómo se configuran los servidores XAMP, WAMP, LAMP o MAMP para trabajar con proyectos basados en Zend Framework. Como sabéis, lo que caracteriza a estos 4 entornos es que te integran de forma semi-automática PHP, APACHE y MySQL, pero ese es otro tema.

Bueno, vamos al grano, lo que hay que hacer es descargar Zend Server desde la página oficial de Zend Framework, a ser posible en una extensión que nos permita descomprimir la carpeta mejor que un ejecutable, por ejemplo en la versión linux. Si estamos entornos Windows podemos instalar el ejecutable y cuando finalicemos el proceso desinstalarlo. 

Una vez que lo hemos descargado, debemos ir a la carpeta de instalación de Zend Server, que suele tener la siguiente estructura: "Zend \ ZendServer \ share \ ZendFramework". Bien, dentro de esa última carpeta tenemos las dos carpetitas que tenemos que copiar en nuestros entorno "AMP", ya sea X,W,L o M. Estos dos directorios son "bin" y "library". 

Debemos ir a la carpeta "xampp \ php" (en mi caso es un XAMP). Allí creamos nuestra carpeta "zend", de forma que queda "xampp \ php \ zend" y dentro de esta ruta copiamos los dos directorios "bin" y "library".

Lo siguiente es configurar el php.ini para que sepa encontrar las librerías de Zend Framework. Para ello, buscamos la directiva:

include_path = ".;C:\xampp\php\PEAR"

Y añadimos al path la ruta de nuestras librerías Zend (la que hemos copiado), quedando así:

include_path = ".;C:\xampp\php\PEAR;C:\xampp\php\zend\library"

Ahora debemos guardar el documento y reiniciar Apache.

La carpeta "bin" que hemos copiado contiene la herramienta Zend Tool que como sabéis, sirve para crear proyectos o items de tipo Zend Framework. Si queréis poder invocarla desde el IDE de desarrollo o la línea de comandos debéis añadir la ruta de "zf.bat" o "zf.sh" dependiendo del entorno a la variable PATH de las variables de entorno del sistema operativo en el que estéis.

Eso es todo, muy fácil, suerte!
spacer

Nuevas etiquetas HTML 5

Buenas a tod@s,

Recientemente he comenzado algunos de los cursos de Microsoft Virtual Academy para aprender un poco sobre las tecnologías .NET. Uno de los cursos que he comenzado es el de Diseño de aplicaciones de Windows 8 en HTML 5. En uno de los módulos, concretamente en el quinto, me he emcontrado una de esas tablas resúmenes tan útiles para ver de un vistazo las nuevas etiquetas de HTML 5 y la es que han desaparecido.

Sin más os dejo la tabla, haced click en la imagen para verla más grande, espero que os sirva:


spacer

Un poco de humor informático

Buenas!

No todo va a ser tecnología, os dejo una serie de gifs animados que llevan bastante tiempo pululando por Internet pero con los que me parto cada vez que los veo. Podéis encontrar muchos más en  Les joies du code (página original en francés), o en The coding love (versión en inglés).

Cuando hago una puesta en producción
Cuando hago una puesta en producción


Cuando encuentro una solución sin buscar en google
 Cuando encuentro una solución sin buscar en google


Cuando se desconecta mi ordenador antes de haber salvado todo
Cuando se desconecta mi ordenador antes de haber salvado todo


 Cuando intento corregir un bug a las 3 de la mañana
Cuando intento corregir un bug a las 3 de la mañana


Cuando mi regexp devuelve exactamente eso que esperaba
Cuando mi regexp devuelve exactamente eso que esperaba


Cuando mis colegas me proponen una pausa para el café en pleno desarrollo
Cuando mis colegas me proponen una pausa para el café en pleno desarrollo


Cuando el becario me propone realizar la web con Joomla!
Cuando el becario me propone realizar la web con Joomla!


Cuando me comunican que el módulo sobre el que he trabajado toda la semana nunca será utilizado
Cuando me comunican que el módulo sobre el que he trabajado toda la semana nunca será utilizado


Cuando ese código que no he testeado en desarrollo funciona perfecto en producción
Cuando ese código que no he testeado en desarrollo funciona perfecto en producción


Cuando los comerciales anuncian a los desarrolladores lo que han vendido al cliente
Cuando los comerciales anuncian a los desarrolladores lo que han vendido al cliente


Cuando aplico un nuevo CSS por primera vez
Cuando aplico un nuevo CSS por primera vez


Cuando el sysadmin nos da por fin el acceso a root
Cuando el sysadmin nos da por fin el acceso a root


Cuando lanzo mi script por primera vez tras varias horas de desarrollo
Cuando lanzo mi script por primera vez tras varias horas de desarrollo


Cuando me voy de fin de semana mientras que todo el mundo intenta todavía corregir bugs
Cuando me voy de fin de semana mientras que todo el mundo intenta todavía corregir bugs


Cuando me piden que eche una mano un viernes por la tarde
Cuando me piden que eche una mano un viernes por la tarde


Cuando el cliente intenta clicar sobre las maquetas
Cuando el cliente intenta clicar sobre las maquetas


Cuando un bug pasa desapercibido durante una presentación
Cuando un bug pasa desapercibido durante una presentación


Cuando el cliente quiere cambiar las especificaciones 2 días antes de la subida a producción
Cuando el cliente quiere cambiar las especificaciones 2 días antes de la subida a producción


Cuando tengo que hacer un desarrollo sin especificaciones
Cuando tengo que hacer un desarrollo sin especificaciones


Cuando mi script por fin ha funcionado
Cuando mi script por fin ha funcionado


Cuando escucho al comercial vender el proyecto al cliente
Cuando escucho al comercial vender el proyecto al cliente


Cuando el jefe de proyecto entra en la sala de trabajo

Cuando el jefe de proyecto entra en la sala de trabajo


Cuando el becario propone añadir una novedad al proyecto

Cuando el becario propone añadir una novedad al proyecto


El cliente propone hacer la página web en Flash

El cliente propone hacer la página web en Flash


Al leer las especificaciones del proyecto por primera vez

Al leer las especificaciones del proyecto por primera vez


Cuando mi compañero quiere simplificar código que funciona

Cuando mi compañero quiere simplificar código que funciona


Cuando tiro los servidores de la universidad en las prácticas

Cuando tiro los servidores de la universidad en las prácticas


Cuando mi compañero me hace entender que su código funciona finalmente

Cuando mi compañero me hace entender que su código funciona finalmente


Cuando me piden actualizar la documentación

cuando se me pide para actualizar la documentación

spacer