CONNECTOR AMB GECAT













Versió Optimitzada

Disponible una nova versió optimitzada del connector. Trobareu més informació al següent apartat.






Introducció

Propòsit

L'objectiu del present document és descriure la metodologia a seguir en la utilització del connector al sistema SAP del Gecat des de qualsevol aplicació Java del Framework J2EE.

L'abast d'aquest connector es basa en la utilització de les funcions d'alta de factures, consultes i reserves online del SAP de Gecat, així com totes les funcions batch.

Context i Escenaris d'Ús

Aquest connector podrà ser utilitzat des de qualsevol aplicació del Framework J2EE.
El connector permet l'accés al SAP mitjançant objectes de consulta. El connector transforma aquests objectes en una cadena de caràcters vàlida per al SAP. La cadena de retorn és transformada novament en un objecte que conté els registres de retorn.

Versions i Dependències

Les dependències descrites a la següent url són requerides per tal de fer funcionar el servei:
Dependències Connector amb GECAT

A qui va dirigit

Aquest document va dirigit als següents perfils:

  1. Programador. Per conéixer l'ús del connector.
  2. Arquitecte. Per conéixer quins són els components i la configuració del connector.

Documents i Fonts de Referència

[1] Anàlisi Funcional - Connector Serveis Funcionals - 16-Nov.doc Document d'anàlisi dels connectors de serveis funcionals.
[2] Consultes a SAP_Annex.doc  
[3] XCOM_GECAT.doc  
[4] XCOM_SAP_to_REMOTS.doc  
[5] XCOM-HOST.doc  
[6] Crides Java a GECAT.pdf  

Descripció Detallada

Arquitectura i Components

Interfícies i Components Genérics

Es pot trobar tota la documentació JavaDoc i el codi font referent aquests components a les següents urls:

JavaDoc: http://canigo.ctti.gencat.net/confluence/canigodocs/site/canigo2_0/canigo-connectors-root/canigo-connectors-gecat/apidocs/index.html
Codi Font:  http://canigo.ctti.gencat.net/confluence/canigodocs/site/canigo2_0/canigo-connectors-root/canigo-connectors-gecat/xref/index.html

Versions disponibles

Actualment existeixen dos versions del connector GECAT, el connector GECAT tal i com el coneixem fins ara i el nou connector GECAT09 que inclou una sèrie de canvis per adaptar-se a les especificacions funcionals de GECAT (codi PEP - codi PIP)  que afecta a certes funcionalitats a partir del 2009. (Per més informació sobre les especificacions funcionals de GECAT poseu-vos en contacte amb els responsables d'aquest servei).

Els projectes que no es vegin afectats per aquests canvis no estan obligats a actualitzar-se a la darrera versió ja que aquestes són independents entre elles i es portarà un manteniment de les dos.

A partir d'ara en aquest document es farà referència al connector GECAT09 però és totalment compatible amb el connector GECAT.

Instal.lació i Configuració

Per poder utilitzar el connector haurem de configurar el projecte perque inclogui 2
llibreries dll i diferents jars:

Les llibreries són sapjcorfc.dll i librfc32.dll i s'han de copiar al directori system32.
Per fer les operacions sobre el sistema SAP del Gecat és necessària la utilització del jar sapjco-2.1.6, que és el connector propi del SAP per fer les crides a les seves funcions BAPI (RFC).
Les classes que utilitzarem per fer els objectes d'operacions estan en el jar del connector Gecat09 canigo-connectors-gecat09-2.3.2.jar
Les classes que utilitzarem per fer les operacions han estat generades amb una eina Open Source anomenada JAXB (Java API for Xml Binding), que genera classes java a partir d'un esquema de xml (XMLSchema). Aquesta eina ens permet no solament generar automàticament classes java sinó també fer validacions per comprovar que les dades que contenen els objectes són vàlides. Per això també haurem d'incloure els jars que necessita JAXB:

- jaxb-api-1.0.1.jar
- jaxb-libs-1.0.1.jar
- jaxb-impl-1.0.1.jar
- jax-qname-1.1.jar
- namespace-1.0.1.jar
- relaxngDatatype-1.0.1.jar
- xsdlib-1.1.2.jar

Aquests jars els inclourem mitjançant les dependencies del projecte definides en l'arxiu pom.xml, tal com acabem d'explicar. Concretament, l'entrada amb la dependència serà tal com

<dependency>
    <groupId>canigo.connectors</groupId>
    <artifactId>canigo-connectors-gecat09</artifactId>
    <version>2.3.2</version>
</dependency>




Ara executarem el goal de Maven 'ctti:generate-classpath' per regenerar la configuració del classpath del projecte en funció del fitxer de project.xml. Aquest goal està definit dins de maven.xml:
<goal name="ctti:generate-classpath"

description="Shortcut in Eclipse  for the goal eclipse:generate-classpath">

<attainGoal  name="eclipse:generate-classpath"/>

</goal>











Utilització del Servei

La utilització del Connector es basa principalment en la configuració. L'ús directe des dels clients es permet mitjançant les interfícies definides.

El connector del Gecat ofereix tres operacions: alta de factures online, consultes i reserves. Cada operació té una classe que conté tota la informació de l'operació (o crida) i un altra amb la informació que retorna SAP per aquesta operació. Cada classe conté un altra classe per cada línia que tingui l'operació.
Si per exemple tenim l'operació consultaFactura, que conté una sola línia, daddadesConsulta, haurem de crear un objecte de la classe DadesConsultaFacturaType i un altre de DadesConsultaType. Aquesta última l'omplirem amb totes les dades que facin falta mitjançant els seus mètodes setters (setSocietat, setCodiCreditor, etc..). Un cop omplert del tot aquest objecte (que representa una sola línia), l'assignarem a l'altre (que és el que representa tota la consulta) mitjançant també un mètode setter: dadesConsultaFactura.setDadesConsulta(dadesConsulta). Si tingués més línies, hauríem de fer el mateix per a totes.
En el cas en que una mateixa línia pugui aparèixer més d'una vegada la forma de fer les operacions canvia, ja que el conjunt de totes les línies del mateix tipus aniran dins d'una llista.
Un cop hem creat l'objecte de crida amb totes les dades necessàries, utilitzarem un objecte de la classe GecatConnector per obtenir l'objecte de retorn amb les dades retornades pel SAP.

L'objecte gecatConnector es pot crear per injecció amb spring, amb la següent definició del bean dins d'un arxiu xml de configuració:

<beans>



      <bean id="gecatConnector"  class="net.gencat.gecat.connector.GecatConnector">

          <property  name="sapService">

                  <ref  bean="sapService"/>

            </property>

             <property name="logService">

                  <ref  bean="loggingService"/>

            </property>

       </bean>



</beans>











Podem veure que el bean gecatConnector conté dos objectes: sapService i loggingService. Aquests beans també han d'estar definits en algún altre fitxer de configuració (podria ser el mateix) d'spring:
- sapService:
<beans>

<!-- SAP service -->
<beans>

<bean id="sapService" class="net.ctti.canigo.services.sap.impl.JCOSapService">
<property name="sapConfigurator">
<ref local="sapConfigurator"/>
</property>
<property name="logService" ref="loggingService"/>
</bean>

<bean id="sapConfigurator" class="net.ctti.canigo.services.sap.impl.JCOSapConfigurator">
<property name="client" value="client_value" />
<property name="user" value="user_name" />
<property name="passwd" value="pwd" />
<property name="lang" value="lang" />
<property name="ashost" value="host_name" />
<property name="sysnr" value="sysnr_value" />
<property name="repository" value="repository_name" />
<property name="connectionPool" value="true" />
<property name="connectionPoolName" value="connection_pool_name" />
</bean>

</beans>










- loggingService:
<beans>
<bean id="loggingConfigurator"
class="net.ctti.canigo.services.logging.log4j.xml.HostDOMConfigurator">
<property name="configFileName" value="classpath:log4j/log4j.xml">
</property>
</bean>
<bean id="loggingService"
class="net.ctti.canigo.services.logging.log4j.Log4JServiceImpl"
init-method="init">
<property name="configurator">
<ref local="loggingConfigurator" />
</property>
</bean>
</beans>










En el cas de no utilitzar spring, haurem de crear aquests beans manualment i assignar-los al gecatConnector mitjançant els respectius mètodes setters.


Integració amb Altres Serveis

Integració amb el Servei de Internacionalització

En els fitxers de configuració es defineixen claus que permeten especificar quins missatges retornar en cas errors. Per a poder traduir aquestes claus és necessari especificar que el connector usarà el Servei d'Internacionalització (veure Configuració).

Exemples

Crides a Gecat sense línies repetides

1. Retorn sense línies repetides

Per mostrar aquest tipus de crida agafarem com exemple la consulta de partida pressupostària.
Primerament crearem tots els objectes que necessitarem per fer el procediment:

net.gencat.gecat.consultes.ConsultaPartidaPressupostaria.ObjectFactory objectFactory = new net.gencat.gecat.consultes.ConsultaPartidaPressupostaria.ObjectFactory();

La classe ObjectFactory és, com el seu nom indica, una classe per crear objectes d'altres classes. Aquestes classes són les que ofereix JAXB per crear objectes amb una certa estructura predefinida. Crearem un objecte de la classe ObjectFactory per crear els objectes que serviran per fer la crida (objectFactory).

Seguidament crearem un objecte que representarà la crida completa. Aquest objecte contindrà un objecte per a cada línia que tingui la crida. Aquests objectes són els que s'han de completar amb la informació de la crida.

DadesConsultaPartidaPressupostariaType dadesConsultaPartidaPressupostaria = objectFactory.createDadesConsultaPartidaPressupostariaType();

DadesConsultaType dadesConsulta = objectFactory.createDadesConsultaType();

dadesConsulta.setCentreGestor("1006");

dadesConsulta.setEntitatCP("1000");

dadesConsulta.setExercici("2002");

dadesConsulta.setPosicioPressupostaria("D/220100100/4551");

dadesConsulta.setVinculacio("S");

dadesConsultaPartidaPressupostaria.setDadesConsulta(dadesConsulta);

Amb aquest objecte ja podem fer la crida al SAP mitjançant el mètode consultaPartidaPressupostaria de la classe GecatConnector. Aquesta funció requereix de l'objecte de consulta.

DadesConsultaPartidaPressupostariaRetornType dadesConsultaRetorn = gecatConnector.consultaPartidaPressupostaria(dadesConsultaPartidaPressupostaria);

En aquest punt ja tenim l'objecte de retorn llest per a ser utilitzat per l'aplicació.

System.out.println("getDenominacio():" + dadesConsultaRetorn.getDadesRetorn().getDenominacio());

2. Retorn amb línies repetides
Per mostrar aquest tipus de crida agafarem com exemple la consulta de creditor.
Primerament crearem tots els objectes que necessitarem per fer el procediment:

net.gencat.gecat.consultes.ConsultaCreditor.ObjectFactory objectFactory = new net.gencat.gecat.consultes.ConsultaCreditor.ObjectFactory();

La classe ObjectFactory és, com el seu nom indica, una classe per crear objectes d'altres classes. Aquestes classes són les que ofereix JAXB per crear objectes amb una certa estructura predefinida. Crearem un objecte de la classe ObjectFactory per crear els objectes que serviran per fer la crida (objectFactory).

Seguidament crearem un objecte que representarà la crida completa. Aquest objecte contindrà un objecte per a cada línia que tingui la crida.

DadesConsultaCreditorType dadesConsultaCreditor = objectFactory.createDadesConsultaCreditorType();

DadesConsultaType dadesConsulta = objectFactory.createDadesConsultaType();

dadesConsulta.setNIFoCodiCreditor("A53062927");

dadesConsulta.setRegistreInicial("001");

dadesConsulta.setSocietat("1000");

dadesConsultaCreditor.setDadesConsulta(dadesConsulta);

Haurem de passar al connector l'objecte de consulta mitjançant el mètode consultaCreditor de l'objecte gecatConnector:

DadesConsultaCreditorRetornType dadesConsultaRetorn = gecatConnector.consultaCreditor(dadesConsultaCreditor);

Ara ja tenim l'objecte de retorn llest per a ser utilitzat:

List finalList = dadesConsultaRetorn.getDadesRetorn().getDadaRetorn();
System.out.println("dadaRetorn.getAdreca:" + ((DadaRetornType)finalList.get(0)).getAdreca());











Crides a Gecat amb línies repetides

Per mostrar aquest altre tipus de crida prendrem com exemple l'alta de factures habilitats.
Crearem tots els objectes que necessitarem per fer el procediment:

net.gencat.gecat.factures.Factures.ObjectFactory objectFactory = new net.gencat.gecat.factures.Factures.ObjectFactory();

La classe ObjectFactory és, com el seu nom indica, una classe per crear objectes d'altres classes. Aquestes classes són les que ofereix JAXB per crear objectes amb una certa estructura predefinida. Crearem un objecte de la classe ObjectFactory per crear els objectes que serviran per fer la crida (objectFactory).

Seguidament crearem un objecte que representarà la crida completa. Aquest objecte contindrà un objecte per a cada línia (o conjunt de línies) que tingui la crida.

DaDadesAltaFacturesHabilitatsOnlineType dadesAltaFacturaHabilitats = objectFactory.
createDadesAltaFacturesHabilitatsOnlineType();

DadesGeneralsFacturaType dadesGeneralsFactura = objectFactory.createDadesGeneralsFacturaType();

dadesGeneralsFactura.setDataCompt("24051980");
dadesGeneralsFactura.setDataDocument("01");
.
.
.
dadesGeneralsFactura.setTransaccio("ZD21");

dadesAltaFacturaHabilitats.setDadesGeneralsFactura(dadesGeneralsFactura);










Si la línia pot estar repetida, com en el cas de retencions habilitat subhabilitat, haurem de crear una llista d'objectes que representen una línia:
RetencionsHabilitatSubhabilitatType retencionsHS = objectFactory.
createRetencionsHabilitatSubhabilitatType();

List retencionsHSList = retencionsHS.getRetencioHabilitatSubhabilitat();

RetencioHabilitatSubhabilitatType retencioHS = objectFactory.
createRetencionsHabilitatSubhabilitatTypeRetencioHabilitatSubhabilitatType();

retencioHS.setImportBase("1500");
retencioHS.setImportRetencio("25000");
retencioHS.setIndicadorRetencio("01");
retencioHS.setTipusRegistre("3");
retencioHS.setOrder(new BigInteger("0"));

retencionsHSList.add(retencioHS);

retencioHS = (RetencioHabilitatSubhabilitatType)retencioHS.getClass().newInstance();

retencioHS.setImportBase("1600");
retencioHS.setImportRetencio("26000");
retencioHS.setIndicadorRetencio("01");
retencioHS.setTipusRegistre("3");
retencioHS.setOrder(new BigInteger("1"));

retencionsHSList.add(retencioHS);

dadesAltaFacturaHabilitats.setRetencionsHabilitatSubhabilitat(retencionsHS);










Fixem-nos que és important donar un ordre a les línies contingudes en la llista:
retencioHS.setOrder(0);










Amb aquest objecte ja podem fer la crida al SAP, mitjançant el mètode altaFacturesHabilitats de l'objecte *gecatConnector*:
DadesConsultaCreditorRetornType dadesConsultaRetorn = gecatConnector.consultaCreditor(dadesConsultaCreditor);
Ara ja disposem de l'objecte de retorn per a ser utilitzat:
List finalList = dadesAltaFacturaRetorn.getDadesRetorn().getDadaRetorn();

System.out.println("dadaRetorn.getClasseDocument():" +
((DadaRetornType)finalList.get(0)).getClasseDocument());













Usuaris de prova

S'han habilitat dos usuaris per a fer proves amb el connector de Gecat. Aquests usuaris es poden fer servir en les proves de desenvolupament, però mai per a producció.

ZBTCCANIGO per a les interfases "batch".

ZINTCANIGO per a les interfases "on-line".

Versió Optimitzada

S'ha portat a terme una optimització del connector de GECAT per tal de reduïr el seu número de classes i com a conseqüència el seu tamany.
Per tal de fer-ho s'han modificat una sèrie de classes, concretament s'han traslladat totes les classes del paquet runtime de la pròpia funcionalitat a un paquet comú accessible per aquestes.

Aquest canvi no hauria d'afectar a cap projecte ja que les classes modificades són utilitzades internament pel propi connector.
Per realitzar el canvi només s'ha de descarregar la nova versió i sobreescriure l'anterior al repositori local de maven.

Podeu trobar la nova versió per descarregar-la al següent enllaç

Nota: El connector GECAT09 ja inclou aquesta optimització