10
I just want to know whether controller class method is accessible from another java class.    

following is my controller and its method.

@Controller
public class TestResultUploadController {
    @RequestMapping(method = RequestMethod.POST,value="/uploadTestResult")  
    public @ResponseBody  
     String uploadTestResult(String testResultBarcode,int deviceLoc) {

         //some code goes here
    return something;
}

I just want to call this controller method from another java class. How can I make it work? please suggest..

6
  • If you have to do that I think you've got a design problem. perhaps you should move the method to a lower level to be accessible to other controllers. Commented Dec 4, 2013 at 12:12
  • FYI. I can call this method by creating controllers object and directly calling that method. but in that case @Autowired fields not get initialized. I know the design is wrong but flow must be in this way, coz I m trying to call this method from thread which get initialized at the time of context initialization. Commented Dec 4, 2013 at 12:15
  • @SwapnilWalivkar you can achieve this flow without having to have the wrong setup. You can just put this method in a service and make the controller and your thread each call this service instead of violating mvc principles. Commented Dec 4, 2013 at 12:31
  • What fo you mean you just want to call? Are you thinking of service I guess so. If you can point further I can provide concrete answer Commented Dec 4, 2013 at 12:39
  • manocha_ak I have thread class which runs in a background. from thread class I am trying to call controller class method (but @autowired is giving me null). I tried creating objects by new keyword but at end in DAO layer the EntityManager is getting null. Thats why I trying to make request from controller itself. Commented Dec 4, 2013 at 12:47

1 Answer 1

7

Short answer: yes, it is possible. In your other class/thread, you can do

// this will create a new instance of that controller where no fields are wired/injected
TestResultUploadController controller = new TestResultUploadController();
controller.uploadTestResult("someString", 1234); 

However, keep in mind that your setup is highly unusual and all your autowired fields wouldn't be wired correctly. If you obtain your controller from the context, you'd be able to have your fields wired/injected properly:

// obtain controller bean from context, should have fields wired properly
TestResultUploadController controller = ctx.getBean(TestResultUploadController.class);
controller.uploadTestResult("someString", 1234); 

or you can, in your other class, have:

@Autowired private TestResultUploadController controller;

....
public void doStuff(){
    controller.uploadTestResult("someString", 1234); 
}

Again, this is highly unusual, but highly possible. However, just cause something is possible to be done, doesn't mean you should do it. I would recommend the more common Spring/MVC approach in which you outsource the business logic to Services. Basically, to have something like this:

@Controller
public class TestResultUploadController {

    @Autowired private UploadTestResultService uploadTestResultService;

    @RequestMapping(method = RequestMethod.POST,value="/uploadTestResult")  
    public @ResponseBody String uploadTestResult(String testResultBarcode,int deviceLoc) {
        return uploadTestResultService.uploadTestResult(testResultBarcode, deviceLoc);
    }
}

And in your thread:

//somehow get the service
UploadTestResultService uploadTestResultService = //somehowGetTheService (whether from context or in some other way)
uploadTestResultService.uploadTestResult(testResultBarcode, deviceLoc);

That way, you'd be able to mock the UploadTestResultService in your tests of the controller, and you'd also be able to test the uploadTestResult method of that service on its own without it being in a controller.

EDIT: How to obtain the Spring context is outside of the scope of this question. I assume you know basic Spring and also basic java.

Sign up to request clarification or add additional context in comments.

8 Comments

I tried all your solutions, but its not working. autowiring is giving me null instance in service layer.
can u please give specification on ctx.getBean
are you doing proper component scan? Are you declaring your services as beans or components? You seem to be new at Spring. It all depends on how your project is setup. Try to get autowiring to work, and if you can't do it, just create a static method somewhere and call it instead of a service: gist.github.com/anonymous/4d072f266ae1bb7bc457
I am trying to get autowired worked. I have some doubts in mind.
Explain what doubts you have. To me, you seem to not be able to quite grasp the idea of how Spring works. You somehow managed to autowire fields in your controller, why wouldn't you be able to autowire fields in your service? My suggestion would be for you to first go through a basic Spring crash course before starting to code seriously.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.