使用Zend Lucene索引相关实体



我已经在我的应用程序中设置了搜索,但希望将其扩展到以一对多的方式索引相关属性。例如,一个人可以有多个用户名,因此必须将它们分开,如下面的示例所示:

person:
  id:         ~
  name:       {type: varchar(100), required: true}
username:
  person_id:  {type: integer, foreignTable: person, foreignReference: id}
  username:   {type: varchar(20), primaryKey: true, required: true}
到目前为止,我已经按照Jobeet的例子在我的应用程序中使用了Zend Lucene,我可以在Person中搜索name的属性,比如name .

我找不到任何通过Symfony或Lucene自动做到这一点的方法,所以我尝试在Person的索引中添加项目,如下所示:

foreach ($this->getUsernames() as $i => $username)
{
  $doc->addField(Zend_Search_Lucene_Field::Text('username' . $i,
      $username->getUsername(), 'utf-8'));
}

我然后尝试更新这个索引每当一个新的用户名被添加通过更新用户名的保存功能:

public function save(PropelPDO $con = null)
{
  $ret = parent::save($con);
  // reindex the person
  $person = $this->getPerson();
  $person->save();
  return $ret;
}

只要这个人是在运行时创建的就可以,但是如果从fixture加载,getUsernames()什么也不返回。代码执行两次(一次在加载Person时,另一次在添加Username时)。这有什么原因吗?我能想办法绕过这个吗?

另一种方式做这个也将是感激的。Lucene似乎可以使用Zend_Lucene_Search_Interface_MultiSearcher类搜索多个索引,如这个问题所述。然而,我似乎不能使它工作。

我在这里发现了一个类似的问题,但是没有找到指针。

我现在使用的是Propel 1.6.

您没有指定使用哪个推进版本。看你在用PDO,你很可能在用1.3+。

如果Username对象初始化正确,即:

<?php
$username = new Username();
$username->setUsername('foobar');
$username->setPerson($person);

调用用户名->保存();也应该触发$person的save(),并且$person对象也应该包含Username对象。

但是对于$person初始化,有一个"特性"。(有些人可能会称之为bug…)

如果初始化$person:

$person = PersonPeer::retrieveByPk(123);
//or for 1.5+
$person = PersonQuery::create()->findPk(123);

$person的Usernames-list将为空。当你调用

 $username->setPerson($person);

$username将被添加到$person的usernames -list中,这意味着调用$person->getUsernames()将不会自动从db中获取用户名,因为该列表已经是非空的。

所以需要用用户名初始化$person。要么像

<?php
$person = PersonQuery::create()->joinWith('Person.Usernames')->filterById(123)->findOne();

<?php
$person = PersonPeer::retrieveByPk(123);
$person->getUsernames(); //trigger list fetch

最新更新