PageRenderTime 87ms CodeModel.GetById 25ms RepoModel.GetById 1ms app.codeStats 0ms

/lib/Doctrine/Import.php

https://github.com/ascorbic/doctrine-tracker
PHP | 445 lines | 188 code | 41 blank | 216 comment | 12 complexity | 67cb01debea777eab3df5ba006dfdd57 MD5 | raw file
Possible License(s): LGPL-2.1
  1. <?php
  2. /*
  3. * $Id$
  4. *
  5. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  6. * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  7. * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  8. * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
  9. * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  10. * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
  11. * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  12. * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  13. * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  14. * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  15. * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  16. *
  17. * This software consists of voluntary contributions made by many individuals
  18. * and is licensed under the LGPL. For more information, see
  19. * <http://www.phpdoctrine.org>.
  20. */
  21. /**
  22. * class Doctrine_Import
  23. * Main responsible of performing import operation. Delegates database schema
  24. * reading to a reader object and passes the result to a builder object which
  25. * builds a Doctrine data model.
  26. *
  27. * @package Doctrine
  28. * @subpackage Import
  29. * @link www.phpdoctrine.org
  30. * @license http://www.opensource.org/licenses/lgpl-license.php LGPL
  31. * @since 1.0
  32. * @version $Revision$
  33. * @author Konsta Vesterinen <kvesteri@cc.hut.fi>
  34. * @author Jukka Hassinen <Jukka.Hassinen@BrainAlliance.com>
  35. */
  36. class Doctrine_Import extends Doctrine_Connection_Module
  37. {
  38. protected $sql = array();
  39. /**
  40. * lists all databases
  41. *
  42. * @return array
  43. */
  44. public function listDatabases()
  45. {
  46. if ( ! isset($this->sql['listDatabases'])) {
  47. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  48. }
  49. return $this->conn->fetchColumn($this->sql['listDatabases']);
  50. }
  51. /**
  52. * lists all availible database functions
  53. *
  54. * @return array
  55. */
  56. public function listFunctions()
  57. {
  58. if ( ! isset($this->sql['listFunctions'])) {
  59. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  60. }
  61. return $this->conn->fetchColumn($this->sql['listFunctions']);
  62. }
  63. /**
  64. * lists all database triggers
  65. *
  66. * @param string|null $database
  67. * @return array
  68. */
  69. public function listTriggers($database = null)
  70. {
  71. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  72. }
  73. /**
  74. * lists all database sequences
  75. *
  76. * @param string|null $database
  77. * @return array
  78. */
  79. public function listSequences($database = null)
  80. {
  81. if ( ! isset($this->sql['listSequences'])) {
  82. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  83. }
  84. return $this->conn->fetchColumn($this->sql['listSequences']);
  85. }
  86. /**
  87. * lists table constraints
  88. *
  89. * @param string $table database table name
  90. * @return array
  91. */
  92. public function listTableConstraints($table)
  93. {
  94. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  95. }
  96. /**
  97. * lists table relations
  98. *
  99. * Expects an array of this format to be returned with all the relationships in it where the key is
  100. * the name of the foreign table, and the value is an array containing the local and foreign column
  101. * name
  102. *
  103. * Array
  104. * (
  105. * [groups] => Array
  106. * (
  107. * [local] => group_id
  108. * [foreign] => id
  109. * )
  110. * )
  111. *
  112. * @param string $table database table name
  113. * @return array
  114. */
  115. public function listTableRelations($table)
  116. {
  117. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  118. }
  119. /**
  120. * lists table constraints
  121. *
  122. * @param string $table database table name
  123. * @return array
  124. */
  125. public function listTableColumns($table)
  126. {
  127. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  128. }
  129. /**
  130. * lists table constraints
  131. *
  132. * @param string $table database table name
  133. * @return array
  134. */
  135. public function listTableIndexes($table)
  136. {
  137. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  138. }
  139. /**
  140. * lists tables
  141. *
  142. * @param string|null $database
  143. * @return array
  144. */
  145. public function listTables($database = null)
  146. {
  147. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  148. }
  149. /**
  150. * lists table triggers
  151. *
  152. * @param string $table database table name
  153. * @return array
  154. */
  155. public function listTableTriggers($table)
  156. {
  157. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  158. }
  159. /**
  160. * lists table views
  161. *
  162. * @param string $table database table name
  163. * @return array
  164. */
  165. public function listTableViews($table)
  166. {
  167. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  168. }
  169. /**
  170. * lists database users
  171. *
  172. * @return array
  173. */
  174. public function listUsers()
  175. {
  176. if ( ! isset($this->sql['listUsers'])) {
  177. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  178. }
  179. return $this->conn->fetchColumn($this->sql['listUsers']);
  180. }
  181. /**
  182. * lists database views
  183. *
  184. * @param string|null $database
  185. * @return array
  186. */
  187. public function listViews($database = null)
  188. {
  189. if ( ! isset($this->sql['listViews'])) {
  190. throw new Doctrine_Import_Exception(__FUNCTION__ . ' not supported by this driver.');
  191. }
  192. return $this->conn->fetchColumn($this->sql['listViews']);
  193. }
  194. /**
  195. * checks if a database exists
  196. *
  197. * @param string $database
  198. * @return boolean
  199. */
  200. public function databaseExists($database)
  201. {
  202. return in_array($database, $this->listDatabases());
  203. }
  204. /**
  205. * checks if a function exists
  206. *
  207. * @param string $function
  208. * @return boolean
  209. */
  210. public function functionExists($function)
  211. {
  212. return in_array($function, $this->listFunctions());
  213. }
  214. /**
  215. * checks if a trigger exists
  216. *
  217. * @param string $trigger
  218. * @param string|null $database
  219. * @return boolean
  220. */
  221. public function triggerExists($trigger, $database = null)
  222. {
  223. return in_array($trigger, $this->listTriggers($database));
  224. }
  225. /**
  226. * checks if a sequence exists
  227. *
  228. * @param string $sequence
  229. * @param string|null $database
  230. * @return boolean
  231. */
  232. public function sequenceExists($sequence, $database = null)
  233. {
  234. return in_array($sequence, $this->listSequences($database));
  235. }
  236. /**
  237. * checks if a table constraint exists
  238. *
  239. * @param string $constraint
  240. * @param string $table database table name
  241. * @return boolean
  242. */
  243. public function tableConstraintExists($constraint, $table)
  244. {
  245. return in_array($constraint, $this->listTableConstraints($table));
  246. }
  247. /**
  248. * checks if a table column exists
  249. *
  250. * @param string $column
  251. * @param string $table database table name
  252. * @return boolean
  253. */
  254. public function tableColumnExists($column, $table)
  255. {
  256. return in_array($column, $this->listTableColumns($table));
  257. }
  258. /**
  259. * checks if a table index exists
  260. *
  261. * @param string $index
  262. * @param string $table database table name
  263. * @return boolean
  264. */
  265. public function tableIndexExists($index, $table)
  266. {
  267. return in_array($index, $this->listTableIndexes($table));
  268. }
  269. /**
  270. * checks if a table exists
  271. *
  272. * @param string $table
  273. * @param string|null $database
  274. * @return boolean
  275. */
  276. public function tableExists($table, $database = null)
  277. {
  278. return in_array($table, $this->listTables($database));
  279. }
  280. /**
  281. * checks if a table trigger exists
  282. *
  283. * @param string $trigger
  284. * @param string $table database table name
  285. * @return boolean
  286. */
  287. public function tableTriggerExists($trigger, $table)
  288. {
  289. return in_array($trigger, $this->listTableTriggers($table));
  290. }
  291. /**
  292. * checks if a table view exists
  293. *
  294. * @param string $view
  295. * @param string $table database table name
  296. * @return boolean
  297. */
  298. public function tableViewExists($view, $table)
  299. {
  300. return in_array($view, $this->listTableViews($table));
  301. }
  302. /**
  303. * checks if a user exists
  304. *
  305. * @param string $user
  306. * @return boolean
  307. */
  308. public function userExists($user)
  309. {
  310. return in_array($user, $this->listUsers());
  311. }
  312. /**
  313. * checks if a view exists
  314. *
  315. * @param string $view
  316. * @param string|null $database
  317. * @return boolean
  318. */
  319. public function viewExists($view, $database = null)
  320. {
  321. return in_array($view, $this->listViews($database));
  322. }
  323. /**
  324. * importSchema
  325. *
  326. * method for importing existing schema to Doctrine_Record classes
  327. *
  328. * @param string $directory
  329. * @param array $databases
  330. * @return array the names of the imported classes
  331. */
  332. public function importSchema($directory, array $databases = array(), array $options = array())
  333. {
  334. $connections = Doctrine_Manager::getInstance()->getConnections();
  335. $classes = array();
  336. foreach ($connections as $name => $connection) {
  337. // Limit the databases to the ones specified by $databases.
  338. // Check only happens if array is not empty
  339. if ( ! empty($databases) && ! in_array($name, $databases)) {
  340. continue;
  341. }
  342. $builder = new Doctrine_Import_Builder();
  343. $builder->setTargetPath($directory);
  344. $builder->setOptions($options);
  345. $definitions = array();
  346. foreach ($connection->import->listTables() as $table) {
  347. $definition = array();
  348. $definition['tableName'] = $table;
  349. $definition['className'] = Doctrine_Inflector::classify(Doctrine_Inflector::tableize($table));
  350. $definition['columns'] = $connection->import->listTableColumns($table);
  351. $definition['connection'] = $connection->getName();
  352. $definition['connectionClassName'] = $definition['className'];
  353. try {
  354. $definition['relations'] = array();
  355. $relations = $connection->import->listTableRelations($table);
  356. $relClasses = array();
  357. foreach ($relations as $relation) {
  358. $table = $relation['table'];
  359. $class = Doctrine_Inflector::classify(Doctrine_Inflector::tableize($table));
  360. if (in_array($class, $relClasses)) {
  361. $alias = $class . '_' . (count($relClasses) + 1);
  362. } else {
  363. $alias = $class;
  364. }
  365. $relClasses[] = $class;
  366. $definition['relations'][$alias] = array(
  367. 'alias' => $alias,
  368. 'class' => $class,
  369. 'local' => $relation['local'],
  370. 'foreign' => $relation['foreign']
  371. );
  372. }
  373. } catch (Exception $e) {}
  374. $definitions[strtolower($definition['className'])] = $definition;
  375. $classes[] = $definition['className'];
  376. }
  377. // Build opposite end of relationships
  378. foreach ($definitions as $definition) {
  379. $className = $definition['className'];
  380. $relClasses = array();
  381. foreach ($definition['relations'] as $alias => $relation) {
  382. if (in_array($relation['class'], $relClasses) || isset($definitions[$relation['class']]['relations'][$className])) {
  383. $alias = $className . '_' . (count($relClasses) + 1);
  384. } else {
  385. $alias = $className;
  386. }
  387. $relClasses[] = $relation['class'];
  388. $definitions[strtolower($relation['class'])]['relations'][$alias] = array(
  389. 'type' => Doctrine_Relation::MANY,
  390. 'alias' => $alias,
  391. 'class' => $className,
  392. 'local' => $relation['foreign'],
  393. 'foreign' => $relation['local']
  394. );
  395. }
  396. }
  397. // Build records
  398. foreach ($definitions as $definition) {
  399. $builder->buildRecord($definition);
  400. }
  401. }
  402. return $classes;
  403. }
  404. }