gabriel.oliva posted on November 20, 2009 18:17

 

 

 

 

 

 

 

 

 

 

 

 

 

Descarga en PDF la edicion numero 21 de The Architecture Journal

AJ21_EN.zip (2.53 mb)

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Una de las cosas mas difíciles para un arquitecto de software es intentar ordenar algo que desde el inicio no fue diseñado como se esperaba, no todo esta perdido, es posible reestructurar lo que se construyó sin tener que reescribirlo nuevamente desde cero, aquí les dejo una excelente presentación de Dan North en donde comparte experiencias personales y estrategias que les ayudaran a atender puntos críticos durante este proceso.

Pimp my architecture !

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:
gabriel.oliva posted on November 17, 2009 21:04

Me dormi hasta las 6:30 de la mañana de hoy terminando de instalar mi maquina de desarrollo y la verdad es que valio la pena, estoy jugando un poco con windows 7 y parece que todo funciona de maravilla, ya les estare platicando como me va y si todo funciona a la perfeccion, hasta el momento realmente nada de que preocuparse ... lo unico fue que la instalacion de VSTS 2005 no pudo terminar 'perfectamente' pues por un issue de compatibilidad no pudo instalar SQL Express 2005 .. pero pensaba instalarle el standard asi que no me importo mucho ... en fin seguiremos jugando un rato con Windows.

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in: General  Tags:
gabriel.oliva posted on November 11, 2009 01:10

Estoy simplemente impresionado por esto ... es un IDE muy parecido a Visual Studio pero para el browser, con la opcion de crear diferentes tipos de soluciones, descargarlas empacadas en un zip, ejecutarlas online y hasta hacer el deploy ... a la nube !!!

increible

 

 

http://coderun.com/ide/ 

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in: Development / Desarrollo , IT Industry  Tags:
gabriel.oliva posted on November 9, 2009 16:41

Posted in: General , IT Industry , MSDN  Tags:

Descarga

Puedes descargar un proyecto con más ejemplos del uso de NHibernate en:

http://codebetter.com/files/folders/codebetter_downloads/entry172562.aspx. El código esta extensamente documentado para explicar varios aspectos del uso de NHibernate. (Si el vinculo de de arriba no funciona, puedes tratar de descargarlo de esta dirección alterna: http://openmymind.net/CodeBetter.Foundations.zip).

En este capítulo

Solo hemos tocado un poco de lo que puedes hacer con NHibernate. No hemos visto las consultas por criterio (que es una API de consulta más íntimamente ligada con tu dominio) sus capacidades de cache, filtrado de colecciones, optimización del rendimiento, registro de bitácoras, o capacidades nativas de SQL. Más allá de la herramienta de NHibernate, afortunadamente es muy probable que hayas aprendido más acerca de cómo definir relaciones entre objetos y estructuras relacionales, y soluciones alternativas de la limitada cesta incluida dentro de .NET. Es difícil abandonar el SQL escrito a mano, ir mas allá de lo que es cómodo, es imposible ignorar los beneficios de las definiciones de conversión entre objetos y estructuras relacionales.

 

¡Estas mas allá de la mitad del camino! Espero que estés disfrutando y aprendiendo mucho. Este puede ser un buen momento para tomar un descanso de la lectura y poner manos a la obra con la aplicación gratuita de aprendizaje Canvas.

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:

Carga diferida

Cuando cargamos un vendedor, haciendo algo como esto: SalesPerson person = session.Get<SalesPerson>(1); la colección Sales no será cargada. Esto es porque, por defecto,  las colecciones son cargadas de manera diferida. Esto es, que no tocaremos la base de datos hasta que la información sea específicamente solicitada (ej. Podemos acceder a la propiedad Sales). Podemos invalidar este comportamiento cambiando la configuración lazy=”false” en el elemento bag.

 

La otra, más interesante, estrategia de carga implementada por NHibernate está en las entidades en sí mismas. Frecuentemente querrás agregar una referencia a un objeto sin tener que cargar el objeto real desde la base de datos. Por ejemplo, cuando agregamos una venta (Sales) a un vendedor (SalesPerson), necesitamos especificar el modelo (Model), pero no queremos cargar cada propiedad / lo único que queremos es obtener el Id para poder guardarlo en la columna ModelId de la tabla Sales. Cuando usas session.Load<T> (id) NHibernate cargara un proxy del objeto actual (a menos de que especifiques lazy=”false” en el elemento clase). Hasta donde puede importarte, el proxy se comporta exactamente igual que el objeto real, pero ningún dato será extraído de la base de datos hasta la primera vez que lo solicitas. Esto hace posible escribir el siguiente código:

Sale sale = new Sale(session.Load<Model>(1), DateTime.Now, 46000.00);

salesPerson.AddSales(sale);

session.SaveOrUpdate(salesPerson);

Sin tener que tocar siquiera la base de datos para cargar el objeto Model.

 

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:

Consultas

NHibernate soporta dos diferentes tipos de esquemas para realizar consultas: Hibernate Query Language (HQL) y Consultas de Criterios (también puedes realizar consultas en SQL convencional, pero perderá portabilidad al hacerlo). HQL es la forma más sencilla de las 2 ya que se parece mucho a SQL – usas From, where, aggregates, order by, group by, etc. Sin embargo en vez de consultar directamente contra tus tablas, escribes consultas contra tu dominio -  lo que significa que HQL soporta los principios de la orientación a objetos tales como la herencia y el polimorfismo. Ambos métodos de consulta son abstracciones arriba de SQL, lo que significa que obtienes portabilidad total – lo único que necesitas hacer para dirigirse a una base de datos diferente es cambiar la configuración de su dialecto.

Con la liberación de .NET 3.5 finalmente se ha agregado una colección  HashSet al marco de trabajo. Idealmente, versiones futuras agregaran otro tipo de conjuntos con un OrderedSet. Los conjuntos son colecciones muy útiles y eficientes, ¡así que considera agregarlos a tu arsenal de herramientas! Puedes aprender más leyendo el artículo en el que Jason Smith describe los conjuntos.

 

HQL funciona a partir de la interfaz IQuery, que se crea con la invocación del método CreateQuery en tu sesión. Con IQuery puedes regresar entidades individuales, colecciones, parámetros substitutos y más. Aquí hay algunos ejemplos:

 

string lastName = "allen";

ISession session = _sessionFactory.OpenSession();

//retrieve a salesperson by last name

IQuery query = s.CreateQuery("from SalesPerson p where p.LastName =

'allen'");

SalesPerson p = query.UniqueResult<SalesPerson>();

//same as above but in 1 line, and with the last name as a variable

SalesPerson p = session.CreateQuery("from SalesPerson p where p.LastName = ?").SetString(0, lastName).UniqueResult<SalesPerson>();

//people with few sales

IList<SalesPerson> slackers = session.CreateQuery("from SalesPerson person where size(person.Sales) < 5").List<SalesPerson>();

 

Esta es solo una muestra de lo que se puede hacer con HQL (el ejemplo que puede descargarse tiene algunos ejemplos ligeramente más complicados).

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:

Relaciones

En nuestro sistema, es importante que rastreemos las ventas – específicamente con relación a la fuerza de ventas, de tal forma que podamos proveer algunos reportes básicos. Se nos ha dicho que una venta solo puede pertenecer a un vendedor, y así establecer una relación uno-a-muchos esto es, un agente de ventas puede tener múltiples ventas, y una venta solo puede pertenecer a un único vendedor. En nuestra base de datos, la relación está representada como una columna  SalesPersonId en la tabla Sales (llave foránea). En nuestro dominio, la clase SalesPerson tiene una colección de Sales y la clase Sales tiene una propiedad SalesPerson (Referencia).

 

Ambos extremos de la relación necesitan ser configurados en el archivo de definición de conversiones apropiado, En el extremo de Sales, que se relaciona con una propiedad única, usamos un elemento property glorificado llamado many-to-one;

 

...

<many-to-one name="SalesPerson"

class="SalesPerson"

column="SalesPersonId"

not-null="true"/>

...

 

Estamos especificando el nombre de la propiedad, el tipo/clase, y el nombre de la columna que es la llave foránea. También estamos especificando una limitante extra, que es, que cuando agregamos un nuevo objeto Sales, la propiedad SalesPerson no puede ser nula.

 

El otro lado de la relación, la colección de ventas (Sales) que tiene un vendedor (SalesPerson), es un poco más complicada – básicamente porque la terminología de NHibernate no pertenece a la jerga estándar usada en .NET. Para configurar una colección usamos un elemento de tipo set, list, map, bag o array. Tu primera inclinación puede ser usar una lista, pero NHibernate requiere que tengas una columna que especifique el índice. En otras palabras, el equipo de NHibernate ve una lista como una colección donde el índice es importante, y por lo tanto debe ser especificado. Lo que la mayoría de los desarrolladores de .NET entienden como un list, NHibernate lo llama una bolsa (Bag).   Siendo algo confuso tal vez, tanto si utilizas un elemento list o bag, tu tipo de dominio debe ser un IList (o su equivalente genérico IList<T>). Esto es debido a que .NET no cuenta con un objeto IBag, En resumen, para las colecciones que uses comúnmente, utiliza el elemento bag y haz tu propiedad del tipo IList.

La otra opción interesante de colección es el set (conjunto). Un conjunto es una colección que no puede contener duplicados- un escenario común para una aplicación empresarial (aunque rara vez se afirma explícitamente). Extrañamente, .NET no tiene una colección de tipo conjunto, asi que NHibernate usa la interfaz Iesi.Collection.ISet. Existen 4 implementaciones especificas, ListSet que es realmente rápida para colecciones muy pequeñas (10 elementos o menos), SortedSet que puede ser ordenada, HashSet la cual es rápida para colecciones más grandes y HybridSet la cual usa inicialmente un ListSet y automáticamente se cambia así misma a un HashSet conforme crece tu colección.

 

Para nuestro sistema usaremos un objeto bag (aún cuando no podemos tener ventas duplicadas , es mucho más sencillo por el momento), así que declaramos nuestra colección de Sales como un IList.

 

private IList<Sale> _sales;

public IList<Sale> Sales

{

get { return _sales;}

}

 

Y agregamos nuestro elemento <bag> al archivo de definición de conversiones para SalesPersons:

<bag name="Sales" access="field.lowercase-underscore"

table="Sales" inverse="true" cascade="all">

<key column="SalesPersonId" />

<one-to-many class="Sale" />

</bag>

 

De nuevo, si observas a cada elemento/atributo, no es tan complicado como podría verse al principio. Identificamos el nombre de nuestra propiedad, especifica la estrategia de acceso (no tenemos un configurador, así que hay que indicarle que use el campo con nuestra convención de nombres), la tabla y la columna que contienen la llave foránea, y el tipo/clase de los elementos en la colección.

 

Tambien hemos configurado el atributo cascade a all lo que significa que cuando nosotros invoquemos la actualización (update) en un objeto del tipo SalesPerson, cualquier cambio que sea hecho a su colección de ventas (Sales) (adiciones, remociones, cambios a las ventas existentes) será automáticamente persistido. La actualización en cascada puede ser un buen ahorrador de tiempo conforme tu sistema crece en complejidad.

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:

Configuración

El secreto para la sorprendente flexibilidad de NHibernate radica en su configurabilidad, Inicialmente el proceso de configurarlo puede ser más bien desalentador, pero después de un proyecto de prueba se vuelve natural. El primer paso es configurar el propio NHibernate. LA configuración más simple, que debe ser agregada a tu app.config o web.config se ve así:

 

<configuration>

<configSections>

<section name="hibernate-configuration"

type="NHibernate.Cfg.ConfigurationSectionHandler, NHibernate" />

</configSections>

<hibernate-configuration xmlns="urn:nhibernate-configuration-2.2">

<session-factory>

<property name="hibernate.dialect">

NHibernate.Dialect.MsSql2005Dialect

</property>

<property name="hibernate.connection.provider">

NHibernate.Connection.DriverConnectionProvider

</property>

<property name="hibernate.connection.connection_string">

Server=SERVER;Initial Catalog=DB;User Id=USER;Password=PASSWORD;

</property>

<mapping assembly="CodeBetter.Foundations" />

</session-factory>

</hibernate-configuration>

</configuration>

Recuerda que nuestro objetivo es ampliar nuestra base de conocimientos viendo diferentes formas de construir sistemas con el fin de proveer un mayor valor a nuestros clientes. Mientras que podríamos hacerlo hablando específicamente de NHibernate, el objetivo es introducir el concepto de Definiciones de conversión Entidad relacional / Objeto, y tratar de corregir la fe ciega que tienen puesta los desarrolladores de .NET en los procedimientos almacenados y ADO.NET

 

De los 4 valores, dialect es el más interesante, este le dice a NHibernate que lenguaje específico habla nuestra base de datos. Sí, en nuestro código, le pedimos a NHibernate que regrese un resultado paginado de Cars y nuestro dialecto está configurado para SQL Server 2005, NHibernate emitirá una sentencia de SELECT utilizando la función de ranking ROW_NUMBER (). Sin embargo, si el dialecto está configurado a MySql, NHibernate emitirá el SELECT con LIMIT. En la mayoría de los casos, configurarás esto una sola vez y te olvidarás del tema. Pero esto proporciona algunos conocimientos sobre las capacidades provistas por la capa que genera todo tu código de acceso a datos.

 

En nuestra configuración, también le dijimos a NHibernate que nuestros archivos de definición de conversión estaban localizados en el ensamblado CodeBetter.Foundations. Los archivos de definición  son archivos incrustados de XML que le dicen a NHibernate como debe ser persistida cada clase. Con esta información, NHibernate es capaz de regresar un objeto de tipo Car (automóvil) cuando tú se lo solicites, así como salvarlo. La convención general es tener un archivo de definición de conversión por cada objeto de dominio, y que estos se localicen dentro de la carpeta Mappings. El archivo de definición para nuestro objeto Model (Modelo), llamado Model.hbm.xml, se ve de esta forma:

 

<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2"

assembly="CodeBetter.Foundations"

namespace="CodeBetter.Foundations">

<class name="Model" table="Models" lazy="true" proxy="Model">

<id name="Id" column="Id" type="int" access="field.lowercase-underscore">

<generator class="native" />

</id>

<property name="Name" column="Name"

type="string" not-null="true" length="64" />

<property name="Description" column="Description"

type="string" not-null="true" />

<property name="Price" column="Price"

type="double" not-null="true" />

</class>

</hibernate-mapping>

 

(Es importante asegurarse de que el parámetro Build Action para todos los archivos de definición de conversiones se configuren como Embedded Resources)

 

Este archivo le dice a NHibernate que la clase Model se refiere a registros en la tabla Models, y que las 4 propiedades Id, Name, Description y Price se refieren a las columnas Id, Name, Description, y Price. La información extra alrededor de la propiedad Id especifica que el valor es generado por la base de datos (en contraposición a NHibernate (para soluciones residentes en clústeres o grupos de servidores),  o nuestro propio algoritmo) y que no hay configurador, así que deberá ingresar a través del campo con la convención de nombres especificada (proveemos Id como el nombre y la estrategia de nomenclatura con minúsculas y guión bajo (lowercase-underscore), para que use el campo llamado _id.

 

Con el archivo de definición de conversiones configurado, podemos comenzar a interactuar con la base de datos:

private static ISessionFactory _sessionFactory;

public void Sample()

{

//Let's add a new car model

Model model = new Model();

model.Name = "Hummbee";

model.Description = "Great handling, built-in GPS to always find your

way back home, Hummbee2Hummbe(tm) communication";

model.Price = 50000.00;

ISession session = _sessionFactory.OpenSession();

session.Save(model);

//Let's discount the x149 model

IQuery query = session.CreateQuery("from Model model where model.Name = ?");

Model model = query.SetString(0, "X149").UniqueResult<Model>();

model.Price -= 5000;

ISession session = _sessionFactory.OpenSession();

session.Update(model);

}

 

El ejemplo de arriba muestra lo fácil que es persistir nuevos objetos a la base de datos, extraerlos y actualizarlos – todo esto sin el uso directo de ADO.NET o SQL.

 

Tal vez te estés preguntando de donde viene el objeto _sessionFactory, y que es exactamente un ISession. _sessionFactory (que implementa la interfaz ISessionFactory) es un objeto global seguro para el uso en hilos de ejecución el cual es muy probable que crees en el inicio de la aplicación. Típicamente necesitaras uno por cada base de datos que tu aplicación este usando (lo que significa que típicamente necesitaras solo uno), y su trabajo, como con la mayoría de las fabricas de objetos, es crear un objeto pre configurado: un objeto ISession no tiene equivalente en ADO.NET, pero si se relaciona con un bajo nivel de cohesión a una conexión de base de datos. Sin embargo, la creación de un ISession no necesariamente abre una conexión, En lugar de eso, el objeto ISession administra de forma inteligente los objetos de tipo conexión y comando por ti. A diferencia de las conexiones que deben ser abiertas tarde y cerradas de manera temprana, no tienes que preocuparte por tener objetos ISession alrededor por un rato (aún cuando estas no sean seguras para su procesamiento en hilos de ejecución). Si estas construyendo una aplicación ASP.NET, puedes abrir de forma segura un objeto que implemente ISession en el método BeginRequest y cerrarlo en el método EndRequest (o mejor aún, cargar de forma diferida en caso de que la solicitud específica no requiera un ISession).

 

La interfaz ITransaction es otra pieza del rompecabezas que es creada llamando el método BeginTransaction en un ISession. Es común para los desarrolladores de .NET ignorar la necesidad de usar transacciones dentro de sus aplicaciones. Esto es desafortunado ya que puede llevarnos a estados inestables e incluso irrecuperables de los datos. Un ITransaction es usado para mantener el rastro de la unidad de trabajo  - rastrear que cambio, o que ha sido agregado o borrado, averiguar qué y cómo aplicarlo a la base de datos, y proveer la capacidad de deshacer en caso de que un paso individual falle.

Digg It!DZone It!StumbleUponTechnoratiRedditDel.icio.usNewsVineFurlBlinkList

Posted in:   Tags:

IT Builder

Conoce mas de los servicios de IT Builder y la forma en la que podemos apoyarte a construir software de clase mundial

* Procesos para el desarrollo de software (CMMI, MSF, TSP, PSP, Moprosoft).
* Habilitacion de ambientes colaborativos y automatizacion con Visual Studio Team System.
* Arquitectura de aplicaciones bajo tecnologia Microsoft.
* Construccion de aplicaciones .NET.

www.itbuilder.com.mx
Imaginalo, nosotros lo construimos !

Calendar

«  September 2010  »
MoTuWeThFrSaSu
303112345
6789101112
13141516171819
20212223242526
27282930123
45678910
View posts in large calendar

MVP

MVP Factor


Disclaimer
The opinions expressed herein are my own personal opinions and do not represent my employer's view in anyway.

© Copyright 2010 ITB - Gabriel Oliva C.