miércoles, 17 de diciembre de 2014

Llamar a Web-Services de Navision desde Navision


PAra consumir los webservices de un servidor de Navision desde otro servidor de Navision tenemos que montar una petición httpRequest pasándole un XML bien formado y recuperar la respuesta para saber que es lo que ha ocurrido en el servidor de destino.

Para ello primero declaramos las variables:
NameDataTypeSubtypeLength
XmlHttpRequest Automation'Microsoft XML, v4.0'.XMLHTTP 
XmlDocAutomation'Microsoft XML, v4.0'.DOMDocument 
XmlStringText 1024
BTSoapBigText  
BTValoresBigText    


Creamos un BigText y le añadimos la cabecera de la petición:

BTPasado.ADDTEXT('<?xml version="1.0" encoding="utf-8"?>');
BTPasado.ADDTEXT('<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">');
BTPasado.ADDTEXT('<soap:Body>');
BTPasado.ADDTEXT(STRSUBSTNO('<%1 xmlns="urn:microsoft-dynamics-schemas/codeunit/%2">','MiFuncion','MiCodeUnit'));

BTValores.ADDTEXT('<nombre_parametro_que_espera_MiCodeunit_MiFuncion>');
BTValores.ADDTEXT('MI-VALOR');
BTValores.ADDTEXT('</nombre_parametro_que_espera_MiCodeunit_MiFuncion>');

BTPasado.ADDTEXT(STRSUBSTNO('</%1>','MiFuncion'));

BTPasado.ADDTEXT('</soap:Body>');
BTPasado.ADDTEXT('</soap:Envelope>');


Como veis es bien sencillo montar la petición de nuestro httprequest.
Ahora hacemos la llamada:

NameDataType         Subtype

XmlDocPasado              Automation'Microsoft XML, v4.0'.DOMDocument

IF (ISCLEAR(XmlHttpRequest)) THEN
  CREATE(XmlHttpRequest);

XmlHttpRequest.open('POST','http://servidor:7047/DynamicsNAV/WS/empresa/Codeunit/MiCodeunit',FALSE,'DOMINIO\usuario','password');
XmlHttpRequest.setRequestHeader('Host', 'localhost');
XmlHttpRequest.setRequestHeader('Content-Type', 'text/xml; charset=utf-8');
XmlHttpRequest.setRequestHeader('Content-Length', FORMAT(BTPasado.LENGTH));
XmlHttpRequest.setRequestHeader('SOAPAction','MiFuncion');
XmlHttpRequest.send(BTPasado);
XmlDocPasado := XmlHttpRequest.responseXML;


Con esto obtendríamos en XmlDocPasado un XML con el resultado.

viernes, 28 de noviembre de 2014

Convertir líneas a columna en una consulta sql

Se puede pasar un resultado de una consulta sql de líneas a un varchar que representaría una columna con la función: COALESCE siempre que no contenga ningún null el resultado de la consulta.

Ejemplo:
DECLARE @valores VARCHAR(1000)
SELECT @valores= COALESCE(@valores + ',', '') + valor FROM MiConsulta-Tabla

Valor es uno de los campos de MiConsulta-Tabla.
El resultado es un varchar concatenado por comas.
Tenemos la limitación de la longitud del varchar (Aunque lo definamos con MAX) pero nos puede ser útil para salir del paso.

viernes, 21 de noviembre de 2014

Crear un informe Recursivo con Reporting Services

Crear un informe recursivo es extremadamente fácil con Reporting Services.
Supongamos un listado que muestra los siguientes datos:
  1. Primera Línea Padre
    1. Primera Línea Hija Primera Línea Padre
    2. Segunda Línea Hija Primera Línea Padre
      1. Primera Línea HijaSegunda Línea Hija Primera Línea Padre
    3. Tercera Línea Hija Primera Línea Padre
  2. Segunda Línea Padre
  3. Tercera Línea Padre
  4. ....
Tenemos un ID que identifica la línea y un ID_PADRE que identifica la línea padre de la línea actual. En Repoting iríamos a la línea y le definiríamos un grupo:
 
En el grupo ponemos como campo de grupo el ID que identifica la línea.

En propiedades avanzadas indicamos cual es el campo recursivo de cada línea, es decir, el campo que identifica cual es su padre.
Y ya esta, ya tenemos nuestro informe recursivo.
Para que visualmente quede mas bonito se cambia el padding del campo para que vaya indentando las líneas y quede así:

También se puede cambiar la visualización del grupo para poder plegarlo o desplegarlo:

jueves, 10 de abril de 2014

Obtener la lista de informes cuanto cuestan de sacar en tiempo

Esta consulta muestra una lista de los informes que mas cuestan de sacar por tiempo. Con esto podemos determinar que informes son los más pesados e intentar optimizarlos.


SELECT EL.UserNAme,Name Informe, b.path Ruta, Parameters Parametros,

FORMAT Formato,TimeStart Inicio, TimeEnd Fin, ByteCount,

(TimedataRetrieval+Timeprocessing+TimeRendering)/1000 AS Seg_TiempoTotal

FROM

[ReportServer].[dbo].[ExecutionLog] EL

JOIN [ReportServer].[dbo].[CATALOG] b

ON EL.reportid = b.itemid

--WHERE Name =@INFORME

ORDER BY (TimedataRetrieval+Timeprocessing+TimeRendering)/1000 DESC

jueves, 3 de abril de 2014

Leer active directory desde SQL

Para acceder desde SQL al LDAP hay que linkar nuestro servidor del Active directory con el servidor de SQL donde queremos hacer la consulta.
La lista de campos disponibles desde el LDAP la podeis encontrar en el siguiente link: lista de campos

Lo primero es linkar el servidor de la siguiente manera_
Exec
 sp_addlinkedserver 'ADSI'
, 'Active Directory Service Interfaces'
, 'ADSDSOObject'
, 'adsdatasource'

Le ponemos un usuario del dominio para que tenga acceso, bien con la instrucción:
EXEC sp_addlinkedsrvlogin 'ADSI', 'false', NULL, 'UsuarioDominio'
O desde las propiedades de la conexión creada (Servidores Vinculados)

En caso de que tengas el "Ad Hoc Distributed Queries" desabilitado, entonces corre esto para habilitarlo:
 sp_configure 'show advanced options'
, 1
reconfigure
go
sp_configure 'Ad Hoc Distributed Queries'
, 1
reconfigure
go



Para ejcutar las consultas, se hace utilizando OpenQuery y de la siguiente manera:
SELECT * FROM OpenQuery(ADSI, 'SELECT   physicalDeliveryOfficeName,sAMAccountName,cn,Name,displayName, sn,givenName,initials,moniker, personalTitle,generationQualifier ,userPrincipalName ,distinguishedName ,adsPath FROM ''LDAP://DC=mi-dominio,DC=local'' WHERE objectCategory=''user'' '

jueves, 27 de marzo de 2014

Imagenes externas en Reporting Services

En una red corporativa, podemos definir en los informes de reporting las imágenes como externas y darles la ruta donde se encuentran para que el servidor de informes las renderice, se hace de la siguiente manera:
file://datos/ImagenesProductos/Historico/imagen.jpg

jueves, 20 de marzo de 2014

Split en Reporting Services

Para utilizar la función de Split en Reporting Services y combinar así nuestra función de Web Services con Reportin Services, es muy útil la función Split de Reporting Services cuya definicón es la siguiente:
CDec(Split(Fields!RESULTADO.Value,"|")(1))