原创文章,谢绝转载

笔者出于工作及学习的目的,经常与Spark源码打交道,也难免对Spark源码做修改及测试。本人一向讲究借助工具提升效率,开发Spark过程中也在摸索如何更加顺畅的对源码进行调试。

Spark基于Scala,采用IntelliJ IDEA和sbt应对日常开发,自然是最佳选择了。如何导入及编译Spark项目,网上资料很多,官网给的教程也比较详细:

本文基于Spark2.x的源码,重点介绍如何使用sbt结合IDEA对Spark进行断点调试开发,这对于经常修改或学习Spark源码的读者较为有益。废话到此,我们进入正题。

Spark源码编译

首次拿到Spark源码,直接导入IDEA会有很多错误,因为SQL项目的catalyst中的SQL语法解析依赖ANTLR语法定义,需要通过编译生成代码,如下是采用sbt打包编译的流程:

git clone https://github.com/apache/spark.git
cd spark
build/sbt package

...经过漫长等待,成功编译后,导入IDEA就可以正常看源码了。

大家可以采用阿里云的Maven仓库,加速下包的过程,可以参考我的这篇文章:https://zhuanlan.zhihu.com/p/25279570

编写测试用例

我习惯于直接在Spark项目中写TestCase的方式作为执行Spark的入口,这种方式对于经常修改Spark源码的开发场景很适用,相比在SparkShell中写测试代码有以下好处:

  • 代码保留在文件中,方便修改重新执行
  • 代码在同一个项目中,源码修改后IDEA无需对代码进行二次索引
  • 方便进行持续测试(Continuous Test)

Spark源码自带大量的TestCase可供我们学习参考,我们以Spark的SQL项目为例,将spark/sql/core/src/test/scala/org/apache/spark/sql/SQLQuerySuite.scala复制为SimpleSuite.scala

注意,这里不要是使用IDEA自带的复制功能,因为IDEA在复制的时候会重新组织代码中import的次序,这有可能会导致编译出错。正确的姿势应该是:

  1. 在IDEA中,找到要复制的文件,右击,复制代码路径

  1. 在IDEA的Terminal窗口中执行cp xxx xxx2完成复制

我们之所以要基于SQLQuerySuite复制出一个SimpleSuite文件是因为:Spark为了确保代码风格一致规范(比如每个代码文件头部需要定义Apache的License注释;import的顺序为java,scala,3rdParty,spark),在项目引入了Scala-style checker,如果代码不合规范,执行编译会出错。直接复制一个文件在上面做修改可以避免踩到代码风格检查的坑。我将SimpleSuite的内容修改如下:

打开IDEA的Terminal窗口,执行build/sbt进入sbt的交互式环境,通过以下方式执行我们的SimpleSuite:

> project sql
> testOnly *SimpleSuite

project sql指的是切换到SQL项目,这样在执行testOnly时可以快速定位到我们的SimpleSuite类,可以执行projects查看Spark定义的所有子模块,当前所在的模块名称前会有个*的标识。首次执行测试的时间比较长,再次执行就会比较快了,如果测试通过的话,会看到如下信息:

在sbt中执行exit退出交互式环境,接下来介绍如何使用sbt结合IDEA进行断点调试。

sbt结合IDEA对Spark进行断点调试

由于sbt是在Terminal中单独启动的进程,要对sbt调试,就需要采用IDEA的远程调试功能了。在IDAE的菜单中选择Run -> Edit Configrations...,在接下来的窗口中添加一个Remote配置:

配置名称大家随意,我这里为Spark,远程调试的端口为5005,如果本地的5005端口被占用,改为其他端口即可。

然后回到Terminal重新启动sbt,启动时需要添加远程调试参数:build/sbt -jvm-debug 5005,启动过程中会提示Listening for transport dt_socket at address: 5005,启动sbt后,我们就可以通过IDEA对sbt进行调试了。

接下来我们给SimpleSuite的test方法内部随意添加一个断点,回到sbt执行:

> project sql
> set fork in Test := false
> testOnly *SimpleSuite

一切顺利的话,执行testOnly的过程中,我们的断点会被命中:

如果对Spark源码或SimpleSuite的代码做了修改只需要重新执行testOnly *SimpleSuite即可。

让IDEA命中断点有一个关键的语句:set fork in Test := false,这个语句的作用是让sbt执行Test时避免fork子进程。我们启动sbt的时候添加的远程调试端口是加在sbt上的,如果执行Test不在一个进程内,IDEA就无法命中断点。

如果频繁修改代码,反复执行testOnly难免有些不便,我们可以采用sbt的持续编译功能简化流程。执行时加上~,也就是~testOnly *SimpleSuite,这样,我们修改代码,在保存,sbt会监控文件变化并自动执行测试,超级方便。这种方式同样适用于compile,test,run等命令。

总结

几个关键点:

# Spark源码目录下执行(以SimpleSuite为例):
$ build/sbt -jvm-debug 5005
> project sql
> set fork in Test := false
> testOnly *SimpleSuite

OK,掌握以上技巧,我们就可以愉快的深入Spark源码内部,了解Spark的运作机制了。

sbt结合IDEA对Spark进行断点调试开发的更多相关文章

  1. IDEA2017 maven Spark HelloWorld项目(本地断点调试)

    作为windows下的spark开发环境 1.应用安装 首先安装好idea2017 java8 scalaJDK spark hadoop(注意scala和spark的版本要匹配) 2.打开idea, ...

  2. Spark应用远程调试

    本来想用Eclipse的.然而在网上找了一圈,发现大家都在说IntelliJ怎样怎样好.我也受到了鼓励,遂决定在这台破机器上鼓捣一次IntelliJ吧. Spark程序远程调试,就是将本地IDE连接到 ...

  3. PhpStorm集成xdebug进行断点调试

    本文介绍如何使用PhpStorm集成xdebug在本地开发环境进行断点调试的技巧. 我配置的环境是:Windows10 + PhpStorm10.0.1 + PHP5.6. 1. 下载xdebug的扩 ...

  4. PyCharm断点调试django

    我在用PyCharm开发django程序的时候,对于打印日志调试程序的方式感觉还是有点麻烦和不直观,所以研究了一下断点调试的方法如下: 1.打开你的工程,在菜单栏里找到Run-->Edit Co ...

  5. netbeans-xdebug 断点调试php

    来自NetBeans官网的帮助文档: https://netbeans.org/kb/docs/php/debugging_zh_CN.html 但具体问题,我们还是要说下 准备工作 本地部署的ser ...

  6. Drools mvel方言drl断点调试方法

    开发环境:myeclipse2014,  jdk1.8.0.91,drools6.4.0.Final, drools-eclipse-plugin,mvel2-2.2.6.Final问题描述:drl使 ...

  7. Eclipse断点调试

    转自:http://blog.csdn.net/maritimesun/article/details/7815903 作为开发人员,掌握开发环境下的调试技巧十分有必要.去年就想把关于Eclipse断 ...

  8. js断点调试心得

    虽然网上已经有多的数不清的调试教程了,但仍然没有发现哪篇文章写的通俗易懂,索性自己尝试写写自己的一些使用习惯或者说是心得,希望对那些还不是很懂得使用断点调试的孩子有一些帮助(大神请无视~). 1.断点 ...

  9. chrome developer tool—— 断点调试篇

    断点,调试器的功能之一,可以让程序中断在需要的地方,从而方便其分析.也可以在一次调试中设置断点,下一次只需让程序自动运行到设置断点位置,便可在上次设置断点的位置中断下来,极大的方便了操作,同时节省了时 ...

随机推荐

  1. PHPSTORM下安装XDEBUG

    本文不是教程安装XDEBUG,具体的请自行百度(我也是按照百度上的一步步来的). 以下纠正几点目前我安装时查看播客的不对之处: 1. Setting > PHP > DEBUG > ...

  2. C++实现动态顺序表

    顺序表是在计算机内存中以数组的形式保存的线性表,是指用一组地址连续的存储单元依次存储数据元素的线性结构.这样的存储方式使得线性表逻辑上相邻的元素,其在物理存储单元中也是相邻的.只要知道了第一个元素的存 ...

  3. 性能调优之Java系统级性能监控及优化

    性能调优之Java系统级性能监控及优化   对于性能调优而言,通常我们需要经过以下三个步骤:1,性能监控:2,性能剖析:3,性能调优 性能调优:通过分析影响Application性能问题根源,进行优化 ...

  4. css实现超出部分用...代替

    如果是一行的话 css为 white-space: nowrap: 保证文本内容不会自动换行,如果多余的内容会在水平方向撑破单元格. overflow: hidden: 隐藏超出单元格的部分. tex ...

  5. Spring基础学习(五)—事务管理

    一.事务基本认识 1.事务的概述      为了保证数据库中数据的一致性,数据的操作应当是离散的成组的逻辑单元.当它全部完成时,数据的一致性可以保持,而当这个单元中的一部分操作失败,整个事务应当全部视 ...

  6. Git安装与上传代码至Github

    转载请注明出处:http://www.cnblogs.com/cnwutianhao/p/6642887.html 这篇文章应该是全网最新,最全,最靠谱的Github安装到上传代码的流程. 1.Git ...

  7. 优化php性能的一点总结

    图示为100个并发,请求1000次目标地址 进行测试 最重要的两个参数:Requests per second :每秒接受请求数,这里每秒接收101个请求 Time per request:一个请求用 ...

  8. IntelliJ IDEA应用[一]下载与安装

    一.IntelliJ IDEA 12.1.6的下载 IntelliJ IDEA的官方下载网站:http://www.jetbrains.com/idea/download/

  9. vue2.0+elementUI构建单页面后台管理平台

    git:https://github.com/reg21st/vue2-management-platform 访问:https://reg21st.github.io/vue2-management ...

  10. SSE 系列内置函数中的 shuffle 函数

    SSE 系列内置函数中的 shuffle 函数 邮箱: quarrying@qq.com 博客: http://www.cnblogs.com/quarryman/ 发布时间: 2017年04月18日 ...