Spark寫入Parquet,暴露JDBC引擎,實現準實時SQL查詢

有一個設想

當有持續不斷的結構化或非結構化大數據集以流(streaming)的方式進入分佈式計算平臺, 能夠保存在大規模分佈式存儲上,並且能夠提供準實時SQL查詢,這個系統多少人求之不得。
今天,咱們就來介紹一下這個計算框架和過程。

問題分解一下

數據哪裏來?

假設,你已經有一個數據收集的引擎或工具(不在本博客討論範圍內,請出門左轉Google右轉百度),怎麼都行, 反正數據能以流的方式給出來,塞進Kafka類似的消息系統。

結構化?非結構化?如何識別業務信息?

關於結構化或非結構化,也不在今天的主要討論範圍,但是,必須要說明的是, 你的數據能夠以某種規則進行正則化,比如:空格分隔,CSV,JSON等。咱們今天以Apache網站日誌數據作爲參照。

類似如下:

124.67.32.161 - - [10/Apr/2016:05:37:36 +0800] "GET /blog/app_backend.html HTTP/1.1" 200 26450

如何處理?寫到哪裏去?

拿到數據,我們需要一些處理,將業務邏輯分離開來,做成二維表,行列分明,就像是關係型數據庫的表。這個事情有Spark DataFrame來完成。

就像寫入關係型數據庫一樣,我們需要將DataFrame寫入某處,這裏,就是Parquet文件,天然支持schema,太棒了。

怎麼取出來?還能是SQL?

我們的數據已經被當做“二維表,Table”寫入了Parquet,取出來當然也得是“表”或其他什麼的,當然最好是能暴露出JDBC SQL,相關人員使用起來就方便了。

這個事情交給Spark的 SparkThriftServer 來完成。

設計藍圖

以上分解似乎完美,一起來看看“設計框架”或“藍圖”。
這裏寫圖片描述

算了,不解釋了,圖,自己看。

Coding Style

從Kafka Stream獲取數據

 // 從Kafka Stream獲取數據
    JavaPairInputDStream<String, String> messages = KafkaUtils.createDirectStream(jssc, String.class, String.class,
            StringDecoder.class, StringDecoder.class, kafkaParams, topicsSet);

寫入Parquet

accessLogsDStream.foreachRDD(rdd -> {
        // 如果DF不爲空,寫入(增加模式)到Parquet文件
        DataFrame df = sqlContext.createDataFrame(rdd, ApacheAccessLog.class);
        if (df.count() > 0) {
            df.write().mode(SaveMode.Append).parquet(Flags.getInstance().getParquetFile());
        }
        return null;
    });

創建Hive表

使用spark-shell,獲取Parquet文件, 寫入一個臨時表;

scala代碼如下:

import sqlContext.implicits._
    val parquetFile = sqlContext.read.parquet("/user/spark/apachelog.parquet")
    parquetFile.registerTempTable("logs")

複製schema到新錶鏈接到Parquet文件。

在Hive中複製表,這裏你會發現,文件LOCATION位置還是原來的路徑,目的就是這個,使得新寫入的文件還在Hive模型中。

我總覺得這個方法有問題,是不是哪位Hive高人指點一下,有沒有更好的辦法來完成這個工作?
CREATE EXTERNAL TABLE apachelog LIKE logs STORED AS PARQUET LOCATION '/user/spark/apachelog.parquet';

啓動你的SparkThriftServer

當然,在集羣中啓用ThriftServer是必須的工作,SparkThriftServer其實暴露的是Hive2服務器,用JDBC驅動就可以訪問了。
發佈了14 篇原創文章 · 獲贊 13 · 訪問量 9萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章