Cuando se acaba el soporte de Microsoft a un producto?

por Daniel Laco  15. abril 2011

 

A menudo nos encontramos en las empresas con aplicaciones, software y tecnologías que les queda poco tiempo de soporte de parte de Microsoft.

En otros cosas el tema es mas complicado porque ya no tienen directamente soporte de ningún tipo.

Hablando con un Arquitecto el otro día me comentaba que tenían varias aplicaciones desarrolladas en .NET 1.1, y que no conseguía que la gerencia encarara un proyecto de migración a versiones mas nuevas de .NET

En el caso de la versión 1.1 ya no tiene mas soporte de MS en cuanto a liberacion de Services Pack por temas de errores del código, y solamente le queda 1 año y medio aproximadamente de soporte extendido (solo sacan hotfixes por temas de seguridad).

Creo que esto es argumento mas que suficiente para para encarar un proyecto de migración serio.

Ni hablar de compañias donde hay muchas aplicaciones corriendo en VB6, Visual Fox, etc.

Aquí les dejo el ink http://support.microsoft.com/lifecycle/search/Default.aspx donde pueden consultar el estado de los productos dentro del ciclo de vida de MS.

 

 

Aquí también dejo un artículo con mas explicación sobre el tema y que fué el que me motivó a escribir esta nota. (http://www.ewaldhofman.nl/post/2011/04/14/When-runs-a-product-out-of-support.aspx)

Tags: ,

.NET

Visual Studio 2010 and .NET Framework 4 Training Kit

por Victor Passador  26. marzo 2011

Ya van quedando cada vez menos excusas para no estar entrenado con lo último. Acaba de salir publicado un Training Kit gratuito para VS 2010 y .NET 4.0.

Es un download de un poco más de 400MB que en disco se transforman en casi 2GB de presentaciones, papers, hand-on-labs, código de ejemplo, etc.

Pueden descargarlo desde aquí.

Enjoy !

Tags: ,

.NET | Visual Studio

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

Que hay de nuevo en VS2010?

por Daniel Laco  4. marzo 2010

Ya se viene la liberación de la versión final de Visual Studio 2010 y .NET 4.0 y uno siempre quiere tener una vista rápida de los cambios, agregados, etc.

En http://msdn.microsoft.com/en-us/library/bb386063(VS.100).aspx pueden encontrar un listado de todos los temas nuevos de esta plataforma.

 

Tags: , , , ,

.NET | ADO.NET | ASP.NET | Entity Framework | Visual Studio | WCF | WinForms

Introducción al Validation Application Block

por Maxi Guillén - Daniel Laco  27. diciembre 2007

 

Enterprise Library Validation Application Block

Uno de los temas siempre mas controversiales en del desarrollo, es el proceso de validación, ya sea en al entrada de datos, en el manejo de las reglas de negocio o en la parte de persistencia de los datos.

Con el Validation Application Block (VAP) contenido en la Enterprise Library podemos resolver de un modo elegante y personalizable toda la problemática de validación en nuestras aplicaciones.

El VAP brinda un entorno común para definir reglas de validación para los objetos del negocio e interfaces de usuario. Facilita varios tipos de clases de validadores que incluyen código para validar tipos de datos de .net. Y pueden desarrollarse validadores personalizados para reutilizar.

Se pueden crear grupos de validadores llamados Rule Set (1 a N validators) mediante parámetros de atributos. Es una forma de validar objetos complejos agrupando validadores de diferentes tipos y aplicándolos a campos, propiedades y a nested objects.

Las validaciones se pueden definir o bien a nivel de atributos en las clases o en un archivo de configuración.


Se puede utilizar con las siguientes tecnologías:
ASP .NET
Windows Forms
Ajax
WCF
WPF Requerimientos:
.Net Framework 2, 3 o 3.5

Para utilizar ValidationBlock no es necesario referenciar toda la Enterpise Library, sólo debemos referenciar las siguientes bibliotecas:
Microsoft.Practices.EnterpriseLibrary.Comon.dll
Microsoft.Practices.EnterpriseLibrary.Validation
Microsoft.Practices.ObjectBuilder.dll
Microsoft.Practices.EnterpriseLibrary.Integration.WinForms (solo en la capa de presentación)

Se utilizan los siguientes name space:
using Microsoft.Practices.EnterpriseLibrary.Validation;
using Microsoft.Practices.EnterpriseLibrary.Validation.Validators;
using Microsoft.Practices.EnterpriseLibrary.Validation.Integration.WinForms; (solo en la capa de presentación)

Validadores predefinidos
Validation Application Block incluye un conjunto de validadores predefinidos que comúnmente se pueden utilizar en las aplicaciones. Cada validador está asociado a un tipo específico. Algunos de estos validadores son:

  • ContainsCharacterValidator
  • NotNullValidator
  • ObjectValidator
  • DomainValidator
  • StringLengthValidator
Ejemplo de utilización de atributos:
public class Customer
{
    // validator attributes with field as target
    [NotNullValidator]
    [StringLengthValidator(1, 50)]
    public string Name;
 
    // validator attribute with property as target
    [DateRangeValidator("2007-10-27T00:00:00", "2008-10-27T00:00:00")]
    public DateTime DateJoined { get { return this.dateJoined; } }
    
    // validator attribute with method as target
    // assume that ShippingAddress is defined elsewhere and has validation
    [ObjectValidator]
    public ShippingAddress GetPrimaryShippingAddress()    {….}
    // validator attribute with method as target (applied to an enumeration)
    [ObjectCollectionValidator(typeof(ShippingAddress))]
    public IEnumerable<ShippingAddress> GetAlternateShippingAddresses()    {….}
}

Validadores compuestos Se pueden crear Validadores compuestos AND u OR (AndCompositeValidator y OrCompositeValidator), agrupa validaciones en forma lógica, es decir en el caso de And todos los validadores deben devolver verdadero para que el objeto sea válido. Las formas para crear validadores compuestos son:

  • Usar la herramienta de configuración
  • Usar atributos
  • Mediante código

Ejemplo por código:

Validator validator = new AndCompositeValidator(new NotNullValidator(), new StringLengthValidator(4, 8));
string password = "123";
ValidationResults results = validator.Validate(password);
bool esValido = results.IsValid;


Ejemplo por atributos:

public class cliente
{
    private string nombre;
    [ValidatorComposition(CompositionType.And)]
    [NotNullValidator(MessageTemplate = ValidatorMsgs.NotNullMsg), 
     StringLengthValidator(1, 50, MessageTemplate = ValidatorMsgs.StringRange50)]
    public string Nombre
    {
        Get{ return nombre; }
        Set{ nombre = value }
    }
}


Atributos modificadores de validación

Permiten modificar el comportamiento de los atributos de validación. Los atributos modificadores son:

  • ValidatorComposition = [CompositionType.And/CompositionType.Or], permite hacer override del comportamiento por defecto (AND) cuando hay más de un atributo de validación.
  • IgnoreNulls, los demás validadores no serán llamados si el valor que se está verificando es nulo.


Propiedades de los atributos de validación

Property name Description
MessageTemplate Descripcion que aparecerá en la propiedad Message del resultado, si se integra con winforms es lo mostrará el ErrorProvider en la intefaz de usuario.
MessageTemplateResourceName This property defines the name of the resource for message templates.
MessageTemplateResourceType This property defines the name of the type used for the message template resource.
Negate Modifica el comportamiento del validador para que falle la validación si se cumple la condición. Al contrario del comportamiento común que consiste en fallar la validación si no se cumple la condición
Tag Se usa para permitir clasificar los resultados
Ruleset Nombre de la regla a la que pertenece el validador


Ejemplo de uso con una clase:

public partial class Estacion : IDisposable
{
    private int _idEstacion;
    private string _nombre;
        private string _ubicacion;
    private string _telefono;
    private IList<OperacionCabina> _operacionCabinaList;
 
    public int IdEstacion
    {
        get { return this._idEstacion; }
    }
 
    [NotNullValidator(MessageTemplate = ValidatorMsgs.NotNullMsg), 
    StringLengthValidator(1, 50, MessageTemplate = ValidatorMsgs.StringRange50)]
    public string Nombre
    {
        get { return this._nombre; }
        set
        {
            this._nombre = value; 
        }
    }…
 


Validación Self
Consiste en implementar la lógica de validación dentro de la misma clase. Se rotula la clase con [HasSelfValidation] y con [SelfValidation] a cada método de la clase que se llamará cuando se efectúe la validación.

Por ejemplo:

[HasSelfValidation]
public class TemperatureRange
{ 
    private int min; 
    private int max;
 
    // ...
 
    [SelfValidation]             
    public void CheckTemperature(ValidationResults results) 
    { 
         if (max < min) 
           results.AddResult(new ValidationResult("Max less than min", this, null, null, null));
    } 
} 


Si se quiere que la validación sea heredable hay que marcar con HasSelfValidation tanto a la clase padre como a sus hijos y el método de validación debe ser público.


Validación de objetos

Puede realizarse mediante un llamado al método Validate de la clase estática Validation, el resultado se obtiene mediante la clase ValidationResults

Ejemplo de validación de una instancia de la clase Estacion:

Estacion estacion = Global.Data.GetObject<Estacion>();
Validation results = Validation.Validate(estacion);
Bool esValido = results.IsValid;


Puede utilizarse también la clase ValidationFactory para crear una instancia del validador.

Customer myCustomer = new Customer( /* ... */ );
Validator<Customer> goldCustomerValidator =   ValidationFactory.CreateValidator<Customer>("GoldCustomer");
ValidationResults results = goldCustomerValidator.Validate(myCustomer);


Resultados de una validación

El método de validación retornará el resultado en una instancia de la clase ValidationResults que es una colección de objetos ValidationResult los cuales tienen las siguientes propiedades:

Property

Description

Key

Nombre que identifica la ubicación del validador. Ej:”Nombre” significa que se colocó un validador en la propiedad nombre de un objeto Cliente.

Object

Puntero al objeto que fue validado

Message

Describe la falla de la validación

Tag

Valor ingresado por código que describe el resultado, se utilize para clasificar o filtrar

Target

Validador que falló



Herencia

Las reglas de validación se aplican a través de la jerarquía de clases. Si una clase hereda un miembro de de otra y no lo sobrecarga se aplican los validadores de la clase de la cual hereda. Si una clase hereda un miembro y lo sobrecarga, entonces no se aplican las validaciones especificadas en la clase de la cual hereda.

Crear un nuevo validador

Se pueden crear clases validadoras, pueden validar tipos de datos de nuevas formas o pueden validar datos complejos como instancias de la clase Cliente.

Para esto se puede heredar de las clases:

  • Validator<T>, para crear validadores fuertemente tipados.
  • Validator

Crear un nuevo atributo perzonalizado

Se pueden crear atributos personalizados heredando de la clase ValidatorAttribute.

Integración con WinForms
Validation Application Block tiene la capacidad de trabajar en conjunto con el objeto ErrorProvider para mostrar el resultado de las validaciones directamente en los controles con el clásico ícono rojo.
Esto se realiza soltando un control ErrorProvider en el Form deseado y luego soltando un control ValidatorProvider (Que debe ser obtenido partir de la biblioteca de Microsoft.Practices.EnterpriseLibrary.Validation.Integration.WinForms.
Cada control ValidatorProvider que se suelte sobre el formulario adiciona 3 nuevas propiedades para cada control del formulario que pueden ser accedidas desde la grilla de propiedades. Estas propiedades son: PerformValidation, SourcePropertyName y ValidatedProperty.
Para que el formulario valide automáticamente los controles debemos efectuar los siguientes pasos:

  1.  
    1. ErrorProvider: seleccionar el control ErrorProvider deseado del formulario.
    2. Enabled: debe ser igual a True
    3. RulesetName: debe ser igual a la regla deseada si no se utilizó este parámetro en los atributos se puede dejar vacío.
    4. SourceTypeName: Se especifica el camino de namespace hasta la clase contiene las validaciones seguido por el nombre de la biblioteca donde se encuentre.
    5. Ej: SourceTypeName = Entidades.Cliente, Entidades
    6. SpecificationSource: declara desde donde se obtienen las reglas de validación, puede ser desde atributos, archivo de configuración o ambos.
    1. PerformValidation: boleano, true para que el control sea validado con el ErrorProvider.
    2. SourcePropertyName: nombre del campo que tiene definida una validación. Ej. SourcePropertyName=Nombre, si definimos por ejemplo una validación mediante el atributo [NotNullValidator] en la propiedad Nombre de la clase Cliente
    3. ValidatedProperty: nombre de la propiedad del control desde la cual se obtendrá el valor para efectuar la validación. Por ejemplo si el control fuera un TextBox usaríamos ValidatedProperty = Text.
  2. 1. Configurar las propiedades del Control ErrorProvider: 2. Configurar las siguientes propiedades de los controles que se deseen que participen de las validaciones:


Ejemplo de una clase Validator y una clase ValidatorAttribute Personalizado

 [ConfigurationElementType(typeof(CustomValidatorData))]
 public class PercentageValidator: Validator<decimal>
 {
        public PercentageValidator(NameValueCollection attributes) : base(null, null)
        {
        }
 
        public PercentageValidator() : this(null)
        {
        }
 
        protected override void DoValidate(decimal objectToValidate, object currentTarget, 
        string key, ValidationResults validationResults)
        {
            if (objectToValidate < 0 || objectToValidate > 100)
            {
                validationResults.AddResult(new 
                 ValidationResult("El valor debe estar entre 0 y 100.", currentTarget, "Decimal", "", this));
            }
        }
 
        protected override string DefaultMessageTemplate
        {
            get { return "Valor inválido"; }
        }
 }
 
 public class PercentageValidatorAttribute : ValidatorAttribute
 {
        public PercentageValidatorAttribute()
        {
        }
 
        protected override Validator DoCreateValidator(Type targetType)
        {
            return new PercentageValidator();
        }
 }
 
 public class ObjetoTest
 {
        private string nombre;
        private decimal valor;
 
        [PercentageValidator()] //Mi Custom Validator
        public decimal Valor
        {
            get { return valor; }
            set { valor = value; }
        }
 
        [NotNullValidator,StringLengthValidator(1,50)]
        public string Nombre
        {
            get { return nombre; }
            set { nombre = value; }
        }
 }


Como se dijo anteriormente, Application Validation Block permite manejar las reglas de validación mediante el archivo de configuración. El archivo puede ser editado mediante la herramienta “Edit Enterprise Library Configuration”, por ejemplo agregamos una sección de Validation Block y luego se selecciona las clases a validar a partir de ensamblados. Especificamos para cada clase los miembros que serán validados y seleccionamos los Validators deseados y especificamos sus parámetros. También podemos especificar las clases que usen SelfValidation.


Este es un ejemplo de un archivo de configuración, con la definición de validaciones.

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <configSections>
    <section name="validation" type="Microsoft.Practices./>
      EnterpriseLibrary.Validation.Configuration.
      ValidationSettings,
      Microsoft.Practices.EnterpriseLibrary.Validation"
  </configSections>
  <validation>
    <type name="EntLib3.Subscriber" defaultRule="default">
      <rule name="default">
        <properties>
          <property name="Name">
            <add name="NameNotNull" type="Microsoft.Practices. />
                 EnterpriseLibrary.
                 Validation.Validators.NotNullValidator,
                 Microsoft.Practices.
                 EnterpriseLibrary.Validation"
            <add name="NameLength" type="Microsoft.Practices.
                 EnterpriseLibrary.
                 Validation.Validators.StringLengthValidator,
                 Microsoft.
                 Practices.EnterpriseLibrary.Validation"
                 lowerBound="1"
                 upperBound="200" lowerBoundType="Inclusive"
                 upperBoundType="Inclusive"/>
          </property>
          <property name="EmailAddress">
            <add name="EmailAddressNotNull" type="Microsoft. />
                Practices.
                 EnterpriseLibrary.Validation.Validators.
                 NotNullValidator,
                 Microsoft.Practices.EnterpriseLibrary.
                 Validation"
            <add name="EmailAddressLength" type="Microsoft.
                 Practices.
                 EnterpriseLibrary.Validation.Validators.
                 StringLengthValidator,
                 Microsoft.Practices.EnterpriseLibrary.
                 Validation"
                 lowerBound="1"
                 upperBound="200" lowerBoundType="Inclusive"
                 upperBoundType="Inclusive"/>
          </property>          
        </properties>
      </rule>
    </type>
  </validation>
</configuration>

 

 

Tags: ,

.NET

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