Talend : Transformer facilement un XML en JSON avec la librairie underscore

Posted on Tue, Jan 7, 2020 JSON JAVA ETL Talend Tuto XML API

La gestion de json un peu complexe peut rapidement devenir fastidieuse dans Talend.

En effet, on devait soit passer énormément de temps à essayer de configurer le composant tWriteJSONField ou alors écrire la génération du JSON directement en JAVA dans un composant tJava.

Pour palier à ce problème, j’ai découvert il y a quelques temps la librairie underscore qui facilite beaucoup le travail notamment si on passe par le composant tXMLMap.

Je vais donc vous la présenter dans ce petit tutoriel.

Objectif

Admettons que pour une API, nous voulons récupérer et retourner une liste de clients avec leurs informations.

Le format du JSON final sera tel que celui-ci :

{
	"clients": [
		{
			"client": {
				"ville": "Monaco",
				"codepostal": "29160-236",
				"adresse": "6942 Rutrum, Rd.",
				"telephone": "04 53 34 32 09",
				"id": 1,
				"nom": "Mckay",
				"prenom": "Austin",
				"email": "dapibus.quam.quis@convallisin.edu",
				"pays": "Sakhalin"
			}
		},
		{
			"client": {
				"ville": "Sri Lanka",
				"codepostal": "58964",
				"adresse": "P.O. Box 111, 1929 Vitae Ave",
				"telephone": "08 16 28 72 14",
				"id": 2,
				"nom": "Frazier",
				"prenom": "Flynn",
				"email": "arcu.Sed.eu@elitpede.org",
				"pays": "Fulda"
			}
		},
		{
			"client": {
				"ville": "Belgium",
				"codepostal": "56239",
				"adresse": "296-4590 Donec Av.",
				"telephone": "08 07 93 73 06",
				"id": 3,
				"nom": "Pacheco",
				"prenom": "Vernon",
				"email": "et.rutrum.non@luctusaliquet.edu",
				"pays": "Cuddalore"
			}
		}
	]
}

Pour notre tutoriel, j'ai stocké les informations dans une base de donnée Postgres :

Etapes :

Vue générale

Etape 1 : le prejob

Le prejob va comporter trois composants :

Je ne vais pas m’attarder sur les deux premiers composants et passer directement au tLibraryLoad dans lequel nous allons importer la libraire java underscore.

Pour se faire, nous devons récupérer le jar et l’importer dans le composant

Etape 2 : le traitement principal

  1. Dans le tDBInput, nous faisons une requête de select pour récupérer l'ensembles des informations des clients :
    SELECT
      id,
      nom,
      prenom,
      email,
      telephone,
      adresse,
      codepostal,
      pays,
      ville
    FROM
      clients
  2. Dans le tXMLMap, nous allons faire le "mapping" entre les données récupérées de la requête et le XML qui sera ensuite transformé en JSON. Nous voulons que le XML ait la structure suivante :
    <?xml version="1.0" encoding="UTF-8"?>
    <root>
    	<clients array="true">
    		<client>
    			<id number="true">1</id>
    			<nom>Mckay</nom>
    			<prenom>Austin</prenom>
    			<email>dapibus.quam.quis@convallisin.edu</email>
    			<telephone>04 53 34 32 09</telephone>
    			<adresse>6942 Rutrum, Rd.</adresse>
    			<codepostal>29160-236</codepostal>
    			<ville>Monaco</ville>
    			<pays>Sakhalin</pays>
    		</client>
    	</clients>
    	<clients array="true">
    		<client>
    			<id number="true">2</id>
    			<nom>Frazier</nom>
    			<prenom>Flynn</prenom>
    			<email>arcu.Sed.eu@elitpede.org</email>
    			<telephone>08 16 28 72 14</telephone>
    			<adresse>P.O. Box 111, 1929 Vitae Ave</adresse>
    			<codepostal>58964</codepostal>
    			<ville>Sri Lanka</ville>
    			<pays>Fulda</pays>
    		</client>
    	</clients>
    	<clients array="true">
    		<client>
    			<id number="true">3</id>
    			<nom>Pacheco</nom>
    			<prenom>Vernon</prenom>
    			<email>et.rutrum.non@luctusaliquet.edu</email>
    			<telephone>08 07 93 73 06</telephone>
    			<adresse>296-4590 Donec Av.</adresse>
    			<codepostal>56239</codepostal>
    			<ville>Belgium</ville>
    			<pays>Cuddalore</pays>
    		</client>
    	</clients>
    </root>

    Nous configurons donc le composant comme ceci :

    Ici, comme dans le JSON nous voulons que clients soit un tableau et que id soit un nombre, nous rajoutons les attributs array et number avec la valeur true pour les deux balises.

  3. Dans le tConvertType, nous transformons le XML du type Document au type String

  4. Enfin c'est dans le tJavaRow que nous allons utiliser la librairie underscore pour faire la transformation du XML vers JSON. Dans les Paramètres simples du composant, nous utilisons le code suivant :
    //Code généré selon les schémas d'entrée et de sortie
    
    String xmlToJson = U.xmlToJson(input_row.xml);
    JSONObject jsonMinify = new JSONObject(xmlToJson);
    
    
    output_row.json = ""+jsonMinify;

    La première ligne va créer une String qui va contenir le XML transformé en JSON. A la fin de cette première étape, le JSON obtenu va être sur plusieurs lignes. On passe donc par une seconde étape avec la création d’un objet JSON qui va nous permettre de remettre la JSON sur une seule ligne.

    Enfin la dernière étape correspond à la sortie du composant tJavaRow dans laquelle nous allons concaténer l’objet JSON à des doubles quotes pour le mettre en type String.

    Nous devons ensuite nous rendre dans les Paramètres avancés du composant, pour là aussi importer la librairie :

    import com.github.underscore.lodash.U;

    Nous pouvons ensuite lancer le job en rajoutant des composants tLogRow et observer le résultat :

    Starting job ws002_getAllClients at 14:48 14/03/2021.
    Null value will be used for context parameter id: For input string: ""
    [statistics] connecting to socket on port 3506
    [statistics] connected
    .--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
    |																																																																																		 tLogRow_2																																																																																		  |
    |=------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------=|
    |xml																																																																																																																																																																						 |
    |=------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------=|
    |<?xml version="1.0" encoding="UTF-8"?>
    <root><clients array="true"><client><id number="true">1</id><nom>Mckay</nom><prenom>Austin</prenom><email>dapibus.quam.quis@convallisin.edu</email><telephone>04 53 34 32 09</telephone><adresse>6942 Rutrum, Rd.</adresse><codepostal>29160-236</codepostal><ville>Monaco</ville><pays>Sakhalin</pays></client></clients><clients array="true"><client><id number="true">2</id><nom>Frazier</nom><prenom>Flynn</prenom><email>arcu.Sed.eu@elitpede.org</email><telephone>08 16 28 72 14</telephone><adresse>P.O. Box 111, 1929 Vitae Ave</adresse><codepostal>58964</codepostal><ville>Sri Lanka</ville><pays>Fulda</pays></client></clients></root>|
    '--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------'
    
    .---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
    |																																																						tLogRow_1																																																						|
    |=-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------=|
    |json																																																																																																													 |
    |=-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------=|
    |{"clients":[{"client":{"ville":"Monaco","codepostal":"29160-236","adresse":"6942 Rutrum, Rd.","telephone":"04 53 34 32 09","id":1,"nom":"Mckay","prenom":"Austin","email":"dapibus.quam.quis@convallisin.edu","pays":"Sakhalin"}},{"client":{"ville":"Sri Lanka","codepostal":"58964","adresse":"P.O. Box 111, 1929 Vitae Ave","telephone":"08 16 28 72 14","id":2,"nom":"Frazier","prenom":"Flynn","email":"arcu.Sed.eu@elitpede.org","pays":"Fulda"}}]}|
    '---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------'
    
    [statistics] disconnected
    
    Job ws002_getAllClients ended at 14:48 14/03/2021. [exit code  = 0]