2017-09-14 82 views
5

我们正在评估ArangoDB在空间计算方面的性能。 有能力做相同的其他产品,无论是通过特殊的API或查询语言的人数:ArangoDB分面搜索性能

  • MarkLogic刻面
  • ElasticSearch聚集
  • Solr的车花等

据我们了解,有在Arango中并没有特别的API来明确计算面板。 但在现实中,并不需要它,感谢全面的AQL可以很容易地通过简单的查询来实现,如:

FOR a in Asset 
    COLLECT attr = a.attribute1 INTO g 
RETURN { value: attr, count: length(g) } 

该查询计算的形式ATTRIBUTE1和产量频率方面:

[ 
    { 
    "value": "test-attr1-1", 
    "count": 2000000 
    }, 
    { 
    "value": "test-attr1-2", 
    "count": 2000000 
    }, 
    { 
    "value": "test-attr1-3", 
    "count": 3000000 
    } 
] 

这就是说,在我的整个集合attribute1中提供了三种形式(test-attr1-1,test-attr1-2和test-attr1-3)并提供了相关计数。 我们运行的是DISTINCT查询和聚合计数。

看起来简单而干净。只有一个,但真正的大问题 - 性能。

上面提供的查询运行31秒!在仅有8M文件的测试集合之上。 我们尝试过不同的索引类型,存储引擎(与rocksdb和没有),调查解释计划无济于事。 我们在这个测试中使用的测试文件非常简洁,只有三个简短的属性。

我们希望在这一点上的任何输入。 要么我们做错了什么。或者ArangoDB根本不是为了在这个特定领域执行而设计的。

顺便说一句,最终目标将是运行像下面的下第二次:

LET docs = (FOR a IN Asset 

    FILTER a.name like 'test-asset-%' 

    SORT a.name 

RETURN a) 

LET attribute1 = (

FOR a in docs 

    COLLECT attr = a.attribute1 INTO g 

RETURN { value: attr, count: length(g[*])} 

) 

LET attribute2 = (

FOR a in docs 

    COLLECT attr = a.attribute2 INTO g 

RETURN { value: attr, count: length(g[*])} 

) 

LET attribute3 = (

FOR a in docs 

    COLLECT attr = a.attribute3 INTO g 

RETURN { value: attr, count: length(g[*])} 

) 

LET attribute4 = (

FOR a in docs 

    COLLECT attr = a.attribute4 INTO g 

RETURN { value: attr, count: length(g[*])} 

) 

RETURN { 

    counts: (RETURN { 

    total: LENGTH(docs), 

    offset: 2, 

    to: 4, 

    facets: { 

     attribute1: { 

     from: 0, 

     to: 5, 

     total: LENGTH(attribute1) 

     }, 

     attribute2: { 

     from: 5, 

     to: 10, 

     total: LENGTH(attribute2) 

     }, 

     attribute3: { 

     from: 0, 

     to: 1000, 

     total: LENGTH(attribute3) 

     }, 

     attribute4: { 

     from: 0, 

     to: 1000, 

     total: LENGTH(attribute4) 

     } 

    } 

    }), 

    items: (FOR a IN docs LIMIT 2, 4 RETURN {id: a._id, name: a.name}), 

    facets: { 

    attribute1: (FOR a in attribute1 SORT a.count LIMIT 0, 5 return a), 

    attribute2: (FOR a in attribute2 SORT a.value LIMIT 5, 10 return a), 

    attribute3: (FOR a in attribute3 LIMIT 0, 1000 return a), 

    attribute4: (FOR a in attribute4 SORT a.count, a.value LIMIT 0, 1000 return a) 

    } 

} 

谢谢!

回答

3

原来在ArangoDB Google Group上发生了主线程。 这里是一个link to a full discussion

这是当前解决方案的摘要:从特定的特性分支,其中的性能改进数目已经做了阿朗戈的

  • 运行自定义生成(希望他们应该使它到主释放不久)是必需的
  • 否索引为一个小面计算
  • MMFiles是优选的存储引擎
  • AQL应WR要使用“COLLECT attr = a。attributeX WITH COUNT INTO length“而不是”count:length(g)“
  • AQL应该被拆分成更小的块并且并行运行(我们正在运行Java8的Fork/Join来传播构面AQL,然后将它们连接到最终结果中)
  • 一个AQL来过滤/分类和检索主实体(如果需要的话。在排序/过滤添加对应skiplist指数)
  • 的其余部分是针对每个方面值小AQL值/频率对

在我们已经获得> 10x与上面提供的原始AQL相比的性能增益。