【问题标题】:Spring Boot CommandLineRunner : filter option argumentSpring Boot CommandLineRunner:过滤选项参数
【发布时间】:2015-01-19 12:21:21
【问题描述】:

考虑到 Spring Boot CommandLineRunner 应用程序,我想知道如何过滤作为外部配置传递给 Spring Boot 的“开关”选项。

例如,用:

@Component
public class FileProcessingCommandLine implements CommandLineRunner {
    @Override
    public void run(String... strings) throws Exception {
        for (String filename: strings) {
           File file = new File(filename);
           service.doSomething(file);
        }
    }
}

我可以打电话给java -jar myJar.jar /tmp/file1 /tmp/file2,这两个文件都会调用该服务。

但是,如果我添加一个 Spring 参数,例如 java -jar myJar.jar /tmp/file1 /tmp/file2 --spring.config.name=myproject,那么配置名称会更新(对!),但也会为文件 ./--spring.config.name=myproject 调用该服务,这当然不存在。

我知道我可以使用类似的文件名手动过滤

if (!filename.startsWith("--")) ...

但是由于所有这些组件都来自 Spring,我想知道是否没有一个选项可以让它管理它,并确保传递给 run 方法的 strings 参数不会包含所有属性选项已在应用程序级别解析。

【问题讨论】:

    标签: java spring command-line spring-batch spring-boot


    【解决方案1】:

    感谢@AndyWilkinson 增强报告,ApplicationRunner 接口被添加到 Spring Boot 1.3.0 中(目前仍在 Milestones 中,但我希望很快会发布)

    这里是使用它和解决问题的方法:

    @Component
    public class FileProcessingCommandLine implements ApplicationRunner {
        @Override
        public void run(ApplicationArguments applicationArguments) throws Exception {
            for (String filename : applicationArguments.getNonOptionArgs()) 
               File file = new File(filename);
               service.doSomething(file);
            }
        }
    }
    

    【讨论】:

      【解决方案2】:

      这是另一个解决方案:

      @Component
      public class FileProcessingCommandLine implements CommandLineRunner {
      
          @Autowired
          private ApplicationConfig config;
      
          @Override
          public void run(String... strings) throws Exception {
      
              for (String filename: config.getFiles()) {
                 File file = new File(filename);
                 service.doSomething(file);
              }
          }
      }
      
      
      @Configuration
      @EnableConfigurationProperties
      public class ApplicationConfig {
          private String[] files;
      
          public String[] getFiles() {
              return files;
          }
      
          public void setFiles(String[] files) {
              this.files = files;
          }
      }
      

      然后运行程序:

      java -jar myJar.jar --files=/tmp/file1,/tmp/file2 --spring.config.name=myproject
      

      【讨论】:

      • 谢谢!但这仍然是一种解决方法,我认为我们会失去对 Spring 提供的 CommandLineRunner 接口的兴趣。
      【解决方案3】:

      一种选择是在 CommandLineRunner impl 的 run() 中使用 Commons CLI

      有一个相关的question你可能会感兴趣。

      【讨论】:

      • 好吧,当您看到备选方案列表时……这正是我希望 Spring 为我选择完成方式而无需调查所有可能的方法的原因。还是谢谢!
      【解决方案4】:

      目前 Spring Boot 中不支持此功能。我已经打开了an enhancement issue,以便我们在未来的版本中考虑它。

      【讨论】:

      • 感谢考虑!
      • 有这方面的消息吗?在过去 6 个月中,至少有 1000 人查看了此问题。
      • 看起来这个问题已经解决了,我们现在有一个如何使用ApplicationArguments 的例子吗?
      • @Jackie 这个问题的已接受答案中有一个例子
      猜你喜欢
      • 1970-01-01
      • 2017-02-02
      • 2017-11-12
      • 2015-02-23
      • 1970-01-01
      • 1970-01-01
      • 2017-07-15
      • 2019-07-02
      • 2020-12-17
      相关资源
      最近更新 更多