Cuando instalamos el webserver de apache en un servidor o maquina casi siempre le decimos con que modulos adicionales queremos que este sea instalado, pero hay casos en que se nos olvida uno que otro modulo y en ocasiones es necesario reinstalar apache, php y otras aplicaciones relacionadas, lo cual nos quita bastante tiempo y hasta puede dejar por fuera del aire los sitios que tengamos allí alojados.
Ayer, tuve que reinstalar un apache y uno de los sitios era muy importante para todo el equipo de desarrolladores, por tal razón instale y copnfigure de manera rápida apache (httpd-2.2.17) y php (php-5.2.14), con tan mala suerte que necesitaba algunos modulos adicionales que no especifique … lo primero que pense fue en recompilar el apache especificando los modulos y recompilar nuevamente php, pero por fortuna en la primer compilación le habia especificado a apache que en el futuro queria poder compilar modulos compartidos, esto se hace de la siguiente manera:
./configure –prefix=/path/to/apache/apache –enable-so
Ahora si a lo que vinimos, para compilar el modulo mod_foo es necesario tener los fuentes de apache y buscar el archivo mod_foo.c, la ruta puede ser
/path/to/source/httpd-2.2.17/modules/mappers/mod_foo.c
y gracias a apxs, herramienta para compilar e instalar modulos para apache que se encuentra en el directorio bin donde instalemos apache, podemos hacerlo mediante dos instrucciones sencillas.
En la primera le decimos a apxs que compile el modulo deseado
/path/to/apache/apache/bin/apxs -c mod_foo.c
si todo sale bien, en la misma carpeta encontraremos unos archivos como los siguientes
mod_foo.slo
mod_foo.o
mod_foo.lo
mod_foo.la
ya con estos archivos generados, y nuevamente gracias a apxs podremos instalar el modulo en php, asi
/path/to/apache/apache/bin/apxs -i -a -n fooname mod_foo.la
la opción -n nos permite definir el nombre con el cual quedara habilitado el modulo en el httpd.conf .
Solo nos resta revisar que todo este OK, revisamos que el archivo mod_foo.so este en la carpeta de los modulos de apache,
[root@myhost]# ls /local/aplicaciones/apache2.2.17/modules/
httpd.exp libphp5.so mod_foo.so
[root@myhost]#
y que la directiva de LoadModule exista en el httpd.conf
LoadModule fooname_module modules/mod_foo.so
y listo, despues de reiniciar el apache ya podemos hacer uso del modulo en nuestros sitios
Tags: --enable-so, apache, apxs, compilar, compile, dso, dynamic shared objects, modules, mod_foo.so, mod_proxy.so, mod_rewrite.so
En este momento como proyecto personal me encuentro pasando una aplicación a ZendFramework, todo funciona 1A en mi maquina virtual, pero en el momento de subirlo a mi proveedor de hosting compartido se presentaron varios inconvenientes, a continuación les cuento como logre solucionarlos para instalar la app.
La estructura de mi aplicación en mi maquina local era la siguiente:
/projectname
/application
/controllers
/views
/models
/public
/ZendFramework
y tenia definido en mi virtualHost de apache el ambiente en el cual me encontraba, y el include del framework de Zend asi:
php_value include_path /home/ubuntu/ZendFramework/ZF-1.10.8/library:/home/ubuntu/projectname
SetEnv APPLICATION_ENV “development”
Claramente y como muchos de ustedes deben saber, no es posible hacer esto en un hosting compartido, no tenemos acceso al virtualHost del apache, por tal razon tuve que crear una carpeta “library” , copiar el framework de zend dentro de ella y modificar el archivo index.php dentro de public para que me tomara la carpeta library en el include asi:
set_include_path(implode(PATH_SEPARATOR, array(
realpath(APPLICATION_PATH . ‘/../library’),
realpath(APPLICATION_PATH . ‘/modules/admin/models’),
get_include_path(),
)));
Perfecto, asi ya funciona la aplicación, nuestro DocumentRoot apunta a nuestra cuenta y no a la carpeta /public como lo hariamos en una maquina local, entonces tendremos que acceder a nuestra aplicación especificando /public en la URl, lo cual no es muy elegante:
http://projectname/public
para solucionar esto, creamos un archivo .htaccess con las siguientes reglas y lo ubicaremos en el DocumentRoot :
#Definimos el ambiente de la APP para aplicar la configuracion de el application.ini
SetEnv APPLICATION_ENV production
#Habilitamos el mod_rewrite
RewriteEngine On
#Ignoramos este archivo, no aplicamos ninguna regla
RewriteRule ^\.htaccess$ – [F]
#Si el URI no tiene nada es decir si accedemos a /, hacemos un rewrite a /public/index.php
RewriteCond %{REQUEST_URI} =”"
RewriteRule ^.*$ /public/index.php [NC,L]
#Si el URI no empieza con /public, le adicionamos /public y hacemos el rewrite, de esta manera no necesitamos escribirlo
RewriteCond %{REQUEST_URI} !^/public/.*$
RewriteRule ^(.*)$ /public/$1
#Si el archivo existe fisicamente en el servidor no hacemos nada
RewriteCond %{REQUEST_FILENAME} -f
RewriteRule ^.*$ – [NC,L]
#Todo lo que venga /public/cualquiercosa lo redireccionamos al index.php para que el bootstrap haga su trabajo
RewriteRule ^public/.*$ /public/index.php [NC,L]
La estructura final es la siguiente:
/projectname
/application
/controllers
/views
/models
/public
/library
/ZendFramework
.htaccess
Y de esa manera queda completamente funcional nuestra aplicacion en un hosting compartido
Tags: app, application, godaddy, hosting, hosting compartido, htaccess, mod_rewrite, shared, shared hosting, web, webserver, ZendFramework
Tengo varias aplicaciones que hacen uso del aplicativo memcached y las cuales se estaban comportando de manera extraña, donde al hacer una modificación de información e invalidar la llave de memcached, la información parecia no ser actualizada.
Lo primero que hice fue aislar el aplicativo para que solo utilizara un servidor de BackEnd, y que este a su vez utilizara unicamente un servidor de Memcached, para poder monitorear de manera controlada el comportamiento de la aplicación.
Una vez aislada la aplicación, ingrese mensajes de debug en el error_log del apache, donde imprimia en la primer linea la operación que estaba realizando, en la segunda linea el valor devuelto por el servidor de memcached y por ultimo el MD5 del key que se almacena en memcached, este era el resultado:
[Thu Sep 30 11:25:09 2010] [error] [client X.X.X.X] REMOVE CACHE, referer: http://myhost.com/somepath/to/my/app
[Thu Sep 30 11:25:09 2010] [error] [client X.X.X.X] 0, referer: http://myhost.com/somepath/to/my/app
[Thu Sep 30 11:25:09 2010] [error] [client X.X.X.X] e81afd654486c19cb137475a687c7f5e
Despues de ver esto se puede evidenciar que el valor devuelto por el aplicativo era cero (0) o false, lo cual indicaba que no estaba realizando la operación de borrado de la información.
Para verificar la información en el servidor de memcached, me conecte por consola y solicite el valor del key antes y despues de modificar un dato en la aplicación web, evidenciando que el dato permanecia intacto en memcached y no era actualizado, por lo tanto el efecto en la aplicación web era que no se estaba actualizando la información, aun cuando en la BD estaba de manera correcta. Para verificar por consola en memcached nos debemos conectar por telnet al puerto definido en la instalación:
[user@webserver ~]$ telnet 192.168.1.XXX 22522
Trying 192.168.1.XXX…
Connected to 192.168.1.XXX (192.168.1.XXX).
Escape character is ‘^]’.
get e81afd654486c19cb137475a687c7f5e
VALUE e81afd654486c19cb137475a687c7f5e 1 49
a:3:{i:0;s:5:”i:11;”;i:1;i:1285880685;i:2;i:300;}
END
Al ver este comportamiento investigue primero en el framework de Zend, en la libreria para trabajar con Memcache, en la funcion “remove” que era la que estaba fallando, alli pude ver que ZendFramework lo que realiza es un llamado a la función “delete” de la clase memcache de PHP.
Investigando en el sitio web de php, http://www.php.net/manual/es/memcache.delete.php, encontre que se trata de un Bug que se presenta en esta función donde recibe un segundo parametro “Opcional” especificando el tiempo en el cual se debe borrar el key, al parecer no resulto ser tan “Opcional” y para que funcione debe especificarse siempre.
Por tal motivo, tuve que editar el archivo de ZendFramework, ZendFramework-1.7.8/library/Zend/Cache/Backend/Memcached.php
ANTES
public function remove($id)
{
return $this->_memcache->delete($id);
}DESPUES
public function remove($id)
{
return $this->_memcache->delete($id, 0);
}
adicionando ese segundo paramétro en cero (0), se soluciona el inconveniente y vuelve a trabajar de manera adecuada el servidor de memcached.
NOTA: Esto sucede con ZendFramework inferior a la versión 1.10.X + pecl-memcache 3.0.4 + memcached 1.4.4
Tags: bug, memcache, php, ZendFramework
En una entrada anterior hablamos sobre los origines y las bondades que tiene el servidor http Nginx, en esta ocasión vamos a instalarlo y a realizar una configuración basica del mismo.
Lo primero que debemos hacer es descargar la ultima versión del servidor Nginx aqui, y la ultima version de pcre(Perl Compatible Regular Expressions) aqui. Para este tutorial vamos a trabajar con las versiónes nginx-0.8.51.tar.gz y pcre-8.10.tar.gz. Adicionalmente vamos a instalar un modulo para nginx que nos permite manejar las cabeceras eTag, desarrollado por kkung, el cual se puede descargar aqui.
Descomprimimos el paquete pcre-8.10.tar.gz e ingresamos a la carpeta generada, ejecutamos los comandos configure, make y make install
tar -zxvf pcre-8.10.tar.gz
cd pcre-8.10
./configure
make
make install
Si todo sale bien, ya tendremos instalado el paquete pcre en nuestro sistema y continuaremos instalando el servidor Nginx.
Lo primero que debemos hacer es descomprimir el modulo de eTags para archivos estaticos y renombrar la carpeta por facilidad, simplemente con:
tar -zxvf kkung-nginx-static-etags-s20090317-3-gce0fdd4.tar.gz
mv kkung-nginx-static-etags-s20090317-3-gce0fdd4 nginx-static-etags
Descomprimimos el paquete nginx-0.8.51.tar.gz e ingresamos a la carpeta generada. Ejecutamos el comando configure incluyendo el paquete que acabamos de descomprimir, asi como la opción que nos permite tener estadisticas del servidor (server-status en apache), seguido de make y make install
tar -zxvf nginx-0.8.51.tar.gz
cd nginx-0.8.51
./configure –user=userowner –group=groupowner –with-http_stub_status_module –add-module=/instaladores/nginx/static-etags
make
make install
Nota: En caso en que al ejeuctar el comando “make” opbtengamos el siguiente error, lo unico que debemos hacer es entrar al archivo /instaladores/nginx-static-etags/ngx_http_static_etags_module.c y generar una linea vacia al final.
/instaladores/nginx-static-etags/ngx_http_static_etags_module.c:168:2: no newline at end of file
make[1]: *** [objs/addon/nginx-static-etags/ngx_http_static_etags_module.o] Error 1
make[1]: Leaving directory `/instaladores/nginx-0.8.51′
make: *** [build] Error 2
Hasta aqui ya tenemos instalado nuestro servidor nginx para HTTP el cual se encuentra en /usr/local/nginx, ahora vamos a realizar unas tareas administrativas para que sea mas sencillo configurar y trabajar con nginx.
Primero que todo vamos a configurar el sistema para que podamos acceder a la configuración del servidor nginx en /etc/nginx, para esto necesitamos crear dos links simbólicos de la siguiente manera:
ln -s /usr/local/nginx/conf/ /etc/nginx
ln -s /usr/local/nginx/sbin/nginx /usr/sbin/nginx
lo segundo, es que vamos a crear un script por medio del cual podemos subir y bajar el servidor nginx como cualquier otro servicio de linux, y lo alojaremos en /etc/init.d/, aca les dejo el script para que los descarguen nginx script inicio
Por último modificaremos el archivo de configuración para colocar un sitio de ejemplo, para esto debemos modificar el archivo /etc/nginx/nginx.conf para que quede de la siguiente manera:
user userowner groupowner;
worker_processes 1;events {
worker_connections 512;
}http {
include mime.types;
default_type application/octet-stream;log_format main ‘$remote_addr – $host $remote_user [$time_local] “$request” ‘
‘$status $body_bytes_sent “$http_referer” “$http_user_agent” “$gzip_ratio” “$http_x_forwarded_for” “$upstream_status”‘;
server {
listen 80;
server_name test.local;access_log /var/log/access.log main;
# [ debug | info | notice | warn | error | crit ]
error_log /var/log/error.log debug;etags on;
etag_hash on;
etag_hash_method md5;#SECCION PRINCIPAL
location / {
root /var/www/;
index index.html index.htm;
}#####NGINGX STATUS
location /nginx_status {
stub_status on;
access_log off;
allow all;
}
error_page 404 /error.html;
}
}
Una vez creado el archivo de configuración de nuestro sitio de prueba, subimos el servicio y listo, al acceder por un navegador podremos ver nuestro sitio funcionando.
/etc/init.d/nginx start
En una próxima entrada estare hablando de configuraciones y optimizaciones especificas para este servidor.
Tags: etag, nginx, pcre, proxy, reverse proxy, web, webserver