jueves, 6 de noviembre de 2014

WP - SQL Server Snippets – Tablas con columna autonumérica

Este primer snippet consiste en una consulta para obtener las tablas de la base de datos en uso (es decir, la base de datos seleccionada actualmente), que poseen una columna autonumerada (IDENTITY), incluyendo el nombre de dicha columna.

La consulta en T-SQL es la siguiente:

USE [BASE_DATOS]
GO
 
SELECT
TABLA.object_id                                    AS object_id,
SCHEMA_NAME(TABLA.schema_id) + '.' + TABLA.name    AS tabla,
COLUMNA.name                                    AS columna_identity
FROM sys.tables TABLA
INNER JOIN sys.columns COLUMNA ON COLUMNA.object_id=TABLA.object_id
WHERE TABLA.type='U'
AND TABLA.name NOT LIKE 'sys%'
AND COLUMNA.is_identity = 1
ORDER BY SCHEMA_NAME(TABLA.schema_id), TABLA.name

A modo de una pequeña descripción, básicamente lo que se hace es consultar las tablas del sistema sys.tables (que contiene información de las tablas), y sys.columns (que contiene información de las columnas). Ambas tablas se unen a través del object_id de la tabla.

Luego, en la cláusula WHERE se filtran los resultados para solamente incluir tablas creadas por el usuario (tipo “U” y que no inicien con “sys”, para descartar la tabla sys.diagrams), y de dichas tablas solamente tomar las columnas con la propiedad IDENTITY (is_identity = 1). Cabe señalar que una tabla en SQL Server puede tener solamente una columna IDENTITY, por lo que la consulta no devolverá más de una fila por tabla.

Nótese además que se obtiene el nombre del esquema de la tabla, a través de la función SCHEMA_NAME, y se concatena con el nombre de la tabla, para obtener el nombre completo de la tabla dentro de la base de datos.

Finalmente, y de forma opcional, se ordenan los resultados por esquema y nombre de tabla, para que se muestren de la misma forma que se muestran en el explorador de objetos del SQL Server Management Studio.

Hasta donde he probado, el script funciona para SQL Server 2005 – 2012.

Espero que les sea de utilidad. Saludos, y como dicen por allí, “happy coding!”.

WP - Atributo de MVC para filtrar acciones para solicitudes AJAX

Esta entrada ha sido reposteada por error, pero utilizando Gists para mejor legibilidad del código, acá: http://itsouvenirs.blogspot.com/2018/01/wp-atributo-de-mvc-2-para-filtrar.html

Ya llevo un par de meses trabajando con ASP.NET MVC Framework 2, y debo decir que me ha encantado. Y sé que van por la versión 4, pero en el trabajo contamoscon Visual Studio 2008, así que hay que aprovechar lo que se tiene, y debo decir que en realidad no es poco.

En esta ocasión quiero mostrar una forma de crear un atributo de filtrado para acciones que deben ser ejecutadas solamente mediante solicitudes Ajax. Esto es útil para acciones que deseamos utilizar exclusivamente para estas solicitudes, y que queremos que el usuario común tenga acceso a ellas solamente a través de esta forma, mediante alguna interacción con la interfaz de usuario (UI), por ejemplo.

Primero, es necesario encontrar una forma de identificar que el tipo de solicitud es XML HTTP request, que es la clase de solicitudes que se hacen mediante AJAX. El objeto HttpRequest del que disponemos en una aplicación ASP.NET no cuenta con un método propio para identificar este tipo de solicitud, por lo que es necesario trabajar un poco en esta parte. Para ello, crearemos un método de extensión que se encargue de verificar esto. El método que presento a continuación es prácticamente una copia de la respuesta de Charlino a la pregunta de StackOverflow titulada How to check if request is ajax or not in codebehind – ASP.NET Webforms, que a su vez se basa en el código fuente del MVC Framework (que es open source, o código libre, por cierto).

using System;
using System.Web;
 
namespace MiProyectoMVC.Extensiones
{
    public static class HttpRequestExtensions
    {
        public static bool IsAjaxRequest(this HttpRequest request)
        {
            if (request == null)
            {
                throw new ArgumentNullException("Request es nulo");
            }
 
            return (request["X-Requested-With"] == "XMLHttpRequest") || ((request.Headers != null) && (request.Headers["X-Requested-With"] == "XMLHttpRequest"));
        }
    }
}
Como puede observarse, el método revisa directamente el encabezado del request, para verificar el tipo de solicitud. Si el tipo de solicitud es XMLHttpRequest, devuelve verdadero, y falso en caso contrario.

Actualización: Existe un método de extensión para la clase HttpRequestBase en el espacio de nombres System.Web.Mvc, con el mismo nombre y funcionalidad que el del método propuesto (IsAjaxRequest). Podría usarse este en vez de crear una nueva extensión, solamente incluyendo el espacio de nombres System.Web.Mvc.

Teniendo este método disponible, podemos proceder a crear el atributo de filtro. Este es un atributo de filtro convencional, por lo que será descendiente o derivado de la clase ActionFilterAttribute. Como se observa a continuación, el atributo es bastante simple:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;
using MiProyectoMVC.Extensiones;
 
namespace MiProyectoMVC.Controllers.Atributos
{
    public class XmlHttpRequestAttribute : ActionFilterAttribute
    {
        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            if (!filterContext.HttpContext.Request.IsAjaxRequest())
            {
                //Si no es solicitud Ajax, mostramos a una página de error completa
                filterContext.Result = new ViewResult() { ViewName = "Error" };
            }
            base.OnActionExecuting(filterContext);
        }
    }
}
Como puede observarse, todo el proceso de verificación se realiza sobrecargando el método OnActionExecuting, que se ejecuta justo antes de proceder a ejecutar la acción. Acá hacemos uso del método de extensión para verificar si la solicitud (request) es de tipo Ajax, y si no lo es, devolvemos como resultado una vista completa, que bien puede ser una página de error personalizada. Cabe mencionar que digo vista completa porque el resultado a generar es un ViewResult. Dado que sabemos que no es una solicitud Ajax, lo común no sería devolver una vista parcial, sino una página completa (.aspx). También, en vez de devolver de una sola vez la página de error, podríamos redireccionar hacia otra acción que consideremos conveniente, a través de un RedirectResult.

Finalmente, decoramos la acción que deseamos filtrar con el atributo que hemos creado, de la siguiente manera:

//...
 
namespace MiProyectoMVC.Controllers
{
    public class EjemploController : Controller
    {
        // ...
 
        [XmlHttpRequest]
        public ActionResult IndexPartial()
        {
            //...
            return PartialView("IndexPartial");
        }
 
        //...
    }
}
Acá les dejo un enlace que encontré por allí, que tiene varios ejemplos de atributos de filtro de acciones bastante interesantes, que puede que les sean de utilidad: Creating Custom Action Filters in ASP.NET MVC


NOTA: Aunque este atributo fue elaborado y probado en MVC Framework 2, de igual forma es aplicable para las versiones 3, 4 y 5 (posiblemente) del framework.


Cualquier comentario será bien recibido, y como dicen por allí, Happy coding!

martes, 4 de noviembre de 2014

WP - Resposive Web Design

La ventaja y objetivo de los diseños responsivos (Responsive Web Design, RWD) es que la página web se pueda ver bien desde dispositivos con casi cualquier resolución (smartphones, tablet, netbooks, PCs, televisores). He de comentar que desde hace algunos años quise hacer algo así sin éxito, pero no conocí este término de RWD hasta que hace un par de meses leí un post de  en TechRepublic, titulado "How to get started with Responsive Web Design". Les recomiendo los artículos de este señor sobre desarrollo web, ya que incluyen nuevos conceptos y ejemplos prácticos en este ámbito. Que Dios les bendiga.

Publicado originalmente el 20/09/2012, en http://itsouvenirs.wordpress.com/type/aside/
Como dato curioso, esta entrada la publiqué al cambiar el tema de mi blog de Wordpress a uno responsivo, llamado "Twenty Eleven".

lunes, 3 de noviembre de 2014

Extraer archivo de base de datos desde dispositivo Android

Para extraer los archivos de base de datos (y en realidad cualquier otro archivo), podemos hacerlo utilizando las herramientas del SDK de Android, ya sea desde la línea de comandos, o haciendo uso del File Manager proporcionado por el Android Device Monitor.

Extraer base de datos desde línea de comandos

Para extraer archivos desde un dispositivo conectado a la computadora o emulador activo, se hace uso del comando adb pull. Si hay un solo dispositivo conectado, se hace de la siguiente manera:

adb pull /data/data/[mi.paquete.app]/databases/[mibasedatos.db] C:\ruta\destino

En donde el primer parámetro es la ruta complete del archive a extraer del dispositivo, que en este caso es la base de datos; y el segundo parámetro es la ruta destino dentro de la computadora. El segundo parámetro es opcional, y si no se especifica, el archivo extraído se guarda en el directorio actual.

Si hay varios dispositivos Android conectados a la computadora, debe especificarse adicionalmente el serial del dispositivo, de la siguiente manera:

adb -s [serial] pull /data/data/[mi.paquete.app]/databases/[mibasedatos.db] C:\ruta\destino

En donde [serial] corresponde al serial específico del dispositivo. Cabe mencionar que para consultar los seriales de los dispositivos conectados, se puede hacer ejecutando el comando:

adb devices

El serial del dispositivo aparece en la primera columna a la izquierda, al ejecutar el comando.

Extraer base de datos usando el Android Device Monitor

Para extraer el archivo de base de datos usando el File Explorer del Android Device Monitor, basta con seleccionar el dispositivo en la barra de dispositivos del monitor, ubicar y seleccionar el archivo en la ficha del File Explorer, y presionar el botón  (Pull a file from the device), ubicado en la parte superior derecha de la ficha.



Luego de esto se nos muestra una ventana de diálogo en la que solamente hay que indicar el nombre del archivo y el directorio destino.

Aunque esta forma parezca la más fácil, puede resultar no serlo, debido a que en algunos casos la carpeta data no puede ser vista desde el File Explorer, debido a que no posee los permisos necesarios.
Con la tecnología de Blogger.