背景
上節我們了解了什么是圖數據庫,作為研究對象的neo4j的特點,優缺點以及基本的環境搭建。
現在我們要講存儲在csv中的通話記錄數據導入到neo4j中去,並且可以通過cql去查詢導入的數據及關系
1.選取導入方式
neo4j的導入方式有很多,我大概總結了一下:
- Cypher CREATE 語句,為每一條數據寫一個CREATE
- Cypher LOAD CSV 語句,將數據轉成CSV格式,通過LOAD CSV讀取數據。
- 官方提供的Java API —— Batch Inserter
- 大牛編寫的 Batch Import 工具
- 官方提供的 neo4j-import 工具
優缺點對比:
create語句 | load csv語句 | Batch Inseter | Batch Import | neo4j-import | |
---|---|---|---|---|---|
適用場景 | 1~1w nodes | 1w~10w nodes | 千萬以上 nodes | 千萬以上 nodes | 千萬以上 nodes |
速度 | 很慢(1000 nodes/s) | 一般(5000 nodes/s) | 非常快(數萬nodes/s) | 非常快(數萬nodes/s) | 非常快(數萬nodes/s) |
優點 | 使用方便,可實時插入。 | 使用方便,可以加載本地 | 遠程CSV;可實時插入 | 基於Batch Inserter,可以直接運行編譯好的jar包;可以在已存在的數據庫中導入數據 | 官方出品,比Batch Import占用更少的資源 |
缺點 | 速度慢 | 需要將數據轉換成csv | 需要轉成CSV;只能在JAVA中使用;且插入時必須停止neo4j | 需要轉成CSV;必須停止neo4j | 需要轉成CSV;必須停止neo4j;只能生成新的數據庫,而不能在已存在的數據庫中插入數據 |
可以看出導入的方式有很多,由於我們導入的數據量較大,所以我這里選擇的是最后一種 neo4j-import,大家也可以去選擇其他的導入方式
neo4j-import 使用
我們打開neo4j-import使用的網站可以看到這樣的一段摘要
Super Fast Batch Importer For Huge Datasets LOAD CSV is great for
importing small – medium sized data, i.e. up to the 10M records range.
For large data sets, i.e. in the 100B records range, we have access to
a specialized bulk importer.We want to use it to import similar order data into Neo4j: customers,
orders and contained products.The tool is located in path/to/neo4j/bin/neo4j-import and is used as
follows:
這段話的大致意思是我們使用load csv無法滿足我們大數據量的業務需要,所以我們不得不去選擇一種新的導入方式,這里我們選擇了neo4j-import這種方式,以下是一個導入的例子
bin/neo4j-import --into retail.db --id-type string \
--nodes:Customer customers.csv --nodes products.csv \
--nodes orders_header.csv,orders1.csv,orders2.csv \
--relationships:CONTAINS order_details.csv \
--relationships:ORDERED customer_orders_header.csv,orders1.csv,orders2.csv
例子中的數據結構為:
如果您調用neo4j-import
沒有參數的腳本,它將列出一個全面的幫助頁面。
該--into retail.db
顯然是目標數據庫,其中不能包含現有數據庫。
重復--nodes
和--relationships
參數是同一實體的多個(可能分裂的)csv文件的組,即具有相同的列結構。
每組的所有文件都被視為可以連接成一個大文件。一個標題行的組的第一個文件是必需的,它甚至可能被包含在其中可能比一個多GB的文本文件更易於處理和編輯一個單行文件。也支持壓縮文件。
customers.csv
直接作為帶有:Customer
標簽的節點導入,屬性直接從文件中獲取。- 對於從
:LABEL
列中獲取節點標簽的產品也是如此。 - 訂單節點取自3個文件,一個標題和兩個內容文件。
- 輸入
:CONTAINS
的order_details.csv
訂單項關系是通過其ID 來創建的,包含與所包含產品的訂單。 - 訂單通過再次使用訂單csv文件連接到客戶,但這次使用不同的標頭,其中:IGNORE是不相關的列
這–id-type string表示所有:ID列都包含字母數字值(對僅數字ID進行優化)。
列名用於節點和關系的屬性名稱,特定列有一些額外的標記
name:ID
- 全局id列,通過該列查找節點以便以后重新連接,- 如果保留屬性名稱,它將不會被存儲(臨時),這就是–id-type所指的
- 如果你有跨實體的重復id,你必須在括號中提供實體(id-group)
:ID(Order)
- 如果您的ID是全球唯一的,您可以將其關閉
- :LABEL - 節點的標簽列,多個標簽可以用分隔符分隔
:START_ID
,:END_ID
- 關系文件列,引用節點ID,用於id-groups使用:END_ID(Order):TYPE
- 關系型列- 所有其他列都被視為屬性,但如果為空或在注釋時跳過:IGNORE
- 類型轉換可以通過后面添加的名稱,例如通過
:INT
,:BOOLEAN
等
導入通話記錄數據
在整理后的csv中我們的通話記錄是這樣的數據:
-
phones.csv 記錄電話號列表,作為nodes結點
-
phone_header 標題文件只有一行數據
phone:ID
-
call.csv 該文件記錄通話記錄的信息,作為以后關系的建立和關系屬性的添加
第一行從左到右字段的含義為:
150 **** 0743給136 **** 5301一共打了125分鍾時長的電話,打了一次,平均一次125分鍾 -
call_header.csv 通話記錄頭信息
這里的:START_ID
指的是關系的起始點,:END_ID
指的是關系的終止點
這些csv文件准備好之后,我們寫一段shell腳本來執行這些文件。
import()
{
#導入命令
neo4j stop
cd /usr/local/Cellar/neo4j/3.5.0/libexec/data/databases
rm -rf graph.db
cd /Documents/歸檔/data
neo4j-admin import \
--database=graph.db
--nodes:phone="../phone_header.csv,phones.csv \
--ignore-duplicate-nodes=true \
--ignore-missing-nodes=true \
--relationships:call="../call_header.csv,call.csv"
neo4j start
}
- 這里以防我們新建的數據庫已經存在,我們選擇刪除已有庫再進行導入
- 記得要先關閉neo4j
查看結果
導入完成之后我們來打開neo4j瀏覽器查看一下導入后的結果
我們打開http://localhost:7474/browser/
首先我們先查看一下Database Information
這里我們可以看到已有的結點數,有多少條關系,占用的存儲空間等數據庫信息
然后我們來查看某個電話號碼的交際圈:
match (p:phone{phone:"13825259929"})-[r]->(o) return p,o,r;
- 1
把鼠標移到對應的結點和關系上時,底部便會出現對應的屬性
現在我們的數據導入就完成了
接下來我們要用springboot + neo4j +d3來展示某人的通話記錄圈。