OrientDB ETL使用匹配条件

时间:2017-03-27 20:44:19

标签: orientdb orientdb2.2 orientdb-etl

我有一些我跟踪的数据看起来像这样:

node.csv
Label1,Label2
Alpha,A
Alpha,B
Alpha,C
Bravo,A
Bravo,B

Label1Label2对在此数据集中定义了唯一条目。

我有另一个表格,其中包含一些我要链接到Table1中创建的顶点的值:

data.csv
Label1,Label2,Data
Alpha,A,10
Alpha,A,20
Alpha,B,30
Bravo,A,99

DataNode字段都匹配时,我希望从Label1Label2的条目生成边缘。

在这种情况下,我有:

Data(Alpha,A,10) ---> Node(Alpha,A)
Data(Alpha,A,20) ---> Node(Alpha,A)
Data(Alpha,B,30) ---> Node(Alpha,B)
Data(Bravo,A,99) ---> Node(Bravo,A)

在另一个question中,似乎只需添加额外的" joinFieldName"即可解决此问题。进入json文件,但我的数据没有得到相同的结果。

我的node.json文件如下所示:

{
    "config": { "log": "info" },
    "source": { "file": { "path": "./node.csv" } },
    "extractor": { "csv": {} },
    "transformers": [ { "vertex": { "class": "Node" } } ],
    "loader": {
        "orientdb": {
            "dbURL": "plocal:test.orientdb",
            "dbType": "graph",
            "batchCommit": 1000,
            "classes": [ {"name": "Node", "extends": "V"} ],
            "indexes": []
        }
    }
}

我的data.json文件如下所示:

{
    "config": { "log": "info" },
    "source": { "file": { "path": "./data.csv" } },
    "extractor": { "csv": { } },
    "transformers": [
            { "vertex": { "class": "Data" } },
            { "edge":   { "class":         "Source",
                          "joinFieldName": "Label1",
                          "lookup":        "Node.Label1",
                          "joinFieldName": "Label2",
                          "lookup":        "Node.Label2",
                          "direction":     "in"
                        }
            }
        ],
    "loader": {
        "orientdb": {
            "dbURL": "plocal:test.orientdb",
            "dbType": "graph",
            "batchCommit": 1000,
            "classes": [ {"name": "Data",   "extends": "V"},
                         {"name": "Source", "extends": "E"}
                       ],
            "indexes": []
        }
    }
}

运行这些后,在查询结果时得到此输出:

orientdb {db=test.orientdb}> SELECT FROM V

+----+-----+------+------+------+-------------------+----+-------------+
|#   |@RID |@CLASS|Label1|Label2|out_Source         |Data|in_Source    |
+----+-----+------+------+------+-------------------+----+-------------+
|0   |#25:0|Node  |Alpha |A     |[#41:0,#43:0,#47:0]|    |             |
|1   |#26:0|Node  |Alpha |B     |[#45:0]            |    |             |
|2   |#27:0|Node  |Alpha |C     |                   |    |             |
|3   |#28:0|Node  |Bravo |A     |[#42:0,#44:0,#48:0]|    |             |
|4   |#29:0|Node  |Bravo |B     |[#46:0]            |    |             |
|5   |#33:0|Data  |Alpha |A     |                   |10  |[#41:0,#42:0]|
|6   |#34:0|Data  |Alpha |A     |                   |20  |[#43:0,#44:0]|
|7   |#35:0|Data  |Alpha |B     |                   |30  |[#45:0,#46:0]|
|8   |#36:0|Data  |Bravo |A     |                   |99  |[#47:0,#48:0]|
+----+-----+------+------+------+-------------------+----+-------------+

9 item(s) found. Query executed in 0.012 sec(s).

这是不正确的。我不想要边缘#42:0,#44:0,#46:0和#47:0:

#42:0 connects Node(Bravo,A) and Data(Alpha,A)
#44:0 connects Node(Bravo,A) and Data(Alpha,A)
#46:0 connects Node(Bravo,B) and Data(Alpha,B) 
#47:0 connects Node(Alpha,A) and Data(Bravo,A)

看起来在变换器中添加多个joinFieldName条目会导致OR操作,但我喜欢' AND'这里。

有谁知道如何解决这个问题?我不确定我的做法与其他StackOverflow问题不同...

1 个答案:

答案 0 :(得分:1)

调试ETL代码后,我想出了一个解决方法。正如你所说,没有办法让多个joinFieldName形成一个边缘。每个joinFieldName都会创建一个优势。

您可以做的是,通过连接“Label1”和“Label2”在CSV文件中生成一个额外的列,并在lookup转换中使用edge查询,例如,假设您的data.csv有一个额外的字段,如label1_label2,该字段的值类似于“label1 ==== label2`。

您的边缘转换应具有以下内容

{ "edge":   { "class": "Source",
              "joinFieldName": "label1_label2",
              "lookup": "select expand(n) from (match {class: Node, as: n} return n) where n.Label1+'===='+n.Label2 = ?",
              "direction": "in"
            }
 }

不要忘记expand顶点,否则ETL认为它是一个文档。这里的技巧是通过连接多个字段并传递等效的joinFieldName来编写一个查询。