/* * RHQ Management Platform * Copyright (C) 2005-2009 Red Hat, Inc. * All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation version 2 of the License. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ package org.rhq.plugins.twitter; import java.util.List; import java.util.Properties; import java.util.Set; import twitter4j.Paging; import twitter4j.Query; import twitter4j.QueryResult; import twitter4j.Status; import twitter4j.Tweet; import twitter4j.Twitter; import twitter4j.TwitterFactory; import twitter4j.conf.PropertyConfiguration; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.rhq.core.domain.configuration.Configuration; import org.rhq.core.domain.measurement.AvailabilityType; import org.rhq.core.domain.measurement.MeasurementDataNumeric; import org.rhq.core.domain.measurement.MeasurementReport; import org.rhq.core.domain.measurement.MeasurementScheduleRequest; import org.rhq.core.pluginapi.event.EventContext; import org.rhq.core.pluginapi.inventory.InvalidPluginConfigurationException; import org.rhq.core.pluginapi.inventory.ResourceComponent; import org.rhq.core.pluginapi.inventory.ResourceContext; import org.rhq.core.pluginapi.inventory.DeleteResourceFacet; import org.rhq.core.pluginapi.measurement.MeasurementFacet; /** * This class represents the resource component for one individual twitter * feed - meaning either a search or a users timeline. * * @author Heiko W. Rupp */ public class FeedComponent implements ResourceComponent<TwitterComponent>, MeasurementFacet, DeleteResourceFacet { private final Log log = LogFactory.getLog(this.getClass()); private static final long NOT_YET_SET = 1; public static final String TOPIC_EVENT = "FeedEvent"; // Same as in Plugin-Descriptor EventContext eventContext; private long lastId = NOT_YET_SET; private boolean isSearch = false; private String keyword; private TwitterEventPoller eventPoller; private TwitterFactory tFactory; /** * Return availability of this resource * @see org.rhq.core.pluginapi.inventory.ResourceComponent#getAvailability() */ public AvailabilityType getAvailability() { // TODO supply real implementation return AvailabilityType.UP; } /** * Start the resource connection * @see org.rhq.core.pluginapi.inventory.ResourceComponent#start(org.rhq.core.pluginapi.inventory.ResourceContext) */ public void start(ResourceContext<TwitterComponent> context) throws InvalidPluginConfigurationException, Exception { Configuration conf = context.getPluginConfiguration(); String kind = conf.getSimpleValue("kind","user"); if (kind.equals("search")) isSearch = true; keyword = conf.getSimpleValue("keyword","Jopr"); // Jopr is fallback .. just in case String serverUrl = context.getParentResourceComponent().getServerUrl(); String searchBase = context.getParentResourceComponent().getSearchUrl(); eventContext = context.getEventContext(); eventPoller = new TwitterEventPoller(TOPIC_EVENT); eventContext.registerEventPoller(eventPoller, 63); Properties props = new Properties(); //props.put(PropertyConfiguration.SOURCE,"Jopr"); props.put(PropertyConfiguration.HTTP_USER_AGENT,"Jopr"); props.put(PropertyConfiguration.SEARCH_BASE_URL, searchBase); props.put(PropertyConfiguration.REST_BASE_URL, serverUrl); twitter4j.conf.Configuration tconf = new PropertyConfiguration(props); tFactory = new TwitterFactory(tconf); } /** * Tear down the rescource connection * @see org.rhq.core.pluginapi.inventory.ResourceComponent#stop() */ public void stop() { eventContext.unregisterEventPoller(TOPIC_EVENT); } /** * Gather measurement data * @see org.rhq.core.pluginapi.measurement.MeasurementFacet#getValues(org.rhq.core.domain.measurement.MeasurementReport, java.util.Set) */ public void getValues(MeasurementReport report, Set<MeasurementScheduleRequest> metrics) throws Exception { for (MeasurementScheduleRequest req : metrics) { if (req.getName().equals("tweetCount")) { Twitter twitter = tFactory.getInstance(); Paging paging = new Paging(); MeasurementDataNumeric res; if (isSearch) { Query q = new Query(keyword); q.setSinceId(lastId); if (lastId == NOT_YET_SET) q.setRpp(1); else q.setRpp(20); QueryResult qr = twitter.search(q); List<Tweet> tweets = qr.getTweets(); res = new MeasurementDataNumeric(req, (double) tweets.size()); eventPoller.addTweets(tweets); if (tweets.size()>0) lastId = tweets.get(0).getId(); } else { List<Status> statuses; if (lastId == NOT_YET_SET) { paging.setCount(1); } else { paging.setCount(100); } paging.setSinceId(lastId); statuses = twitter.getUserTimeline(keyword,paging); res = new MeasurementDataNumeric(req, (double) statuses.size()); eventPoller.addStatuses(statuses); if (statuses.size()>0) lastId = statuses.get(0).getId(); } report.addData(res); } } } /** * Used to uninventoy children -- this is not really * deleting physical resources and so nothing really to do. * @throws Exception */ public void deleteResource() throws Exception { log.info("deleteResouces called"); } }