当维护大量组织,品牌和型号时,筛选对象时 ,这些条件会显示全部的项目,比如下图,筛选服务器,出现了 网络设备的品牌,如果品牌数量超过50,还会以 autocomplete
模式显示,即隐藏项目列表,需要用户输入,根据用户输入显示匹配的项目,用户需要先知道有哪些品牌,体验较差。
较理想的方式是,搜索条件只显示当前对象用到的 AttributeExternalKey
对象,已知可以通过以下查询得到所有服务器正在使用的 品牌:
SELECT Brand AS b JOIN Server AS s ON s.brand_id=b.id
因此,我们的目标就是让 iTop 显示搜索表单时支持这种筛选。代码如下。如果是 AttributeExternalKey
类型,直接生成一个 ValueSet
,应用以上的 OQL
。
diff --git a/tmp/web/sources/application/search/searchform.class.inc.php b/sources/application/search/searchform.class.inc.php
index 7b77e5f..78ef3c8 100644
--- a/tmp/web/sources/application/search/searchform.class.inc.php
+++ b/sources/application/search/searchform.class.inc.php
@@ -45,6 +45,7 @@ use TrueExpression;
use utils;
use WebPage;
use UserRights;
+use ValueSetObjects;
class SearchForm
{
@@ -450,6 +451,19 @@ class SearchForm
{
/** @var \AttributeExternalKey $oAttrDef */
$sTargetClass = $oAttrDef->GetTargetClass();
+ $sClass = $oAttrDef->GetHostClass();
+ $sAttCode = $oAttrDef->GetKeyAttCode();
+ $sFilter = 'SELECT ' . $sTargetClass . ' AS t JOIN ' . $sClass . ' AS c ON c.' . $sAttCode . '=t.id';
+ $oValSetDef = new ValueSetObjects($sFilter);
+ $aAllowedValues = $oValSetDef->GetValues([]);
+ if (count($aAllowedValues) > $iMaxComboLength)
+ {
+ return array('autocomplete' => true);
+ }
+ else
+ {
+ return array('values' => $aAllowedValues);
+ }
}
try
{
最终的效果如下,只显示 HP
和 未定义 两个品牌项。
顺便提一下,编辑 PhysicalDevice 填写品牌时也会遇到这样的问题,比如编辑服务器,网络设备的品牌也会出现,可以为 brand_id
属性加以下 filter 来解决
<filter>SELECT Brand AS b JOIN Model AS m ON m.brand_id=b.id WHERE m.type = :this->finalclass</filter>
发表回复