如果用户希望在spark sql 中,执行某个sql 后,将其结果集保存到本地,并且指定csv 或者 json 格式,在 beeline 中,实现起来很麻烦。通常的做法是将其create table tempTable as *** ,通过将结果集写入到新的临时表中,进行保存,然后再通过其他方式export 到本地。

这种方式,对于 HDFS 是可行到,但是如果数据是保存在像SequoiaDB 中,就比较难办了。因为spark 向 SequoiaDB 写入记录时,可能部分task 会失败重试,这样就容易造成SequoiaDB 目标表中写入了重复记录,从而造成数据不准确的问题。

因此,需要寻找一种的新的方式,将其结果集准确地读取出来,并且写入本地文件。

在网上有很多替代方案,无外乎是通过beeline 或者 spark-sql ,执行 SQL 命令,通过重定向的方式,将结果集保存到指定文件中。

这样的方式,首先不讨论其输出格式的问题,最无法让人接受的是,spark-sql 需要将所有的结果数据收集到一个 Driver 进程中后,才会开始输出终端。这个过程有以下 3 个问题

  1. 时间久,如果数据量大了,Driver 收集的过程会很久,并且通过top 可以查看到进程CPU 飙升
  2. 容易OOM,当数据量增大后,因为需要将所有结果数据存储在内存中,一旦数据量用超了,就抛出 OOM 的错误,一切前功尽弃
  3. 输出格式,因为保存本地文件的内容就是输出终端的数据,CSV 格式不友好,有时候甚至会因为不可见字符而导致整个本地文件格式错乱,最终导致数据无法恢复

所以本文主要是向读者们介绍一种新的方式,直接使用 scala / python 语言开发的程序,利用 RDD 将其结果数据保存本地,输出格式支持 CSV 和 JSON。

  • scala 版本

scala 版本作者没有直接编写程序,但是通过 spark-shell 进行了验证

import org.apache.spark.sql.hive.HiveContext
// sc - existing spark context
val sqlContext = new HiveContext(sc)
val df = sqlContext.sql("SELECT * FROM test_sdb")
df.coalesce().write.format("com.databricks.spark.csv").mode("overwrite").option("header", "true").save("/opt/sequoiadb/chenfool")

如果有用户喜欢这个方式,可以考虑将程序打包成jar 包来执行。

导出格式的更多参数,请参考 python 版本

  • python 版本

在执行python 的脚本前,首先需要设置一下环境变量

export SPARK_HOME=/root/software/spark-2.1.-bin-hadoop2.
export PYTHONPATH=${SPARK_HOME}/python/:${SPARK_HOME}/python/lib/py4j-0.10.-src.zip;

注意:py4j-0.10.4-src.zip 文件名可能随不同的spark 版本有所变化

然后准备以下脚本程序, spark_sql_export.py

import atexit
import os
import platform import pyspark
from pyspark.context import SparkContext
from pyspark.sql import SparkSession, SQLContext spark = SparkSession \
.builder \
.enableHiveSupport() \
.getOrCreate() df = spark.sql("SELECT * FROM test_sdb limit 100") #df.coalesce(1).write.format("org.apache.spark.sql.json").mode("overwrite") \
# .save("/opt/sequoiadb/chenfool") df.coalesce(1).write.format("com.databricks.spark.csv").mode("overwrite") \
.option("enforceSchema", "false") \
.option("quoteAll", "true") \
.option("escapeQuotes", "false") \
.option("header", "true") \
.option("delimiter", "|") \
.option("charToEscapeQuoteEscaping", "\"") \
.option("inferSchema", "true") \
.option("ignoreLeadingWhiteSpace", "false") \
.option("ignoreTrailingWhiteSpace", "false") \
.save("/opt/sequoiadb/chenfool")

执行方式

python spark_sql_export.py

结果数据就会被保存在 /opt/sequoiadb/chenfool/part-00000* 文件中。

结果数据只会被保存在一个文件中,因为设置了 coalesce 参数。

JSON 格式请参考 spark_sql_export.py 注释部分。

CSV 的详细参数,可以参考spark 源码:${SPARK_HOME}/sql/core/src/main/scala/org/apache/spark/sql/execution/datasources/csv/CSVOptions.scala

注意:

在spark 2.1.1 版本中,ignoreLeadingWhiteSpace 和 ignoreTrailingWhiteSpace 参数无法生效,默认值为:true。在 spark 2.4.0 版本中,经过测试,这两个参数才能够生效。如果要求保存的数据中不做 trim 操作,只能够将spark 升级为2.4.0 版本。

本博客参考了之前 spark 学习(二) 的内容,里面有介绍如果利用python 来执行spark 的程序的说明,感兴趣的读者们可以移步查阅

spark sql 导出数据的更多相关文章

  1. SQL导出数据到EXCEL的问题

    DTS导出向导 不会 我这有个是用C#语言写的 try { Excel.Application xApp = new Excel.ApplicationClass(); xApp.Visible = ...

  2. 使用sql导出数据_mysql

    在mysql中 使用sql 脚本导出数据的方式之一: select * from table_name where x=y  INFO OUTFILE "/tmp/table_name.tx ...

  3. Sql Server 2000/2008 用Sql导出数据表结构(包括注释)到Excel

    --Sql Server 2000 declare @id int, ), ) declare cur_1 cursor for select id,name from sysobjects wher ...

  4. spark sql中将数据保存成parquet,json格式

    val df = sqlContext.load("/opt/modules/spark1.3.1/examples/src/main/resources/people.json" ...

  5. Spark SQL数据加载和保存实战

    一:前置知识详解: Spark SQL重要是操作DataFrame,DataFrame本身提供了save和load的操作, Load:可以创建DataFrame, Save:把DataFrame中的数 ...

  6. Spark SQL读取Oracle的number类型的数据时精度丢失问题

    Spark SQL读取数据Oracle的数据时,发现number类型的字段在读取的时候精度丢失了,使用的spark版本是Spark2.1.0的版本,竟然最后经过排查和网上查资料发现是一个bug.在Sp ...

  7. Spark SQL数据载入和保存实战

    一:前置知识具体解释: Spark SQL重要是操作DataFrame,DataFrame本身提供了save和load的操作. Load:能够创建DataFrame. Save:把DataFrame中 ...

  8. 新闻网大数据实时分析可视化系统项目——18、Spark SQL快速离线数据分析

    1.Spark SQL概述 1)Spark SQL是Spark核心功能的一部分,是在2014年4月份Spark1.0版本时发布的. 2)Spark SQL可以直接运行SQL或者HiveQL语句 3)B ...

  9. Spark SQL笔记——技术点汇总

    目录 概述 原理 组成 执行流程 性能 API 应用程序模板 通用读写方法 RDD转为DataFrame Parquet文件数据源 JSON文件数据源 Hive数据源 数据库JDBC数据源 DataF ...

随机推荐

  1. PL/SQL学习笔记_01_基础:变量、流程控制

    PL/SQL语句可以在Oracle客户端的 SQL窗口或者 command  窗口中运行 在SQL窗口中运行步骤同 SQL语句 在command  窗口中运行的步骤如下: 1)File—new com ...

  2. django学习笔记(二)模板

    1.当模板中的变量名遇到点时,以下面的顺序查找(短路逻辑): (1)字典类型查找: >>> from django.template import Template, Context ...

  3. Linux下视频流媒体直播服务器搭建详解

    目标: 搭建网络直播流媒体服务器系统(Linux操作系统) 背景: 用于OTT-TV大并发的直播和点播的一套流媒体服务器系统.支持N x 24小时录制回看和直播的服务器端解决方案. 解决方案: l  ...

  4. Arc076_E Connected?

    传送门 题目大意 给定$H\times W$的网格$(W,H\leq 10^8)$上的$N$对顶点,即两线交叉的交叉点而非格子内部$(N\leq 10^5)$,求是否存在至少一种方案使得每对点之间都有 ...

  5. 2017-2018-1 20179203《Linux内核原理与分析》第二周作业

    攥写人:李鹏举 学号:20179203 ( 原创作品转载请注明出处) ( 学习课程:<Linux内核分析>MOOC课程http://mooc.study.163.com/course/US ...

  6. 【转】CSS制作图形速查表-存档

      http://www.w3cplus.com/css/css-simple-shapes-cheat-sheet http://www.cnblogs.com/powertoolsteam/p/c ...

  7. WPF Invoke与BeginInvoke的区别

    Control.Invoke 方法 (Delegate) :在拥有此控件的基础窗口句柄的线程上执行指定的委托. Control.BeginInvoke 方法 (Delegate) :在创建控件的基础句 ...

  8. 树莓派 Learning 001 装机 ---之 1 安装NOOBS系统

    树莓派安装NOOBS系统 (使用的树莓派板卡型号:Raspberry Pi 2 Model B V1.1)(板卡的型号在板子正面的丝印层上印着,你可以看到.) RASPBERRY PI 2 MODEL ...

  9. R: data.frame 数据框的:查询位置、排序(sort、order)、筛选满足条件的子集。。

    ################################################### 问题:数据框 data.frame 查.排序等,   18.4.27 怎么对数据框 data.f ...

  10. IPMITOOL常用操作指令V1.0

    一.开关机,重启 1. 查看开关机状态: ipmitool -H (BMC的管理IP地址) -I lanplus -U (BMC登录用户名) -P (BMC 登录用户名的密码) power statu ...