miércoles, 30 de septiembre de 2009

Reglas en Workflow Foundation

Workflow Foundation es una tecnología que nos permite definir e implementar flujos de trabajo para nuestras aplicaciones de una manera sencilla y sin necesidad de escribir cuantiosas líneas de código, ya que esta tecnología encapsula en sí misma diversas funcionalidades necesarias para la ejecución y control de dichos flujos.
Para la implementación de estos flujos necesitamos implementar reglas que nos permitan tomar desiciones, es decir, actuar según sea el camino tomado.
Primero vamos a crear un nuevo proyecto, por lo que seleccionaremos:
File -
    New Project - 
           Sequential Workflow Console Application





Una vez que creamos el proyecto, arrastramos del toolbox la condición "IfElse". Por lo que nos quedará de la siguiente manera.





 Una vez añadida la condición, iremos al codigo (click derecho - View Code). En él crearemos una variable pública de tipo entero llamada edad. Luego debajo de InitializeComponent(); le asignaremos un valor (en este caso edad = 25).
Luego volveremos al diseño y configuraremos las reglas. La actividad IfElse requiere que le asignemos la condición que evaluará para determinar si es verdadera o falsa. Para hacer esto seleccionemos la actividad IfElseBranchActivity1 en el diseñador y asignemos la propiedad Condition en la ventana de propiedades (si la ventana de propiedades no es visible en este momento selecciónela del menú View->Properties Window). Si expandimos la lista desplegable de la propiedad Condition se nos presentan dos opciones: Code Condition y Declarative Rule Condition tal y como lo muestra la siguiente imágen.


 


La primera opción nos permite especificar el nombre de un método que deseemos que sirva como expresión condicional. Asimismo, la segunda opción nos permite definir una regla de manera declarativa que sirva como expresión condicional. 
Seleccionamos la segunda opción y tendremos dos nuevas opciones (Condition Name - Expression), en la siguiente imágen podemos verlo claramente.






Luego hacemos click en el botón "...", y aparecerá la siguiente ventana para crear las reglas:





Haremos click en New... , e iremos a una caja de dialogo que escribiremos lo siguiente:


 


Ahora bien, tenemos configurada la regla, pero tenemos que añadir alguna actividad a realizar según el camino que siga, por lo tanto vamos a añadir dos "Code" del toolbox arrastrandolos, como podemos ver en la siguiente imágen.





 Para finalizar vamos simplemente a codificar "codeActivity1" y "codeActivity2". Como en IfElseBranchActivity1 la regla es que sea mayor a 17 años, entonces si pasa por esta rama, es decir por "codeActivity1", pondremos que la persona es mayor de edad, mientras que si pasa por la otra será menor de edad.


Para ello haremos doble click sobre la actividad y escribiremos el siguiente código, en cada una de ellas:


     private void codeActivity1_ExecuteCode(object sender, EventArgs e)
     {
         Console.WriteLine("La persona es mayor de edad.");
         Console.ReadLine();
     }

     private void codeActivity2_ExecuteCode_1(object sender, EventArgs e)
     {
         Console.WriteLine("La persona es menor de edad.");
         Console.ReadLine();
     }  



Para finalizar corremos el programa, y teniendo en cuenta que la edad ingresada había sido 25, entonces vemos como se aplica la regla.
 

Para verificar que se cumple la regla, se puede cambiar la edad en el código ( edad = 15;), y veremos lo siguiente.





miércoles, 16 de septiembre de 2009

Delegados

Un delegado es un tipo que hace referencia a un método. Cuando se asigna un método a un delegado, éste se comporta exactamente como el método. El método delegado se puede utilizar como cualquier otro método, con parámetros y un valor devuelto.

Comenzamos creando un proyecto de escritorio en C#, al que llamaremos Delegados:

 
Luego añadimos una clase al proyecto para crear un método, la cual se llamará Clase.
Hacemos click derecho sobre el proyecto en el Explorador de Solución y aparecera el siguiente menú:

 
  
Una vez creada la clase escribiremos en ella el siguiente código (método que nos devuelve un string):
public string despedida()
        {
            return "Buen viaje";
        } 
Luego en el codigo del formulario declararemos los delegados y otro método, que serán utilizados posteriormente, mediante el siguiente código:
public delegate void saludo1();
public delegate string despedida1();
      
public static void bienvenida()
{
    MessageBox.Show("Hola");
}

Luego en el formulario agregaremos un botón (button desde el toolbox y arrastrar hasta el formulario). Una vez creado el botón (podemos cambiarle el nombre mediante las propiedades) haremos doble click y nos llevará al evento click del mismo, donde escribiremos el siguiente código:
 
saludo1 misaludo = new saludo1(bienvenida);
misaludo.Invoke();
            
Clase clase = new Clase();
despedida1 midespedida = new despedida1(clase.despedida);
MessageBox.Show(midespedida.Invoke());
En las primeras dos líneas podemos ver la instanciación de un delegado haciendo referencia a un método.
En la tercera línea instanciamos la clase, para luego en la cuarta línea poder llamar al método en la instanciación del delegado.

El código final en el formulario quedaría de la siguiente manera:

Una vez que corremos el proyecto obtendremos lo siguiente:

 
Al hacer click en el boton se llamará al método declarado en el formulario mediante el delegado saludo1, y obtendremos lo siguiente:
 
 Luego de hacer click se llama al método creado en la clase mediante el delegado despedida1, y obtendremos lo siguiente:

 
De esta manera podemos ver un ejemplo de como utilizar delegados.

Métodos de Extensión

Los métodos de extensión constituyen un tipo especial de método estático, pero se les llama como si se tratasen de métodos de instancia en el tipo extendido.
Para comenzar creamos un proyecto de consola C#, al cual llamaremos MetodoDeExtension:

 
Luego añadiremos una clase para crear un método, a la cual llamaremos metodo de MetodoDeExtension1:
  
Una vez creada la clase escribiremos el siguiente código en ella:
public static int ContadorDePalabras (this String texto)
           {
            return texto.Split(new char[] { ' ', '.', '?' }, StringSplitOptions.RemoveEmptyEntries).Length;
           }
          

El método recibe por parámetro un texto y retorna la cantidad de palabras que contiene el mismo.
Luego de crear el método iremos al programa principal y escribiremos el siguiente código:
            string texto = "Mis métodos de extension. Contador de palabras.";
            int i = texto.ContadorDePalabras();
            Console.WriteLine(texto);
            Console.WriteLine("El texto contiene " + i + " palabras.");
            Console.ReadLine();
           

En la primer línea declaramos el texto, en la segunda línea llamamos al método, en la tercer y cuarta línea imprimimos en pantalla el texto y el resultado del método respectivamente.
Cuando corremos el proyecto obtendremos lo siguiente:
Otro ejemplo es crear un método que se encargue de hacer todo sin paso de parámetros, es decir, añadimos una clase nuevamente a la cual llamaremos MetodoDeExtension2 y dento de ella escribiremos el siguiente código:
 public static void OrdenarEnteros()
        {       
        int[] enteros = { 10, 45, 15, 39, 21, 26 };       
        Console.WriteLine(" ");       
            foreach (var i in enteros)
            {
                System.Console.Write(i + " ");
            }
        var result = enteros.OrderBy(g => g);       
        Console.WriteLine(" ");
        Console.WriteLine("Ordenamos la lista de enteros.");
        Console.WriteLine(" ");
        foreach (var i in result)
            {
                System.Console.Write(i + " ");
            }
        }


Luego en el programa principal escribimos el siguiente código para llamar al método:
        MetodoDeExtension2.OrdenarEnteros();
Por lo que el código del programa principal nos quedaría:
namespace MetodosDeExtension
{
    class Program
    {
        static void Main(string[] args)
        {
            string texto = "Mis métodos de extension. Contador de palabras.";
            int i = texto.ContadorDePalabras();
            Console.WriteLine(texto);
            Console.WriteLine("El texto contiene " + i + " palabras.");
            MetodoDeExtension2.OrdenarEnteros();
            Console.ReadLine();        
        }
    }
}

Cuando corremos el proyecto obtendremos:
 
En el último método estamos utilizando expresión lambda (g => g) e inferencia de datos (var result), estos temas serán tratados próximamente.

De esta manera podemos ver dos formas de como trabajar con métodos de extensión.

miércoles, 2 de septiembre de 2009

Seguridad en ASP.NET

Seguridad

En primer lugar en esta guía, en la que brindaremos seguridad a una página Web, mostraremos como organizar en carpetas en el explorador de soluciones las diferentes partes del sitio para luego configurar los accesos y permisos a las mismas. Utilizaremos el Visual Studio 2005 y abriremos un nuevo sitio Web
ASP.Net.
Para comenzar vamos a utilizar el control Login de nuestro cuadro de herramientas.



Además en las propiedades de este control podemos direccionar el logueo del usuario hacia una página del sitio. La propiedad usada es DestinationPageUrl.
Con clic derecho sobre el control Login abrimos la etiqueta inteligente en donde podemos darle un formato automático.



En la etiqueta inteligente también podemos acceder al administrador del sitio Web.




Dentro del administrador del sitio Web en la pestaña seguridad daremos de alta los usuarios, los roles y también podremos configurar los permisos a las diferentes carpetas del sitio.



En la sección de reglas de acceso configuramos las mismas seleccionando la carpeta a la que deseemos aplicarle un permiso y a qué usuarios o funciones se aplicará la regla.



Ahora vamos a seguir conociendo los demás controles de Inicio de sesión. El registro de usuarios se puede realizar por el administrador Web como ya vimos o por el control CreateUserWizard que a continuación mostramos.


Otro control muy útil de Inicio de sesión es el ChangePassword, para el caso en que el usuario registrado quiera cambiar su contraseña.


Aquí observamos el control PasswordRecovery para recuperar la contraseña en caso de olvidarla y recibir en nuestro correo la nueva contraseña.

Para que la sitio Web envíe la nueva contraseña de la cuenta debemos configurar el servidor SMTP, esto lo realizamos en la pestaña Aplicación de el administrador Web.



Dos controles que utilizamos también son el LoginStatus y el LoginName, el primero visualiza el estado de la sesión y la posibilidad de cambiar ese estado y el segundo muestra el nombre del usuario logueado si es que existe uno.


Por último vamos a mostrar como utilizamos los hipervínculos para darle navegabilidad a la página. En las propiedades, en NavigateUrl elegimos la página a la cual queremos que nos direccione la página Web.

Cambiar Contraseña

 
Se agradece el aporte a José Bertoli.

lunes, 31 de agosto de 2009

Manejo de Estados

Variable de Sesión

En este artículo vamos a ver manejos de estados a través de las variables de sesión y aplicación y a través de cookies.
En primer lugar, agrego dos elementos al proyecto, elementos del tipo Web Form, para poder luego hacer referencia entre las páginas y mostrar la variable.


En la página principal agregamos una serie de tools, un label que contiene un mensaje del texto a ingresar, un textbox que es el mensaje ingresado (variable de sesión) y un button que nos va a conectar con la siguiente página.



 Luego hacemos doble click sobre el botón (página siguiente) de la página principal, en este evento (evento click del botón) creamos la variable de sesión y referenciamos la siguiente página con el siguiente código:

protected void Button3_Click(object sender, EventArgs e)
{
         Session.Add("Nombre", this.TextBox1.Text);
         Response.Redirect("~/Sitio/Pagina2.aspx");
}

En la página secundaria donde se va a mostrar la variable se agrega un label y se codifica lo siguiente:

protected void Page_Load(object sender, EventArgs e)
{
         this.Label2.Text = "Bienvenido " + Session["Nombre"].ToString();
}


Una vez realizado esto, se ejecuta y como resultado se obtendrá lo siguiente:


Una vez ingresado el nombre, hacemos click sobre el botón y se obtendrá lo siguiente:

Variables de Aplicación

Siguiendo con el proyecto de “Variable de Sesión”, para poder utilizar Variables de Aplicación debemos añadir al proyectoun elemento del tipo Global.asax, en el cual se va a crear la variable. 

Una vez dentro de Global.asax podemos ver las distintas opciones, para manejar por ejemplo información de inicio desesión (Session_Start) y de fin de sesión (Session_End), de inicio y fin de la aplicación. Nosotros vamos a crear una variable de aplicación llamada “Contador” inicializada en cero dentro de inicio de la aplicación (Aplication_Start), que se encarga de contar la cantidad de visitantes de la página. Para ello vamos a ingresar el siguiente código:

protected void Application_Start(object sender, EventArgs e)
{
          Application.Add("Contador",0);
}

Una vez creada la variable en el Global.asax, vamos a ir a la página principal y en la carga de la página (Load) ingresamos el siguiente código:

protected void Page_Load(object sender, EventArgs e)
{
        Application.Lock();
        Application["Contador"] = (int)Application["Contador"] + 1;
        Application.UnLock();
        Response.Write ("Usted es el visitante: " + Application["Contador"].ToString());
}

La segunda línea de código es la que se encarga de incrementar el contador cada vez que se carga la página y la última línea de código se encarga de mostrar el valor del contador. Mientras que la primera y la tercera es para evitar problemas de concurrencia en la página debido a que la variable es pública.
Hay que tener en cuenta que esta variable va a volver a cero cada vez que se reinicie el Internet Information Server, para que el contador no vuelva a cero se puede asociar la variable a un archivo que persista el valor.


Una vez listo esto ejecutamos el proyecto y obtendremos:

 
Y cada vez que refresquemos la página (F5), o salgamos y volvamos a entrar el contador aumentará, en este caso la página se refresco 3 veces.

 
Cookies
Para utilizar las cookies añadimos en la página principal un label y text box, y añadimos al botón (página siguiente) ya existente el código para crear la cookie. Por lo que quedaría de la siguiente manera:


protected void Button3_Click(object sender, EventArgs e)
{
        Session.Add("Nombre", this.TextBox1.Text);
        Response.Cookies.Add(new HttpCookie ("Equipo",TextBox2.Text));
        Response.Redirect("~/Sitio/Pagina2.aspx");
}

Luego en la página secundaria a la que hace referencia el botón, se le agrega un label en el cual se va a mostrar la cookie, para ello se agrega el siguiente código cuando se carga la página (load):


protected void Page_Load(object sender, EventArgs e)
{
          this.Label2.Text = "Bienvenido " + Session["Nombre"].ToString();
          lblequipo.Text = "Su equipo es: " + Request.Cookies["Equipo"].Value.ToString();
}

Una vez realizado estos pasos, al ejecutarse la aplicación se obtendrá lo siguiente:

Una vez ingresado el nombre y el eauipo, hacemos click sobre el botón y se obtendrá lo siguiente:

viernes, 28 de agosto de 2009

Creación de Master Page

En primer lugar, agrego un nuevo elemento al proyecto, un elemento del tipo Master Page, para crear un plantilla de la misma.

En él se define todo el diseño que se va a visualizar en todas las páginas que deseemos del proyecto.

Luego agrego una Content Page haciendo clic derecho en el elemento MasterPage.master y seleccionando Add Content Page. Ésta página será asignada al ContentPlaceHolder de esa Master Page.
El código HTML de la cabecera de las páginas que no pertenecen a ninguna Master Page es el siguiente:

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="Default3" %>


Y cuando pertenecen a una Master Page, se visualiza de esta manera:

<%@ Page Language="C#" MasterPageFile="~/MasterPage.master" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="Default" Title="Untitled Page" %>

Y en la última parte, se especifica en que ContentPlaceHolder va a mostrarse la página:

Runat="Server">


Observamos que cuando modificamos el diseño de las Content Pages, no se puede modificar nada del Master Page.
Por último, agregamos otra página de contenido al sitio para crear navegabilidad añadiendo unos botones:




Se agradece el aporte a Mauro Luque.