Jak z xml vytvořit kategorie

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
jAkErCZ
Člen | 324
+
0
-

Zdravím,
mám takový jednoduchý xml perser a rád bych ho upravil na nového dodavetele který mi poskytl xml produktů.. jenže jde o vytváření kategorií ve starém xml to bylo děláno formou

<level1>Kemp</level1>
<level2>Les</level2>
<level3>Spacáky</level3>

Php který vytvářel kategorie

 public function zpracujXmlKategorie($xml) {

        $poleLevel1 = [
            'Outdoor' => 2
        ];

        foreach ($xml->StoItem as $item) {
            $tmp1 = explode(' ', $item->SPresentTree->Level1);
            unset($tmp1[0]);
            $level1 = trim(implode(' ', $tmp1));
            $idLevel0 = isset($poleLevel1[$level1]) ? $poleLevel1[$level1] : false;

            /* level 1 */
            if ($level1) {
                $data = $this->vratDataProKategorii($idLevel0, $level1);
                $kategorieId_1 = $this->connection->query(sprintf('SELECT category_id FROM category WHERE url = "%s" LIMIT 1', $data['url']))->fetch();
                if (!$kategorieId_1) {
                    $this->connection->query('INSERT INTO category', $data);
                    Debugger::log(sprintf('Vytvořena kategorie úrovně %d s názvem %s', 1, $level1), 'import');
                    $kategorieId_1 = $this->connection->getInsertId();
                } else {
                    $kategorieId_1 = $kategorieId_1->category_id;
                }

                /* level 2 */
                $tmp2 = explode(' ', $item->SPresentTree->Level2);
                unset($tmp2[0]);
                $level2 = trim(implode(' ', $tmp2));
                if ($level2) {
                    $data = $this->vratDataProKategorii($kategorieId_1, $level2);
                    $kategorieId_2 = $this->connection->query(sprintf('SELECT category_id FROM category WHERE url = "%s" LIMIT 1', $data['url']))->fetch();
                    if (!$kategorieId_2) {
                        $this->connection->query('INSERT INTO category', $data);
                        Debugger::log(sprintf('Vytvořena kategorie úrovně %d s názvem %s', 2, $level2), 'import');
                        $kategorieId_2 = $this->connection->getInsertId();
                    } else if (is_object($kategorieId_2)){
                        $kategorieId_2 = $kategorieId_2->category_id;
                    }

                    /* level 3 */
                    $tmp3 = explode(' ', $item->SPresentTree->Level3);
                    unset($tmp3[0]);
                    $level3 = trim(implode(' ', $tmp3));
                    if ($level3) {
                        $data = $this->vratDataProKategorii($kategorieId_2, $level3);
                        $kategorieId_3 = $this->connection->query(sprintf('SELECT category_id FROM category WHERE url = "%s" LIMIT 1', $data['url']))->fetch();
                        if (!$kategorieId_3) {
                            $this->connection->query('INSERT INTO category', $data);
                            Debugger::log(sprintf('Vytvořena kategorie úrovně %d s názvem %s', 3, $level3), 'import');
                        }
                    }
                }
            }
        }
    }

Ale od dodavatele nového mám nový xml kde kategorie jsou dělány takto

<CATEGORIES>
<CATEGORY id="20390" parent_id="0">Sacharidy, gainery</CATEGORY>
<CATEGORY id="20391" parent_id="20390">Do 20% proteinů, bílkovin</CATEGORY>
<CATEGORY id="20392" parent_id="20391">Do 2500g</CATEGORY>
</CATEGORIES>

Jak tedy funkci zpracujXmlKategorie($xml) upravit tak aby to fungovalo?

Předem děkuji všem za pomoc :)

GEpic
Člen | 566
+
+1
-

Pokud dostáváš různé formáty ale potřebuješ s nimi pracovat, jako by to byl jeden formát, udělej si nějaký interface pro parsování a ten poté implementuj pro každý parser (dodavatele) zvlášť, aby si nemusel bastlit vše do jedné funkce.

Toto si pak zavolej pro každý případ zvlášť a databázi a uložení bych řešil až někde mimo. Nechal bych parser dělat čistě jen parsování.

interface ICategoryParser
{
	public function parseCategories(string $xml): array;
}


class Dodavatel1CategoryParser implements ICategoryParser
{
	public function parseCategories(string $xml): array
	{
		// nějaká logika
	}
}


class Dodavatel2CategoryParser implements ICategoryParser
{
	public function parseCategories(string $xml): array
	{
		// nějaká jina logika
	}
}

Nechápu sice souvislost mezi kempy, spacáky a gainery. Každopádně formát pole, které vrací funkce parseCategories, by měl být naprosto totožný ať už ho voláš na jakémkoliv dodavateli, aby kdokoliv kdo bude nějaký z parserů volat, nemusel řešit jeho formát.

V tvém případě bych si vymyslel nějaký vlastní abstraktní formát dat, který bude předvídat xml v jakémkoliv jiném formátu (např. že v druhém případě, kde máš parent_id, abych si rovnou tato data zanořil do dalšího rozměru pod tohoto parenta a tento údaj úplně vyhodil, jelikož je to nějaké externí číslování, které ti může akorát přidělat starosti.)

Editoval GEpic (31. 7. 2018 22:35)