PageRenderTime 26ms CodeModel.GetById 26ms RepoModel.GetById 1ms app.codeStats 0ms

/Classes/Utility/DynamicConfiguration/SQL.php

https://bitbucket.org/imia_de/t3ext-imia-base-ext
PHP | 262 lines | 193 code | 18 blank | 51 comment | 27 complexity | ad458ebd2b886964b6e2de1ce8a110fe MD5 | raw file
Possible License(s): Apache-2.0
  1. <?php
  2. /***************************************************************
  3. * Copyright notice
  4. *
  5. * (c) 2016 IMIA net based solutions (info@imia.de)
  6. * All rights reserved
  7. *
  8. * This script is part of the TYPO3 project. The TYPO3 project is
  9. * free software; you can redistribute it and/or modify
  10. * it under the terms of the GNU General Public License as published by
  11. * the Free Software Foundation; either version 2 of the License, or
  12. * (at your option) any later version.
  13. *
  14. * The GNU General Public License can be found at
  15. * http://www.gnu.org/copyleft/gpl.html.
  16. *
  17. * This script is distributed in the hope that it will be useful,
  18. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  19. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  20. * GNU General Public License for more details.
  21. *
  22. * This copyright notice MUST APPEAR in all copies of the script!
  23. ***************************************************************/
  24. namespace IMIA\ImiaBaseExt\Utility\DynamicConfiguration;
  25. use IMIA\ImiaBaseExt\Metadata\ClassMetadata;
  26. use IMIA\ImiaBaseExt\Metadata\PropertyMetadata;
  27. use TYPO3\CMS\Core\Utility\GeneralUtility;
  28. /**
  29. * @package imia_base_ext
  30. * @subpackage Utility\DynamicConfiguration
  31. * @author David Frerich <d.frerich@imia.de>
  32. */
  33. class SQL
  34. {
  35. /**
  36. * @var string
  37. */
  38. private $extKey;
  39. /**
  40. * @param string $extKey
  41. * @param ClassMetadata $classMetadata
  42. * @return string
  43. */
  44. static public function getTableName($extKey, $classMetadata)
  45. {
  46. if ($classMetadata->sqlTable && $classMetadata->sqlTable->name) {
  47. $tableName = $classMetadata->sqlTable->name;
  48. } else {
  49. $className = substr($classMetadata->name, strrpos($classMetadata->name, '\\') !== false ? strrpos($classMetadata->name, '\\') + 1 : 0);
  50. $tableName = 'tx_' . str_replace('_', '', $extKey) . '_domain_model_' . GeneralUtility::camelCaseToLowerCaseUnderscored($className);
  51. }
  52. return $tableName;
  53. }
  54. /**
  55. * @param PropertyMetadata $propertyMetadata
  56. * @return string
  57. */
  58. static public function getColumnName($propertyMetadata)
  59. {
  60. if ($propertyMetadata->sqlColumn && $propertyMetadata->sqlColumn->name) {
  61. $name = $propertyMetadata->sqlColumn->name;
  62. } else {
  63. $name = GeneralUtility::camelCaseToLowerCaseUnderscored($propertyMetadata->name);
  64. }
  65. return $name;
  66. }
  67. /**
  68. * @param string $extKey
  69. */
  70. public function __construct($extKey)
  71. {
  72. $this->extKey = $extKey;
  73. }
  74. /**
  75. * @param ClassMetadata $metadata
  76. * @return string
  77. */
  78. public function build($metadata)
  79. {
  80. $sql = '### EXTENSION: ' . $this->extKey . " ###";
  81. foreach ($metadata as $className => $classMetadata) {
  82. if ($classMetadata->sqlTable && !$classMetadata->reflection->isAbstract()) {
  83. if (!$classMetadata->tcaTable || !$classMetadata->tcaTable->ignore) {
  84. $tableName = self::getTableName($this->extKey, $classMetadata);
  85. $columnSql = $this->buildColumns($classMetadata);
  86. if ($columnSql) {
  87. $sql .=
  88. LF .
  89. LF .
  90. "## CLASS: " . $className . LF .
  91. "# Table structure for table '" . $tableName . "'" . LF .
  92. "CREATE TABLE `" . $tableName . "` (" . LF .
  93. $columnSql .
  94. ");";
  95. }
  96. }
  97. }
  98. // MM Tables
  99. if ($classMetadata->tcaTable && !$classMetadata->tcaTable->ignore && !$classMetadata->reflection->isAbstract()) {
  100. foreach ($classMetadata->propertyMetadata as $property => $propertyMetadata) {
  101. $column = $propertyMetadata->tcaColumn;
  102. if ($column) {
  103. $type = $column::$fixed['type'] ?: $column->type;
  104. if (in_array($type, ['select', 'group'])) {
  105. $mmTableName = $column::$fixed['MM'] ?: $column->MM;
  106. $mmOppositeField = $column::$fixed['MM_opposite_field'] ?: $column->MM_opposite_field;
  107. if ($mmTableName && $mmOppositeField) {
  108. $sql .=
  109. LF .
  110. LF .
  111. "## CLASS: " . $className . " | MM PROPERTY: " . $property . LF .
  112. "# Table structure for table '" . $mmTableName . "'" . LF .
  113. "CREATE TABLE `" . $mmTableName . "` (" . LF .
  114. " uid int(11) NOT NULL auto_increment," . LF .
  115. " uid_local int(11) DEFAULT '0' NOT NULL," . LF .
  116. " uid_foreign int(11) DEFAULT '0' NOT NULL," . LF .
  117. " sorting int(11) DEFAULT '0' NOT NULL," . LF .
  118. " sorting_foreign int(11) DEFAULT '0' NOT NULL," . LF .
  119. " KEY uid_local (uid_local)," . LF .
  120. " KEY uid_foreign (uid_foreign)," . LF .
  121. " PRIMARY KEY (uid)," . LF .
  122. ");";
  123. }
  124. }
  125. }
  126. }
  127. }
  128. }
  129. $sql .= LF . LF;
  130. return $sql;
  131. }
  132. /**
  133. * @param ClassMetadata $metadata
  134. * @return string
  135. */
  136. private function buildColumns($metadata)
  137. {
  138. $sql = '';
  139. $keys = [];
  140. $uniqueKeys = [];
  141. $primaryKey = '';
  142. foreach ($metadata->propertyMetadata as $property => $propertyMetadata) {
  143. $column = $propertyMetadata->sqlColumn;
  144. if ($column && $column->create) {
  145. $name = self::getColumnName($propertyMetadata);
  146. $length = (int)$column->length;
  147. $decimal = (int)$column->decimal;
  148. $nullable = (boolean)$column->nullable;
  149. $unsigned = (boolean)$column->unsigned;
  150. $autoIncrement = (boolean)$column->autoIncrement;
  151. $default = (string)$column->default;
  152. $type = $column->type;
  153. if (!$primaryKey && (boolean)$column->primaryKey) {
  154. $primaryKey = $name;
  155. }
  156. if ($column->key) {
  157. $keyName = $column->key;
  158. if (!array_key_exists($keyName, $keys)) {
  159. $keys[$keyName] = [];
  160. }
  161. $keys[$keyName][] = $name;
  162. }
  163. if ($column->unique) {
  164. $keyName = $column->key ? $name : $name;
  165. if (!array_key_exists($keyName, $uniqueKeys)) {
  166. $uniqueKeys[$keyName] = [];
  167. }
  168. $uniqueKeys[$keyName][] = $name;
  169. }
  170. switch ($type) {
  171. case 'char':
  172. case 'varchar':
  173. $sql .= ' `' . $name . '` ' . $type . '(' . ($length <= 255 ? $length : 255) . ') DEFAULT ' . ($default ? '\'' . str_replace(["'", '"'], ["\'", '\"'], $default) . '\'' : ($nullable ? 'NULL' : '\'\'')) . ($nullable ? '' : ' NOT NULL') . ',' . LF;
  174. break;
  175. case 'int':
  176. case 'tinyint':
  177. case 'smallint':
  178. case 'mediumint':
  179. case 'bigint':
  180. $sql .= ' `' . $name . '` ' . $type . '(' . ($length <= 11 ? $length : 11) . ')' . ($unsigned ? ' unsigned' : '') . ($autoIncrement ? '' : ' DEFAULT ' . ($default ? '\'' . (int)$default . '\'' : ($nullable ? 'NULL' : '\'0\''))) . ($nullable ? '' : ' NOT NULL') . ($autoIncrement ? ' auto_increment' : '') . ',' . LF;
  181. break;
  182. case 'text':
  183. case 'tinytext':
  184. case 'mediumtext':
  185. case 'longtext':
  186. $sql .= ' `' . $name . '` ' . $type . ' ' . ($nullable ? '' : 'NOT NULL') . ',' . LF;
  187. break;
  188. case 'float':
  189. case 'double':
  190. case 'real':
  191. case 'decimal':
  192. $sql .= ' `' . $name . '` ' . $type . '(' . $length . ',' . $decimal . ') DEFAULT ' . ($default && (float)$default != 0 ? '\'' . (float)$default . '\'' : ($nullable ? 'NULL' : '\'0' . ($decimal ? '.' . str_pad('', $decimal, '0') : '') . '\'')) . ($nullable ? '' : ' NOT NULL') . ',' . LF;
  193. break;
  194. case 'date':
  195. case 'time':
  196. $sql .= ' `' . $name . '` ' . $type . ',' . LF;
  197. break;
  198. case 'blob':
  199. case 'tinyblob':
  200. case 'mediumblob':
  201. case 'longblob':
  202. $sql .= ' `' . $name . '` ' . $type . ',' . LF;
  203. break;
  204. }
  205. }
  206. }
  207. if ($metadata->sqlIndex) {
  208. if ($metadata->sqlIndex->keys && is_array($metadata->sqlIndex->keys)
  209. && count($metadata->sqlIndex->keys) > 0
  210. ) {
  211. foreach ($metadata->sqlIndex->keys as $keyName => $columns) {
  212. $keys[$keyName] = $columns;
  213. }
  214. }
  215. if ($metadata->sqlIndex->uniqueKeys && is_array($metadata->sqlIndex->uniqueKeys)
  216. && count($metadata->sqlIndex->uniqueKeys) > 0
  217. ) {
  218. foreach ($metadata->sqlIndex->uniqueKeys as $keyName => $columns) {
  219. $uniqueKeys[$keyName] = $columns;
  220. }
  221. }
  222. }
  223. if ($sql) {
  224. if ($primaryKey || count($keys) > 0 || count($uniqueKeys) > 0) {
  225. $sql .= LF;
  226. if ($primaryKey) {
  227. $sql .= ' PRIMARY KEY (`' . $primaryKey . '`),' . LF;
  228. }
  229. foreach ($keys as $keyName => $columns) {
  230. $sql .= ' KEY `' . $keyName . '` (`' . implode('`,`', $columns) . '`),' . LF;
  231. }
  232. foreach ($uniqueKeys as $keyName => $columns) {
  233. $sql .= ' UNIQUE `' . $keyName . '` (`' . implode('`,`', $columns) . '`),' . LF;
  234. }
  235. }
  236. $sql = substr($sql, 0, -2) . LF;
  237. }
  238. return $sql;
  239. }
  240. }