1: <?php
2:
3: 4: 5: 6: 7: 8: 9: 10: 11:
12:
13:
14:
15: 16: 17: 18: 19: 20: 21: 22: 23:
24: class DibiDatabaseInfo extends DibiObject
25: {
26:
27: private $reflector;
28:
29:
30: private $name;
31:
32:
33: private $tables;
34:
35:
36:
37: public function __construct(IDibiReflector $reflector, $name)
38: {
39: $this->reflector = $reflector;
40: $this->name = $name;
41: }
42:
43:
44:
45: 46: 47:
48: public function getName()
49: {
50: return $this->name;
51: }
52:
53:
54:
55: 56: 57:
58: public function getTables()
59: {
60: $this->init();
61: return array_values($this->tables);
62: }
63:
64:
65:
66: 67: 68:
69: public function getTableNames()
70: {
71: $this->init();
72: $res = array();
73: foreach ($this->tables as $table) {
74: $res[] = $table->getName();
75: }
76: return $res;
77: }
78:
79:
80:
81: 82: 83: 84:
85: public function getTable($name)
86: {
87: $name = DibiTranslator::substitute($name);
88: $this->init();
89: $l = strtolower($name);
90: if (isset($this->tables[$l])) {
91: return $this->tables[$l];
92:
93: } else {
94: throw new DibiException("Database '$this->name' has no table '$name'.");
95: }
96: }
97:
98:
99:
100: 101: 102: 103:
104: public function hasTable($name)
105: {
106: $name = DibiTranslator::substitute($name);
107: $this->init();
108: return isset($this->tables[strtolower($name)]);
109: }
110:
111:
112:
113: 114: 115:
116: protected function init()
117: {
118: if ($this->tables === NULL) {
119: $this->tables = array();
120: foreach ($this->reflector->getTables() as $info) {
121: $this->tables[strtolower($info['name'])] = new DibiTableInfo($this->reflector, $info);
122: }
123: }
124: }
125:
126: }
127:
128:
129:
130:
131: 132: 133: 134: 135: 136: 137: 138: 139: 140: 141: 142: 143:
144: class DibiTableInfo extends DibiObject
145: {
146:
147: private $reflector;
148:
149:
150: private $name;
151:
152:
153: private $view;
154:
155:
156: private $columns;
157:
158:
159: private $foreignKeys;
160:
161:
162: private $indexes;
163:
164:
165: private $primaryKey;
166:
167:
168:
169: public function __construct(IDibiReflector $reflector, array $info)
170: {
171: $this->reflector = $reflector;
172: $this->name = $info['name'];
173: $this->view = !empty($info['view']);
174: }
175:
176:
177:
178: 179: 180:
181: public function getName()
182: {
183: return $this->name;
184: }
185:
186:
187:
188: 189: 190:
191: public function isView()
192: {
193: return $this->view;
194: }
195:
196:
197:
198: 199: 200:
201: public function getColumns()
202: {
203: $this->initColumns();
204: return array_values($this->columns);
205: }
206:
207:
208:
209: 210: 211:
212: public function getColumnNames()
213: {
214: $this->initColumns();
215: $res = array();
216: foreach ($this->columns as $column) {
217: $res[] = $column->getName();
218: }
219: return $res;
220: }
221:
222:
223:
224: 225: 226: 227:
228: public function getColumn($name)
229: {
230: $name = DibiTranslator::substitute($name);
231: $this->initColumns();
232: $l = strtolower($name);
233: if (isset($this->columns[$l])) {
234: return $this->columns[$l];
235:
236: } else {
237: throw new DibiException("Table '$this->name' has no column '$name'.");
238: }
239: }
240:
241:
242:
243: 244: 245: 246:
247: public function hasColumn($name)
248: {
249: $name = DibiTranslator::substitute($name);
250: $this->initColumns();
251: return isset($this->columns[strtolower($name)]);
252: }
253:
254:
255:
256: 257: 258:
259: public function getForeignKeys()
260: {
261: $this->initForeignKeys();
262: return $this->foreignKeys;
263: }
264:
265:
266:
267: 268: 269:
270: public function getIndexes()
271: {
272: $this->initIndexes();
273: return $this->indexes;
274: }
275:
276:
277:
278: 279: 280:
281: public function getPrimaryKey()
282: {
283: $this->initIndexes();
284: return $this->primaryKey;
285: }
286:
287:
288:
289: 290: 291:
292: protected function initColumns()
293: {
294: if ($this->columns === NULL) {
295: $this->columns = array();
296: foreach ($this->reflector->getColumns($this->name) as $info) {
297: $this->columns[strtolower($info['name'])] = new DibiColumnInfo($this->reflector, $info);
298: }
299: }
300: }
301:
302:
303:
304: 305: 306:
307: protected function initIndexes()
308: {
309: if ($this->indexes === NULL) {
310: $this->initColumns();
311: $this->indexes = array();
312: foreach ($this->reflector->getIndexes($this->name) as $info) {
313: foreach ($info['columns'] as $key => $name) {
314: $info['columns'][$key] = $this->columns[strtolower($name)];
315: }
316: $this->indexes[strtolower($info['name'])] = new DibiIndexInfo($info);
317: if (!empty($info['primary'])) {
318: $this->primaryKey = $this->indexes[strtolower($info['name'])];
319: }
320: }
321: }
322: }
323:
324:
325:
326: 327: 328:
329: protected function initForeignKeys()
330: {
331: throw new NotImplementedException;
332: }
333:
334: }
335:
336:
337:
338:
339: 340: 341: 342: 343: 344: 345: 346:
347: class DibiResultInfo extends DibiObject
348: {
349:
350: private $driver;
351:
352:
353: private $columns;
354:
355:
356: private $names;
357:
358:
359:
360: public function __construct(IDibiResultDriver $driver)
361: {
362: $this->driver = $driver;
363: }
364:
365:
366:
367: 368: 369:
370: public function getColumns()
371: {
372: $this->initColumns();
373: return array_values($this->columns);
374: }
375:
376:
377:
378: 379: 380: 381:
382: public function getColumnNames($fullNames = FALSE)
383: {
384: $this->initColumns();
385: $res = array();
386: foreach ($this->columns as $column) {
387: $res[] = $fullNames ? $column->getFullName() : $column->getName();
388: }
389: return $res;
390: }
391:
392:
393:
394: 395: 396: 397:
398: public function getColumn($name)
399: {
400: $name = DibiTranslator::substitute($name);
401: $this->initColumns();
402: $l = strtolower($name);
403: if (isset($this->names[$l])) {
404: return $this->names[$l];
405:
406: } else {
407: throw new DibiException("Result set has no column '$name'.");
408: }
409: }
410:
411:
412:
413: 414: 415: 416:
417: public function hasColumn($name)
418: {
419: $name = DibiTranslator::substitute($name);
420: $this->initColumns();
421: return isset($this->names[strtolower($name)]);
422: }
423:
424:
425:
426: 427: 428:
429: protected function initColumns()
430: {
431: if ($this->columns === NULL) {
432: $this->columns = array();
433: $reflector = $this->driver instanceof IDibiReflector ? $this->driver : NULL;
434: foreach ($this->driver->getResultColumns() as $info) {
435: $this->columns[] = $this->names[$info['name']] = new DibiColumnInfo($reflector, $info);
436: }
437: }
438: }
439:
440: }
441:
442:
443:
444:
445: 446: 447: 448: 449: 450: 451: 452: 453: 454: 455: 456: 457: 458: 459: 460:
461: class DibiColumnInfo extends DibiObject
462: {
463:
464: private static $types;
465:
466:
467: private $reflector;
468:
469:
470: private $info;
471:
472:
473:
474: public function __construct(IDibiReflector $reflector = NULL, array $info)
475: {
476: $this->reflector = $reflector;
477: $this->info = $info;
478: }
479:
480:
481:
482: 483: 484:
485: public function getName()
486: {
487: return $this->info['name'];
488: }
489:
490:
491:
492: 493: 494:
495: public function getFullName()
496: {
497: return isset($this->info['fullname']) ? $this->info['fullname'] : NULL;
498: }
499:
500:
501:
502: 503: 504:
505: public function hasTable()
506: {
507: return !empty($this->info['table']);
508: }
509:
510:
511:
512: 513: 514:
515: public function getTable()
516: {
517: if (empty($this->info['table']) || !$this->reflector) {
518: throw new DibiException("Table is unknown or not available.");
519: }
520: return new DibiTableInfo($this->reflector, array('name' => $this->info['table']));
521: }
522:
523:
524:
525: 526: 527:
528: public function getTableName()
529: {
530: return isset($this->info['table']) ? $this->info['table'] : NULL;
531: }
532:
533:
534:
535: 536: 537:
538: public function getType()
539: {
540: if (self::$types === NULL) {
541: self::$types = new DibiLazyStorage(array(__CLASS__, 'detectType'));
542: }
543: return self::$types->{$this->info['nativetype']};
544: }
545:
546:
547:
548: 549: 550:
551: public function getNativeType()
552: {
553: return $this->info['nativetype'];
554: }
555:
556:
557:
558: 559: 560:
561: public function getSize()
562: {
563: return isset($this->info['size']) ? (int) $this->info['size'] : NULL;
564: }
565:
566:
567:
568: 569: 570:
571: public function isUnsigned()
572: {
573: return isset($this->info['unsigned']) ? (bool) $this->info['unsigned'] : NULL;
574: }
575:
576:
577:
578: 579: 580:
581: public function isNullable()
582: {
583: return isset($this->info['nullable']) ? (bool) $this->info['nullable'] : NULL;
584: }
585:
586:
587:
588: 589: 590:
591: public function isAutoIncrement()
592: {
593: return isset($this->info['autoincrement']) ? (bool) $this->info['autoincrement'] : NULL;
594: }
595:
596:
597:
598: 599: 600:
601: public function getDefault()
602: {
603: return isset($this->info['default']) ? $this->info['default'] : NULL;
604: }
605:
606:
607:
608: 609: 610: 611:
612: public function getVendorInfo($key)
613: {
614: return isset($this->info['vendor'][$key]) ? $this->info['vendor'][$key] : NULL;
615: }
616:
617:
618:
619: 620: 621: 622: 623: 624:
625: public static function detectType($type)
626: {
627: static $patterns = array(
628: 'BYTEA|BLOB|BIN' => dibi::BINARY,
629: 'TEXT|CHAR|BIGINT|LONGLONG' => dibi::TEXT,
630: 'BYTE|COUNTER|SERIAL|INT|LONG' => dibi::INTEGER,
631: 'CURRENCY|REAL|MONEY|FLOAT|DOUBLE|DECIMAL|NUMERIC|NUMBER' => dibi::FLOAT,
632: '^TIME$' => dibi::TIME,
633: 'TIME' => dibi::DATETIME, 634: 'YEAR|DATE' => dibi::DATE,
635: 'BOOL|BIT' => dibi::BOOL,
636: );
637:
638: foreach ($patterns as $s => $val) {
639: if (preg_match("#$s#i", $type)) {
640: return $val;
641: }
642: }
643: return dibi::TEXT;
644: }
645:
646: }
647:
648:
649:
650:
651: 652: 653: 654: 655: 656: 657: 658: 659:
660: class DibiForeignKeyInfo extends DibiObject
661: {
662:
663: private $name;
664:
665:
666: private $references;
667:
668:
669:
670: public function __construct($name, array $references)
671: {
672: $this->name = $name;
673: $this->references = $references;
674: }
675:
676:
677:
678: 679: 680:
681: public function getName()
682: {
683: return $this->name;
684: }
685:
686:
687:
688: 689: 690:
691: public function getReferences()
692: {
693: return $this->references;
694: }
695:
696: }
697:
698:
699:
700:
701: 702: 703: 704: 705: 706: 707: 708: 709: 710:
711: class DibiIndexInfo extends DibiObject
712: {
713:
714: private $info;
715:
716:
717: public function __construct(array $info)
718: {
719: $this->info = $info;
720: }
721:
722:
723:
724: 725: 726:
727: public function getName()
728: {
729: return $this->info['name'];
730: }
731:
732:
733:
734: 735: 736:
737: public function getColumns()
738: {
739: return $this->info['columns'];
740: }
741:
742:
743:
744: 745: 746:
747: public function isUnique()
748: {
749: return !empty($this->info['unique']);
750: }
751:
752:
753:
754: 755: 756:
757: public function isPrimary()
758: {
759: return !empty($this->info['primary']);
760: }
761:
762: }
763: