-
Notifications
You must be signed in to change notification settings - Fork 523
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[RESTWS-673] Scheduler REST Implementation #293
Conversation
Can you add some tests? |
I just ran the tests :) Tests in TaskActionController1_8Test.java fail. |
58e1557
to
7c082ef
Compare
// @Override | ||
// public DelegatingResourceDescription getUpdatableProperties() { | ||
// DelegatingResourceDescription description = new DelegatingResourceDescription(); | ||
// description.addRequiredProperty("name"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did you take a look at this? https://wiki.openmrs.org/display/docs/Java+Conventions#JavaConventions-Donotcommentoutcode
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removed those Comments
*/ | ||
@Override | ||
public TaskDefinition save(TaskDefinition taskDefinition) { | ||
//Context.getSchedulerService().saveTaskDefinition(taskDefinition); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is the above line for? https://wiki.openmrs.org/display/docs/Java+Conventions#JavaConventions-Donotcommentoutcode
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removed that line
schedulerService.scheduleTask(task); | ||
} | ||
catch (SchedulerException e) { | ||
throw new UnsupportedOperationException(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does this really mean that the operation is not supported? The same applies elsewhere.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removed unwanted Catch Exceptions
*/ | ||
package org.openmrs.module.webservices.helper; | ||
|
||
import org.openmrs.scheduler.*; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did you take a look at this? https://wiki.openmrs.org/display/docs/Java+Conventions#JavaConventions-Donotusewildcardimports
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Refactored :-)
// ensure they're not trying to modify the REST module | ||
for (TaskDefinition taskDef : taskDefinitions) { | ||
// if they specified a module that's not loaded, it will show up here as null | ||
if (taskDef == null) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How does taskDefinitions become a collection of nulls?
@Autowired | ||
RestService restService; | ||
|
||
private TaskDefinition TestTask = new TaskDefinition(1, "TestTask", "TestTask Description", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Our convention is to use variable names that start with lower case.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Refactored
|
||
MockTaskFactoryWrapper mockTaskFactory = new MockTaskFactoryWrapper(); | ||
|
||
String TestTaskMockJson = "{\"id\" : 1,\"name\":\"TestTask\",\"description\":\"TestTask Description\"," |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
same as above for variable names.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Refactored
|
||
@Test | ||
public void shouldStopTestTask() throws Exception { | ||
System.out.println("shouldStopTestTask"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Take a look at this: https://wiki.openmrs.org/display/docs/Java+Conventions#JavaConventions-Donotprintout
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removed :-)
@dkayiwa I have refactored the code about your comments |
How about other comments that have nothing to do with refactoring? |
|
||
ServletContext servletContext = getServletContext(context); | ||
|
||
if (action.getAction().equals("SCHEDULETASK") || action.getAction().equals("RESCHEDULETASK") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Don't you already have constants for SCHEDULETASK, RESCHEDULETASK, etc?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed with constants from TaskAction
taskFactoryWrapper.reScheduleTask(taskDef); | ||
} | ||
catch (SchedulerException e) { | ||
throw new UnsupportedOperationException(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see so many UnsupportedOperationException. Does this mean if anything goes wrong during these actions, it means that the REST call is not supported?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I couldn't throw the SchedulerException , because method implemented from Creatable Interface doesn't allow to throw the SchedulerException. Else I wanted to change the Creatable Interface. So I decided to throw UnsupportedOperationException
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can't throw ResponseException instead of UnsupportedOperationException. Because I can't instantiate that abstract here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since you are not doing anything with the thrown exception, just do not catch it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I do not catch it, then want to throw it by methods.
If I throw it from here, then want to throw it from Create method.
But I can't throw it because It is a overridden method. So I caught and throw like this.
Are there any perfect methods for this?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@dkayiwa Shall I throw like this,
throw new ResourceDoesNotSupportOperationException("SchedulerException");
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@dkayiwa If I throw the exception from here, then I can catch this from the angular REST request to indicate the user as well
Is it good to use like,
throw ObjectNotFoundException("SchedulerException : Ca not execute the action")
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do something along these lines:
throw new APIException("Errors occurred while rescheduling task", e);
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed! Thanks @dkayiwa :-)
} | ||
if (!contains) { | ||
scheduledTasks.add(task.getName()); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did you intentionally decide to silently ignore a call for scheduling a task which does not exist?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The same applies for others like task shutdown, reschedule, etc
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here, I am doing same as ModuleAction Test. I using mock collections to maintain registered and scheduled tasks. When REST call arrives at Resource, that will call these MockTaskFactoryWrapper class methods. Here I am mocking that tasks and assigning to the collections to check the status from Test Class.
taskFactoryWrapper.unloadTask(taskDef); | ||
} | ||
catch (SchedulerException e) { | ||
throw new APIException("Errors occurred while shutdowning all tasks", e); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this exception message correct?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ow sorry, Missed :-(
Changed to "Errors occurred while deleting task".
4a068e8
to
aaf0df0
Compare
@dkayiwa Completed 😊 Can you please take a look to merge! |
} | ||
if (!action.isAllTasks()) { | ||
for (TaskDefinition taskDef : taskDefinitions) { | ||
if (taskDef == null) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can a collection contain a null value?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have removed this Condition, because the wrong TaskDefinition will be caught by the setConvertedProperties() and If there are any issues, then It will throw the error.
} | ||
|
||
@Test | ||
public void shouldScheduleTestTask() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No need to add "Test" to any of these test methods. For instance, shouldScheduleTask is enough instead of shouldScheduleTestTask
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Refactored
} | ||
|
||
@Test | ||
public void shouldGetModuleByUuid() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should get what?
|
||
@Test | ||
@Override | ||
public void shouldGetDefaultByUuid() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When you say shouldGet, add what exactly you are getting.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here I have @OverRide the method from the super class. that will express the Default representation and I can't change the name here
/** | ||
* It will used to retrieve the required data from the Scheduler Service | ||
*/ | ||
public class TaskServiceWrapper { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What value does this class add?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wrapping the required task information between related resource and SchedulerService
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This wrapping is simply one method call hence rendering it useless.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yah, but in the flow I want this class to create another Mock class for testing.
Otherwise, I can't do the testing.
I am using TaskServiceWrapper for active service works
MockTaskServiceWrapper for mock testing works
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can always mock Context.getSchedulerService().getTask(), etc without writing new mock classes.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here I followed the same way of the ModuleActionResource and ModuleWrapper and achieve the target 😊
What do you mean by the mocking Services?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok, let us go with what you have. 😊
@dkayiwa So Finally If you haven't any concerns or comments, Could we move to merge it 😊 |
|
||
@Override | ||
public TaskAction getByUniqueId(String uniqueId) { | ||
throw new UnsupportedOperationException("TaskAction cannot get by id"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't we take this to be the internal id, if a number, or task name?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh sorry. Just ignore the above. 😊
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here It is the integer number. Here I have overridden that method in TaskAction.
Anyway, TaskAction is not supported to that function.
|
||
@Override | ||
@Test(expected = Exception.class) | ||
public void shouldGetDefaultByUuid() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should get what?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Overridden method. It is also like used to get Default Representation. But not supported to TaskAction.
* @throws SchedulerException - It will throw in case of any SchedulerService exceptions | ||
*/ | ||
public void deleteTask(TaskDefinition task) throws SchedulerException { | ||
if (Context.getSchedulerService().getTaskByName(task.getName()).getStarted()) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is the use of this logic? Isn't it taken care of by the service layer? Why don't you just Context.getSchedulerService().deleteTask?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nope, SchedulerService is allowed to delete only the shutdown tasks. Otherwise, It threw the error. (I think, Core doesn't care about the task status)
So I just check about the task status before delete that task
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Even then, that is the business of the service layer. Your duty is to simply call Context.getSchedulerService().deleteTask
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Okay 😊
assertPropEquals("started", getObject().getStarted()); | ||
assertPropEquals("taskClass", getObject().getTaskClass()); | ||
assertPropEquals("lastExecutionTime", getObject().getLastExecutionTime()); | ||
assertPropPresent("startTimePattern"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't the above also be assertPropEquals()?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
changed
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about the one below it? 😊
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That too changed 😊
MockHttpServletRequest req = request(RequestMethod.POST, getURI()); | ||
req.setContent(json.getBytes()); | ||
deserialize(handle(req)); | ||
Assert.assertEquals(mockTaskServiceWrapper.getTaskByName("MockTask").getName(), "MockTask"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How sure can i be that this task did not exist before saving?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I will add another test before to this to confirm that
} | ||
|
||
@Test | ||
public void shouldGetAllRegistered() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is the difference between shouldGetAll and shouldGetAllRegistered?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Defaultly GetAll method in the resource has been set to return the list of Scheduled tasks. (I can't change the name because it is an Overriden method)
So I am using another separate method to test about the Registered tasks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Isn't it more natural for GetAll to return all tasks regardless of whether they are scheduled or not?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So I will change the way to retrieve all the registered for the getAll method
} | ||
|
||
@Test | ||
public void shouldDoNothingIfTaskAlreadyShutdown() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be: shutdown_shouldDoNothingIfTaskAlreadyShutdown
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed to shutdownTask_shouldDoNothingIfTaskAlreadyShutdown
} | ||
|
||
@Test | ||
public void shouldDoNothingIfTaskAlreadyScheduled() throws Exception { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
scheduleTask _shouldDoNothingIfTaskAlreadyScheduled
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed
mockTaskServiceWrapper.scheduledTasks.add(testTask); | ||
deserialize(handle(newPostRequest(getURI(), "{\"action\": \"shutdowntask\", \"tasks\":[\"" + getTestTaskName() | ||
+ "\"]}"))); | ||
assertThat(mockTaskServiceWrapper.scheduledTasks, not(hasItem(testTask))); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How how are you that the task wasn't already shutdown even before the shutdown command?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here I am checking the Scheduled list before making shout down the request. The scheduled list will contain this task If it is not shut down.
After the request, It will be removed from the Scheduled list (shutdown). Then I am checking for removal.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh which line number are you checking that the task is not already shutdown?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ohh, Sorry really missed that 😢
I will add it quickly
5ff8ce8
to
15140a5
Compare
update TaskDefinition and TaskAction Implementation
Thank you so much @dkayiwa for the review and merge 😊 |
Thank you too for responding to all my back and forth review comments! 😊 |
Created TaskDefinitionResource1_8 for the task REST implementation