Carsten Brandt
11 years ago
37 changed files with 897 additions and 108 deletions
@ -0,0 +1,116 @@
|
||||
<?php |
||||
/** |
||||
* @link http://www.yiiframework.com/ |
||||
* @copyright Copyright (c) 2008 Yii Software LLC |
||||
* @license http://www.yiiframework.com/license/ |
||||
*/ |
||||
|
||||
namespace yii\db\cubrid; |
||||
|
||||
use yii\base\InvalidParamException; |
||||
|
||||
/** |
||||
* QueryBuilder is the query builder for CUBRID databases (version 9.1.x and higher). |
||||
* |
||||
* @author Carsten Brandt <mail@cebe.cc> |
||||
* @since 2.0 |
||||
*/ |
||||
class QueryBuilder extends \yii\db\QueryBuilder |
||||
{ |
||||
/** |
||||
* @var array mapping from abstract column types (keys) to physical column types (values). |
||||
*/ |
||||
public $typeMap = array( |
||||
Schema::TYPE_PK => 'int NOT NULL AUTO_INCREMENT PRIMARY KEY', |
||||
Schema::TYPE_STRING => 'varchar(255)', |
||||
Schema::TYPE_TEXT => 'varchar', |
||||
Schema::TYPE_SMALLINT => 'smallint', |
||||
Schema::TYPE_INTEGER => 'int', |
||||
Schema::TYPE_BIGINT => 'bigint', |
||||
Schema::TYPE_FLOAT => 'float(7)', |
||||
Schema::TYPE_DECIMAL => 'decimal(10,0)', |
||||
Schema::TYPE_DATETIME => 'datetime', |
||||
Schema::TYPE_TIMESTAMP => 'timestamp', |
||||
Schema::TYPE_TIME => 'time', |
||||
Schema::TYPE_DATE => 'date', |
||||
Schema::TYPE_BINARY => 'blob', |
||||
Schema::TYPE_BOOLEAN => 'smallint', |
||||
Schema::TYPE_MONEY => 'decimal(19,4)', |
||||
); |
||||
|
||||
/** |
||||
* Creates a SQL statement for resetting the sequence value of a table's primary key. |
||||
* The sequence will be reset such that the primary key of the next new row inserted |
||||
* will have the specified value or 1. |
||||
* @param string $tableName the name of the table whose primary key sequence will be reset |
||||
* @param mixed $value the value for the primary key of the next new row inserted. If this is not set, |
||||
* the next new row's primary key will have a value 1. |
||||
* @return string the SQL statement for resetting sequence |
||||
* @throws InvalidParamException if the table does not exist or there is no sequence associated with the table. |
||||
*/ |
||||
public function resetSequence($tableName, $value = null) |
||||
{ |
||||
$table = $this->db->getTableSchema($tableName); |
||||
if ($table !== null && $table->sequenceName !== null) { |
||||
$tableName = $this->db->quoteTableName($tableName); |
||||
if ($value === null) { |
||||
$key = reset($table->primaryKey); |
||||
$value = (int)$this->db->createCommand("SELECT MAX(`$key`) FROM " . $this->db->schema->quoteTableName($tableName))->queryScalar() + 1; |
||||
} else { |
||||
$value = (int)$value; |
||||
} |
||||
return "ALTER TABLE " . $this->db->schema->quoteTableName($tableName) . " AUTO_INCREMENT=$value;"; |
||||
} elseif ($table === null) { |
||||
throw new InvalidParamException("Table not found: $tableName"); |
||||
} else { |
||||
throw new InvalidParamException("There is not sequence associated with table '$tableName'."); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* Generates a batch INSERT SQL statement. |
||||
* For example, |
||||
* |
||||
* ~~~ |
||||
* $connection->createCommand()->batchInsert('tbl_user', array('name', 'age'), array( |
||||
* array('Tom', 30), |
||||
* array('Jane', 20), |
||||
* array('Linda', 25), |
||||
* ))->execute(); |
||||
* ~~~ |
||||
* |
||||
* Note that the values in each row must match the corresponding column names. |
||||
* |
||||
* @param string $table the table that new rows will be inserted into. |
||||
* @param array $columns the column names |
||||
* @param array $rows the rows to be batch inserted into the table |
||||
* @return string the batch INSERT SQL statement |
||||
*/ |
||||
public function batchInsert($table, $columns, $rows) |
||||
{ |
||||
if (($tableSchema = $this->db->getTableSchema($table)) !== null) { |
||||
$columnSchemas = $tableSchema->columns; |
||||
} else { |
||||
$columnSchemas = array(); |
||||
} |
||||
|
||||
foreach ($columns as $i => $name) { |
||||
$columns[$i] = $this->db->quoteColumnName($name); |
||||
} |
||||
|
||||
$values = array(); |
||||
foreach ($rows as $row) { |
||||
$vs = array(); |
||||
foreach ($row as $i => $value) { |
||||
if (!is_array($value) && isset($columnSchemas[$columns[$i]])) { |
||||
$value = $columnSchemas[$columns[$i]]->typecast($value); |
||||
} |
||||
$vs[] = is_string($value) ? $this->db->quoteValue($value) : $value; |
||||
} |
||||
$values[] = '(' . implode(', ', $vs) . ')'; |
||||
} |
||||
|
||||
return 'INSERT INTO ' . $this->db->quoteTableName($table) |
||||
. ' (' . implode(', ', $columns) . ') VALUES ' . implode(', ', $values); |
||||
} |
||||
} |
@ -0,0 +1,259 @@
|
||||
<?php |
||||
/** |
||||
* @link http://www.yiiframework.com/ |
||||
* @copyright Copyright (c) 2008 Yii Software LLC |
||||
* @license http://www.yiiframework.com/license/ |
||||
*/ |
||||
|
||||
namespace yii\db\cubrid; |
||||
|
||||
use yii\base\NotSupportedException; |
||||
use yii\db\Expression; |
||||
use yii\db\TableSchema; |
||||
use yii\db\ColumnSchema; |
||||
|
||||
/** |
||||
* Schema is the class for retrieving metadata from a CUBRID database (version 9.1.x and higher). |
||||
* |
||||
* @author Carsten Brandt <mail@cebe.cc> |
||||
* @since 2.0 |
||||
*/ |
||||
class Schema extends \yii\db\Schema |
||||
{ |
||||
/** |
||||
* @var array mapping from physical column types (keys) to abstract column types (values) |
||||
* Please refer to [CUBRID manual](http://www.cubrid.org/manual/91/en/sql/datatype.html) for |
||||
* details on data types. |
||||
*/ |
||||
public $typeMap = array( |
||||
// Numeric data types |
||||
'short' => self::TYPE_SMALLINT, |
||||
'smallint' => self::TYPE_SMALLINT, |
||||
'int' => self::TYPE_INTEGER, |
||||
'integer' => self::TYPE_INTEGER, |
||||
'bigint' => self::TYPE_BIGINT, |
||||
'numeric' => self::TYPE_DECIMAL, |
||||
'decimal' => self::TYPE_DECIMAL, |
||||
'float' => self::TYPE_FLOAT, |
||||
'real' => self::TYPE_FLOAT, |
||||
'double' => self::TYPE_FLOAT, |
||||
'double precision' => self::TYPE_FLOAT, |
||||
'monetary' => self::TYPE_MONEY, |
||||
// Date/Time data types |
||||
'date' => self::TYPE_DATE, |
||||
'time' => self::TYPE_TIME, |
||||
'timestamp' => self::TYPE_TIMESTAMP, |
||||
'datetime' => self::TYPE_DATETIME, |
||||
// String data types |
||||
'char' => self::TYPE_STRING, |
||||
'varchar' => self::TYPE_STRING, |
||||
'char varying' => self::TYPE_STRING, |
||||
'nchar' => self::TYPE_STRING, |
||||
'nchar varying' => self::TYPE_STRING, |
||||
'string' => self::TYPE_STRING, |
||||
// BLOB/CLOB data types |
||||
'blob' => self::TYPE_BINARY, |
||||
'clob' => self::TYPE_BINARY, |
||||
// Bit string data types |
||||
'bit' => self::TYPE_STRING, |
||||
'bit varying' => self::TYPE_STRING, |
||||
// Collection data types (considered strings for now, may add support for them later) |
||||
'set' => self::TYPE_STRING, |
||||
'multiset' => self::TYPE_STRING, |
||||
'list' => self::TYPE_STRING, |
||||
'sequence' => self::TYPE_STRING, |
||||
'enum' => self::TYPE_STRING, |
||||
); |
||||
|
||||
/** |
||||
* Quotes a table name for use in a query. |
||||
* A simple table name has no schema prefix. |
||||
* @param string $name table name |
||||
* @return string the properly quoted table name |
||||
*/ |
||||
public function quoteSimpleTableName($name) |
||||
{ |
||||
return strpos($name, "`") !== false ? $name : "`" . $name . "`"; |
||||
} |
||||
|
||||
/** |
||||
* Quotes a column name for use in a query. |
||||
* A simple column name has no prefix. |
||||
* @param string $name column name |
||||
* @return string the properly quoted column name |
||||
*/ |
||||
public function quoteSimpleColumnName($name) |
||||
{ |
||||
return strpos($name, '`') !== false || $name === '*' ? $name : '`' . $name . '`'; |
||||
} |
||||
|
||||
/** |
||||
* Quotes a string value for use in a query. |
||||
* Note that if the parameter is not a string, it will be returned without change. |
||||
* @param string $str string to be quoted |
||||
* @return string the properly quoted string |
||||
* @see http://www.php.net/manual/en/function.PDO-quote.php |
||||
*/ |
||||
public function quoteValue($str) |
||||
{ |
||||
if (!is_string($str)) { |
||||
return $str; |
||||
} |
||||
|
||||
$this->db->open(); |
||||
// workaround for broken PDO::quote() implementation in CUBRID 9.1.0 http://jira.cubrid.org/browse/APIS-658 |
||||
if (version_compare($this->db->pdo->getAttribute(\PDO::ATTR_CLIENT_VERSION), '9.1.0', '<=')) { |
||||
return "'" . addcslashes(str_replace("'", "''", $str), "\000\n\r\\\032") . "'"; |
||||
} else { |
||||
return $this->db->pdo->quote($str); |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* Creates a query builder for the CUBRID database. |
||||
* @return QueryBuilder query builder instance |
||||
*/ |
||||
public function createQueryBuilder() |
||||
{ |
||||
return new QueryBuilder($this->db); |
||||
} |
||||
|
||||
/** |
||||
* Loads the metadata for the specified table. |
||||
* @param string $name table name |
||||
* @return TableSchema driver dependent table metadata. Null if the table does not exist. |
||||
*/ |
||||
protected function loadTableSchema($name) |
||||
{ |
||||
$this->db->open(); |
||||
$tableInfo = $this->db->pdo->cubrid_schema(\PDO::CUBRID_SCH_TABLE, $name); |
||||
|
||||
if (isset($tableInfo[0]['NAME'])) { |
||||
$table = new TableSchema(); |
||||
$table->name = $tableInfo[0]['NAME']; |
||||
|
||||
$sql = 'SHOW FULL COLUMNS FROM ' . $this->quoteSimpleTableName($table->name); |
||||
$columns = $this->db->createCommand($sql)->queryAll(); |
||||
|
||||
foreach ($columns as $info) { |
||||
$column = $this->loadColumnSchema($info); |
||||
$table->columns[$column->name] = $column; |
||||
if ($column->isPrimaryKey) { |
||||
$table->primaryKey[] = $column->name; |
||||
if ($column->autoIncrement) { |
||||
$table->sequenceName = ''; |
||||
} |
||||
} |
||||
} |
||||
|
||||
$foreignKeys = $this->db->pdo->cubrid_schema(\PDO::CUBRID_SCH_IMPORTED_KEYS, $table->name); |
||||
foreach($foreignKeys as $key) { |
||||
if (isset($table->foreignKeys[$key['FK_NAME']])) { |
||||
$table->foreignKeys[$key['FK_NAME']][$key['FKCOLUMN_NAME']] = $key['PKCOLUMN_NAME']; |
||||
} else { |
||||
$table->foreignKeys[$key['FK_NAME']] = array( |
||||
$key['PKTABLE_NAME'], |
||||
$key['FKCOLUMN_NAME'] => $key['PKCOLUMN_NAME'] |
||||
); |
||||
} |
||||
} |
||||
$table->foreignKeys = array_values($table->foreignKeys); |
||||
|
||||
return $table; |
||||
} else { |
||||
return null; |
||||
} |
||||
} |
||||
|
||||
/** |
||||
* Loads the column information into a [[ColumnSchema]] object. |
||||
* @param array $info column information |
||||
* @return ColumnSchema the column schema object |
||||
*/ |
||||
protected function loadColumnSchema($info) |
||||
{ |
||||
$column = new ColumnSchema(); |
||||
|
||||
$column->name = $info['Field']; |
||||
$column->allowNull = $info['Null'] === 'YES'; |
||||
$column->isPrimaryKey = strpos($info['Key'], 'PRI') !== false; |
||||
$column->autoIncrement = stripos($info['Extra'], 'auto_increment') !== false; |
||||
|
||||
$column->dbType = strtolower($info['Type']); |
||||
$column->unsigned = strpos($column->dbType, 'unsigned') !== false; |
||||
|
||||
$column->type = self::TYPE_STRING; |
||||
if (preg_match('/^([\w ]+)(?:\(([^\)]+)\))?/', $column->dbType, $matches)) { |
||||
$type = $matches[1]; |
||||
if (isset($this->typeMap[$type])) { |
||||
$column->type = $this->typeMap[$type]; |
||||
} |
||||
if (!empty($matches[2])) { |
||||
if ($type === 'enum') { |
||||
$values = explode(',', $matches[2]); |
||||
foreach ($values as $i => $value) { |
||||
$values[$i] = trim($value, "'"); |
||||
} |
||||
$column->enumValues = $values; |
||||
} else { |
||||
$values = explode(',', $matches[2]); |
||||
$column->size = $column->precision = (int)$values[0]; |
||||
if (isset($values[1])) { |
||||
$column->scale = (int)$values[1]; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
$column->phpType = $this->getColumnPhpType($column); |
||||
|
||||
if ($column->type === 'timestamp' && $info['Default'] === 'CURRENT_TIMESTAMP' || |
||||
$column->type === 'datetime' && $info['Default'] === 'SYS_DATETIME' || |
||||
$column->type === 'date' && $info['Default'] === 'SYS_DATE' || |
||||
$column->type === 'time' && $info['Default'] === 'SYS_TIME') { |
||||
$column->defaultValue = new Expression($info['Default']); |
||||
} else { |
||||
$column->defaultValue = $column->typecast($info['Default']); |
||||
} |
||||
|
||||
return $column; |
||||
} |
||||
|
||||
/** |
||||
* Returns all table names in the database. |
||||
* @param string $schema the schema of the tables. Defaults to empty string, meaning the current or default schema. |
||||
* @return array all table names in the database. The names have NO schema name prefix. |
||||
*/ |
||||
protected function findTableNames($schema = '') |
||||
{ |
||||
$this->db->open(); |
||||
$tables = $this->db->pdo->cubrid_schema(\PDO::CUBRID_SCH_TABLE); |
||||
$tableNames = array(); |
||||
foreach($tables as $table) { |
||||
// do not list system tables |
||||
if ($table['TYPE'] != 0) { |
||||
$tableNames[] = $table['NAME']; |
||||
} |
||||
} |
||||
return $tableNames; |
||||
} |
||||
|
||||
/** |
||||
* Determines the PDO type for the give PHP data value. |
||||
* @param mixed $data the data whose PDO type is to be determined |
||||
* @return integer the PDO type |
||||
* @see http://www.php.net/manual/en/pdo.constants.php |
||||
*/ |
||||
public function getPdoType($data) |
||||
{ |
||||
static $typeMap = array( |
||||
'boolean' => \PDO::PARAM_INT, // CUBRID PDO does not support PARAM_BOOL |
||||
'integer' => \PDO::PARAM_INT, |
||||
'string' => \PDO::PARAM_STR, |
||||
'resource' => \PDO::PARAM_LOB, |
||||
'NULL' => \PDO::PARAM_NULL, |
||||
); |
||||
$type = gettype($data); |
||||
return isset($typeMap[$type]) ? $typeMap[$type] : \PDO::PARAM_STR; |
||||
} |
||||
} |
@ -0,0 +1,110 @@
|
||||
/** |
||||
* This is the database schema for testing CUBRID support of Yii DAO and Active Record. |
||||
* The database setup in config.php is required to perform then relevant tests: |
||||
*/ |
||||
|
||||
DROP TABLE IF EXISTS tbl_composite_fk; |
||||
DROP TABLE IF EXISTS tbl_order_item; |
||||
DROP TABLE IF EXISTS tbl_item; |
||||
DROP TABLE IF EXISTS tbl_order; |
||||
DROP TABLE IF EXISTS tbl_category; |
||||
DROP TABLE IF EXISTS tbl_customer; |
||||
DROP TABLE IF EXISTS tbl_type; |
||||
DROP TABLE IF EXISTS tbl_constraints; |
||||
|
||||
CREATE TABLE `tbl_constraints` |
||||
( |
||||
`id` integer not null, |
||||
`field1` varchar(255) |
||||
); |
||||
|
||||
|
||||
CREATE TABLE `tbl_customer` ( |
||||
`id` int(11) NOT NULL AUTO_INCREMENT, |
||||
`email` varchar(128) NOT NULL, |
||||
`name` varchar(128) NOT NULL, |
||||
`address` string, |
||||
`status` int (11) DEFAULT 0, |
||||
PRIMARY KEY (`id`) |
||||
); |
||||
|
||||
CREATE TABLE `tbl_category` ( |
||||
`id` int(11) NOT NULL AUTO_INCREMENT, |
||||
`name` varchar(128) NOT NULL, |
||||
PRIMARY KEY (`id`) |
||||
); |
||||
|
||||
CREATE TABLE `tbl_item` ( |
||||
`id` int(11) NOT NULL AUTO_INCREMENT, |
||||
`name` varchar(128) NOT NULL, |
||||
`category_id` int(11) NOT NULL, |
||||
PRIMARY KEY (`id`), |
||||
CONSTRAINT `FK_item_category_id` FOREIGN KEY (`category_id`) REFERENCES `tbl_category` (`id`) ON DELETE CASCADE |
||||
); |
||||
|
||||
CREATE TABLE `tbl_order` ( |
||||
`id` int(11) NOT NULL AUTO_INCREMENT, |
||||
`customer_id` int(11) NOT NULL, |
||||
`create_time` int(11) NOT NULL, |
||||
`total` decimal(10,0) NOT NULL, |
||||
PRIMARY KEY (`id`), |
||||
CONSTRAINT `FK_order_customer_id` FOREIGN KEY (`customer_id`) REFERENCES `tbl_customer` (`id`) ON DELETE CASCADE |
||||
); |
||||
|
||||
CREATE TABLE `tbl_order_item` ( |
||||
`order_id` int(11) NOT NULL, |
||||
`item_id` int(11) NOT NULL, |
||||
`quantity` int(11) NOT NULL, |
||||
`subtotal` decimal(10,0) NOT NULL, |
||||
PRIMARY KEY (`order_id`,`item_id`), |
||||
CONSTRAINT `FK_order_item_order_id` FOREIGN KEY (`order_id`) REFERENCES `tbl_order` (`id`) ON DELETE CASCADE, |
||||
CONSTRAINT `FK_order_item_item_id` FOREIGN KEY (`item_id`) REFERENCES `tbl_item` (`id`) ON DELETE CASCADE |
||||
); |
||||
|
||||
CREATE TABLE `tbl_type` ( |
||||
`int_col` int(11) NOT NULL, |
||||
`int_col2` int(11) DEFAULT '1', |
||||
`char_col` char(100) NOT NULL, |
||||
`char_col2` varchar(100) DEFAULT 'something', |
||||
`char_col3` string, |
||||
`enum_col` enum('a', 'b'), |
||||
`float_col` double NOT NULL, |
||||
`float_col2` double DEFAULT '1.23', |
||||
`blob_col` blob, |
||||
`numeric_col` decimal(5,2) DEFAULT '33.22', |
||||
`time` timestamp NOT NULL DEFAULT '2002-01-01 00:00:00', |
||||
`bool_col` smallint NOT NULL, |
||||
`bool_col2` smallint DEFAULT 1 |
||||
); |
||||
|
||||
CREATE TABLE `tbl_composite_fk` ( |
||||
`id` int(11) NOT NULL, |
||||
`order_id` int(11) NOT NULL, |
||||
`item_id` int(11) NOT NULL, |
||||
PRIMARY KEY (`id`), |
||||
CONSTRAINT `FK_composite_fk_order_item` FOREIGN KEY (`order_id`,`item_id`) REFERENCES `tbl_order_item` (`order_id`,`item_id`) ON DELETE CASCADE |
||||
); |
||||
|
||||
INSERT INTO tbl_customer (email, name, address, status) VALUES ('user1@example.com', 'user1', 'address1', 1); |
||||
INSERT INTO tbl_customer (email, name, address, status) VALUES ('user2@example.com', 'user2', 'address2', 1); |
||||
INSERT INTO tbl_customer (email, name, address, status) VALUES ('user3@example.com', 'user3', 'address3', 2); |
||||
|
||||
INSERT INTO tbl_category (name) VALUES ('Books'); |
||||
INSERT INTO tbl_category (name) VALUES ('Movies'); |
||||
|
||||
INSERT INTO tbl_item (name, category_id) VALUES ('Agile Web Application Development with Yii1.1 and PHP5', 1); |
||||
INSERT INTO tbl_item (name, category_id) VALUES ('Yii 1.1 Application Development Cookbook', 1); |
||||
INSERT INTO tbl_item (name, category_id) VALUES ('Ice Age', 2); |
||||
INSERT INTO tbl_item (name, category_id) VALUES ('Toy Story', 2); |
||||
INSERT INTO tbl_item (name, category_id) VALUES ('Cars', 2); |
||||
|
||||
INSERT INTO tbl_order (customer_id, create_time, total) VALUES (1, 1325282384, 110.0); |
||||
INSERT INTO tbl_order (customer_id, create_time, total) VALUES (2, 1325334482, 33.0); |
||||
INSERT INTO tbl_order (customer_id, create_time, total) VALUES (2, 1325502201, 40.0); |
||||
|
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (1, 1, 1, 30.0); |
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (1, 2, 2, 40.0); |
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (2, 4, 1, 10.0); |
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (2, 5, 1, 15.0); |
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (2, 3, 1, 8.0); |
||||
INSERT INTO tbl_order_item (order_id, item_id, quantity, subtotal) VALUES (3, 2, 1, 40.0); |
@ -0,0 +1,89 @@
|
||||
<?php |
||||
|
||||
namespace yiiunit\framework\db; |
||||
|
||||
use yii\caching\FileCache; |
||||
use yii\db\Schema; |
||||
|
||||
class SchemaTest extends DatabaseTestCase |
||||
{ |
||||
|
||||
public function testGetPDOType() |
||||
{ |
||||
$values = array( |
||||
array(null, \PDO::PARAM_NULL), |
||||
array('', \PDO::PARAM_STR), |
||||
array('hello', \PDO::PARAM_STR), |
||||
array(0, \PDO::PARAM_INT), |
||||
array(1, \PDO::PARAM_INT), |
||||
array(1337, \PDO::PARAM_INT), |
||||
array(true, \PDO::PARAM_BOOL), |
||||
array(false, \PDO::PARAM_BOOL), |
||||
array($fp=fopen(__FILE__, 'rb'), \PDO::PARAM_LOB), |
||||
); |
||||
|
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
foreach($values as $value) { |
||||
$this->assertEquals($value[1], $schema->getPdoType($value[0])); |
||||
} |
||||
fclose($fp); |
||||
} |
||||
|
||||
public function testFindTableNames() |
||||
{ |
||||
/** @var Schema $schema */ |
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
$tables = $schema->getTableNames(); |
||||
$this->assertTrue(in_array('tbl_customer', $tables)); |
||||
$this->assertTrue(in_array('tbl_category', $tables)); |
||||
$this->assertTrue(in_array('tbl_item', $tables)); |
||||
$this->assertTrue(in_array('tbl_order', $tables)); |
||||
$this->assertTrue(in_array('tbl_order_item', $tables)); |
||||
$this->assertTrue(in_array('tbl_type', $tables)); |
||||
} |
||||
|
||||
public function testGetTableSchemas() |
||||
{ |
||||
/** @var Schema $schema */ |
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
$tables = $schema->getTableSchemas(); |
||||
$this->assertEquals(count($schema->getTableNames()), count($tables)); |
||||
foreach($tables as $table) { |
||||
$this->assertInstanceOf('yii\db\TableSchema', $table); |
||||
} |
||||
} |
||||
|
||||
public function testGetNonExistingTableSchema() |
||||
{ |
||||
$this->assertNull($this->getConnection()->schema->getTableSchema('nonexisting_table')); |
||||
} |
||||
|
||||
public function testSchemaCache() |
||||
{ |
||||
/** @var Schema $schema */ |
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
$schema->db->enableSchemaCache = true; |
||||
$schema->db->schemaCache = new FileCache(); |
||||
$noCacheTable = $schema->getTableSchema('tbl_type', true); |
||||
$cachedTable = $schema->getTableSchema('tbl_type', true); |
||||
$this->assertEquals($noCacheTable, $cachedTable); |
||||
} |
||||
|
||||
public function testCompositeFk() |
||||
{ |
||||
/** @var Schema $schema */ |
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
$table = $schema->getTableSchema('tbl_composite_fk'); |
||||
|
||||
$this->assertCount(1, $table->foreignKeys); |
||||
$this->assertTrue(isset($table->foreignKeys[0])); |
||||
$this->assertEquals('tbl_order_item', $table->foreignKeys[0][0]); |
||||
$this->assertEquals('order_id', $table->foreignKeys[0]['order_id']); |
||||
$this->assertEquals('item_id', $table->foreignKeys[0]['item_id']); |
||||
} |
||||
} |
@ -0,0 +1,9 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yiiunit\framework\db\ActiveRecordTest; |
||||
|
||||
class CubridActiveRecordTest extends ActiveRecordTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
} |
@ -0,0 +1,72 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yiiunit\framework\db\CommandTest; |
||||
|
||||
class CubridCommandTest extends CommandTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
|
||||
public function testBindParamValue() |
||||
{ |
||||
$db = $this->getConnection(); |
||||
|
||||
// bindParam |
||||
$sql = 'INSERT INTO tbl_customer(email, name, address) VALUES (:email, :name, :address)'; |
||||
$command = $db->createCommand($sql); |
||||
$email = 'user4@example.com'; |
||||
$name = 'user4'; |
||||
$address = 'address4'; |
||||
$command->bindParam(':email', $email); |
||||
$command->bindParam(':name', $name); |
||||
$command->bindParam(':address', $address); |
||||
$command->execute(); |
||||
|
||||
$sql = 'SELECT name FROM tbl_customer WHERE email=:email'; |
||||
$command = $db->createCommand($sql); |
||||
$command->bindParam(':email', $email); |
||||
$this->assertEquals($name, $command->queryScalar()); |
||||
|
||||
$sql = "INSERT INTO tbl_type (int_col, char_col, char_col2, enum_col, float_col, blob_col, numeric_col, bool_col, bool_col2) VALUES (:int_col, '', :char_col, :enum_col, :float_col, CHAR_TO_BLOB(:blob_col), :numeric_col, :bool_col, :bool_col2)"; |
||||
$command = $db->createCommand($sql); |
||||
$intCol = 123; |
||||
$charCol = 'abc'; |
||||
$enumCol = 'a'; |
||||
$floatCol = 1.23; |
||||
$blobCol = "\x10\x11\x12"; |
||||
$numericCol = '1.23'; |
||||
$boolCol = false; |
||||
$boolCol2 = true; |
||||
$command->bindParam(':int_col', $intCol); |
||||
$command->bindParam(':char_col', $charCol); |
||||
$command->bindParam(':enum_col', $enumCol); |
||||
$command->bindParam(':float_col', $floatCol); |
||||
$command->bindParam(':blob_col', $blobCol); |
||||
$command->bindParam(':numeric_col', $numericCol); |
||||
$command->bindParam(':bool_col', $boolCol); |
||||
$command->bindParam(':bool_col2', $boolCol2); |
||||
$this->assertEquals(1, $command->execute()); |
||||
|
||||
$sql = 'SELECT * FROM tbl_type'; |
||||
$row = $db->createCommand($sql)->queryOne(); |
||||
$this->assertEquals($intCol, $row['int_col']); |
||||
$this->assertEquals($enumCol, $row['enum_col']); |
||||
$this->assertEquals($charCol, $row['char_col2']); |
||||
$this->assertEquals($floatCol, $row['float_col']); |
||||
$this->assertEquals($blobCol, fread($row['blob_col'], 3)); |
||||
$this->assertEquals($numericCol, $row['numeric_col']); |
||||
$this->assertEquals($boolCol, $row['bool_col']); |
||||
$this->assertEquals($boolCol2, $row['bool_col2']); |
||||
|
||||
// bindValue |
||||
$sql = 'INSERT INTO tbl_customer(email, name, address) VALUES (:email, \'user5\', \'address5\')'; |
||||
$command = $db->createCommand($sql); |
||||
$command->bindValue(':email', 'user5@example.com'); |
||||
$command->execute(); |
||||
|
||||
$sql = 'SELECT email FROM tbl_customer WHERE name=:name'; |
||||
$command = $db->createCommand($sql); |
||||
$command->bindValue(':name', 'user5'); |
||||
$this->assertEquals('user5@example.com', $command->queryScalar()); |
||||
} |
||||
} |
@ -0,0 +1,17 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yiiunit\framework\db\ConnectionTest; |
||||
|
||||
class CubridConnectionTest extends ConnectionTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
|
||||
public function testQuoteValue() |
||||
{ |
||||
$connection = $this->getConnection(false); |
||||
$this->assertEquals(123, $connection->quoteValue(123)); |
||||
$this->assertEquals("'string'", $connection->quoteValue('string')); |
||||
$this->assertEquals("'It''s interesting'", $connection->quoteValue("It's interesting")); |
||||
} |
||||
} |
@ -0,0 +1,80 @@
|
||||
<?php |
||||
|
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yii\base\NotSupportedException; |
||||
use yii\db\sqlite\Schema; |
||||
use yiiunit\framework\db\QueryBuilderTest; |
||||
|
||||
class CubridQueryBuilderTest extends QueryBuilderTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
|
||||
/** |
||||
* this is not used as a dataprovider for testGetColumnType to speed up the test |
||||
* when used as dataprovider every single line will cause a reconnect with the database which is not needed here |
||||
*/ |
||||
public function columnTypes() |
||||
{ |
||||
return array( |
||||
array(Schema::TYPE_PK, 'int NOT NULL AUTO_INCREMENT PRIMARY KEY'), |
||||
array(Schema::TYPE_PK . '(8)', 'int NOT NULL AUTO_INCREMENT PRIMARY KEY'), |
||||
array(Schema::TYPE_PK . ' CHECK (value > 5)', 'int NOT NULL AUTO_INCREMENT PRIMARY KEY CHECK (value > 5)'), |
||||
array(Schema::TYPE_PK . '(8) CHECK (value > 5)', 'int NOT NULL AUTO_INCREMENT PRIMARY KEY CHECK (value > 5)'), |
||||
array(Schema::TYPE_STRING, 'varchar(255)'), |
||||
array(Schema::TYPE_STRING . '(32)', 'varchar(32)'), |
||||
array(Schema::TYPE_STRING . ' CHECK (value LIKE "test%")', 'varchar(255) CHECK (value LIKE "test%")'), |
||||
array(Schema::TYPE_STRING . '(32) CHECK (value LIKE "test%")', 'varchar(32) CHECK (value LIKE "test%")'), |
||||
array(Schema::TYPE_STRING . ' NOT NULL', 'varchar(255) NOT NULL'), |
||||
array(Schema::TYPE_TEXT, 'varchar'), |
||||
array(Schema::TYPE_TEXT . '(255)', 'varchar'), |
||||
array(Schema::TYPE_TEXT . ' CHECK (value LIKE "test%")', 'varchar CHECK (value LIKE "test%")'), |
||||
array(Schema::TYPE_TEXT . '(255) CHECK (value LIKE "test%")', 'varchar CHECK (value LIKE "test%")'), |
||||
array(Schema::TYPE_TEXT . ' NOT NULL', 'varchar NOT NULL'), |
||||
array(Schema::TYPE_TEXT . '(255) NOT NULL', 'varchar NOT NULL'), |
||||
array(Schema::TYPE_SMALLINT, 'smallint'), |
||||
array(Schema::TYPE_SMALLINT . '(8)', 'smallint'), |
||||
array(Schema::TYPE_INTEGER, 'int'), |
||||
array(Schema::TYPE_INTEGER . '(8)', 'int'), |
||||
array(Schema::TYPE_INTEGER . ' CHECK (value > 5)', 'int CHECK (value > 5)'), |
||||
array(Schema::TYPE_INTEGER . '(8) CHECK (value > 5)', 'int CHECK (value > 5)'), |
||||
array(Schema::TYPE_INTEGER . ' NOT NULL', 'int NOT NULL'), |
||||
array(Schema::TYPE_BIGINT, 'bigint'), |
||||
array(Schema::TYPE_BIGINT . '(8)', 'bigint'), |
||||
array(Schema::TYPE_BIGINT . ' CHECK (value > 5)', 'bigint CHECK (value > 5)'), |
||||
array(Schema::TYPE_BIGINT . '(8) CHECK (value > 5)', 'bigint CHECK (value > 5)'), |
||||
array(Schema::TYPE_BIGINT . ' NOT NULL', 'bigint NOT NULL'), |
||||
array(Schema::TYPE_FLOAT, 'float(7)'), |
||||
array(Schema::TYPE_FLOAT . '(16)', 'float(16)'), |
||||
array(Schema::TYPE_FLOAT . ' CHECK (value > 5.6)', 'float(7) CHECK (value > 5.6)'), |
||||
array(Schema::TYPE_FLOAT . '(16) CHECK (value > 5.6)', 'float(16) CHECK (value > 5.6)'), |
||||
array(Schema::TYPE_FLOAT . ' NOT NULL', 'float(7) NOT NULL'), |
||||
array(Schema::TYPE_DECIMAL, 'decimal(10,0)'), |
||||
array(Schema::TYPE_DECIMAL . '(12,4)', 'decimal(12,4)'), |
||||
array(Schema::TYPE_DECIMAL . ' CHECK (value > 5.6)', 'decimal(10,0) CHECK (value > 5.6)'), |
||||
array(Schema::TYPE_DECIMAL . '(12,4) CHECK (value > 5.6)', 'decimal(12,4) CHECK (value > 5.6)'), |
||||
array(Schema::TYPE_DECIMAL . ' NOT NULL', 'decimal(10,0) NOT NULL'), |
||||
array(Schema::TYPE_DATETIME, 'datetime'), |
||||
array(Schema::TYPE_DATETIME . " CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')", "datetime CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')"), |
||||
array(Schema::TYPE_DATETIME . ' NOT NULL', 'datetime NOT NULL'), |
||||
array(Schema::TYPE_TIMESTAMP, 'timestamp'), |
||||
array(Schema::TYPE_TIMESTAMP . " CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')", "timestamp CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')"), |
||||
array(Schema::TYPE_TIMESTAMP . ' NOT NULL', 'timestamp NOT NULL'), |
||||
array(Schema::TYPE_TIME, 'time'), |
||||
array(Schema::TYPE_TIME . " CHECK(value BETWEEN '12:00:00' AND '13:01:01')", "time CHECK(value BETWEEN '12:00:00' AND '13:01:01')"), |
||||
array(Schema::TYPE_TIME . ' NOT NULL', 'time NOT NULL'), |
||||
array(Schema::TYPE_DATE, 'date'), |
||||
array(Schema::TYPE_DATE . " CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')", "date CHECK(value BETWEEN '2011-01-01' AND '2013-01-01')"), |
||||
array(Schema::TYPE_DATE . ' NOT NULL', 'date NOT NULL'), |
||||
array(Schema::TYPE_BINARY, 'blob'), |
||||
array(Schema::TYPE_BOOLEAN, 'smallint'), |
||||
array(Schema::TYPE_BOOLEAN . ' NOT NULL DEFAULT 1', 'smallint NOT NULL DEFAULT 1'), |
||||
array(Schema::TYPE_MONEY, 'decimal(19,4)'), |
||||
array(Schema::TYPE_MONEY . '(16,2)', 'decimal(16,2)'), |
||||
array(Schema::TYPE_MONEY . ' CHECK (value > 0.0)', 'decimal(19,4) CHECK (value > 0.0)'), |
||||
array(Schema::TYPE_MONEY . '(16,2) CHECK (value > 0.0)', 'decimal(16,2) CHECK (value > 0.0)'), |
||||
array(Schema::TYPE_MONEY . ' NOT NULL', 'decimal(19,4) NOT NULL'), |
||||
); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,9 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yiiunit\framework\db\QueryTest; |
||||
|
||||
class CubridQueryTest extends QueryTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
} |
@ -0,0 +1,31 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\cubrid; |
||||
|
||||
use yiiunit\framework\db\SchemaTest; |
||||
|
||||
class CubridSchemaTest extends SchemaTest |
||||
{ |
||||
public $driverName = 'cubrid'; |
||||
|
||||
public function testGetPDOType() |
||||
{ |
||||
$values = array( |
||||
null => \PDO::PARAM_NULL, |
||||
'' => \PDO::PARAM_STR, |
||||
'hello' => \PDO::PARAM_STR, |
||||
0 => \PDO::PARAM_INT, |
||||
1 => \PDO::PARAM_INT, |
||||
1337 => \PDO::PARAM_INT, |
||||
true => \PDO::PARAM_INT, // CUBRID PDO does not support PARAM_BOOL |
||||
false => \PDO::PARAM_INT, // CUBRID PDO does not support PARAM_BOOL |
||||
); |
||||
|
||||
$schema = $this->getConnection()->schema; |
||||
|
||||
foreach($values as $value => $type) { |
||||
$this->assertEquals($type, $schema->getPdoType($value)); |
||||
} |
||||
$this->assertEquals(\PDO::PARAM_LOB, $schema->getPdoType($fp=fopen(__FILE__, 'rb'))); |
||||
fclose($fp); |
||||
} |
||||
} |
@ -0,0 +1,14 @@
|
||||
<?php |
||||
namespace yiiunit\framework\db\sqlite; |
||||
|
||||
use yiiunit\framework\db\SchemaTest; |
||||
|
||||
class SqliteSchemaTest extends SchemaTest |
||||
{ |
||||
protected $driverName = 'sqlite'; |
||||
|
||||
public function testCompositeFk() |
||||
{ |
||||
$this->markTestSkipped('sqlite does not allow getting enough information about composite FK.'); |
||||
} |
||||
} |
Loading…
Reference in new issue