viernes, 17 de julio de 2009

Gráficos dinámicos en sharepoint


Amigos del mundo sharepoint: supongo que como yo, habrán notado que no es tan sencillo extraer información de las listas de sharepoint y mostrarla en forma gráfica en un tablero de control. He estado investigando el tema y me he encontrado con demasiadas opciones. Hasta el momento he seleccionada una, que a continuación les presentaré. Espero que alguno de ustedes critique la opción elegida y presente alguna mejor, porque estoy en búsqueda de la luz.
La alternativa que elegí es FusionCharts Free debido a que:

  • Funciona en WSS 3. No requiere MOSS, como Excel Services.

  • No ha sido discontinuada por el fabricante, como los OWC.

  • No existe complicación para extraer datos de las listas, siempre que estemos dispuestos a escribir un spquery en CAML.

  • No requiere instalación de componentes en el cliente, asumiendo que Flash es algo típicamente instalado.

  • Es bonita. Los tableros son para los directivos y a los directivos les gusta ver gráficos bonitos.

  • Es open source (existe una versión no abierta con mayor funcionalidad)

  • Es liviana.
¿Cómo funciona?

Luego de leer el Help de la herramienta, seleccioné una de las tantas maneras que tiene de obtener datos de una fuente para generar un gráfico. La siguiente imagen esquematiza la interacción entre los distintos componentes (en la opción elegida).






Los pasos para implementar la solución son:
  1. Crear una Application Page para extraer datos de las listas de Sharepoint a través de un SPQuery.
  2. Generar como resultado de la Application Page un XML con el esquema que requieren los componentes de FusionCharts para armar el gráfico.
  3. Conectar el XML con los SWF (flash) y hacer el "render" del gráfico vía JavaScript
El resultado se puede ver parcialmente en la siguiente imagen (parcialmente porque no se ve la parte animada)









1. SP Query

Esta es una de las opciones para consultar datos de una lista en sharepoint. A continuación muestro parte del código para una lista en particular llamada "Proyectos".

SPWeb yq_web = SPContext.Current.Web;
SPList list = yq_web.Lists["Proyectos"];
SPQuery query = new SPQuery();
query.ViewFields = "<FieldRef Name='Title' /><FieldRef Name='Referencia' /><FieldRef Name='Cliente' /><FieldRef Name='Jefe_x0020_de_x0020_Proyecto' /><FieldRef Name='Estado' /><FieldRef Name='ID' /><FieldRef Name='Fecha_x0020_de_x0020_inicio' /><FieldRef Name='Fecha_x0020_prevista_x0020_final' />";
query.Query = "<Where><Eq><FieldRef Name='Estado' /><Value Type='Choice'>Activo</Value></Eq></Where>";
query.Query += "<OrderBy><FieldRef Name='Title' /><FieldRef Name='ID' /></OrderBy>";
SPListItemCollection items = list.GetItems(query);

2. XML
La siguiente porción de código muestra como recorrer la lista y generar el XML que necesitan los componentes de FusionCharts para armar un gráfico de barras apiladas en 3D.

string strXML;
strXML = "<graph xaxisname='Costos' yaxisname='Importe' hovercapbg='DEDEBE' hovercapborder='889E6D' rotateNames='0' animation='1' decimalPrecision='0' showNames='1' numberSuffix='$' >";
strXML += "<categories>";

strXML += "<category name='Contrataciones'/>";strXML += "<category name='Otros gastos'/>";strXML += "</categories>";(…)
foreach (SPListItem imp_item in imp_items){strXML += "<dataset seriesname=(…)
strXML += "</graph>";

Response.ContentType = "text/xml";
Response.Write(strXML);
3. JavaScript

Finalmente, tomamos los datos del XML y lo graficamos dentro de un DIV mediante JavaScript.


document.write("<div id='chartdiv' align='left'>The chart will appear within this DIV. This text will be replaced by the chart.</div>");
var myChart = new

FusionCharts("./FusionCharts/FCF_MSColumn3D.swf?XMLLoadingText=Cargando datos. Espere por favor...&ChartNoDataText=No existen datos para mostrar.", "myChartId", "800", "300");

myChart.setDataURL("/_layouts/ProyectoControlChart.aspx);

myChart.render("chartdiv");

Fin
Aquí termina, He simplificado el código con fines didácticos. El Help posee una muy buena referencia del XML a generar (muy sencillo) y varias opciones para llegar al objetivo. Aquí mostré la opción CAML-ASPX-XML-JAVASCRIPT, pero hay otras.
Espero que este haya sido un artículo útil. Si alguien conoce otras opciones para cumplir con este tipo de requerimientos (como FLEX), envíe comentarios por favor. Serán bienvenidos.


Hasta el próximo artículo.

59 comentarios:

Hola, tendras un demo de como hacerlo usando WebServices?
ya tengo el WebServices hecho y devuelve un XML con la estructura necesaria, pero no se como pasarle al Chart, Tiene alguna idea de como hacer eso?

Hola Marco: no lo he usado con web services. ¿Has consultado el help de fusioncharts? En ese help muestra todas las opciones de armado del gráfico: PHP, ASP, JavaScript, VB.Net, C#, JSP y RoR. ¿Cómo estás invocando tu el web service?

Si pero he tenido problemas con la manipulacion de los datos XML, asi que mejorer usare la opcion que tu has implementado.
Crear un WebPart que trabaje con una pagina ASPX que devuelva la data como XML.
Tengo una duda el codigo de la pagina lo pones donde? al mismo nivel de la pagina aspx o crear algun directorio app_code por ejemplo?
Estoy volviendo a rearmar mi blog, luego te paso el link.

Hola de nuevo, estuve haciendo la prueba y tengo problemas con la pagina aspx.
la he puesto en LAYOUTS, el codigo lo he puesto en wss\VirtualDirectories\80, pero nada, puedes darme una mano con este tema, te lo agradeceria muchisimo.

Hola Marcos, intentaré darte una mano:
1) En mi caso también usé una applicacion page para generar el XML. El código de llamado a la AP pára hacer el gráfico lo puse dentro de un javascript en una Content Editor Wev Part
2) La application page la debes poner en c:\program files\common files\microsoft shared \web server extensions\12\TEMPLATE\LAYOUTS
Qué error te está dando? Cómo estás invocando la página?

Juan, gracias puse la aplicacion en c:\program files\common files\microsoft shared \web server extensions\12\TEMPLATE\LAYOUTS y ya funciona esa parte ahora estoy reescribiendo el codigo.
Gracias por el tiempo, cualquier cosa te escribo.

De nada, cualquier consulta no dejes de avisarnos. Saludos!

Juan, para poder usar este codigo:

var myChart = new
FusionCharts("./FusionCharts/FCF_MSColumn3D.swf?XMLLoadingText=Cargando datos. Espere por favor...&ChartNoDataText=No existen datos para mostrar.", "myChartId", "800", "300");




myChart.setDataURL("/_layouts/ProyectoControlChart.aspx);




myChart.render("chartdiv");

Necesitas referencias a alguna libreria javascript? y donde estas poniendo tus archivos swf para que puedas llamarlos?

Si, las necesitas, fijate como:

<script type="text/javascript" src="/miaplicacion/_layouts/noblebase/FusionCharts/FusionCharts.js"></script>

Los swf los estoy copiando en LAYOUTS, en mi caso en:
\TEMPLATE\LAYOUTS\MiAplicacion\FusionCharts

Saludos!

Juan Pablo, ya casi lo tengo dominado, hice un webpart que te permite seleccionar un lista, la vista y que campos mostrar, me falta darle unos ajustes y lo subire a mi blog para que otro lo pueda usar y mejorar.
Gracias por todo tu apoyo.

De nada Marcos, me alegro haber podido ayudar. Cuando lo subas a tu blog, no dejes de agregar un comentario en este post con el link a tu artículo, así vemos cómo lo implementaste. Saludos!

Hola, sabes tengo una duda (otra para variar)
Lo que pasa es que necesito hacer un grafico pero con agrupacion en el eje X, no se si me explico.
Sabes si es posible y si lo es su puedes pasarme el link o alguna ayuda.
Gracias.

Hola Marco, has consultado la galería de gráficos de FusionCharts en http://www.fusioncharts.com/free/gallery/ ???

Con agrupamiento te refieres a jerarquías? En ese caso te recomiendo utilizar OWC. Verifica este artículo:
http://surpoint.blogspot.com/2009/07/owc-2003-en-sharepoint-2007.html

Saludos Marco!

buenas tardes

estoy probrando este control para hacer graficas en MOSS 2007 segui todos los pasos pero las graficas no se muestran se queda en blanco y no muestra ningun error que podra ser ??????

Fabian

mil gracias

Hola Fabián! En blanco? Tienes instalado el addin de Flash en el explorer?

muchas gracias por la repuesta

si instale la ultima version de flash player tanto en el server como en la maquina cliente pero sigue saliendo en blanco y sequeda pensando como si intentara cargar pero igual no sale nada.

Consultando con mi colega, Sebastián, dice que le ha pasado cuando el XML está mal armado.
Te sugiero que revises el XML.

Una prueba que puedes hacer es cambiar el setDataURL y apuntarlo a un XML ejemplo de los que vienen con la ayuda de Fusion Charts y verificar si funciona.

Saludos!

gracias de nuevo

te cuento que esa pruega ya la realice con los ejemplos que trae y tambien baje unos de internet y sigue los mismo ya sea direccionandolo al archivo XML o en el Chart Xml Content insertandole el codigo y lo mismo
tambien intente utilizar el control amarrado a una lista de share point y acepta toda la configuracion pero no me muestra la grafica se queda en blanco cargando.

gracias

fabian

Hola Juan Pablo:

Estaba viendo tu articulo y te cuento que estoy haciendo algo similar a lo que mecionas, solo que yo utilizo dundas, y me he trabado con algo, no se si me puedas ayudar. Quiero graficar la cantidad de items de 3 bibliotecas de sharepoint por mes, el punto es que al hacer el spquery, solo me cuenta de 2 bibliotecas, y de la tercera no. Esta ya contiene información, he tratado de hacer solo el codigo de esa sola y nada mas noo he podido....tienes alguna idea de que pueda ser?

Perdona no te puse el ejemplo de mi spquery...es el siguiente..

myQuery.Query = ""+i+"";


***el i es por que está dentro de un for para hacerlo por mes del año...

Saludos!

Fabián, no logro darme cuenta cuál puede ser el problema. Si gustas pegar tu código aquí, quizá podamos revisarlo. ¿Tienes copiado en el servidor todas las librerías de Fusion Charts?

Anónimo: no he usado dundas, pero si gustas pegar el código del query, tal vez podamos encontrar el error.

Saludos!

Gracias Juan Pablo, el codigo del query es....

myQuery.Query = "< Where >< Contains >< FieldRef Name='Mes'/><Value Type='Number>1</Value></Contains></Where">;

NOTA: en mi query es 'Number', solo que si en el blog te lo pongo así no pone el codigo completo.
El 1 se refiere al mes de enero, solo como ejemplo.
Lo extraño es que este mismo query lo ejecuto con otras bibliotecas y corre perfectamente, a pesar de que contienen los mismos campos,y con otra que ya contiene aproximadamente 100 registros no lo hace.

Alguna idea??...saludos!

gracias de nuevo

yo instale el fusion charts en el sever este ya venia empaquetado el se intalo solito yo lo unico que hago es adicionar un elemento web a mi sitio sharepoint ya sea del tipo chartfromlist y/o chartfromxml y edito sus propiedades segun su manual y pasa lo que te he contado, revise en la galeria de elementos web que estubieran los archivos ChartFromList.webpart y ChartFromXml.webpart este ultimo si se abre debe mostrar una grafica de ejemplo pero pasa lo mismo se queda cargando.

-
-











-











-











-













este es uno de los XML que no grafica

gracias

Fabian

graph PYAxisName="Amount" SYAxisName="Quantity" shownames="1" showvalues="0" showLegend="1" rotateNames="0" formatNumberScale="1" decimalPrecision="2" limitsDecimalPrecision="0" divLineDecimalPrecision="1" formatNumber="1" chartTopMargin="15">
categories>
category name="Ernst..." hoverText="Ernst Handel" />
category name="QUICK..." hoverText="QUICK-Stop" />
category name="Save-..." hoverText="Save-a-lot Markets" />
category name="Hanar..." hoverText="Hanari Carnes" />
category name="Rattl..." hoverText="Rattlesnake Canyon Grocery" />
category name="Hungr..." hoverText="Hungry Owl All-Night Grocers" />
category name="König..." hoverText="Königlich Essen" />
category name="White..." hoverText="White Clover Markets" />
category name="Folk ..." hoverText="Folk och fä HB" />
category name="Suprê..." hoverText="Suprêmes délices" />
/categories>
dataset seriesname="Amount" showValues="0" color="AFD8F8" parentYAxis="P" numberPrefix="$">
set value="41210.65" />
set value="37217.32" />
set value="36310.11" />
set value="23821.2" />
set value="21238.27" />
set value="20402.12" />
set value="19582.77" />
set value="15278.9" />
set value="13644.06" />
set value="11644.6" />
/dataset>
dataset seriesname="Discount" showValues="0" color="FDC12E" parentYAxis="P" numberPrefix="$">
set value="1202.27254486084" />
set value="2736.60256195068" />
set value="5047.74497413635" />
set value="337.672510147095" />
set value="404.888009995222" />
set value="1844.77046012878" />
set value="528.849014282227" />
set value="0" />
set value="1798.85203838348" />
set value="174.320002555847" />
/dataset>
-dataset seriesname="Quantity" showValues="0" color="FF8000" anchorBorderColor="FF8000" parentYAxis="S" lineThickness="4">
set value="1756" />
set value="1096" />
set value="1817" />
set value="478" />
set value="438" />
set value="395" />
set value="400" />
set value="360" />
set value="560" />
set value="532" />
/dataset>
/graph>


este es el archivo de ejemplo quite < al inicio de las lineas para que se pueda ver en este blog peor el archi los tiene

gracias

Fabián, no logro encontrar el problema. La verdad es que en nuestro caso lo hemos usado desd JavaScript, dentro de una Content Editor Web Part, creo que no es la misma situación verdad?

Anónimo, tal vez el problema no esté en el query, sino en la lógica del bucle...

gracias

me podrias explicar como lo hacen ud para yo realizarlo en mi sitio de sharepoint

Gracias Juan Pablo,

Tienes razón, el problema no es en el query. Debido a que en la biblioteca tengo 4 carpetas en la raiz, pues aplica el query en esa parte y pues no tengo ningun item ahí.Por lo que cambié mi codigo por esto....


SPListCollection Listas = Web.Lists;
SPList Lista1 = Listas[nombre_Biblioteca];
SPFolder Folder = Lista1.RootFolder.SubFolders[nombre_folder];
SPQuery oQuery = new SPQuery();
oQuery.Folder= Folder;
SPListItemCollection collListItems = Lista1.GetItems(oQuery);
int suma = collListItems.Count;


hasta aqui todo bien, por que me cuenta los items de la carpeta especifica de la biblioteca, pero quiero a eso mismo aplicarle un query, es decir a los items de esa carpeta contarlos por el query que te habia mandado antes..mes

myQuery.Query = "< Where >< Contains >< FieldRef Name='Mes'/><Value Type='Number>1</Value></Contains></Where">;

Pero no se como hacerlo...espero no fastidiarte, pero es que en internet no encuentro mucha ayuda...Gracias!!

Fijate si puedes obtener algo de info en este link, hay una sección que habla sobre armar las consultas en carpetas: http://sharepointmagazine.net/technical/development/writing-caml-queries-for-retrieving-list-items-from-a-sharepoint-list
Saludos!

Fabián, nosotros lo hacemos como dice el artículo. En particular, la parte del Javascript la incluimos dentro de una Content Editor Web Part.

Te sugiero que para empezar a encontrar el problema hagas los siguientes:

1) Incluye el código javascript en una content editor web part dentro de un tag script

2) Toma como origen de datos un archivo XML de ejemplo de FusionCharts (no una página ASPX)

3) Verifica que estén instaladas las liberías de fusioncharts de JS y las películas SWF (y que puedan ser accedidas desde tu javascript)

Si eso funciona, luego puedes empezar a hacer cambios para encontrar el problema.
Saludos y suerte!

Hola Juan Pablo, ya pude resolver el problema que te habia comentado, gracias por la página.
Y Felicidades por tu tercer estrella...lo acabo de leer jeje..
Y que bueno que te guste compartir de tus experiencias y conocimientos, la verdad hay pocos que dedican tiempo a problemas de este tipo de otras personas...
Saludos y ya te estaremos siguiendo con cada post nuevo...

De nada, cómo lo resolviste? Si tienes algo de tiempo, cuéntanos.

Ya estás en hispapoint???

Hola a todos:

Estoy probando esta solucion en mi pc, copie el paquete para mi HD en la carpeta de mi aplicacion y despues cree una pagina de aplicacion desde vstudio 2008 con este codigo:



var myChart = new FusionCharts("Area2D.swf", "ChartId", "600", "275", "0", "0");
myChart.setDataURL("Area2D.xml");
myChart.render("chartdiv");


Pero no se muestra nada cuando comilo la pagina

Alguna idea?

Gracias

Copiaste los archivos swf y javascript de fusion charts al servidor?
Tienes acceso a la ruta en donde están los archivos? Verifica si es necesario poner el path relativo.
Saludos!

Es una prueba, es decir estoy ejecutando el servidor virtual de vstudio 2008 para despues pasarlo a mi sharepoint, solo estoy ejecutando mi aspx con las referencias a la carpeta donde se genera el aspx que es "Mis documentos\Visual Studio 2008\WebSites\Chart", ahi copio el swf y el xml para probar pero nada?

Alguna otra idea? Y en el caso de mi wss donde debo copiar los swf, el js?

Tienes flash instalado?
Los archivos conviene copiarlos en alguna carpeta dentro de Layouts.

Si aún continúa el problema, te recomiendo que arrancar la prueba con un ejemplo básico de los que vienen con FusionCharts.

Saludos!

Tengo este error, que puede ser?

No se puede mostrar la página XML
No se puede ver la entrada XML con la hoja de estilo XSL. Corrija el error y haga clic en el botón Actualizar, o inténtelo de nuevo más tarde.

--------------------------------------------------------------------------------

No puede existir una declaración DOCTYPE fuera de un prólogo. Error al procesar el recurso http://localhost:1190/Chart/Char...

























"

Ahora bien, cuando hago esto mismo usando el metodo: return FusionCharts.RenderChartHTML("StackedColumn2D.swf", "", xmlDataT.ToString(), "myNext", "400", "300", false); TRABAJA bien pero no cuando intento usar el JS.

Gracias por su ayuda

Hola, en dónde estás incluyendo tu código? En una página, webpart, dónde?

Es una pagina web creada en vstudio 2008, cuando genero el ejemplo que aqui proponen usando la clase InfoSoftGlobal y el metodo RenderChartHTML todo funciona bien, pero cuando pruebo usando solo el funsionchart.js que es el ejemplo que aqui proponen me da ese error que mostre antes.

gracias Juan Pablo

Hola:

Tengo mi pagina de aplicacion aspx funcionando desde mi vstudio, mi pregunta es:
Como hago para que me funcione en mi wss 3.0.
Cree en Layouts la galeria de swf, pero como publico mi pagina aspx en mi servidor wss 3.0, y ademas como configuro el acceso a la dll FusionCharts.dll para poder utilizar la clase InfoSoftGlobal con la cual genero el grafico.

Muchas Gracias

Hola, si has creado una página con Visual Studio, supongo que se trata de una página ASPX, con lo cual no creo que debas usar la opción de JS, sino la de ASP. En el ejemplo de este artículo se usa JavaScript, pero ten en cuenta que se está incluyendo dentro de una Content Editor Web Part.

Fijate si te sirve este artículo que explica como crear páginas de aplicación en wss:

http://msdn.microsoft.com/en-us/library/bb418732.aspx

Saludos!

Gracias Juan Pablo, disculpa otra pregunta, entonces donde es que creas el SP Query y la generacion del xml?

Gracias Juan Pablo

Disculpa otra pregunta donde creas el SP Query y generas el xml?

Saludos

Hola: el XML y el SPQuery se generan en una application page (aspx). No lo he aclarado bien en el punto anterior.

El javascript puede llamarse desde una CEWP.

Al menos esta es la forma en que normalmente lo uso, aunque no es la única por supuesto.

Saludos!

Perdona puedes poner un ejemplo de como quedaria el codigo en la CEWP?

Gracias

El código es el que está en el artículo en la sección "3 JavaScript".

En este enlace tienes un ejemplo de como agregar JavaScript en una Content Editor WebPart: http://www.cleverworkarounds.com/2008/02/28/more-sharepoint-branding-customisation-using-javascript-part-2/

Por supuesto hay muchas formas de hacerlo (y ordenarlo), pero ahí tienes un ejemplo.

No olvides usar el tag "script"

Gracias Juan Pablo por tu paciencia, he probado este ejemplo y me da errores en la creacion del xml que ya he probado en la variante de usar la dll y el metodo RenderChartHTML y aqui si me funciona bien, pero en este ejemplo que propones aqui cuando le doy la direccion de algun xml de los ejemplos la pagina no da errores pero no sale el grafico, sale en blanco la pagina, incluso he probado el web part de funsioncharts y me pasa lo mismo el web part no muestra nada, tienes alguna idea cual puede ser el problema?

Saludos

Has verificado que los archivos swf y js estén accesibles?

Asi es lo estan, en el caso del js la pagina misma en el vstudio te lo dice, y en el caso de los swf y el xml estan en la raiz del sitio virtual que genera el Vstudio, y por eso uso:

var myChart = new FusionCharts("StackedColumn2D.swf", "ChartId", "600", "275", "0", "0");
myChart.setDataURL("StCol2D.xml");
myChart.render("chartdiv");

Gracias

Normalmente dejo los archivos en LAYOUTS (en alguna subcarpeta) para segurarme que puedan ser accedidos...

Hola buenas tardes:

quisiera saber los pasos necesarios que debo seguir para crear una webpart en sharepoint 3.0 de graficos, les agradeceria a todos sus comentarios gracias

¿Qué tipo de gráficos? ¿Cómo los que se muestra en este artículo? Te pregunto porque depende un poco de la plataforma de gráficos que utilices.

¿Qué es lo que estás necesitando exactamente?

Serian de todo tipo(del tipo de ejemplo que explicaste, tipo dashboard y maps tendrás algún ejemplo? Me podrías orientar por favor.

Gracias

Buenas Tardes:

Como hago una conexion de una base de datos de sqlserver por ejemplo una base de datos llamada "Usuarios" con SPQuery

Si lo que necesitás es hacer gráficos, hay muchas opciones de herramientas. Por ejemplo Report Builder. Aquí te dejo un enlace:

http://surpoint.blogspot.com/2011/01/comparacion-entre-report-builder-v1-y.html

SPQuery no está pensado para consultar base de datos, sino listas de SharePoint. Aquí el enlace de MSDN:

http://msdn.microsoft.com/en-us/library/microsoft.sharepoint.spquery.aspx

Saludos!

De que manera podria ligar entonces un grafico por medio de una consulta de bd hacia sharepoint, ya lo genere en asp.net pero de que manera puedo ligarlo a sharepoint

Saludos.

Bien, entonces el camino de la webpart es una alternativa. Te dejo dos enlaces que pueden serte útil:

http://www.returngis.net/2010/05/los-webparts-de-sharepoint-2007/

http://msmvps.com/blogs/lfranco/archive/2007/02/02/webparts-1-creando-nuestro-primer-webpart-para-sharepoint-services-3-0.aspx

Saludos!

Publicar un comentario