Announcement Announcement Module
No announcement yet.
Preventing circumvention of Spring Batch framework Page Title Module
Move Remove Collapse
Conversation Detail Module
  • Filter
  • Time
  • Show
Clear All
new posts

  • Preventing circumvention of Spring Batch framework

    One of the important aspects of the Spring Batch framework in my opinion is the fact that all jobs that use the same basic service configuration are handled consistently in terms of interaction with the repository, etc.

    However, there is at least one hole in this - if a tasklet calls System.exit, for instance, the framework will exit without performing any further tasks.

    I submitted this as a feature request already, since I believe this should be handled consistently by Spring Batch and should not require the end user to have to intervene to enforce this.

    I was hoping I could get some input back from the community as to whether this ought to be part of the framework or implemented individually, whether or not you see this as a real problem, how it should be implemented alternatively, etc.

    My original proposal was to register a new SecurityManager (which would use as its basis the current SecurityManager) that would to capture calls to exit the VM during execution and map it to a Spring Batch exception, thus allowing the repository to be properly updated. Any thoughts as to whether or not this is sufficient, prudent, etc?

    Please reference original request at:

    Comments greatly appreciated!

  • #2
    Personally I agree with you on the fact that the integrity and reliability of the framework should be guaranteed as much as possible so conditions like a system.exit or a runtime exception in a framework user's code should not be able to break things like the exitcode and the restartability of a job.

    I don't know enough about SecurityManagers to be able to comment on your suggested solution, but there are probably not many alternatives around. (if any) However, I can also understand Dave's concern, an organisation might already have it's own SecurityManager in place and this should not conflict with Spring-batch.

    If the batch security manager really inherits everything from the active security manager and only overrides the permissions that can somehow interfer with the batch-framework functionality I don't see the harm in that. Especially if at the end of the JobLauncher the original security manager's settings are put back.


    • #3
      There is always infinity of imaginative ways how to do things wrong, but I think a framework deliberately shouldn't care about these - I believe it should care about things that make life easier for developers and administrators, which is hard enough.

      Is there a real-life example where framework-integrated security manager would be helpful? Calling System.exit() in tasklet seems purely hypothetical to me, but maybe I just lack enough bad experience


      • #4
        In most cases, the developer doing something they shouldn't and causing some kind of crazy error is completely out of the framework's hands. There isn't much we can do about it. Even an architecture team that is much closer to the developers can't do much short of peer reviewing code. However, even if the developer does something crazy, it can still be seen in status. If it's causing a huge performance problem, dividing the total runtime by the task count can give you an idea, or a crazy exception is logged and an exit code returned. The big problem with System.exit() is that it completely removes any chance for the framework to report on the status of the job. An operations person looking into the status tables to try and find the error would see a null END_TIME and no exit code or message. The scheduler also wouldn't get any return code back, just a process that errored out. It would be extremely hard to figure out why the job failed.

        In an ideal world, making a call to System.exit() would be caught in peer review, or during testing. However, we all know that doesn't always happen the way it should, or the call could be buried in some weird processing chain that would only happen on leap years.

        I'm not sure I feel strongly one way or another, although I would be curious if there were any other application frameworks that would use a SecurityManager at all by default. I would imagine that none do, and I'm not sure if we should depart from that trend. Please correct me though if there is a precedent for this.


        • #5
          "The big problem with System.exit() is that it completely removes any chance for the framework to report on the status of the job."

          What about providing a simple JVM shutdown hook i.e. writing a class that extends from Thread and calling Runtime.getRuntime().addShutdownHook()?


          • #6
            We could add a call to ApplicationContext.registerShutdownHook() in the BatchCommandLineLauncher (if anyone likes the idea just add a JIRA). But that isn't bullet proof by any means - nobody forces you to use BatchCommandLineLauncher - it is only really a very thin wrapper and quite a simple tool (at one point we weren't planning on including it in the distribution at all - and I guess that decision is still open to an extent). Anyone can abuse a tool, so we can never provide guarantees - just best practices.


            • #7
              I will add this as another possible resolution under my original JIRA request.


              • #8
                I realize there's no silver bullet for security. We can't control peoples' minds and actions, and there's no way around that. However, if there is a glaring hole that can be patched, I feel it is worthwhile to do so. In this case, remember that it is not only the user's code that we have to worry about, but also any other packages that the user's code calls, including (but not limited to) open source projects, proprietary corporate packages, legacy code from the user's own project, etc. which the user himself may not have control over.

                In my opinion, it is very sensible that the END_TIME field and related status fields should always be populated and if there is a method by which a user can, with intent, circumvent this, then it makes the concept of a 'framework' rather moot. The point of having a framework is to ensure a consistent set of useful black-box behaviors around user-defined behaviors. If these framework behaviors are non-deterministic, in what sense do you still have a useful framework?