martes, 19 de abril de 2011

Crear una sección personalizada en Umbraco (II)

prueba_umbraco

Creando el icono de la nueva sección

Antes que nada vamos a eliminar los archivos temporales situados en la ruta: \App_Data\TEMP, no olvidéis este paso porque me pasé un buen ratito hasta dar con la tecla de donde se encontraba la caché de la hoja de estilos.

Ahora, vamos a la carpeta \umbraco\images\tray\traySprites.png y modificamos el archivo gráfico con nuestro editor favorito, solo hemos de tener en cuenta que la separación entre iconos debe ser de 72 pixles.

Después, abrimos la hoja de estilos \umbraco\css\umbracoGui.css y añadimos la clase que creamos en la tabla UmbracoApp y campo appIcon

.trayjcantos { background-position: -18px -594px;}

Añadiendo el nombre de la sección al archivo de recurso local


Localizamos el archivo de recurso para el que hemos configurado el sitio web e idioma predeterminado, en nuestra caso \umbraco\config\lang\es.xml y añadimos la entrada:

<area alias="sections">
(...)
<key alias="jcantos">Javi Cantos</key>

Presta atención de que el valor de la propiedad alias en el elemento key debe ser el mismo que pusimos en la tabla UmbracoApp y campo appAlias



Incluyendo los nodos de la nueva sección


La inclusión de los nuevos nodos debe realizarse desde un proyecto externo de tipo asp.net y que después será referenciado y añadido al sitio web de umbraco.


Para la nueva sección crearemos dos páginas, la primera la llamaremos MantCategorias.aspx y la segunda MantProductos.aspx, cada una de estas páginas contiene la lógica necesaria para lo que pretendemos en cada caso, un mantenimiento de categorías y otro de productos.


Como el nombre de la aplicación que hemos elegido es jcantos debemos de:



  1. Crear un nuevo proyecto donde añadir las referencias umbraco.dll e interfaces.dll, estas la podéis encontrar en el directorio bin de umbraco.

  2. Añadimos dos páginas MantCategorias.aspx y MantProductos.aspx, aquí incluimos el código de la lógica para ambos mantenimientos.

  3. Creamos y añadimos una clase a nuestro proyecto a la que podemos llamar loadjcantos, este el tipo que debemos poner en el campo treeHandlerType de la tabla UmbracoAppTree

  4. Comprobamos el valor del campo treeHandlerAssembly de la tabla UmbracoAppTree, en nuestro caso PruebaUmbraco, sin la extensión .dll

  5. Por otra parte, crear una carpeta dentro del directorio umbraco que se llame jcantos, nos debería quedar así \umbraco\jcantos, en esta carpeta es donde copiamos los aspx mencionados anteriormente.

  6. Copiar al directorio bin de umbraco la librería resultante de nuestro nuevo proyecto.

Os dejo el código fuente de la clase loadjcantos:

using System;
using System.Text;
using umbraco.cms.presentation.Trees;

namespace PruebaUmbraco
{
public class loadjcantos : BaseTree
{
public loadNewsletter(string application)
: base(application)
{ }

protected override void CreateRootNode(ref XmlTreeNode rootNode)
{
rootNode.Icon = FolderIcon;
rootNode.OpenIcon = FolderIconOpen;
rootNode.NodeType = "init" + TreeAlias;
rootNode.NodeID = "init";
}

///
/// Override the render method to create the newsletter tree
///
///
public override void Render(ref XmlTree Tree)
{
// Nodo mantenimiento de categorías
var mtoCategorias = XmlTreeNode.Create(this);
mtoCategorias.Text = "Mantenimiento de categorías";
mtoCategorias.Icon = "docPic.gif";
mtoCategorias.Action = "javascript:openMtoCateogorias()";
// añadimos el nodo al árbol
Tree.Add(mtoCategorias);

// Nodo mantenimiento de productos
var mtoProductos = XmlTreeNode.Create(this);
mtoProductos.Text = "Mantenimiento de productos";
mtoProductos.Icon = "docPic.gif";
mtoProductos.Action = "javascript:openMtoProductos()";
// añadimos el nodo al árbol
Tree.Add(mtoProductos);
}

public override void RenderJS(ref StringBuilder Javascript)
{
Javascript.Append(@"
function openMtoCategorias() {
parent.right.document.location.href = 'jcantos/MantCategorias.aspx';
}
");

Javascript.Append(@"
function openMtoProductos() {
parent.right.document.location.href = 'jcantos/MantProductos.aspx';
}
");
}
}
}

Resultado final


El resultado final es una plena integración de componentes personalizados que pueden ser administrados directamente desde la propia plataforma, sin necesidad de crear nuevos espacios webs que contengan las piezas que no encajen en el estándar de Umbraco.


resultado_section


Fuente: http://www.geckonewmedia.com/blog/2009/8/3/how-to-create-a-custom-section-in-umbraco-4

viernes, 15 de abril de 2011

Crear una sección personalizada en Umbraco (I)

seccion_umbraco

Una de las cosas que más me ha sorprendido de este CMS es la cierta facilidad para crear nuevas secciones y ser incorporadas al panel de administración.

Con estas breves instrucciones que veremos a continuación vamos a tunear, tunear en todas sus reglas y además de forma oficial con nuevas características que nos permitirán poner nuestro CMS al doscientos por ciento.

Empezamos por la base de datos

Empezaremos por localizar las siguientes tablas en la nueva base de datos generada en la instalación de Umbraco.
  • umbracoApp, en esta tabla se almacén todas las secciones que se encuentran disponibles.
  • umbracoAppTree, aquí especificamos los datos del nuevo nodo como el nombre de la librería o la clase de inicialización.
  • umbracoUser2app, aquí definimos los permisos para la nueva sección.

 

Tabla UmbracoApp

  • sortOrder: indica el orden en el que aparecerá en la interfaz dentro del módulo secciones.
  • appAlias: simplemente un nombre identificativo, vaya el identificador.
  • appIcon: la clase CSS que representa al icono, ahora lo vemos.
  • appName: esto es un nombre descriptivo pero no prestéis atención porque el nombre definitivo será ajustado mediante archivos de configuración regional, ahora lo vemos.
  • appInitWithTreeAlias: valor NULL.

Tabla UmbracoAppTree

  • treeSilent: ponemos False.
  • treeInitialize: ponemos True.
  • treeSortOrder: ponemos un cero, será el primer elemento.
  • appAlias: el mismo de antes.
  • treeAlias: el mismo valor que appAlias.
  • treeTitle: el mismo valor que appAlias.
  • treeIconClosed: ponemos .sprTreeFolder.
  • treeIconOpen: ponemos .sprTreeFolder_o.
  • treeHandlerAssembly: este campo representa el nombre del ensamblado que contiene la clase para iniciar la nueva sección, por ejemplo si la libreria resultante es “holamundo.dll” pondríamos “holamundo”, obviando la extensión.
  • treeHandlerType: el nombre de la clase que contiene los métodos que ejecutarán la carga del árbol de la nueva sección, ahora lo vemos.
  • action: valor NULL.

Tabla UmbracoUser2app

En esta tabla es donde damos los permisos al usuario administrador para que acceda a la nueva sección.

  • user: ponemos un cero.
  • app: ponemos el mismo valor que appAlias

miércoles, 13 de abril de 2011

Primer acercamiento a Umbraco

logo_umbraco

 

Instalación

Tan solo comentar que podéis realizar la instalación desde Web Platform Installer, será todo mucho más rápido y transparente con la excepción de indicar que la instalación se realice como un nuevo sitio web, me encontré problemas intentándolo instalar como directorio virtual.

También podéis acceder a http://umbraco.com/ donde encontrar bastante información y documentación de partida, sobre todo muy interesante la sección de videos.

Personalizando el splash de login

Para acceder al área de administración escribimos la siguiente ruta: http://host/umbraco/login.aspx,

Tenemos que editar y modificar los siguientes recursos gráficos para adaptarlos a la identidad de nuestro sitio web. Para ello simplemente lo abrimos con nuestro editor gráfico preferido y actualizamos los siguientes recursos:

/umbraco/images/loginbg.gif
/umbraco/images/loginbg.png
/umbraco/images/umbracosplash.gif
/umbraco/images/umbracosplash.png

Para modificar el texto de la pantalla de login localizamos el archivo:

/umbraco/config/lang/es.xml

y buscamos la entrada “topText” y “bottomText” para modificar el texto de la pantalla de login, podría ser algo parecido a esto:

<key alias="topText"><![CDATA[Bienvenido a www.midominio.com, escribe tu nombre de usuario y clave en los campos de debajo:]]></key>

<key alias="bottomText"><![CDATA[<p style="text-align:right;">&copy; 2001 - %0% <br /><a href=http://www.midominio.com style="text-decoration: none" target="_blank">www.midominio.com</a></p> ]]></key>

Con estos sencillos pasos tendréis vuestra pantalla de acceso a CMS Umbraco personalizado y a vuestro gusto.

domingo, 10 de abril de 2011

Perdón, me he equivocado…

error

¿Porqué cuando llega el jefe de una reunión con el cliente o de una visita, lo primero que dice es?: “señores tenemos una oportunidad y es de vital importancia para la empresa”.

El empleado piensa que será otra patata caliente y lo realmente importante es otro objetivo….comenta al compañero ”y esto de que va ahora, ¿en este momento?, ¿no está viendo que no nos lleva a ningún lado el hacerlo de esta manera?, si lo que estaba haciendo es realmente lo que tenía que hacer!!!”.

¿Os suena?, seguro que nos ha pasado en alguna ocasión, y si esto ocurre es que algo en el sistema no funciona, por varios factores.

¿Me he sabido comunicar de la manera correcta?
¿He hablado en el momento adecuado?
¿He expresado con claridad mi punto de vista?
¿He aceptado mis errores e intentado corregirlos?
¿Tenéis oportunidad de preguntar el porqué de las decisiones?
¿He preguntado el porqué de una decisión cuando he tenido oportunidad?
¿Habéis puesto el freno antes de llegar al callejón sin salida, aún sabiendo que no la tenía?
¿Somos conscientes del dinamismo de las necesidades?
¿Sois conscientes de la seguridad virtual en la que vive un empleado?
¿Tendría que haber dicho NO en alguna ocasión?

Tras varias victorias y derrotas a lo largo de mi trayectoria profesional, hoy he vuelto a equivocarme, pero levanto la cabeza y lo digo a lo dos punto cero, sí, me he equivocado, seguramente mañana volveré a hacer las mismas cosas pero os aseguro que de manera distinta.

Después de un largo fin de semana de reflexión, todavía no soy consciente de las cosas que he hecho mal pero lo que si esta claro es que por las razones que sean no estoy cumpliendo los objetivos que me marqué hace unos meses, así que ahora toca seguir reflexionando, recapacitar, echar leña al fuego, ponerse las pilas y corregir el rumbo.

miércoles, 6 de abril de 2011

SEO rápido, posiciona tu web con ASP.NET + IIS 7

 

Si quieres mejorar la visibilidad de tu página web y competir con el resto del mercado puedes seguir estas pequeñas pautas realizando un mínimo esfuerzo en el desarrollo y publicación de tu sitio web, la creación de estos pasos no te llevará más de 20 minutos.

Calidad del contenido

Esto es fundamental y estamos ya hartos de escucharlo pero si no ofrecemos algo de interés y calidad al usuario, ten claro que no volverá a nuestra web y pasará a convertirse en visitante Kleenex.

Semántica del contenido

Esto si que nos cuesta poco trabajo y veo cada regalito todos los días que a veces se me ponen los pelos de punta. Si queremos indicar que el texto es un título por favor usemos una etiqueta <h1>, y no usemos etiquetas para formatear y poner bonita nuestra web, del tipo….pongo un <br/><br/><br/> que hace falta para “respirar” según dice el “creativo”.

Título de las páginas y descripción

Ponle un titulo y descripción a cada una de tus páginas utilizando la siguiente etiquetas en tu documento html.

<meta name="description" content="Descripción corta de mi página, no más de 125 caracteres" />
<title>Título de mi página</title>

Uso de palabras claves

Utiliza la etiqueta keywords para añadir palabras o tags que permitan a los buscadores localizar los contenidos de tus páginas.

<meta name="keywords" content="coche, venta, segundamano" />

Inclusión de archivo sitemap.xml

Para la inclusión de nuestro archivo sitemap usaremos la herramienta on-line XML Sitemaps Generator, tan solo tenemos que indicar el sitio de nuestra web y el solito generará el archivito listo para copiar y pegar en el raíz de nuestra web. Tan solo echo en falta la etiqueta

<priority>0.65</priority> para cada uno de los nodos, es algo que podemos hacer para una segunda vuelta, esto nos permitirá de cada a los buscadores indicar que página es “más importante” dentro de nuestro sitio web, por ejemplo la home debería tener una prioridad más elevada que por ejemplo el aviso legal.

Inclusión de archivo robots.txt

Si por ejemplo queréis que cualquier robot de búsqueda o rastreador no cachee los contenidos de la carpeta imágenes o directorio upload, incluid estas líneas en un archivo llamado robots.txt y lo colgáis en el raíz del site.

User-Agent: *
Disallow: /imagenes/
Disallow: /upload/

Tuneando el web.config de nuestra web

Nos apoyaremos en la extensión URL Rewrite que debéis instalar en vuestro servidor, podeis utilizar la herramienta Web Platform Installer que ella se encargará solita de la instalación.

Antes de subir a producción vuestro sitio web debéis tunear un poco el web.config para aquellos que trabajéis con APS.NET Webforms, de manera que dentro del nodo system.webServer colocáis esto.

<rewrite>
  <rules>

    <rule name="CanonicalHostNameRule1">
      <match url="(.*)" />
      <conditions>
        <add input="{HTTP_HOST}" pattern="^www\.midominio\.com$" negate="true" />
      </conditions>
    </rule>


    <rule name="LowerCaseRule1" stopProcessing="true">
      <match url="[A-Z]" ignoreCase="false" />
      <action type="Redirect" url="{ToLower:{URL}}" />
      <conditions>
        <add input="{URL}" matchType="Pattern" pattern="WebResource.axd" ignoreCase="true" negate="true" />
      </conditions>
    </rule>


    <rule name="Default Document URL Rewrite" stopProcessing="true">
      <match url="(.*?)/?Default\.aspx$" />
      <action type="Redirect" url="{R:1}/" />
    </rule>

 Si por ejemplo tenéis una página del tipo http://www.midominio.com/avisolegal.aspx y queréis convertirla a http://www.midominio.com/aviso-legal incluir las siguientes reglas, una por cada página aspx que tengáis en vuestro proyecto  

<rule name="RedirectUserFriendlyURL1" stopProcessing="true">
      <match url="^avisolegal\.aspx$" />
      <conditions>
        <add input="{REQUEST_METHOD}" pattern="^POST$" negate="true" />
      </conditions>
      <action type="Redirect" url="aviso-legal" appendQueryString="false" />
    </rule>
    <rule name="RewriteUserFriendlyURL1" stopProcessing="true">
      <match url="^aviso-legal$" />
      <conditions>
        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
      </conditions>
      <action type="Rewrite" url="avisolegal.aspx" />
    </rule>

        </rules>

Igualmente aplicamos las reglas de salida, para convertir http://www.midominio.com/aviso-legal en http://www.midominio.com/avisolegal.aspx y pueda ser interpretado por el framework.


      <outboundRules>
        <rule name="OutboundRewriteUserFriendlyURL1" preCondition="ResponseIsHtml1">
          <match filterByTags="A, Form, Img" pattern="^(.*)avisolegal\.aspx$" />
          <action type="Rewrite" value="{R:1}/aviso-legal" />
        </rule>

    <preConditions>
      <preCondition name="ResponseIsHtml1">
        <add input="{RESPONSE_CONTENT_TYPE}" pattern="^text/html" />
      </preCondition>
    </preConditions>
  </outboundRules>
</rewrite>

Dando a conocer nuestra web

Podéis visitar http://www.google.es/addurl/ y dar de alta la dirección electrónica de vuestro sitio web.

Además es interesante darnos de alta en http://www.dmoz.org/, repositorio común utilizado por muchos de los buscadores conocidos.

Con estos simples pasos, lograréis ganar presencia, calidad y posicionamiento a vuestra web, claro que existen muchos más técnicas y factores a tener en cuenta, pero puede ser un buen punto de partida para profundizar y realizar otra serie de mejoras que veremos en nuevos posts.

sábado, 1 de enero de 2011

Desarrollo orientado a productos

 

Network ServiceYa nadie puede discutir que el modelo SaaS como enfoque de modelo de negocio es una realidad cotidiana, donde normalmente existen grandes ventajas tanto para el cliente como el proveedor, pero…¿habéis hecho una pausa en el desarrollo de vuestro producto y considerado la posibilidad de convertirlo realmente en un servicio?.

Seguramente, la mayoría de vuestros desarrollos serán técnicamente de muy alto valor, pero de que nos sirve si todo ese potencial no es capaz de transmitirse y comunicarse con el resto de la comunidad 3.0, o incluso bajando el listón con otras aplicaciones de valor añadido.

Si después de trabajar meses en un producto redondo con una inteligencia de negocio fantástica no sois capaces de transmitirlo el fracaso estará en la primera línea de código, y vamos a explicarlo más claramente con un ejemplo.

Imaginaros a Albert Einstein formulando en su cabeza la teoría de la relatividad, y de repente decidiera no disponer de boca, mano u oídos, sería un desastre y una pena no conocer las posibilidades de este genio.

Pues a nuestro producto le puede ocurrir lo mismo si decidimos no escuchar la problemática real del usuario, es decir, si por ejemplo hemos trabajado en un fantástico CRM sería genial que pudiera exportar determinada información de contactos a un formato estándar para agregarlos o sincronizarlos con mi IPhone.

De igual manera si dispongo de unos contactos perfectamente organizados en mi Google Contacts, podría ofrecer la posibilidad de agregarlos a mi producto para enriquecerlo y darle un valor añadido apoyado por otras herramientas de mercado.

Espero vuestras opiniones que seguro serán interesantes.

lunes, 1 de noviembre de 2010

Reutilización de informes en entornos de aplicación orientadas a productos

 

Merece la pena escribir este post, ya que me ha dado algún que otro dolor de cabeza hasta llegar a la solución. Vamos a jugar un ratito a pasar como parámetro la cadena de conexión para visualizar un informe mediante Report Viewer 2010.

 

Generando el informe con Report Builder 3.0

Esta herramienta, ya mencionada en posts anteriores, nos permitirá crear la definición del informe y obtener un archivo en formato RDL (Report Definition Language) se trata de un fichero estándar XML que nos permite cotillear las tripas y ver lo que ocurre en la “sala de máquinas”.

Primeramente tendremos que incluir un nuevo parámetro en el informe al que llamaremos BaseDatos, lo marcaremos como oculto, guardamos y salimos de Report Builder.

 

Modificando el RDL

Partiendo de cualquier informe generado previamente con dicha herramienta, solo nos queda guardar el archivo (en el escritorio de Windows por ejemplo) y usar el bloc de notas para ver en detalle la definición del mismo. Tendremos que localizar al principio del documento la sección ConnectString del elemento DataSource y modificarlo de la siguiente manera:

<?xml version="1.0" encoding="utf-8"?>
<Report xmlns:rd="http://schemas.microsoft.com/SQLServer/reporting/reportdesigner"xmlns:cl="http://schemas.microsoft.com/sqlserver/reporting/2010/01/componentdefinition"xmlns="http://schemas.microsoft.com/sqlserver/reporting/2010/01/reportdefinition">
  <AutoRefresh>0</AutoRefresh>
  <DataSources>
    <DataSource Name="GIE">
      <ConnectionProperties>
        <DataProvider>SQL</DataProvider>
        <ConnectString>="Password=XXXX;Persist Security Info=True;User ID=XXXX;Data Source=XXXX;Initial Catalog=" &amp; Parameters!BaseDatos.Value</ConnectString>
      </ConnectionProperties>
      <rd:DataSourceID>2bf79f31-84cc-4a46-b53d-93fbf236f92d</rd:DataSourceID>
    </DataSource>
  </DataSources>

Lo que hemos modificado con respecto al original ha sido la inclusión de la expresión Parameters!BaseDatos.Value embebida en la cadena de conexión delDataSource

Os dejo un enlace de interés donde podréis indagar mas sobre estas cuestiones:http://msdn.microsoft.com/en-us/library/ms156450.aspx#Expressions

Hay otro punto importantísimo y que también me costo un buen rato, no se porque razón la definición del parámetro BaseDatos tiene que ser el primero de la colección, podemos observar también su definición en el propio documento RDL casi al final del archivo:

<ReportParameters>
  <ReportParameter Name="BaseDatos">
    <DataType>String</DataType>
    <Prompt>BaseDatos</Prompt>
    <Hidden>true</Hidden>
  </ReportParameter>
  <ReportParameter Name="IdUsuarioComercial">
    <DataType>Integer</DataType>
    <DefaultValue>
      <DataSetReference>
        <DataSetName>Comerciales</DataSetName>
        <ValueField>IdUsuario</ValueField>
      </DataSetReference>
    </DefaultValue>
    <Prompt>Comercial</Prompt>
    <ValidValues>
      <DataSetReference>
        <DataSetName>Comerciales</DataSetName>
        <ValueField>IdUsuario</ValueField>
        <LabelField>Comercial</LabelField>
      </DataSetReference>
    </ValidValues>
    <MultiValue>true</MultiValue>
  </ReportParameter>

 

Publicación del informe mediante Report Manager

Ya sabéis que Report Manager es la herramienta web que nos permite gestionar y publicar informes cuando nos basamos en RemoteMode, solo tendremos que asegurarnos de indicar que no se necesitan credenciales para la visualización del informe, os dejo la pantalla donde se parametriza:

report_manager

 

Report Viewer en Visual Studio

Os dejo el código a implementar desde Visual Studio con la llamada al informe:

if (!IsPostBack)
{
    ReportViewer1.ProcessingMode = ProcessingMode.Remote;
    ServerReport serverReport = ReportViewer1.ServerReport;
    serverReport.ReportServerUrl = new Uri(Properties.Settings.Default.ReportServer);
    serverReport.ReportPath = Request["ReportPath"].ToString();
    ReportParameter rp = new ReportParameter("BaseDatos",”XXXXX”);
    serverReport.SetParameters(rp);

}

Esto nos permitirá reutilizar informes que compartan diferentes bases de datos con misma estructura, imprescindible cuando se trata por ejemplo de desarrollo de aplicaciones orientadas a productos donde existe un único repositorio de ejecución de aplicación pero diferentes bases de datos (una para cada cliente).

Como inconveniente es que no podéis hacer ingeniería inversa, si abres el informe (ya modificado desde el bloc de notas anteriormente) mediante Report Manager al volverlo a publicar o grabar destroza la expresión de paso de parámetros de la cadena de conexión. Se lo comunicaremos a Redmond para que lo corrijan Guiño

Related Posts Plugin for WordPress, Blogger...