Vous cherchez à créer un flux XML à partir d'un tableau de feuilles Google
Vous cherchez de l'aide s'il vous plaît, j'ai bricolé avec le code presque toute la journée et je suis bloqué, et cela semble être la meilleure solution que j'ai trouvée jusqu'à présent.
J'essaie de créer un script qui créera un fichier XML à partir d'un tableau Google Sheet.
La feuille d'exemple est comme ceci >>https://docs.google.com/spreadsheets/d/1tSWMiXBRyhFcAmwpH5tEJiyHCB5vjlGwuHFv865-85A/edit?usp=sharing
Je suis tombé sur cet exemple de code Google Script Export Spreadsheet to XML File et c'est à 90% ce dont j'ai besoin et je l'ai fait fonctionner via la publication en tant qu'application Web ici >>https://script.google.com/macros/s/AKfycbxVcUi6dXw0D1CWfZTlwf94gAT9QjqpG__-SaCIHVFVPzftndU/exec?id=1tSWMiXBRyhFcAmwpH5tEJiyHCB5vjlGwuHFv865-85A
Je suis maintenant bloqué pour le faire boucler sur les en-têtes et les valeurs car le XML doit être formaté.
Je rencontre également certaines des valeurs ont des attributs, donc je trouve difficile d'ajouter le xml:lang="x-default" dans l'exemple ci-dessous 10h : 18h
Voici un exemple de ce que j'essaie de créer
<store store-id="F123">
<name>Store One</name>
<address1>123 Street</address1>
<address2></address2>
<city>London</city>
<postal-code>L67 9JF</postal-code>
<phone>123 456</phone>
<store-hours xml:lang="x-default">10AM | 6PM</store-hours>
<custom-attribute attribute-id="freeTextTitle" xml:lang="x-default">Store Description Title</custom-attribute>
<custom-attribute attribute-id="v3_store_open_hours_0" xml:lang="x-default">11 AM|7 PM</custom-attribute>
</store>
<store store-id="G456">
<name>Store Two</name>
<address1>123 Street</address1>
<address2></address2>
<city>Manchester</city>
<postal-code>L67 9DS</postal-code>
<phone>123 456</phone>
<store-hours xml:lang="x-default">10AM | 6PM</store-hours>
<custom-attribute attribute-id="freeTextTitle" xml:lang="x-default">Store Description Title</custom-attribute>
<custom-attribute attribute-id="v3_store_open_hours_0" xml:lang="x-default">11 AM|7 PM</custom-attribute>
</store>
Merci beaucoup
** Ajout de plus de contexte
Merci, Tous les deux, je suis en fait bloqué sur la fonction JavaScript map() dans la fonction doIt essayant de mapper les en-têtes et les attributs
function doGet(e) {
var content;
try {
content = doIt(e);
} catch(err) {
content = '<error>' + (err.message || err) + '</error>';
}
return ContentService.createTextOutput(content).setMimeType(ContentService.MimeType.XML);
}
function doIt(e) {
if (!e) throw 'you cannot run/debug this directly\nyou have to either call the url or mock a call';
if (!e.parameter.id) throw '"id" parameter not informed. Please provide a spreadsheet id.';
var values = SpreadsheetApp.openById(e.parameter.id).getSheets()[0].getRange('A1:J4').getValues();
return '<sheet>' + values.map(function(row, i) {
return '<row>' + row.map(function(v) {
return '<cell>' + v + '</cell>';
}).join('') + '</row>';
}).join('') + '</sheet>';
}
values saisit toutes les valeurs de la plage, mais je suis un peu perdu en essayant de décomposer les valeurs.
J'ai fait quelques lectures sur la fonction map() donc je vais encore essayer
Réponses
En tant que simple modification, que diriez-vous de la modification suivante ?
Dans votre script, les balises <sheet>
, <row>
et sont utilisées. <cell>
Mais il semble que ceux-ci ne soient pas inclus dans votre résultat attendu. Lorsque vous souhaitez utiliser la ligne d'en-tête de la 1ère ligne comme chaque balise, il est nécessaire de les utiliser dans le script. Lorsque votre script est modifié, il devient comme suit.
Scénario modifié :
Dans cette modification, votre doIt()
a été modifié.
function doIt(e) {
if (!e) throw 'you cannot run/debug this directly\nyou have to either call the url or mock a call';
if (!e.parameter.id) throw '"id" parameter not informed. Please provide a spreadsheet id.';
var values = SpreadsheetApp.openById(e.parameter.id).getSheets()[0].getRange('A1:J4').getValues();
// I modified below script.
var header = values.shift();
return values.reduce((s, r) => {
r.forEach((c, j, a) => {
s += j == 0 ? `<${header[j]}="${c}">` : `<${header[j]}>${c}<\/${header[j].split(" ")[0]}>`;
if (j == a.length - 1) s += `<\/${header[0].split(" ")[0]}>`;
});
return s;
}, "");
}
Résultat:
Lorsque le script modifié ci-dessus est exécuté, le résultat suivant est obtenu.
<store store-id="F123">
<name>Store One</name>
<address1>123 Street</address1>
<address2 />
<city>London</city>
<postal-code>L67 9JF</postal-code>
<phone>123 456</phone>
<store-hours xml:lang="x-default">10AM | 6PM</store-hours>
<custom-attribute attribute-id="freeTextTitle" xml:lang="x-default">Store Description Title</custom-attribute>
<custom-attribute attribute-id="v3_store_open_hours_0" xml:lang="x-default">11 AM|7 PM</custom-attribute>
</store>
<store store-id="G456">
<name>Store Two</name>
<address1>124 Street</address1>
<address2 />
<city>Manchester</city>
<postal-code>L67 9DS</postal-code>
<phone>124 111</phone>
<store-hours xml:lang="x-default">9AM | 5PM</store-hours>
<custom-attribute attribute-id="freeTextTitle" xml:lang="x-default">Store Description Title</custom-attribute>
<custom-attribute attribute-id="v3_store_open_hours_0" xml:lang="x-default">12 AM|7 PM</custom-attribute>
</store>
<store store-id="J542">
<name>Store Three</name>
<address1>777 High Street</address1>
<address2 />
<city>Leeds</city>
<postal-code>L7 9GG</postal-code>
<phone>555 222</phone>
<store-hours xml:lang="x-default">10AM | 6PM</store-hours>
<custom-attribute attribute-id="freeTextTitle" xml:lang="x-default">Store Description Title</custom-attribute>
<custom-attribute attribute-id="v3_store_open_hours_0" xml:lang="x-default">12 AM|7 PM</custom-attribute>
</store>
Noter:
Lorsque vous utilisez le résultat ci-dessus comme données xml, par exemple, je pense qu'il est nécessaire de joindre like
<contents>{above results}</contents>
. S'il vous plaît soyez prudent cela. Donc, si vous souhaitez exporter les données XML valides, veuillez utiliser le script suivant. Dans ce cas,<contents>
est un exemple de balise.function doIt(e) { if (!e) throw 'you cannot run/debug this directly\nyou have to either call the url or mock a call'; if (!e.parameter.id) throw '"id" parameter not informed. Please provide a spreadsheet id.'; var values = SpreadsheetApp.openById(e.parameter.id).getSheets()[0].getRange('A1:J4').getValues(); // I modified below script. var header = values.shift(); var data = values.reduce((s, r) => { r.forEach((c, j, a) => { s += j == 0 ? `<${header[j]}="${c}">` : `<${header[j]}>${c}<\/${header[j].split(" ")[0]}>`; if (j == a.length - 1) s += `<\/${header[0].split(" ")[0]}>`; }); return s; }, ""); return XmlService.getPrettyFormat().format(XmlService.parse(`<contents>${data}$</contents>`)); }
Lorsque vous avez modifié le script des Web Apps, veuillez redéployer les Web Apps en tant que nouvelle version. Ainsi, le dernier script est reflété dans les applications Web. S'il vous plaît soyez prudent cela.
Veuillez utiliser ce script avec l'activation de V8.
Références:
- réduire()
- pour chaque()