Como obtener el Connection String clásico con Entity Framework

por Andres Stang  28. enero 2011

Como sabrán Entity Framework utiliza un conection string para saber con qué base de datos trabajar, el tema es que además de contener la cadena de conexión que conocemos de toda la vida, tiene un poco más de información que utiliza para indicarle otras cosas que no vienen al caso.

Si quisiéramos recuperar la clásica cadena de conexión para, por ejemplo, no utilizar Entity Framework y acceder directamente a la base de datos con ADO.NET uno pensaria en hacer:

 

   1:  MiModeloEntities miEntities = new MiModeloEntities();
   2:  string connStringEF = miEntities.Connection.ConnectionString;

 

Pero no nos serviría! Ya que tenemos la cadena de conexión de Entity Framework que incluye metadata que antes mencionamos. Ya sé, seguramente ya estás pensando en usar expresiones regulares… Momento! La solución? Simplemente:

 

   1:  MiModeloEntities miEntities = new MiModeloEntities();
   2:  string connString = ((System.Data.EntityClient.EntityConnection)miEntities.Connection).StoreConnection.ConnectionString;

 

Y de esta manera nos evitamos tener duplicada la información en nuestra configuración y evitamos parsear el string innecesariamente.

Tags: ,

.NET | Entity Framework | ORM | SQL Server

Seguridad y Autorizacion centralizada en base de datos con Asp.Net MVC

por Andres Stang  22. diciembre 2010

La palabra Seguridad es siempre una consulta que recibo cuando hablo de cómo programar en Asp.Net, y siempre me gusta dar el mismo chiste como respuesta: “Vamos por partes decía Jack el Destripador”. Es importante dividir un problema grande en problemas más pequeños y por ende más manejables, y hablando de seguridad la fórmula es sencilla.

 

SEGURIDAD = AUTENTICACIÓN + AUTORIZACIÓN


Es decir, tenes que resolver por un lado como identificar al usuario, para saber que es quien dice ser que es, y por el otro lado una vez que sepamos su identidad, tenemos que decidir si lo dejamos acceder o no.

Cuando creamos un proyecto nuevo de MVC, el template nos da una GRAN ayuda y propone resolver (mejor dicho, ya lo implementa y lo resuelve por defecto) cada tema con un componente específico. Para la autenticación utiliza Asp.Net Membership y para la autorización el decorador [Authorize].

Ambos componentes funcionan maravillosamente pero hay uno que me gusta y otro que no. Concretamente Asp.Net Membership me parece perfecto para resolver una gran cantidad de escenarios y contextos, y generalmente lo utilizo en mis proyectos. Pero el decorador de autorización a mi criterio tiene dos grandes falencias:

  • Falta de flexibilidad: el componente de autorización puede recibir como parámetro el usuario y el rol, pero esto queda explícito en el código, es decir, si me surge la necesidad de agregar un nuevo rol al sistema deberé recorrer el código, cambiarlo, recompilar y realizar un deploy del sitio.
  • Verborragico: el componente requiere gran escritura y definición por parte del programador. Esto, mas allá de la poca elegancia del código, define que sea el programador quien decide quien esté autorizado a entrar a cada acción. Y ante un error, descuido o falta de memoria del programador podemos comprometer a nuestra aplicación dejando expuesta funcionalidad sensible a usuarios indeseados.

 

¿Cómo resolvemos esto?


Allá por el año 2007 Daniel Laco escribió uno de los post más consultados de este sitio:


Autenticación de usuarios basada en Roles utilizando HTTPModules en ASP.NET


De forma muy sencilla y elegante resuelve las dos falencias presentadas. Y si bien el código no es compatible con todas las versiones del .net framework, o con el paradigma MVC, el concepto si aplica en el universo Asp.net.

Lo que haremos el día de hoy, es actualizar un poco el código para que puede ser utilizado en nuestros proyectos de MVC ;)

Lo primero que tenemos que hacer es programar el método de nuestro modulo, quedaría algo así:

 

 public void Init(HttpApplication context)
 {
     context.AuthorizeRequest += new EventHandler(OnAuthorizeRequest);
 }
 
 void OnAuthorizeRequest(object sender, EventArgs e)
 {
     HttpContext context = ((HttpApplication)sender).Context;
 
     RouteData routeData = RouteTable.Routes.GetRouteData(new HttpContextWrapper(context));
 
     if (routeData != null)
     {
         string controller = routeData.GetRequiredString("controller");
         string action = routeData.GetRequiredString("action");
 
         if (!EstaAutorizado(controller, action, context.User))
         {
             /// 401 es el codigo de resultado HTTP para acceso no autorizado
             context.Response.StatusCode = 401; 
             context.Response.End();
         }
     }
 }

 

En el código vemos cómo recuperar la información de la ruta para saber que método estamos ejecutando, y luego definir que si no se encuentra autorizado el usuario, le responderemos con un código HTTP estándar: 401 (lista de códigos)

De esta forma dejamos actuar al framework de asp.net que ya tiene resuelto el enganche y resolución del caso. Por ejemplo, MVC viene configurado por defecto que ante un error de autenticación redirija al usuario automáticamente a la página de login:

 

<authentication mode="Forms">
   <forms loginUrl="~/Account/LogOn" timeout="2880" />
</authentication>

 

Lo único que nos falta, es recordar agregar el modulo a nuestro web.config para que se ejecute:

<httpModules>
  <add name="MiModulo" type="AutorizacionMVCHttpModule.Models.MiModulo"/>
</httpModules>

 

Listo! Con muy pocas líneas hemos resuelto de manera elegante y limpia un requerimiento esencial y controversial en la mayoría de nuestros proyectos.

Les dejo el código fuente de ejemplo para que lo puedan descargar y ver implementado
Download AutorizacionMVCHttpModule.zip (262,77 kb)

Happy coding!

Tags: , , , , ,

.NET | ASP.NET | Desarrollo Web

Formulario Cabecera-Detalle en Asp.Net MVC con el default ModelBinder

por Andres Stang  30. marzo 2010

 

Descargar Codigo Fuente

Tal vez les suceda que alguna vez en su feliz programación de Asp.Net MVC quieren generar un formulario de entrada de datos que permita, sin los molestos tiempos de carga de postback, agregar N cantidad de elementos.

Es decir, generar un modelo de Cabecera-Detalle en el cliente, y luego poder leerlo del lado servidor utilizando solo MVC y Javascript. No, me refiero a SOLO MVC, es decir sin un ModelBinder personalizado, que sería la opción que primero nos viene a la mente gracias a la extensibilidad propuesta por el framework.

Podemos imaginarnos el siguiente ejemplo de modelo:

   1: public class Materia
   2: {
   3:     public int Codigo { get; set; }
   4:     
   5:     public string Nombre { get; set; }
   6:  
   7:     public List<Alumno> AlumnosInscriptos { get; set; }
   8: }

Supongamos que queremos permitir al usuario generar una nueva materia y asignarle alumnos a la misma desde una lista de selección. Para simplificar el alumno va a estar definido por:

   1: public class Alumno
   2: {
   3:     public int Matricula { get; set; }
   4:  
   5:     public string Nombre { get; set; }
   6: }

 

Entonces realizamos el siguiente formulario web:

 

En el mismo vamos a poder cargar las propiedades de la materia y mediante javascript permitiremos que se agreguen los alumnos al seleccionarlos del combo al presionar “Agregar”.

Pero… como hacemos luego para leer las propiedades de la materia y los N alumnos seleccionados del lado del servidor?

Muy fácil, utilizando el ModelBinder por defecto de MVC. Es decir, el framework ya viene preparado para este escenario, solo que (a mi apreciación) está poco documentado.

Es decir, en nuestro método de controlador solo tendremos que colocar la siguiente definición:

   1: [AcceptVerbs(HttpVerbs.Post)]
   2: public ActionResult Index(Materia nuevaMateria)
   3: {
   4:     // HACER ALGO CON LA NUEVA MATERIA
   5:  
   6:     ViewData["CantidadAlumnos"] = nuevaMateria.AlumnosInscriptos.Count;
   7:  
   8:     return View("Alumnos");
   9: }

Y automáticamente podemos leer la instancia de la clase Materia con sus alumnos relacionados.

Donde está el secreto???

Lo importante es que al generar las filas dinámicamente de la tabla de alumnos también generemos los inputs para los valores de los alumnos que vayamos agregando. Por ejemplo, al agregar la fila nueva también insertaremos dos inputs ocultos de html con los valores que requiere la clase Alumno, es decir Matricula y Nombre:

   1: <input type="hidden" value="22" name="AlumnosInscriptos[1].Matricula" 
   2:     id="AlumnosInscriptos[1].Matricula" />
   3: <input type="hidden" value="Pedro" name="AlumnosInscriptos[1].Nombre" 
   4:     id="AlumnosInscriptos[1].Nombre" />

Podemos observar la particularidad del nombre y id del tag, es decir, debemos llamarlos de la siguiente manera:

<NombrePropiedadPadre>[indice].<NombrePropiedadHijo>

O para nuestro ejemplo:

AlumnosInscriptos[0].Nombre

De esta manera, el ModelBinder interpretara que se trata un elemento perteneciente a nuestra colección y nos facilitara el trabajo.

 

 

Pongo a disposición el código fuente perteneciente al ejemplo de este post:

ListBinder.zip (264,49 kb)

Happy Programming!

Tags: ,

ASP.NET | Desarrollo Web

Acerca de los Autores

Este es el blog del equipo de VEMN SA 
Presentaremos temas que nos parezcan de interés sobre tecnología .NET, Procesos y Metodologías y todo aquello relacionado con el proceso de desarrollo de Software

Month List

BlogRoll

Download OPML file OPML