我正在创建一个房地产网站,每个房源都附有清单ID。我正在通过CakePHP中的shell运行一个脚本,该脚本正在解析一个csv文件,并且应该更新已经存在的任何列表,或者如果不存在则插入新的列表。
问题在于我不断获得Duplicate entry '###' for key "PRIMARY'
,其中###是CSV提供的列表ID。此脚本正在从命令行运行。
这是我的表格包含的较小版本:
CREATE TABLE `listings` (
`ListingID` int(11) NOT NULL,
`AccessibilityYN` varchar(50) DEFAULT NULL COMMENT 'AccessibilityYN',
`BathsFull` int(6) DEFAULT NULL COMMENT 'BathsFull',
`BathsPartial` int(6) DEFAULT NULL COMMENT 'BathsPartial',
`BathsTotal` decimal(5,1) DEFAULT NULL COMMENT 'BathsTotal',
`Beds` int(11) DEFAULT NULL COMMENT 'Beds',
PRIMARY KEY (`ListingID`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
这是我的清单模型(注意我有public $primaryKey = 'ListingID';
)
class Listing extends AppModel {
public $name = 'Listing';
public $primaryKey = 'ListingID';
public $belongsTo = array(
'Agent' => array(
'className' => 'Agent',
'foreignKey' => 'AgentID'
)
);
}
这是我通过命令行运行的shell:
class MyShell extends AppShell {
public $uses = array('Listing');
public function update_imported_listings() {
/***SOME CODE HERE TO GET THE $entry FROM THE CSV***/
$this->Listing->ListingID = $entry['ListingID'];
if(!$this->Listing->exists()){
$this->Listing->create();
}
if($this->Listing->save($entry)){
echo "Saved Listing";
} else {
echo "Listing Failed";
}
}
}
我知道CakePHP通常喜欢id
作为数据库中使用的字段,但是我在模型中设置了$primaryKey = 'ListingID'
。我已经尝试在数据库中将ListingID设置为Auto Increment
,但这不起作用。
有人有什么想法吗?我刚刚出去。
答案 0 :(得分:5)
这一行是你的问题:
$this->Listing->ListingID = $entry['ListingID'];
。
无论您的实际主键字段在数据库中是什么,始终使用Model->id
属性指定主键值。因此,请将其更改为:
$this->Listing->id = $entry['ListingID'];
无需显式检查是否存在具有特定主键值的记录。如果传递给save()
的数据数组包含db中存在的有效主键值,Cake将自动更新并记录而不是创建新的。如果您在循环中使用create()
,请确保在保存之前致电save()
。
答案 1 :(得分:0)
不要破坏CakePHP约定,使用'id'字段作为主键。
http://book.cakephp.org/view/24/Model-and-Database-Conventions
答案 2 :(得分:0)
我在运行cakePHP shell脚本时得到了同样的错误,结果是最新记录的ID处于列大小所允许的最大值(无论是谁使表使用了中间int作为id列),所以auto_increment没有用。更改了列以允许更大的数字进行修复。可能是显而易见的事情,但可能会帮助那些人。