Over a million developers have joined DZone.
{{announcement.body}}
{{announcement.title}}

RESTful Timers in JavaEE

DZone's Guide to

RESTful Timers in JavaEE

Learn how you can expose a simple RESTful interface to work with EJB Timers.

· Java Zone
Free Resource

Download Microservices for Java Developers: A hands-on introduction to frameworks and containers. Brought to you in partnership with Red Hat.

The EJB @Schedule annotation comes in handy in case you need to create timers automatically. One can use cron-like expression to configure the appropriate schedule. If you need more flexibility, the good old TimerService works like a charm.

Quick background

  • The TimerService interface was Introduced in EJB 2.1 [yeah .. J2EE days ! ;-) ]
  • Used to create Timer objects programmatically
  • Used to work in conjunction with an implementation of the TimedObject interface [pre EJB 3.0] to serve as a call back for timer triggers
  • Since EJB 3.0, the @Timeout annotation was used to mark a method in a (stateless/singleton/message driven) bean to act as the receiver of timer call backs from the EBJ container
  • Things were further improved in EJB 3.1 with the introduction of ScheduleExpression which allowed fine grained timer scheduling – this was the programmatic equivalent of @Schedule

EJB Timer related components (for quick reference)

RESTful Timers

One can easily expose a simple RESTful interface to work with EJB Timers. Actions such as creating timers, fetching timer details as well cancelling timers can be executed on the fly.

A simple implementation is available via this Github project. It’s a simple Java EE 7 Maven project built on Netbeans. You should be able to set it up easily.

Here is a gist

  • POST a request to schedule a timer (JSON/XML payload representing the schedule configuration)

  • @POST
    @Consumes({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
    public Response schedule(@HeaderParam("name") final String timerName, final ScheduleConfiguration config) {
        auditScheduler.schedule(from(config), new TimerConfig(timerName, config.isPersistent()));
        return Response.created(UriBuilder.fromResource(AuditSchedulerResource.class).path(timerName).build(timerName)).build();
    }


  • GET all active timers and their respective details (JSON/XML representation)
  • @GET
    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
    public Response getAllTimers() {
        List<String> ejbTimers = auditScheduler.getAllTimers();
        List<ScheduledTimerInfo> timers = ejbTimers.stream().map((id) -> auditScheduler.getTimerInfo(id)).collect(Collectors.toList());
        GenericEntity<List<ScheduledTimerInfo>> entities = new GenericEntity<List<ScheduledTimerInfo>>(timers) {};
        return Response.ok(entities).build();
    }


  • GET information for a specific timer (JSON/XML representation)
  • @GET
    @Path("{id}")
    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
    public Response getTimerInfo(@PathParam("id") String name) {
        ScheduledTimerInfo info = auditScheduler.getTimerInfo(name);
        return Response.ok(info).build();
    }


  • DELETE (cancel) an existing timer
  • @DELETE
    @Path("{id}")
    public void cancel(@PathParam("id") String name) {
        auditScheduler.cancel(name);
    }


    The WADL should tell the story

    Image title



    Download Building Reactive Microservices in Java: Asynchronous and Event-Based Application Design. Brought to you in partnership with Red Hat

    Topics:
    timer ,scheduling ,scheduler ,ejb ,rest ,timers ,java ee 7

    Published at DZone with permission of Abhishek Gupta, DZone MVB. See the original article here.

    Opinions expressed by DZone contributors are their own.

    THE DZONE NEWSLETTER

    Dev Resources & Solutions Straight to Your Inbox

    Thanks for subscribing!

    Awesome! Check your inbox to verify your email so you can start receiving the latest in tech news and resources.

    X

    {{ parent.title || parent.header.title}}

    {{ parent.tldr }}

    {{ parent.urlSource.name }}