domingo, 25 de agosto de 2013

Ejemplo PHP de servicio RESTful - Parte 2

En el anterior tutorial creamos un sencillo servicio RESTful. Ahora vamos a ver como interactuar con él.
Para hacer peticiones al servicio RESTFul vamos a utilizar la herramineta cURL desde el interprete de comandos y la librería libcurl para utilizar la misma herramienta desde PHP.

Peticiones desde el interprete de comandos

1. Petición para recibir listado de usuarios:

  curl http://localhost/login_restful/usuarios  

Resultado:

  {"estado":"correcto","usuarios":[{"id":"5","nombre":"modificado","email":"prueba4@ejemplo.com"},{"id":"7","nombre":"modificado2","email":"prueba6@ejemplo.com"},{"id":"10","nombre":"pepe","email":"prueba@e.com"}]}  

2. Petición para crear un nuevo usuario:

 curl -d "nombre=otroUsuario&email=prueba@ejemplo.com&pwd=1234" http://localhost/login_restful/crearUsuario  

Resultado:

  {"estado":"correcto","msg":"usuario creado correctamente","usuario":{"id":"11","nombre":"otroUsuario","email":"prueba@ejemplo.com"}}  

Ejemplo PHP de servicio RESTful - Parte 1

Vamos a crear un sencillo servicio RESTful  orientado a objetos, con el que podremos realizar las siguientes peticiones, utilizando para ello URL's amigables:
- Pedir una lista de usuarios mediante una petición GET.  URL de la petición:  http://localhost/login_restful/usuarios
- Crear un nuevo usuario mediante una petición POST en la que aportaremos los datos del usuario. El sistema asignará el identificador del recurso. URL de la petición: http://localhost/login_restful/crearUsuario
- Solicitar autenticación de un usuario mediante una petición POST y los datos necesarios para la autenticación. URL de la petición: http://localhost/login_restful/login
- Actualizar un usuario mediante una petición PUT a un determinado identificador de recurso. URL de la petición: http://localhost/login_restful/actualizarNombre/1
- Eliminar un usuario mediante una petición DELETE. URL de la petición:  http://localhost/login_restful/borrarUsuario/1

Por cada petición vamos a recibir un objeto JSON ya sea informando de un error o dando información de que la petición se ha resuelto correctamente.

jueves, 22 de agosto de 2013

PHP y cURL (libcurl)

En el tutorial anterior, se explicó el funcionamiento de la herramienta cURL para utilizarla en el interprete de comandos. Ahora vamos a ver como podemos utilizar esa misma herramienta en nuestros scripts PHP.
Para ello utilizaremos la librería de PHP libcurl. Si en nuestra configuración de PHP no la tenemos activa, simplemente modificaremos php.ini y evidentemente reiniciaremos el servidor Apache. Si por el contrario no la tenemos instalada (se puede comprobar con la función phpinfo() en un script), seguiremos las siguientes instrucciones:

 sudo apt-get install php5-curl  
 sudo service apache2 restart //tras cualquier cambio en PHP o mysql es necesario reiniciar el servidor  

Ahora centrémonos en como utilizar la librería en PHP.

Herramienta cURL en el interprete de comandos

cURL es una herramienta muy útil para hacer peticiones HTTP/S, que es multiplataforma y que nos permite utilizar varios protocolos dichas peticiones. Por lo tanto se convierte en una herramienta importantísima a la hora de realizar peticiones a un recurso de un servicio RESTful. Recuerda que un recurso puede ser un fichero XML, JSON o XHTML.
Es posible utilizarla bajo el interprete de comandos (terminal) y mediante PHP gracias a la librería libcurl. En este tutorial vamos a centrarnos en el uso en el interprete de comandos.

Instalación en Ubuntu

Lo normal es que la herramienta cURL para utilizarse en el interprete de comandos ya venga instalada en versión de sistema operativo. Pero si no es el caso, su instalación en Ubuntu es muy sencilla:

 sudo apt-get install curl  

miércoles, 21 de agosto de 2013

Introducción servicios RESTful

Los servicios web son un conjunto de aplicaciones o de tecnologías con capacidad para interoperar en la Web. Estas aplicaciones o tecnologías intercambian datos entre sí con el objetivo de ofrecer unos servicios. Los proveedores ofrecen sus servicios como procedimientos remotos y los usuarios solicitan un servicio llamando a estos procedimientos a través de la Web. Ya que un servicio web esta identificado por un URI.

Estos servicios proporcionan mecanismos de comunicación estándares entre diferentes aplicaciones, que interactúan entre sí para presentar información dinámica al usuario. Para proporcionar interoperabilidad y extensibilidad entre estas aplicaciones, y que al mismo tiempo sea posible su combinación para realizar operaciones complejas, es necesaria una arquitectura de referencia estándar.

Diagrama ejemplo de un servicio Rest

Excepciones en PHP

Una excepción es un objeto derivado de la clase Exception de PHP que se encarga de mantener e informar de cualquier error producido. Por lo tanto su uso principal es para detener la ejecución del programa, notificar de errores y ayudar a depurar información.
Una excepción se creará ante una situación anómala en la ejecución del programa que provoca que este no pueda continuar con normalidad.
La clase Excepción recibe en su constructor dos argumentos opcionales: mensaje y código de error a mostrar. Algunos de los métodos más importantes de la clase Excepcion y que debemos de conocer son los siguientes:
- getMessage(): Devuelve la cadena de error que le llega al constructor de la clase Excepción.
- getCodeError(): Devuelve el entero que representa el código de error que llega al constructor de la clase Exception.
- getFile(): Devuelve el fichero donde se ha producido la excepción.
- getLine(): Devuelve la linea donde se produjo la excepción.
- getTrace(): Devuelve un array multidimensional con información del fichero y linea donde se produce la excepción, además de la función/método donde se produce la misma y los argumentos de entrada.
- getTraceAsString(): Devuelve la información de la función anterior pero en formato de cadena.

martes, 20 de agosto de 2013

PHP orientado a objetos - Clases y métodos Final

Gracias a la herencia, los métodos definidos en una clase base estarán disponibles en las clases que hereden de esta. Siempre y cuando tengan una visibilidad permisiva. O lo que es lo mismo, que su visibilidad no sea privada. Sin embargo hay ocasiones en las que queramos que las clases hijas puedan utilizar los métodos heredados pero no puedan modificarlos o 'sobreescribirlos'. Para ello antepondremos la palabra reservada final a la definición del método en la clase base (la que va a ser heredada). Se antepondrá a otros modificadores.

 class Usuario{  
   protected $nombre;  
   function getNombre(){  
     return $this->nombre;  
   }  
   final function setNombre($name){  
     $this->nombre = $name;  
   }  
 }  
 class Editor extends Usuario{  
   function setNombre($name){  
     echo "intento de modificar método padre";  
   }  
 }  

Si ejecutamos esto obtendremos el siguiente error: Fatal error: Cannot override final method Usuario::setNombre() in ... Con lo que protegemos al método setNombre() de que sea modificado por una clase heredera.

Espacio de nombres (namespaces) en PHP

En un proyecto grande, el número de clases aumenta con facilidad. Y según se van definiendo más clases, y sobre todo si hay diferentes programadores en el desarrollo, es mas probable que se produzcan colisiones entre nombres de dichas clases o funciones. Hasta PHP 5.3 una solución empleada en muchos proyectos era utilizar nombres de clases muy largos para evitar conflictos. Con la llegada de los espacios de nombres, en PHP 5.3, podemos agrupar clases y funciones en contenedores con identificadores. De forma que no haya conflictos con clases y funciones que se llamen igual en los diferentes contenedores (espacios de nombres).

Definir un espacio de nombres

Si no se indica lo contrario, todas las clases y funciones serán definidas en un entorno global. Con la posibilidad de que haya las colisiones de nombres comentadas anteriormente. Así que vamos a empezar a definir un espacio de nombres. Para definir uno, simplemente tenemos que utilizar la palabra reservada namespace seguida del nombre identificador del espacio de nombres. Además la definición de un espacio de nombres es lo primero que tiene que aparecer en el script. Posteriormente ya se pueden hacer los 'includes' necesarios.

sábado, 17 de agosto de 2013

PHP orientado a objetos - Función mágica de autocarga (__autoload)

En la parte1 y parte 2 del tutorial de métodos mágicos vimos métodos que se pueden definir en una clase y que serán llamados por PHP automáticamente dependiendo de la situación. Ahora vamos a ver una función mágica que se va a encargar de la autocarga de clases: __autoload().

La forma clásica de trabajar con programación orientada a objetos es la de definir una clase en cada script y hacer una inclusión de la misma en los scripts que necesiten hacer uso de ella. Pero si tenemos decenas de clases y tenemos que incluirlas múltiples de veces puede ser muy tedioso. Por eso en PHP 5 aparece la función mágica __autoload(). Que será llamada en el momento que se intente utilizar una clase o interfaz que todavía no ha sido definida mediante ninguna inclusión. Y mediante la definición de su lógica intentar incluirla. De esta forma se puede evitar que los desarrolladores tengan que definir una larga lista de 'includes' al principio de los scripts. Ya que estamos haciendo una carga dinámica.

PHP orientado a objetos - Métodos mágicos - Parte 2

En la primera parte del tutorial presentamos los método mágicos __clone(), __set, __get, __toString , __call y __callStatic. Pero aún faltan varios método que vamos a ver a continuación.

__isset y __unset

Si están definidos estos método mágicos son llamados automáticamente cuando se utilizan las funciones isset() y unset() sobre un atributo no definido o inaccesible en el objeto. Recordemos que isset() sirve para comprobar la existencia de una variable y unset() sirve para destruir una variable. Pero para que la comprobación se realice sobre atributos de un objeto tendremos que definir los método mágicos.

El método mágico __isset() recibe un argumento – nombre del atributo a comprobar si existe o no.
El método mágico __unset() recibe un argumento – nombre del atributo que queremos  destruir.

 class Objeto {  
   protected $id;  
   protected $nombre;  
   protected $email;  
   function __construct($id, $nombre, $email) {  
     $this->id = $id;  
     $this->nombre = $nombre;  
     $this->email = $email;  
   }  
   function __isset($atributo) {  
     return isset($this->$atributo);  
   }  
   function __unset($atributo) {  
     if(isset($this->$atributo))  
       unset($this->$atributo);  
   }  
 }  
 $obj2 = new Objeto(1, "objeto1", "prueba1@ejemplo.com");  
 echo isset($obj2->nombre);  

Funciones anónimas en PHP (closures)

En 5.3 aparece un nuevo tipo de concepto: la función anónima o cláusula (closure). Conocida de los programadores de javascript. Una cláusula  es una función que se ejecuta en su propio contexto. Lo que significa que el contexto en el que la función es definido permanecerá hasta el cierre de la misma. Con lo que podemos declarar una función sin nombre y la podremos almacenar en una variable. Y para llamar a la cláusula llamaremos a la variable seguida de los paréntesis de apertura y cierra.
La sintaxis para definir un 'closure' es muy simple:

 function(){  
   //implementacion  
 }  

Hay que tener en cuenta 3 cuestiones de las funciones anónimas y las variables:

lunes, 12 de agosto de 2013

PHP orientado a objetos - Métodos mágicos - Parte 1

En PHP las clases tiene reservadas ciertos nombres de métodos que llevan como prefijo distintivo una doble barra baja. El programador será el encargado de escribir el comportamiento de estos métodos. Pero la caracteristica más importante es que estos métodos nunca serán llamados directamente por el programador. PHP, si están definidos, se encarga de llamarlos en el momento adecuado. Y es por eso que reciben el nombre de método mágicos.
Dos de estos métodos mágicos, __construct y __destruct(), ya los vimos en un tutorial anterior. Por lo tanto vamos a centrarnos en otros métodos nuevos.

__clone()

En PHP 4 se podía copiar un objeto simplemente asignándolo de una variable a otra. Y de esta forma se podía modificar la copia sin que ello afectara al original.

 $objecto1->nombre = "nombre 1";  
 $objecto2 = $objecto1;  
 $objecto2->nombre = "nombre 2";  
 echo $objecto1->nombre; // nombre 1"  

jueves, 8 de agosto de 2013

PHP orientado a objetos - Herencia múltiple

PHP al igual que Java u Objectice-C no soporta herencia múltiple. Ello se debe a que si se heredasen dos clases que contengan métodos con el mismo nombre no sabría que clase debería de tener preferencia.

Pero si estamos ante una situación en la que necesitamos herencia múltiple no está todo perdido.  Ya que existen dos métodos para conseguir simular este tipo de herencia. Aunque el segundo de ellos solo está disponible a partir de PHP 5.4.

Uso de interfaces para simular la herencia múltiple

Como comentamos en el tutorial sobre las interfaces, una clase que implementa una interfaz tiene disponible todos los métodos definidos. Además de estar obligada a implementarlos. Por lo que si una clase implementa una interfaz significa que puede hacer todo lo que la interfaz quiere que haga.

martes, 6 de agosto de 2013

PHP orientado a objetos - Clases abstractas e interfaces

Clase abstractas

La llegada de las interfaces fue uno de los grandes cambios de PHP5. Ya que con ella PHP daba un paso más hacia la programación orientada a objetos completa.
Una clase abstracta es una clase que no se puede instanciar (provocaría error) y por lo tanto no se puede crear un objeto a partir de ella. Su intención es definir una estructura (plantilla), que puede estar parcialmente implementada, para cualquier clase que quiera extenderla. Puede implementear ciertas funcionalidades y dejar que sus herederas terminen de implementearla.
Para crear una clase abstracta debemos usar la palabra clave abstract:

 abstract class Ejemplo{  
 }  

Una clase abstracta debe contener como mínimo un método abstracto. Los métodos abstractos no tienen implementación, sino que definen una funcionalidad que será implementada obligatoriamente en las clases herederas.

 abstract class Animal {   
  function presentacion() {   
   $sonido = $this->sonido();     
   return strtoupper($sonido);   
  }   
  abstract function sonido();     
 }   

lunes, 5 de agosto de 2013

PHP orientado a objetos - Elementos estáticos

Métodos y atributos estáticos

La palabra reservada static, en PHP y cualquier otro lenguaje de programación, es una declaración que se les da a miembros y/o métodos de una clase. Un miembro o método de una clase declarado como static va a poder ser accedido sin necesidad de hacer una instancia del objecto en una variable. Por lo que va a ser accedido a través de la clase y no a través de un objeto.
La palabra clave static se debe de colocar después de la definición de visibilidad (si no existe la visibilidad es pública) y antes del nombre del atributo o método.

Un método estático es lo más parecido a una función de un lenguaje estructurado. Solo que se encapsula dentro de una clase. Y el hecho de estar en un ámbito de clase y no de objeto tiene dos características:

domingo, 4 de agosto de 2013

PHP orientado a objetos - Herencia

Introducción

A grandes rasgos, el termino herencia significa que una o varias clases pueden derivar de una clase base o 'padre'. Una clase que hereda de otra se llama subclase. Esta hereda todas los atributos y métodos de la clase 'padre'. Y además añade sus propias características (atributos y métodos). Por eso se suele decir que una subclase extiende a la clase base.
El concepto de herencia es el mismo que en el mundo real: hijos heredan características de los padres. Por lo que una subclase tendrá a su disposición todas los atributos y métodos de la clase base. Pero esta última (clase base) no podrá utilizar ninguna de las características que extiendan las clases herederas.
Podríamos concluir la introducción con lo dicho en los anteriores párrafos respecto al total acceso a las características de la clase base por parte de las subclases. Pero estaríamos equivocados. Ya que no hemos tenido en cuenta el concepto de visibilidad explicado en el anterior tutorial. Ya que como explicamos, los lenguajes de programación orientados a objetos permiten indicar que atributos y métodos son internos de la clase base y cuáles son accesibles desde fuera de la clase. Y eso quiere decir que la clase heredera solo podrá tener acceso a los atributos y métodos que se hayan especificado con una visibilidad pública (public) o protegida (protected). Los miembros privados  no serán accesibles directamente. Por lo que nuevamente estamos ante el concepto de encapsulación ya que  la clase hija no puede acceder a todas la implementación interna de la clase padre. Solamente puede acceder a ciertos atributos y métodos que la clase padre permita.