tuan
11/7/2015 - 1:12 PM

Functions which convert from csv to xml #XML #PHP #CSV #Convert

Functions which convert from csv to xml #XML #PHP #CSV #Convert

<?php

class convertCsvToXml {

    protected $arrCol = ["a", "b", "c"];
    protected $arrXPath = [
        0 => "product-families/product-family[name='{{f-name}}']/product-models",
        1 => "product-families/product-family[name='{{f-name}}']/product-models/product-model[name='{{m-name}}']/accessory-types",
        2 => "product-families/product-family[name='{{f-name}}']/product-models/product-model[name='{{m-name}}']/accessory-types/accessory-type[name='{{a-name}}' or sku='{{sku}}']",
    ];

    protected $csvDelimiter = ",";
    protected $arrData = [];
    protected $file;


    public function __construct()
    {
    }

    /**
     * Set path to csv file
     *
     * @param $file
     * @throws Exception
     */
    public function setFileCsvPath($file)
    {
        if(!file_exists($file)) {
            throw new Exception("Cannot open file: " . $file);
        }
        $this->file = $file;
    }

    /**
     * get arr data
     *
     * @return array
     * @throws Exception
     */
    public function getArrDataFromFileCsv()
    {
        if(!file_exists($this->file)) {
            throw new Exception("File path cannot be found");
        }

        $file = $this->file;
        $arr = file($file);
        array_filter($arr, function(&$v) {
            $v = str_replace(["\r\n", "\n", "\r"], "", $v);
        });

        return $this->_specialRule($arr);

    }

    /**
     * merge sku and name into an array of row
     *
     * @param $arr
     * @return array
     */
    private function _specialRule($arr)
    {
        $return = [];

        foreach ($arr as $l) {
            list($pf, $pm, $an, $asku) = explode($this->csvDelimiter, $l);
            $return[] = [
                ["name" => $pf],
                ["name" => $pm],
                [
                    "name" => $an,
                    "sku" => $asku,
                ],
            ];
        }

        return $return;
    }

    /**
     * Get xpath by level
     *
     * @param $index
     * @param $arrRow
     * @return bool|mixed
     */
    public function fullfillXpath($index, $arrRow) {
        if(!isset($this->arrXPath[0])) return false;

        if($index == 0 ) {
            return preg_replace("/{{f-name}}/", $arrRow[0]['name'], $this->arrXPath[0]);
        }

        if(!isset($this->arrXPath[1])) return false;
        if($index == 1) {
            return preg_replace(["/{{f-name}}/", "/{{m-name}}/"], [$arrRow[0]['name'], $arrRow[1]['name']], $this->arrXPath[1]);
        }

        if(!isset($this->arrXPath[2])) return false;
        if($index == 2) {
            return preg_replace(["/{{f-name}}/", "/{{m-name}}/", "/{{a-name}}/", "/{{sku}}/"], [$arrRow[0]['name'], $arrRow[1]['name'], $arrRow[2]['name'], $arrRow[2]['sku']], $this->arrXPath[2]);
        }
    }

    /**
     * Create xml element
     *
     * @param $root
     * @param $parent
     * @param $index
     * @param $row
     * @return mixed
     */
    private function _createElement($root, $parent, $index, $row)
    {
        if($index === 0) {
            $pf = $root->createElement("product-family");
            $name = $root->createElement("name");
            $pms =  $root->createElement("product-models");
            $name->appendChild($root->createCDATASection($row[0]["name"]));

            $pf->appendChild($name);
            $pf->appendChild($pms);
            $parent->appendChild($pf);


            return $pms;
        }
        elseif($index === 1) {
            $pm = $root->createElement("product-model");
            $ats = $root->createElement("accessory-types");
            $name = $root->createElement("name");

            $name->appendChild($root->createCDATASection($row[1]["name"]));
            $pm->appendChild($name);
            $pm->appendChild($ats);
            $parent->appendChild($pm);

            return $ats;
        }
        elseif($index === 2) {
            $at = $root->createElement("accessory-type");
            $name = $root->createElement("name");
            $name->appendChild($root->createCDATASection($row[2]["name"]));
            $sku = $root->createElement("sku");
            $sku->appendChild($root->createCDATASection($row[2]["sku"]));

            $at->appendChild($name);
            $at->appendChild($sku);


            $parent->appendChild($at);

            return $at;
        }
    }

    /**
     * Toxml string
     *
     * @return string
     * @throws Exception
     */
    public function toXML()
    {
        $root_name = "config";

        $doc = new DomDocument('1.0', 'UTF-8');
        $docXPath = new DOMXPath($doc);
        $root = $doc->createElement($root_name);
        $pfs = $doc->createElement("product-families");
        $doc->appendChild($root);
        $root->appendChild($pfs);

        $arrData = $this->getArrDataFromFileCsv();

        foreach($arrData as $row) {

            $lastParent = $pfs;
            foreach($row as $k => $v) {

                // Find node
                $xPath = $this->fullfillXpath($k, $row);
                syslog(LOG_ERR, $xPath);
                $node = $docXPath->query($xPath);

                if($node !== false && $node->length !== 0 ) {
                    $lastParent = $node->item(0);
                    continue;
                }
                else {
                    $lastParent = $this->_createElement($doc,$lastParent,  $k, $row);
                }
            }

        }

        return $doc->saveXML();
    }

}