我正在寻找一种方法,只有在使用sqlite3的PHP脚本中不存在列时才向表中添加列。看起来单独使用SQL无法帮助我,比如像
这样的东西ALTER TABLE items ADD COLUMN IF NOT EXISTS new_col INTEGER;
好吧,我正在考虑像尝试运行查询这样的黑客攻击,如果失败,则认为该列尚不存在:
if ($db->querySingle('SELECT new_col FROM items') === FALSE) {
// False means the query failed
$db->exec('ALTER TABLE items ADD COLUMN new_col INTEGER');
}
update_stuff_with_new_column($db);
我想它应该可行,但如果查询由于其他原因(例如,事务正在运行)失败怎么办?
我可以想到其他一些解决方案,但它们看起来都是一样的:“如果查询失败,列可能不存在,请创建它”。有没有更好的方法呢?
答案 0 :(得分:1)
您可以在CREATE TABLE
表中找到sqlite_master
语句的SQL;您需要解析它以查看是否已定义new_col
:
sqlite> create table items (col1, col2);
sqlite> select sql from sqlite_master where type = 'table' and name = 'items';
CREATE TABLE items (col1, col2)
sqlite> alter table items add column new_col;
sqlite> select sql from sqlite_master where type = 'table' and name = 'items';
CREATE TABLE items (col1, col2, new_col)
附录:
查看表中是否已存在列的其他方法包括:
尝试准备(sqlite3_prepare_v2
)表格
select ColumnToCheck from TableToCheck;
并查看它是否出错(感谢Igor Tandetnik!)。
或使用
PRAGMA table_info(myTable)
记录here。
答案 1 :(得分:0)
php file
===========
<pre>
<?php
define(DB_USER,'root');
define(DB_PASS,'');
define(DB_NAME,'DATABASENAME');
//Load the class
/* Creating Connection for database where we want to make changes using sql file */
$con = mysql_connect('localhost',DB_USER,DB_PASS) or die ("error in connecting $sitename ");
mysql_select_db(DB_NAME,$con) or die("error in databse selction in $sitename");
/* getting content from sql file where we have updated fields */
$fp= file_get_contents('blank_hotel_version_1.0.sql', true);
/* getting list of create table query from sql file content */
$pattern_gettable = '/CREATE TABLE IF NOT EXISTS (.*?) ;/is';
preg_match_all($pattern_gettable,$fp,$tables);
foreach($tables[0] as $value):
mysql_query($value,$con) or die(mysql_error());
endforeach;
//exit;
/* getting Database table list */
$tables_db ="*";
if($tables_db == '*')
{
$tables_db = array();
$result = mysql_query('SHOW TABLES');
while($row = mysql_fetch_row($result))
{
$tables_db[] = $row[0];
}
}
else
{
$tables_db = is_array($tables_db) ? $tables_db : explode(',',$tables_db);
}
foreach($tables_db as $tablename):
$pattern = "CREATE TABLE IF NOT EXISTS `{$tablename}`";
foreach($tables[0] as $value):
if(strpos($value,$pattern)=== false):
else:
/*getting columns list from perticular table query of sql file */
$pattern_cloumn="/CREATE TABLE IF NOT EXISTS `{$tablename}` \((.*?) PRIMARY KEY/is";
preg_match_all($pattern_cloumn,$value,$columns);
/*Replacing comma with # so that while we exploade we can easily make array of columns othere wise it make problem for enum(..) datatype or comment */
$pattern_cm="/\n/ims";
$columns[1][0]= preg_replace($pattern_cm,"#",$columns[1][0]);
$colmn=explode("#",$columns[1][0]);
array_shift($colmn);
/*Getting name of columns currently we have columns with sql query like "`id` int(11) not null," and we get column name like 'id' into $columnnames array */
$columnnames=array();
foreach($colmn as $cols):
$pattern = '/`(.*?)`/is';
preg_match_all($pattern, $cols ,$namecols);
array_push($columnnames,$namecols[1][0]);
endforeach;
/*Getting column names from database table */
$column_query="SHOW COLUMNS FROM {$tablename}";
$result_clm=mysql_query($column_query);
$colum_db_array=array();
while($row_clm=mysql_fetch_array($result_clm))
{
array_push($colum_db_array,$row_clm['Field']);
}
foreach($columnnames as $key=>$value_cols)
{
/*if column not exists in database table then we add column into table */
if(!in_array($value_cols,$colum_db_array) && $value_cols!="")
{
if(substr($colmn[$key],strlen($colmn[$key])-2)=="',")
{
$query_cl="ALTER TABLE {$tablename} ADD ".substr($colmn[$key],0,strlen($colmn[$key])-1);
}
else
{
$query_cl="ALTER TABLE {$tablename} ADD ".substr($colmn[$key],0,strlen($colmn[$key])-1);
}
mysql_query($query_cl) or die(mysql_error());
}
}
endif;
endforeach;
endforeach;
exit;
?>
</pre>
Sql File
========
<pre>
-- --------------------------------------------------------
--
-- Table structure for table `advertising`
--
CREATE TABLE IF NOT EXISTS `advertising` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`image` varchar(255) NOT NULL,
`title_tag` varchar(255) NOT NULL,
`alt_tag` varchar(255) NOT NULL,
`d_order` int(11) NOT NULL,
`is_visible` varchar(11) NOT NULL DEFAULT 'Y',
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=5 ;
--
-- Dumping data for table `advertising`
--
-- --------------------------------------------------------
--
-- Table structure for table `advertising_enquiry`
--
CREATE TABLE IF NOT EXISTS `advertising_enquiry` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`advertising_id` varchar(255) NOT NULL,
`name` varchar(255) NOT NULL,
`address` varchar(255) NOT NULL,
`city` varchar(255) NOT NULL,
`state` varchar(255) NOT NULL,
`country` varchar(255) NOT NULL,
`phone` varchar(255) NOT NULL,
`mobile` varchar(255) NOT NULL,
`email` varchar(255) NOT NULL,
`website` varchar(255) NOT NULL,
`enquiry` text NOT NULL,
`budget` varchar(255) NOT NULL,
`create_date` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=15 ;
--
-- Dumping data for table `advertising_enquiry`
--
-- --------------------------------------------------------
--
-- Table structure for table `agents`
--
CREATE TABLE IF NOT EXISTS `agents` (
`id` int(3) NOT NULL AUTO_INCREMENT,
`agent_name` varchar(150) NOT NULL,
`contact` varchar(1000) NOT NULL,
`cat_id` int(3) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=9 ;
--
-- Dumping data for table `agents`
--
-- --------------------------------------------------------
--
-- Table structure for table `amenities`
--
CREATE TABLE IF NOT EXISTS `amenities` (
`id` int(3) NOT NULL AUTO_INCREMENT,
`am_name` varchar(200) NOT NULL,
`type` enum('H','R','RE') DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 AUTO_INCREMENT=234 ;
--
-- Dumping data for table `amenities`
--
</pre>
这可能会对你有所帮助