/** * @param Object\ClassDefinition $class */ public function createUpdateTable(Object\ClassDefinition $class) { $table = $this->getTableName($class); $this->db->query("CREATE TABLE IF NOT EXISTS `" . $table . "` (\n\t\t `o_id` int(11) NOT NULL default '0',\n\t\t `index` int(11) default '0',\n `fieldname` varchar(190) default '',\n PRIMARY KEY (`o_id`,`index`,`fieldname`(190)),\n INDEX `o_id` (`o_id`),\n INDEX `index` (`index`),\n INDEX `fieldname` (`fieldname`)\n\t\t) DEFAULT CHARSET=utf8mb4;"); $existingColumns = $this->getValidTableColumns($table, false); // no caching of table definition $columnsToRemove = $existingColumns; $protectedColums = ["o_id", "index", "fieldname"]; Object\ClassDefinition\Service::updateTableDefinitions($this->tableDefinitions, [$table]); foreach ($this->model->getFieldDefinitions() as $value) { $key = $value->getName(); if (is_array($value->getColumnType())) { // if a datafield requires more than one field foreach ($value->getColumnType() as $fkey => $fvalue) { $this->addModifyColumn($table, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColums[] = $key . "__" . $fkey; } } else { if ($value->getColumnType()) { $this->addModifyColumn($table, $key, $value->getColumnType(), "", "NULL"); $protectedColums[] = $key; } } $this->addIndexToField($value, $table); if ($value instanceof Object\ClassDefinition\Data\Localizedfields) { $value->classSaved($class, ["context" => ["containerType" => "fieldcollection", "containerKey" => $this->model->getKey()]]); } } $this->removeUnusedColumns($table, $columnsToRemove, $protectedColums); $this->tableDefinitions = null; }
/** * @todo refactor steps into proper methods instead of doing it all in the action * @throws Exception */ public function indexAction() { // reachable via http://your.domain/plugin/Prototyper/admin/index $this->view->previewData = null; $this->view->csvText = $this->getParam('csv'); $this->view->classname = $this->getParam('classname'); $csvData = array(); $rowNr = 0; $rows = str_getcsv($this->view->csvText, "\n"); //parse the rows foreach ($rows as $row) { $rowNr++; $rowData = str_getcsv($row, ";"); $csvData[] = $rowData; if ($rowNr == 1) { $fieldNames = array(); $fieldTitles = array(); foreach ($rowData as $cell) { $fieldTitles[] = $cell; $fieldNames[] = $this->getFieldName($cell); } $csvData[] = $fieldNames; } if ($rowNr > 10) { break; } } $this->view->previewTable = $csvData; $fieldList = array(); foreach ($fieldNames as $fieldName) { $fieldTitle = array_shift($fieldTitles); ob_start(); include __DIR__ . "/../classes/field.json.php"; $fieldList[] = ob_get_clean(); } $fields = implode(',', $fieldList); ob_start(); include __DIR__ . "/../classes/object.json.php"; $jsonText = ob_get_clean(); if ($this->getParam('generate') != '') { $class = Object\ClassDefinition::getByName($this->correctClassname($this->getParam("classname"))); if ($class == null) { $class = Object\ClassDefinition::create(array('name' => $this->correctClassname($this->getParam("classname")), 'userOwner' => $this->user->getId())); $class->save(); } $class = Object\ClassDefinition::getById($class->getId()); $success = Object\ClassDefinition\Service::importClassDefinitionFromJson($class, $jsonText); if ($success) { $this->view->successMessage = '<strong>Class generation successful.</strong>'; } } }
/** * @param Object\ClassDefinition $class */ public function createUpdateTable(Object\ClassDefinition $class) { $tableStore = $this->getTableName($class, false); $tableQuery = $this->getTableName($class, true); $this->db->query("CREATE TABLE IF NOT EXISTS `" . $tableStore . "` (\n\t\t `o_id` int(11) NOT NULL default '0',\n `fieldname` varchar(255) default '',\n PRIMARY KEY (`o_id`,`fieldname`),\n INDEX `o_id` (`o_id`),\n INDEX `fieldname` (`fieldname`)\n\t\t) DEFAULT CHARSET=utf8;"); $this->db->query("CREATE TABLE IF NOT EXISTS `" . $tableQuery . "` (\n\t\t `o_id` int(11) NOT NULL default '0',\n `fieldname` varchar(255) default '',\n PRIMARY KEY (`o_id`,`fieldname`),\n INDEX `o_id` (`o_id`),\n INDEX `fieldname` (`fieldname`)\n\t\t) DEFAULT CHARSET=utf8;"); $existingColumnsStore = $this->getValidTableColumns($tableStore, false); // no caching of table definition $columnsToRemoveStore = $existingColumnsStore; $existingColumnsQuery = $this->getValidTableColumns($tableQuery, false); // no caching of table definition $columnsToRemoveQuery = $existingColumnsQuery; $protectedColumnsStore = ["o_id", "fieldname"]; $protectedColumnsQuery = ["o_id", "fieldname"]; Object\ClassDefinition\Service::updateTableDefinitions($this->tableDefinitions, [$tableStore, $tableQuery]); foreach ($this->model->getFieldDefinitions() as $value) { $key = $value->getName(); // if a datafield requires more than one column in the query table if (is_array($value->getQueryColumnType())) { foreach ($value->getQueryColumnType() as $fkey => $fvalue) { $this->addModifyColumn($tableQuery, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColumnsQuery[] = $key . "__" . $fkey; } } // if a datafield requires more than one column in the datastore table => only for non-relation types if (!$value->isRelationType() && is_array($value->getColumnType())) { foreach ($value->getColumnType() as $fkey => $fvalue) { $this->addModifyColumn($tableStore, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColumnsStore[] = $key . "__" . $fkey; } } // everything else if (!is_array($value->getQueryColumnType()) && !is_array($value->getColumnType())) { if ($value->getQueryColumnType()) { $this->addModifyColumn($tableQuery, $key, $value->getQueryColumnType(), "", "NULL"); $protectedColumnsQuery[] = $key; } if ($value->getColumnType() && !$value->isRelationType()) { $this->addModifyColumn($tableStore, $key, $value->getColumnType(), "", "NULL"); $protectedColumnsStore[] = $key; } } // add indices $this->addIndexToField($value, $tableStore); $this->addIndexToField($value, $tableQuery); } $this->removeUnusedColumns($tableStore, $columnsToRemoveStore, $protectedColumnsStore); $this->removeUnusedColumns($tableQuery, $columnsToRemoveQuery, $protectedColumnsQuery); }
/** * @param $table * @param $colName * @param $type * @param $default * @param $null */ protected function addModifyColumn($table, $colName, $type, $default, $null) { $existingColumns = $this->getValidTableColumns($table, false); $existingColName = null; // check for existing column case insensitive eg a rename from myInput to myinput $matchingExisting = preg_grep('/^' . preg_quote($colName, '/') . '$/i', $existingColumns); if (is_array($matchingExisting) && !empty($matchingExisting)) { $existingColName = current($matchingExisting); } if ($existingColName === null) { $this->db->query('ALTER TABLE `' . $table . '` ADD COLUMN `' . $colName . '` ' . $type . $default . ' ' . $null . ';'); $this->resetValidTableColumnsCache($table); } else { if (!Object\ClassDefinition\Service::skipColumn($this->tableDefinitions, $table, $colName, $type, $default, $null)) { $this->db->query('ALTER TABLE `' . $table . '` CHANGE COLUMN `' . $existingColName . '` `' . $colName . '` ' . $type . $default . ' ' . $null . ';'); } } }
/** * @param string $name * @return ClassDefinition * @throws \Exception */ public function createClass($name) { $def = file_get_contents(sprintf('%s/class_%s.json', $this->baseDir, $name)); $conf = json_decode($def, true); $layoutDefinitions = ClassDefinition\Service::generateLayoutTreeFromArray($conf['layoutDefinitions']); if (!$layoutDefinitions) { throw new \Exception('Unable to generate class layout for ' . $name); } $class = ClassDefinition::create(); $class->setName($name); $class->setUserOwner($this->getUser()->getId()); $class->setLayoutDefinitions($layoutDefinitions); $class->setIcon($conf['icon']); $class->setAllowInherit($conf['allowInherit']); $class->setAllowVariants($conf['allowVariants']); $class->setParentClass($conf['parentClass']); $class->setPreviewUrl($conf['previewUrl']); $class->setPropertyVisibility($conf['propertyVisibility']); $class->save(); return $class; }
/** * */ public function createUpdateTable() { $table = $this->getTableName(); $context = $this->model->getContext(); if ($context && $context["containerType"] == "fieldcollection") { $this->db->query("CREATE TABLE IF NOT EXISTS `" . $table . "` (\n `ooo_id` int(11) NOT NULL default '0',\n `index` INT(11) NOT NULL DEFAULT '0',\n `fieldname` VARCHAR(190) NOT NULL DEFAULT '',\n `language` varchar(10) NOT NULL DEFAULT '',\n PRIMARY KEY (`ooo_id`, `language`, `index`, `fieldname`),\n INDEX `ooo_id` (`ooo_id`),\n INDEX `index` (`index`),\n INDEX `fieldname` (`fieldname`),\n INDEX `language` (`language`)\n ) DEFAULT CHARSET=utf8mb4;"); } else { $this->db->query("CREATE TABLE IF NOT EXISTS `" . $table . "` (\n `ooo_id` int(11) NOT NULL default '0',\n `language` varchar(10) NOT NULL DEFAULT '',\n PRIMARY KEY (`ooo_id`,`language`),\n INDEX `ooo_id` (`ooo_id`),\n INDEX `language` (`language`)\n ) DEFAULT CHARSET=utf8mb4;"); } $existingColumns = $this->getValidTableColumns($table, false); // no caching of table definition $columnsToRemove = $existingColumns; Object\ClassDefinition\Service::updateTableDefinitions($this->tableDefinitions, [$table]); if ($context && $context["containerType"] == "fieldcollection") { $protectedColumns = ["ooo_id", "language", "index", "fieldname"]; $containerKey = $context["containerKey"]; $container = Object\Fieldcollection\Definition::getByKey($containerKey); } else { $protectedColumns = ["ooo_id", "language"]; $container = $this->model->getClass(); } foreach ($container->getFielddefinition("localizedfields")->getFielddefinitions() as $value) { if ($value->getColumnType()) { $key = $value->getName(); if (is_array($value->getColumnType())) { // if a datafield requires more than one field foreach ($value->getColumnType() as $fkey => $fvalue) { $this->addModifyColumn($table, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColumns[] = $key . "__" . $fkey; } } else { if ($value->getColumnType()) { $this->addModifyColumn($table, $key, $value->getColumnType(), "", "NULL"); $protectedColumns[] = $key; } } $this->addIndexToField($value, $table); } } $this->removeUnusedColumns($table, $columnsToRemove, $protectedColumns); $validLanguages = Tool::getValidLanguages(); if ($container instanceof Object\ClassDefinition) { foreach ($validLanguages as &$language) { $queryTable = $this->getQueryTableName(); $queryTable .= "_" . $language; $this->db->query("CREATE TABLE IF NOT EXISTS `" . $queryTable . "` (\n `ooo_id` int(11) NOT NULL default '0',\n `language` varchar(10) NOT NULL DEFAULT '',\n PRIMARY KEY (`ooo_id`,`language`),\n INDEX `ooo_id` (`ooo_id`),\n INDEX `language` (`language`)\n ) DEFAULT CHARSET=utf8mb4;"); // create object table if not exists $protectedColumns = ["ooo_id", "language"]; $existingColumns = $this->getValidTableColumns($queryTable, false); // no caching of table definition $columnsToRemove = $existingColumns; Object\ClassDefinition\Service::updateTableDefinitions($this->tableDefinitions, [$queryTable]); $fieldDefinitions = $this->model->getClass()->getFielddefinition("localizedfields")->getFielddefinitions(); // add non existing columns in the table if (is_array($fieldDefinitions) && count($fieldDefinitions)) { foreach ($fieldDefinitions as $value) { if ($value->getQueryColumnType()) { $key = $value->getName(); // if a datafield requires more than one column in the query table if (is_array($value->getQueryColumnType())) { foreach ($value->getQueryColumnType() as $fkey => $fvalue) { $this->addModifyColumn($queryTable, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColumns[] = $key . "__" . $fkey; } } // everything else if (!is_array($value->getQueryColumnType()) && $value->getQueryColumnType()) { $this->addModifyColumn($queryTable, $key, $value->getQueryColumnType(), "", "NULL"); $protectedColumns[] = $key; } // add indices $this->addIndexToField($value, $queryTable); } } } // remove unused columns in the table $this->removeUnusedColumns($queryTable, $columnsToRemove, $protectedColumns); } $this->createLocalizedViews(); } $this->tableDefinitions = null; }
public function createFieldCollection($name, $jsonPath = null) { try { $fieldCollection = Object\Fieldcollection\Definition::getByKey($name); } catch (\Exception $e) { if ($jsonPath == null) { $jsonPath = PIMCORE_PLUGINS_PATH . "/CoreShop/install/fieldcollection-{$name}.json"; } $fieldCollection = new Object\Fieldcollection\Definition(); $fieldCollection->setKey($name); $json = file_get_contents($jsonPath); $result = Plugin::getEventManager()->trigger('install.fieldcollection.preCreate', $this, array("fieldcollectionName" => $name, "json" => $json), function ($v) { return !preg_match('/[^,:{}\\[\\]0-9.\\-+Eaeflnr-u \\n\\r\\t]/', preg_replace('/"(\\.|[^"\\\\])*"/', '', $v)); }); if ($result->stopped()) { $resultJson = $result->last(); if ($resultJson) { $json = $resultJson; } } Object\ClassDefinition\Service::importFieldCollectionFromJson($fieldCollection, $json, true); } return $fieldCollection; }
/** * Process import * * @param AbstractModel $definition * @param string $json * @return bool */ protected function import(AbstractModel $definition, $json) { return Service::importObjectBrickFromJson($definition, $json); }
/** * @throws \Exception * @throws \Zend_Db_Adapter_Exception */ public function update() { $class = get_object_vars($this->model); $data = []; foreach ($class as $key => $value) { if (in_array($key, $this->getValidTableColumns("classes"))) { $data[$key] = $value; } } $this->db->update("classes", $data, $this->db->quoteInto("id = ?", $this->model->getId())); $objectTable = "object_query_" . $this->model->getId(); $objectDatastoreTable = "object_store_" . $this->model->getId(); $objectDatastoreTableRelation = "object_relations_" . $this->model->getId(); $objectView = "object_" . $this->model->getId(); // create object table if not exists $protectedColums = ["oo_id", "oo_classId", "oo_className"]; $protectedDatastoreColumns = ["oo_id"]; $this->db->query("CREATE TABLE IF NOT EXISTS `" . $objectTable . "` (\n\t\t\t `oo_id` int(11) NOT NULL default '0',\n\t\t\t `oo_classId` int(11) default '" . $this->model->getId() . "',\n\t\t\t `oo_className` varchar(255) default '" . $this->model->getName() . "',\n\t\t\t PRIMARY KEY (`oo_id`)\n\t\t\t) DEFAULT CHARSET=utf8mb4;"); // update default value of classname columns $this->db->query('ALTER TABLE `' . $objectTable . "` ALTER COLUMN `oo_className` SET DEFAULT '" . $this->model->getName() . "';"); $this->db->query("CREATE TABLE IF NOT EXISTS `" . $objectDatastoreTable . "` (\n\t\t\t `oo_id` int(11) NOT NULL default '0',\n\t\t\t PRIMARY KEY (`oo_id`)\n\t\t\t) DEFAULT CHARSET=utf8mb4;"); $this->db->query("CREATE TABLE IF NOT EXISTS `" . $objectDatastoreTableRelation . "` (\n `src_id` int(11) NOT NULL DEFAULT '0',\n `dest_id` int(11) NOT NULL DEFAULT '0',\n `type` varchar(50) NOT NULL DEFAULT '',\n `fieldname` varchar(70) NOT NULL DEFAULT '0',\n `index` int(11) unsigned NOT NULL DEFAULT '0',\n `ownertype` enum('object','fieldcollection','localizedfield','objectbrick') NOT NULL DEFAULT 'object',\n `ownername` varchar(70) NOT NULL DEFAULT '',\n `position` varchar(70) NOT NULL DEFAULT '0',\n PRIMARY KEY (`src_id`,`dest_id`,`ownertype`,`ownername`,`fieldname`,`type`,`position`),\n KEY `index` (`index`),\n KEY `src_id` (`src_id`),\n KEY `dest_id` (`dest_id`),\n KEY `fieldname` (`fieldname`),\n KEY `position` (`position`),\n KEY `ownertype` (`ownertype`),\n KEY `type` (`type`),\n KEY `ownername` (`ownername`)\n ) DEFAULT CHARSET=utf8mb4;"); $existingColumns = $this->getValidTableColumns($objectTable, false); // no caching of table definition $existingDatastoreColumns = $this->getValidTableColumns($objectDatastoreTable, false); // no caching of table definition $columnsToRemove = $existingColumns; $datastoreColumnsToRemove = $existingDatastoreColumns; Object\ClassDefinition\Service::updateTableDefinitions($this->tableDefinitions, [$objectTable, $objectDatastoreTable]); // add non existing columns in the table if (is_array($this->model->getFieldDefinitions()) && count($this->model->getFieldDefinitions())) { foreach ($this->model->getFieldDefinitions() as $key => $value) { // if a datafield requires more than one column in the query table if (is_array($value->getQueryColumnType())) { foreach ($value->getQueryColumnType() as $fkey => $fvalue) { $this->addModifyColumn($objectTable, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedColums[] = $key . "__" . $fkey; } } // if a datafield requires more than one column in the datastore table => only for non-relation types if (!$value->isRelationType() && is_array($value->getColumnType())) { foreach ($value->getColumnType() as $fkey => $fvalue) { $this->addModifyColumn($objectDatastoreTable, $key . "__" . $fkey, $fvalue, "", "NULL"); $protectedDatastoreColumns[] = $key . "__" . $fkey; } } // everything else // if (!is_array($value->getQueryColumnType()) && !is_array($value->getColumnType())) { if (!is_array($value->getQueryColumnType()) && $value->getQueryColumnType()) { $this->addModifyColumn($objectTable, $key, $value->getQueryColumnType(), "", "NULL"); $protectedColums[] = $key; } if (!is_array($value->getColumnType()) && $value->getColumnType() && !$value->isRelationType()) { $this->addModifyColumn($objectDatastoreTable, $key, $value->getColumnType(), "", "NULL"); $protectedDatastoreColumns[] = $key; } // } // add indices $this->addIndexToField($value, $objectTable, "getQueryColumnType"); $this->addIndexToField($value, $objectDatastoreTable, "getColumnType"); } } // remove unused columns in the table $this->removeUnusedColumns($objectTable, $columnsToRemove, $protectedColums); $this->removeUnusedColumns($objectDatastoreTable, $datastoreColumnsToRemove, $protectedDatastoreColumns); // remove / cleanup unused relations if (is_array($datastoreColumnsToRemove)) { foreach ($datastoreColumnsToRemove as $value) { if (!in_array(strtolower($value), array_map('strtolower', $protectedDatastoreColumns))) { $tableRelation = "object_relations_" . $this->model->getId(); $this->db->delete($tableRelation, "fieldname = " . $this->db->quote($value) . " AND ownertype = 'object'"); // @TODO: remove localized fields and fieldcollections } } } // create view try { //$this->db->query('CREATE OR REPLACE VIEW `' . $objectView . '` AS SELECT * FROM `objects` left JOIN `' . $objectTable . '` ON `objects`.`o_id` = `' . $objectTable . '`.`oo_id` WHERE `objects`.`o_classId` = ' . $this->model->getId() . ';'); $this->db->query('CREATE OR REPLACE VIEW `' . $objectView . '` AS SELECT * FROM `' . $objectTable . '` JOIN `objects` ON `objects`.`o_id` = `' . $objectTable . '`.`oo_id`;'); } catch (\Exception $e) { Logger::debug($e); } $this->tableDefinitions = null; }
/** * Process import * * @param AbstractModel $definition * @param string $json * @return bool */ protected function import(AbstractModel $definition, $json) { return Service::importClassDefinitionFromJson($definition, $json); }
/** * See http://www.pimcore.org/issues/browse/PIMCORE-2358 * Add option to export/import all class definitions/brick definitions etc. at once */ public function bulkExportAction() { $result = []; $this->removeViewRenderer(); $fieldCollections = new Object\Fieldcollection\Definition\Listing(); $fieldCollections = $fieldCollections->load(); foreach ($fieldCollections as $fieldCollection) { $key = $fieldCollection->key; $fieldCollectionJson = json_decode(Object\ClassDefinition\Service::generateFieldCollectionJson($fieldCollection)); $fieldCollectionJson->key = $key; $result["fieldcollection"][] = $fieldCollectionJson; } $classes = new Object\ClassDefinition\Listing(); $classes->setOrder("ASC"); $classes->setOrderKey("id"); $classes = $classes->load(); foreach ($classes as $class) { $data = Model\Webservice\Data\Mapper::map($class, "\\Pimcore\\Model\\Webservice\\Data\\ClassDefinition\\Out", "out"); unset($data->fieldDefinitions); $result["class"][] = $data; } $objectBricks = new Object\Objectbrick\Definition\Listing(); $objectBricks = $objectBricks->load(); foreach ($objectBricks as $objectBrick) { $key = $objectBrick->key; $objectBrickJson = json_decode(Object\ClassDefinition\Service::generateObjectBrickJson($objectBrick)); $objectBrickJson->key = $key; $result["objectbrick"][] = $objectBrickJson; } $customLayouts = new Object\ClassDefinition\CustomLayout\Listing(); $customLayouts = $customLayouts->load(); foreach ($customLayouts as $customLayout) { /** @var $customLayout Object\ClassDefinition\CustomLayout */ $classId = $customLayout->getClassId(); $class = Object\ClassDefinition::getById($classId); $customLayout->className = $class->getName(); $result["customlayout"][] = $customLayout; } header("Content-type: application/json"); header("Content-Disposition: attachment; filename=\"bulk_export.json\""); $result = json_encode($result); echo $result; }
/** * @param $classname * @param $filepath * @throws \Exception */ private static function createClass($classname, $filepath) { $class = \Pimcore\Model\Object\ClassDefinition::getByName($classname); if (!$class) { $class = new \Pimcore\Model\Object\ClassDefinition(); $class->setName($classname); } $json = file_get_contents($filepath); $success = \Pimcore\Model\Object\ClassDefinition\Service::importClassDefinitionFromJson($class, $json); if (!$success) { throw new \Exception("Could not import {$classname} Class."); } }
/** * @todo */ private static function installObjectBricks() { $sourceFiles = scandir(PIMCORE_PLUGINS_PATH . '/OnlineShop/install/objectbrick_sources'); foreach ($sourceFiles as $filename) { if (!is_dir($filename)) { preg_match('/_(.*)_/', $filename, $matches); $key = $matches[1]; try { $brick = \Pimcore\Model\Object\Objectbrick\Definition::getByKey($key); } catch (Exception $e) { $brick = new \Pimcore\Model\Object\Objectbrick\Definition(); $brick->setKey($key); } $data = file_get_contents(PIMCORE_PLUGINS_PATH . '/OnlineShop/install/objectbrick_sources/' . $filename); $success = \Pimcore\Model\Object\ClassDefinition\Service::importObjectBrickFromJson($brick, $data); if (!$success) { Logger::err("Could not import {$key} ObjectBrick."); } } } }