flume ExecSource 源码分析

本文介绍了一个名为ExecSource的类,该类通过Process监听命令执行后的数据流,并将数据包装成事件进行处理。文章详细展示了如何配置和实现命令的执行、错误日志记录、数据流读取及批处理等功能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

public class ExecSource extends AbstractSource implements EventDrivenSource,Configurable

关键静态内部类private static class ExecRunnable implements Runnable

public ExecRunnable(String command, ChannelProcessor channelProcessor,
        CounterGroup counterGroup, boolean restart, long restartThrottle,
        boolean logStderr, int bufferCount) {
      this.command = command;
      this.channelProcessor = channelProcessor;
      this.counterGroup = counterGroup;
      this.restartThrottle = restartThrottle;
      this.bufferCount = bufferCount;
      this.restart = restart;
      this.logStderr = logStderr;
    }


    private String command;
    private ChannelProcessor channelProcessor;
    private CounterGroup counterGroup;
    private volatile boolean restart;
    private long restartThrottle;
    private int bufferCount;
    private boolean logStderr;


    @Override
    public void run() {
      do {
        String exitCode = "unknown";
        BufferedReader reader = null;
        Process process = null;
        try {
          String[] commandArgs = command.split("\\s+");
          process = new ProcessBuilder(commandArgs).start();
          reader = new BufferedReader(
              new InputStreamReader(process.getInputStream()));


          // StderrLogger dies as soon as the input stream is invalid
          StderrReader stderrReader = new StderrReader(new BufferedReader(
              new InputStreamReader(process.getErrorStream())), logStderr);
          stderrReader.setName("StderrReader-[" + command + "]");
          stderrReader.setDaemon(true);
          stderrReader.start();


          String line = null;
          List<Event> eventList = new ArrayList<Event>();
          while ((line = reader.readLine()) != null) {
            counterGroup.incrementAndGet("exec.lines.read");
            eventList.add(EventBuilder.withBody(line.getBytes()));
            if(eventList.size() >= bufferCount) {
              channelProcessor.processEventBatch(eventList);
              eventList.clear();
            }
          }
          if(!eventList.isEmpty()) {
            channelProcessor.processEventBatch(eventList);
          }
        } catch (Exception e) {
          logger.error("Failed while running command: " + command, e);
          if(e instanceof InterruptedException) {
            Thread.currentThread().interrupt();
          }
        } finally {
          if (reader != null) {
            try {
              reader.close();
            } catch (IOException ex) {
              logger.error("Failed to close reader for exec source", ex);
            }
          }
          if(process != null) {
            process.destroy();
            try {
              exitCode = String.valueOf(process.waitFor());
            } catch (InterruptedException ex) {
              Thread.currentThread().interrupt();
            }
          }
        }
        if(restart) {
          logger.info("Restarting in {}ms, exit code {}", restartThrottle, exitCode);
          try {
            Thread.sleep(restartThrottle);
          } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
          }
        }
      } while(restart);


通过Process来监听命令执行之后的数据流

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值