
# Storm-HDFS开发指引
#### 操作场景
本章节只适用于MRS产品中Storm和HDFS交互的场景。本章中描述的jar包的具体版本信息请以实际情况为准。
安全模式下登录方式分为两种，票据登录和keytab文件登录，两种方式操作步骤基本一致，票据登录方式为开源提供的能力，后期需要人工上传票据，存在可靠性和易用性问题，因此推荐使用keytab方式。
#### 应用开发操作步骤
1. 确认Storm和HDFS组件已经安装，并正常运行。
2. 将storm-examples导入到IntelliJ IDEA开发环境，请参见[准备Storm应用开发环境](https://support.huaweicloud.com/devg3-mrs/mrs_07_210005.html)。
3. 如果集群启用了安全服务，按登录方式需要进行以下配置：
   
   - keytab方式：需要从管理员处获取一个"人机"用户，用于登录FusionInsight Manager平台并通过认证，并且获取到该用户的keytab文件。
   
   - 票据方式：从管理员处获取一个"人机"用户，用于后续的安全登录，开启Kerberos服务的renewable和forwardable开关并且设置票据刷新周期，开启成功后重启kerberos及相关组件。
   
   
   ![](https://support.huaweicloud.com/devg3-mrs/public_sys-resources/note_3.0-zh-cn.png)
   - 获取的用户需要属于storm组。
   
   - 默认情况下，用户的密码有效期是90天，所以获取的keytab文件的有效期是90天。如果需要延长该用户keytab的有效期，修改用户的密码策略并重新获取keytab。
   
   - Kerberos服务的renewable、forwardable开关和票据刷新周期的设置在Kerberos服务的配置页面的"系统"标签下，票据刷新周期的修改可以根据实际情况修改"kdc_renew_lifetime"和"kdc_max_renewable_life"的值。
    
   
   
4. 下载并安装HDFS客户端。
5. 获取相关配置文件。获取方法如下：
   
   在安装好的HDFS客户端目录下找到目录"/opt/clientHDFS/HDFS/hadoop/etc/hadoop"，在该目录下获取到配置文件"core-site.xml"和"hdfs-site.xml"。
   如果使用keytab登录方式，按[3](https://support.huaweicloud.com/devg3-mrs/mrs_07_210031.html#mrs_07_210031__ref436129888)获取keytab文件；如果使用票据方式，则无需获取额外的配置文件。
   ![](https://support.huaweicloud.com/devg3-mrs/public_sys-resources/note_3.0-zh-cn.png)
   获取到的keytab文件默认文件名为user.keytab，若用户需要修改，可直接修改文件名，但在提交任务时需要额外上传修改后的文件名作为参数。
   
   
6. 获取相关jar包。获取方法如下：
   
   - 在安装好的HDFS客户端目录下找到目录HDFS/hadoop/share/hadoop/common/lib，获取如下jar包：
     - commons-cli-\<version\>.jar
     
     - commons-io-\<version\>.jar
     
     - commons-lang-\<version\>.jar
     
     - commons-lang3-\<version\>.jar
     
     - commons-collections-\<version\>.jar
     
     - commons-configuration2-\<version\>.jar
     
     - commons-logging-\<version\>.jar
     
     - guava-\<version\>.jar
     
     - hadoop-\*.jar
     
     - protobuf-java-\<version\>.jar
     
     - jackson-databind-\<version\>.jar
     
     - jackson-core-\<version\>.jar
     
     - jackson-annotations-\<version\>.jar
     
     - re2j-\<version\>.jar
     
     - jaeger-core-\<version\>.jar
     
     - opentracing-api-\<version\>.jar
     
     - opentracing-noop-\<version\>.jar
     
     - opentracing-tracerresolver-\<version\>.jar
     
     - opentracing-util-\<version\>.jar
      
   
   - 在安装好的HDFS客户端目录下找到目录"HDFS/hadoop/share/hadoop/common"，获取该目录下的hadoop-\*.jar。
   
   - 在安装好的HDFS客户端目录下找到目录"HDFS/hadoop/share/hadoop/client"，获取该目录下的hadoop-\*.jar。
   
   - 在安装好的HDFS客户端目录下找到目录"HDFS/hadoop/share/hadoop/hdfs"，获取该目录下的hadoop-hdfs-\*.jar。
   
   - 在样例工程"/src/storm-examples/storm-examples/lib"中获取如下jar包：
     - storm-hdfs-\<version\>.jar
     
     - storm-autocreds-\<version\>.jar
      
   
   
   
   
 
#### IntelliJ IDEA代码样例
创建Topology。
```
public static void main(String[] args) throws Exception   
    {  
      TopologyBuilder builder = new TopologyBuilder();  
      // 分隔符格式，当前采用“|”代替默认的“，”对tuple中的field进行分隔  
      // HdfsBolt必选参数  
      RecordFormat format = new DelimitedRecordFormat()  
              .withFieldDelimiter("|");  
      // 同步策略，每1000个tuple对文件系统进行一次同步  
      // HdfsBolt必选参数  
      SyncPolicy syncPolicy = new CountSyncPolicy(1000);  
      // 文件大小循环策略，当文件大小到达5M时，从头开始写  
      // HdfsBolt必选参数  
      FileRotationPolicy rotationPolicy = new FileSizeRotationPolicy(5.0f, Units.MB);  
      // 写入HDFS的目的文件  
      // HdfsBolt必选参数  
      FileNameFormat fileNameFormat = new DefaultFileNameFormat()  
              .withPath("/user/foo/");  
      //创建HdfsBolt  
      HdfsBolt bolt = new HdfsBolt()  
              .withFsUrl(DEFAULT_FS_URL)
              .withFileNameFormat(fileNameFormat)  
              .withRecordFormat(format)  
              .withRotationPolicy(rotationPolicy)  
              .withSyncPolicy(syncPolicy);  
      //Spout生成随机语句  
      builder.setSpout("spout", new RandomSentenceSpout(), 1);   
      builder.setBolt("split", new SplitSentence(), 1).shuffleGrouping("spout");  
      builder.setBolt("count", bolt, 1).fieldsGrouping("split", new Fields("word"));  
      //增加Kerberos认证所需的plugin到列表中，安全模式必选  
      setSecurityConf(conf,AuthenticationType.KEYTAB); 
      Config conf = new Config();  
      //将客户端配置的plugin列表写入config指定项中，安全模式必配  
      conf.put(Config.TOPOLOGY_AUTO_CREDENTIALS, auto_tgts);  
      if(args.length >= 2)  
      {  
          //用户更改了默认的keytab文件名，这里需要将新的keytab文件名通过参数传入  
          conf.put(Config.STORM_CLIENT_KEYTAB_FILE, args[1]);  
      }  
      //命令行提交拓扑  
      StormSubmitter.submitTopology(args[0], conf, builder.createTopology());  
    }
```
![](https://support.huaweicloud.com/devg3-mrs/public_sys-resources/note_3.0-zh-cn.png)
Storm不支持将HDFS的目的文件路径设置为HDFS的SM4加密分区。
#### 部署运行及结果查看
1. 导出本地jar包，请参见[打包Storm样例工程应用](https://support.huaweicloud.com/devg3-mrs/mrs_07_210017.html)。
2. 将[1]导出的本地Jar包，[5](https://support.huaweicloud.com/devg3-mrs/mrs_07_210031.html#mrs_07_210031__li1579110)中获取的配置文件和[6](https://support.huaweicloud.com/devg3-mrs/mrs_07_210031.html#mrs_07_210031__li13541370145425)中获取的jar包合并统一打出完整的业务jar包，请参见[打包Storm业务](https://support.huaweicloud.com/devg3-mrs/mrs_07_210018.html)。
3. 执行命令提交拓扑。 
   keytab方式下，若用户修改了keytab文件名，如修改为"huawei.keytab"，则需要在命令中增加第二个参数进行说明，提交命令示例（拓扑名为hdfs-test）：
   **storm jar /opt/jartarget/** **source.jar** **com.huawei.storm.example.hdfs.SimpleHDFSTopology hdfs-test huawei.keytab**
   ![](https://support.huaweicloud.com/devg3-mrs/public_sys-resources/note_3.0-zh-cn.png)
   安全模式下在提交source.jar之前，请确保已经进行kerberos安全登录，并且keytab方式下，登录用户和所上传keytab所属用户必须是同一个用户。
   
   
4. 拓扑提交成功后请登录HDFS集群查看。
5. 如果使用票据登录，则需要使用命令行定期上传票据，具体周期由票据刷新截止时间而定，步骤如下： 
   1. 在安装好的storm客户端目录的"Storm/storm-1.2.1/conf/storm.yaml"文件尾部新起一行添加如下内容： **topology.auto-credentials:** **- org.apache.storm.security.auth.kerberos.AutoTGT**
      
   
   2. 执行命令：**./storm upload-credentials hdfs-test**
   
   
   
   
 
