Javascript - jak šikovně uhandlovat XML
Dobrý den, celý den,
uff. Už jsem se něco nakódoval, tak teď dám prostor schopnějším.
Mám pseudo-XML s adresami :
<typ:id>6090</typ:id>
<typ:company>Společnost OKD</typ:company>
<typ:division>Bc. Kateřina Kalinovičová</typ:division>
<typ:city>Karlovy Vary</typ:city>
<typ:street>Újezdová</typ:street>
<typ:zip>360 01</typ:zip>
<typ:phone>766 152 101</typ:phone>
<typ:email>kalinovicova@email.cz</typ:email>
<typ:id>2626</typ:id>
<typ:company>Společnost ČKD</typ:company>
<typ:city>Karlovy Vary -Vrata</typ:city>
<typ:street>Jiřího Strnada</typ:street>
<typ:defaultShipAddress>true</typ:defaultShipAddress>
<typ:zip>360 01</typ:zip>
<typ:id>1230</typ:id>
<typ:company>Výtahy Stropnický</typ:company>
<typ:city>Karlovy Vary Vrhovice</typ:city>
<typ:street>Náměstí E. Dieslové</typ:street>
<typ:zip>360 07</typ:zip>
<typ:id>1263</typ:id>
<typ:company>Agrofert</typ:company>
<typ:city>Karlovy Vary -Olšová Vrata</typ:city>
<typ:street>Počernická 66</typ:street>
<typ:zip>360 01</typ:zip>
<typ:id>618</typ:id>
<typ:company>Fatra a.s.</typ:company>
<typ:city>Karlovy Vary - Budlínská</typ:city>
<typ:street>U Brodského 77</typ:street>
<typ:zip>360 07</typ:zip>
<typ:id>613</typ:id>
<typ:company>Benzina a.s.</typ:company>
<typ:city>Karlovy Vary U Benziny</typ:city>
<typ:street>Napadejelská 11</typ:street>
<typ:zip>360 07</typ:zip>
A potřeboval bych navést, jak elegantně vytvořit pole objektů typu Adresa v JavaScriptu:
Třeba:
adresa1 = {
id: '',
company: '',
division: '',
name: '',
city: '',
street: '',
zip: ''
}
poleAdres = new array();
poleAdres.push(adresa1);
V podstatě teď jsem narazil na část, kdy:
1)XML mám už ve stringu
2) Nemám úplně jasno v tom, jak ze stringu naplnit všechny objekty typu adresa1 a postupně jejich hodnoty (atributy)
Při čemž je potřeba brát v úvahu, co bych potřeboval zpracovat:
<typ:division> někdy je, a někdy není vůbec. Přesto pokud nebude nalezen, měl by být přítomen jako prázdný řetězec v objektu typu adresa1
Stejně tak třeba atribut <typ:phone> Nebo atribut <typ:email> Někdy jsou a někdy nejsou.
Trochu oříšek a už je večer.
Děkuji za každé řešení. 👍
Ukaž, co už máš za kód.
Nemyslím si, že je to o tom dělat ramena.
Do objektů typu adresa potřebuju "nastrouhat" jednotlivé části adresy (Ulice, jméno společnosti atd...)
adresa1 = {
id: '6090',
company: 'Společnost OKD',
division: 'Bc. Kateřina Kalinovičová',
city: 'Karlovy Vary',
street: 'Újezdová',
zip: '360 01',
phone: '766 152 101'
}
V podstatě mě napadá ne příliš elegantně explodovat řetězec na <typ:id>
tedy něco jako:
XML = 'celé XML';
XML1 = XML.split("<typ:id>"); // A tyto řetězce postupně prohledávat a vytvářet z nich jednotlivé objekty typu Adresa.
Ale je to neefektivní a škaredé. Ne moc čitelné.
Toto mě napadlo teď. Ale nechtěl bych jít touto cestou.
Jsou tady jiní borci, jako např. Wikan atp...
Opravdu nechápu, co je na tom o ukazování ramen. Sám jsi psal, že už máš něco hotového, tak je snad naprosto legitimní požadavek vědět co, aby nebylo nutné to psát od začátku.
Taky by se hodilo vědět, kde to děláš, jestli to potřebuješ v prohlížeči nebo ti to někdě běží v nodejs či podobně.
Oki, Má to běžet v prohlížeči.
XML = "
<typ:id>6090</typ:id>
<typ:company>Společnost OKD</typ:company>
<typ:division>Bc. Kateřina Kalinovičová</typ:division>
<typ:city>Karlovy Vary</typ:city>
<typ:street>Újezdová</typ:street>
<typ:zip>360 01</typ:zip>
<typ:phone>766 152 101</typ:phone>
<typ:email>kalinovicova@email.cz</typ:email>
<typ:id>2626</typ:id>
<typ:company>Společnost ČKD</typ:company>
<typ:city>Karlovy Vary -Vrata</typ:city>
<typ:street>Jiřího Strnada</typ:street>
<typ:defaultShipAddress>true</typ:defaultShipAddress>
<typ:zip>360 01</typ:zip>
<typ:id>1230</typ:id>
<typ:company>Výtahy Stropnický</typ:company>
<typ:city>Karlovy Vary Vrhovice</typ:city>
<typ:street>Náměstí E. Dieslové</typ:street>
<typ:zip>360 07</typ:zip>
<typ:id>1263</typ:id>
<typ:company>Agrofert</typ:company>
<typ:city>Karlovy Vary -Olšová Vrata</typ:city>
<typ:street>Počernická 66</typ:street>
<typ:zip>360 01</typ:zip>
<typ:id>618</typ:id>
<typ:company>Fatra a.s.</typ:company>
<typ:city>Karlovy Vary - Budlínská</typ:city>
<typ:street>U Brodského 77</typ:street>
<typ:zip>360 07</typ:zip>
<typ:id>613</typ:id>
<typ:company>Benzina a.s.</typ:company>
<typ:city>Karlovy Vary U Benziny</typ:city>
<typ:street>Napadejelská 11</typ:street>
<typ:zip>360 07</typ:zip>
";
Kde jednotlivé adresy v XML jsem pro přehlednost označil mezerou (ta tam není)
Potřebuji to přehodit do pole objektů, abych to mohl nabídnout uživateli.
Bude to teda takto zhruba:
function doplnAdresy(adresy) {
for(i=0; i<adresy.length; i++ ){
id = adresa[i].substring(adresa[i].indexOf("<typ:id>")+9, adresa[i].indexOf("</typ:id>"));
company = adresa[i].substring(adresa[i].indexOf("<typ:company>")+14, adresa[i].indexOf("</typ:company>"));
division = adresa[i].substring(adresa[i].indexOf("<typ:division>")+15, adresa[i].indexOf("</typ:division>"));
city = adresa[i].substring(adresa[i].indexOf("<typ:city>")+11, adresa[i].indexOf("</typ:city>"));
psc = adresa[i].substring(adresa[i].indexOf("<typ:zip>")+10, adresa[i].indexOf("</typ:zip>"));
ulice = adresa[i].substring(adresa[i].indexOf("<typ:street>")+13, adresa[i].indexOf("</typ:street>"));
... // zalozeni objektu a dalsi ops
}
}
Můžeš zkusit něco takového:
Ten řádek:
je tam proto, že v xml se před dvojtečkou uvádí namespace a tak potřebujeme říct parseru, co je to zač.
Pak už na tom můžeš iterovat přes:
Děkuji za nápad.
Už jsem to udělal takto:
function doplnAdresy(adresa) {
poleAdres = [];
id = "";
company= "";
division = "";
city = "";
street = "";
zip = "";
email = "";
telefon = "";
for(i=0; i<adresa.length; i++ ){
if(adresa[i].indexOf("<typ:id>") > -1)
id = adresa[i].substring(adresa[i].indexOf("<typ:id>")+9, (adresa[i].indexOf("</typ:id>")));
if(adresa[i].indexOf("<typ:company>") > -1 )
company = adresa[i].substring(adresa[i].indexOf("<typ:company>")+13, adresa[i].indexOf("</typ:company>"));
if(adresa[i].indexOf("<typ:division>") > -1)
division = adresa[i].substring(adresa[i].indexOf("<typ:division>")+14, adresa[i].indexOf("</typ:division>"));
if( adresa[i].indexOf("<typ:city>") > -1 )
city = adresa[i].substring(adresa[i].indexOf("<typ:city>")+10, adresa[i].indexOf("</typ:city>"));
if( adresa[i].indexOf("<typ:zip>") > -1 )
psc = adresa[i].substring(adresa[i].indexOf("<typ:zip>")+9, adresa[i].indexOf("</typ:zip>"));
if( adresa[i].indexOf("<typ:street>") > -1 )
ulice = adresa[i].substring(adresa[i].indexOf("<typ:street>")+12, adresa[i].indexOf("</typ:street>"));
if( adresa[i].indexOf("<typ:phone>") > -1)
telefon = adresa[i].substring(adresa[i].indexOf("<typ:phone>")+11, adresa[i].indexOf("</typ:phone>"));
if( adresa[i].indexOf("<typ:email>") > -1)
email = adresa[i].substring(adresa[i].indexOf("<typ:email>")+11, adresa[i].indexOf("</typ:email>"));
poleAdres[i] = {
id: id,
company: company,
division: division,
city: city,
street: ulice,
zip: psc,
phone: telefon,
email: email
}
}
}
Dost neefektivní a obtížně udržitelné. Ale pokud to funguje, nebude se tím parsovat velké množství dat nebo upravovovat v budoucnu, tak proč ne.
Tak asi čistší by IMHO bylo ten XM už vytvářet s tím, že jednotlivé adresy by byly uzavřené v nějakém tagu (třeba <adresa> kus XML </adresa><adresa> další kus XML</adresa>...) a pak to prostě nechat načíst jakoukoli standardní knihovnou
než následně vymýšlet rovnáky na vohejbáky ...