2014-08-08 16:49:02 +02:00
|
|
|
package com.commafeed.frontend.resource;
|
|
|
|
|
|
|
|
|
|
import io.dropwizard.hibernate.UnitOfWork;
|
2013-05-20 14:06:09 +02:00
|
|
|
|
2013-06-25 16:57:48 +02:00
|
|
|
import java.util.Date;
|
2013-05-20 14:06:09 +02:00
|
|
|
import java.util.List;
|
|
|
|
|
|
2014-08-17 14:16:30 +02:00
|
|
|
import javax.inject.Inject;
|
|
|
|
|
import javax.inject.Singleton;
|
2013-05-20 14:06:09 +02:00
|
|
|
import javax.servlet.http.HttpServletRequest;
|
|
|
|
|
import javax.ws.rs.Consumes;
|
|
|
|
|
import javax.ws.rs.GET;
|
|
|
|
|
import javax.ws.rs.POST;
|
|
|
|
|
import javax.ws.rs.Path;
|
|
|
|
|
import javax.ws.rs.Produces;
|
|
|
|
|
import javax.ws.rs.QueryParam;
|
|
|
|
|
import javax.ws.rs.core.Context;
|
|
|
|
|
import javax.ws.rs.core.MediaType;
|
|
|
|
|
import javax.ws.rs.core.Response;
|
|
|
|
|
import javax.ws.rs.core.Response.Status;
|
|
|
|
|
|
2014-08-08 16:49:02 +02:00
|
|
|
import lombok.RequiredArgsConstructor;
|
2013-08-11 11:45:32 +02:00
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
import org.apache.commons.io.IOUtils;
|
2014-10-28 16:36:09 +01:00
|
|
|
import org.apache.commons.lang3.ArrayUtils;
|
|
|
|
|
import org.apache.commons.lang3.StringUtils;
|
2013-05-20 14:06:09 +02:00
|
|
|
|
2013-08-18 16:29:07 +02:00
|
|
|
import com.codahale.metrics.MetricRegistry;
|
2014-08-08 16:49:02 +02:00
|
|
|
import com.commafeed.CommaFeedConfiguration;
|
2013-06-05 21:50:26 +02:00
|
|
|
import com.commafeed.backend.dao.FeedDAO;
|
2014-08-08 16:49:02 +02:00
|
|
|
import com.commafeed.backend.feed.FeedParser;
|
|
|
|
|
import com.commafeed.backend.feed.FeedQueues;
|
|
|
|
|
import com.commafeed.backend.feed.FetchedFeed;
|
2013-05-20 14:06:09 +02:00
|
|
|
import com.commafeed.backend.model.Feed;
|
2013-08-01 13:35:04 +02:00
|
|
|
import com.google.common.base.Preconditions;
|
2013-05-20 14:06:09 +02:00
|
|
|
|
|
|
|
|
@Path("/push")
|
2013-08-11 11:45:32 +02:00
|
|
|
@Slf4j
|
2014-08-17 14:16:30 +02:00
|
|
|
@RequiredArgsConstructor(onConstructor = @__({ @Inject }))
|
|
|
|
|
@Singleton
|
2014-08-08 16:49:02 +02:00
|
|
|
public class PubSubHubbubCallbackREST {
|
2013-05-20 14:06:09 +02:00
|
|
|
|
|
|
|
|
@Context
|
2013-08-01 13:35:04 +02:00
|
|
|
private HttpServletRequest request;
|
2013-05-20 14:06:09 +02:00
|
|
|
|
2014-08-08 16:49:02 +02:00
|
|
|
private final FeedDAO feedDAO;
|
|
|
|
|
private final FeedParser parser;
|
|
|
|
|
private final FeedQueues queues;
|
|
|
|
|
private final CommaFeedConfiguration config;
|
|
|
|
|
private final MetricRegistry metricRegistry;
|
2013-06-27 09:50:11 +02:00
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
@Path("/callback")
|
|
|
|
|
@GET
|
2014-08-08 16:49:02 +02:00
|
|
|
@UnitOfWork
|
2013-05-20 14:06:09 +02:00
|
|
|
@Produces(MediaType.TEXT_PLAIN)
|
2013-07-25 09:17:33 +02:00
|
|
|
public Response verify(@QueryParam("hub.mode") String mode, @QueryParam("hub.topic") String topic,
|
|
|
|
|
@QueryParam("hub.challenge") String challenge, @QueryParam("hub.lease_seconds") String leaseSeconds,
|
2013-05-20 14:06:09 +02:00
|
|
|
@QueryParam("hub.verify_token") String verifyToken) {
|
2014-12-04 10:52:41 +01:00
|
|
|
if (!config.getApplicationSettings().getPubsubhubbub()) {
|
2013-07-05 18:33:39 +02:00
|
|
|
return Response.status(Status.FORBIDDEN).entity("pubsubhubbub is disabled").build();
|
|
|
|
|
}
|
2013-06-27 09:50:11 +02:00
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
Preconditions.checkArgument(StringUtils.isNotEmpty(topic));
|
|
|
|
|
Preconditions.checkArgument("subscribe".equals(mode));
|
|
|
|
|
|
2013-05-21 14:44:55 +02:00
|
|
|
log.debug("confirmation callback received for {}", topic);
|
2013-05-20 14:06:09 +02:00
|
|
|
|
2013-06-05 21:50:26 +02:00
|
|
|
List<Feed> feeds = feedDAO.findByTopic(topic);
|
2013-05-20 14:06:09 +02:00
|
|
|
|
2013-06-08 17:15:44 +02:00
|
|
|
if (feeds.isEmpty() == false) {
|
2013-06-05 21:50:26 +02:00
|
|
|
for (Feed feed : feeds) {
|
2013-07-25 09:17:33 +02:00
|
|
|
log.debug("activated push notifications for {}", feed.getPushTopic());
|
2013-06-25 16:57:48 +02:00
|
|
|
feed.setPushLastPing(new Date());
|
2013-05-20 14:06:09 +02:00
|
|
|
}
|
2013-06-06 09:54:17 +02:00
|
|
|
feedDAO.saveOrUpdate(feeds);
|
2013-05-20 14:06:09 +02:00
|
|
|
return Response.ok(challenge).build();
|
|
|
|
|
} else {
|
2013-05-22 14:03:54 +02:00
|
|
|
log.debug("rejecting callback: no push info for {}", topic);
|
2013-05-20 14:06:09 +02:00
|
|
|
return Response.status(Status.NOT_FOUND).build();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@Path("/callback")
|
|
|
|
|
@POST
|
2014-08-08 16:49:02 +02:00
|
|
|
@UnitOfWork
|
2013-05-20 14:06:09 +02:00
|
|
|
@Consumes({ MediaType.APPLICATION_ATOM_XML, "application/rss+xml" })
|
|
|
|
|
public Response callback() {
|
2013-08-01 11:17:45 +02:00
|
|
|
|
2014-12-04 10:52:41 +01:00
|
|
|
if (!config.getApplicationSettings().getPubsubhubbub()) {
|
2013-07-05 18:33:39 +02:00
|
|
|
return Response.status(Status.FORBIDDEN).entity("pubsubhubbub is disabled").build();
|
|
|
|
|
}
|
2013-08-01 11:17:45 +02:00
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
try {
|
|
|
|
|
byte[] bytes = IOUtils.toByteArray(request.getInputStream());
|
2013-08-01 11:17:45 +02:00
|
|
|
|
2013-07-29 12:21:46 +02:00
|
|
|
if (ArrayUtils.isEmpty(bytes)) {
|
|
|
|
|
return Response.status(Status.BAD_REQUEST).entity("empty body received").build();
|
|
|
|
|
}
|
2013-08-01 11:17:45 +02:00
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
FetchedFeed fetchedFeed = parser.parse(null, bytes);
|
2013-06-10 12:53:46 +02:00
|
|
|
String topic = fetchedFeed.getFeed().getPushTopic();
|
2013-07-29 12:21:46 +02:00
|
|
|
if (StringUtils.isBlank(topic)) {
|
|
|
|
|
return Response.status(Status.BAD_REQUEST).entity("empty topic received").build();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.debug("content callback received for {}", topic);
|
|
|
|
|
List<Feed> feeds = feedDAO.findByTopic(topic);
|
|
|
|
|
if (feeds.isEmpty()) {
|
|
|
|
|
return Response.status(Status.BAD_REQUEST).entity("no feeds found for that topic").build();
|
2013-05-20 14:06:09 +02:00
|
|
|
}
|
2013-07-29 12:21:46 +02:00
|
|
|
|
|
|
|
|
for (Feed feed : feeds) {
|
|
|
|
|
log.debug("pushing content to queue for {}", feed.getUrl());
|
2014-08-08 16:49:02 +02:00
|
|
|
queues.add(feed, false);
|
2013-07-29 12:21:46 +02:00
|
|
|
}
|
2014-08-08 16:49:02 +02:00
|
|
|
metricRegistry.meter(MetricRegistry.name(getClass(), "pushReceived")).mark();
|
2013-07-29 12:21:46 +02:00
|
|
|
|
2013-05-20 14:06:09 +02:00
|
|
|
} catch (Exception e) {
|
2013-05-22 21:56:22 +02:00
|
|
|
log.error("Could not parse pubsub callback: " + e.getMessage());
|
2013-05-20 14:06:09 +02:00
|
|
|
}
|
|
|
|
|
return Response.ok().build();
|
|
|
|
|
}
|
|
|
|
|
}
|