我将Phalcon \ Mvc \ Model用于我项目中的所有实体(以保持标准化)。 今天我必须在我的mysql数据库中导入maxmind geoip数据库,以实现某些实体和maxmind位置(和块)之间的本机关系。
默认情况下,maxmind数据库是在csv中提供的,所以如何在mysql中组织它是每个开发人员必须根据他的需要解决的问题。 Maxmind数据库包含2个文件:
大多数教程建议使用以下表定义来存储具有ip范围的表:
CREATE TABLE IF NOT EXISTS `GeoLiteCity_Blocks` (
`startIpNum` int(10) unsigned NOT NULL,
`endIpNum` int(10) unsigned NOT NULL,
`locId` int(10) unsigned NOT NULL,
PRIMARY KEY (`startIpNum`,`endIpNum`)
) ENGINE=InnoDB;
如您所见,存在复合主键。可以在Phalcon \ Mvc \ Model中使用这样的键吗?我想有一些限制(逻辑上,它们应该存在,例如,我无法预测Phalcon \ Mvc \ Model :: findFirst($ key)方法行为)
真的,我不关心这个表会使用的磁盘大小,对我来说只有一件事是重要的 - 性能。此外,我想保持所有模型标准化,而不是记住每个实体/表的大量小方面。
所以,我的问题是:将复合键使用Phalcon \ Mvc \ Model是否可以,或者最好再制作一个id
列,这将是主键和&将索引添加到startIpNum
和endIpNum
以使选择更快?
答案 0 :(得分:3)
Phalcon \ Mvc \ Model可以与具有复合主键的表一起使用。但是,findFirst快捷方式不可用,您可以这样做:
GeoLiteBlocks::findFirst(array(
'startipnum = ?0 AND endipnum = ?1',
'bind' => array($start, $end)
));
此外,可以在模型中添加一种方法来减少编码:
class GeoLiteBlocks extends Phalcon\Mvc\Model
{
public function static findBlock($start, $end)
{
return self::findFirst(array(
'startipnum = ?0 AND endipnum = ?1',
'bind' => array($start, $end)
));
}
}