Package mashup.fm.github

Source Code of mashup.fm.github.GithubService

/**
* Copyright 2011 The Apache Software Foundation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* @author Felipe Oliveira (http://mashup.fm)
*
*/
package mashup.fm.github;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;

import mashup.fm.github.comparator.CoderImpactComparator;
import mashup.fm.github.schema.CoderImpact;
import mashup.fm.github.schema.Commit;
import mashup.fm.github.schema.Repository;
import mashup.fm.github.schema.User;
import models.SearchHistory;

import org.apache.commons.lang.StringUtils;

import play.Logger;
import play.cache.Cache;
import util.ExceptionUtil;

/**
* The Class GithubClient.
*/
@Path("/github")
public class GithubService extends BaseService {

  /** The Constant searchPattern. */
  protected static final String searchPattern = "http://github.com/api/v2/json/repos/search/%s?start_page=%s";

  /** The Constant commitsPattern. */
  protected static final String commitsPattern = "http://github.com/api/v2/json/commits/list/%s/%s/master?page=%s";

  /** The Constant treePattern. */
  protected static final String treePattern = "http://github.com/api/v2/json/tree/full/%s/%s/%s";

  /** The Constant userCheckPattern. */
  protected static final String userCheckPattern = "http://github.com/api/v2/json/user/show/%s";

  /** The Constant repositoryCheckPattern. */
  protected static final String repositoryCheckPattern = "http://github.com/api/v2/json/repos/show/%s/%s";

  /** The Constant contributorsCheckPattern. */
  protected static final String contributorsCheckPattern = "http://github.com/api/v2/json/repos/show/%s/%s/contributors";

  /** The Constant useCache. */
  protected static final boolean useCache = true;

  /** The Constant cacheExpiration. */
  protected static final String cacheExpiration = "2h";

  /**
   * Repository.
   *
   * @param user
   *            the user
   * @param repository
   *            the repository
   * @return the json object
   */
  @GET
  @Path("/repository/{user}/{repository}")
  @Produces("application/json")
  public Repository repository(@PathParam("user") String user, @PathParam("repository") String repository) {
    // Check Input
    this.checkInputParam("user", user);
    this.checkInputParam("repository", repository);

    // Check Cache If Needed
    String cacheKey = "repository_" + user + "_" + repository;
    try {
      if (useCache) {
        Repository cachedObject = Cache.get(cacheKey, Repository.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Cache Not Found - Hit Remote Service
    Repository results = asObject(Repository.class, "repository", repositoryCheckPattern, user, repository);

    // Set Cache
    try {
      Cache.set(cacheKey, results, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return Results
    return results;
  }

  /**
   * User.
   *
   * @param user
   *            the user
   * @return the json object
   */
  @GET
  @Path("/user/{user}")
  @Produces("application/json")
  public User user(@PathParam("user") String user) {
    // Check Input
    this.checkInputParam("user", user);

    // Check Cache If Needed
    String cacheKey = "user_" + user;
    try {
      if (useCache) {
        User cachedObject = Cache.get(cacheKey, User.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Cache Not Found - Hit Remote Service
    User results = asObject(User.class, "user", userCheckPattern, user);

    // Set Cache
    try {
      Cache.set(cacheKey, results, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return Results
    return results;
  }

  /**
   * Search.
   *
   * @param q
   *            the q
   * @return the json array
   */
  @GET
  @Path("/search/{q}/{startPage}")
  @Produces("application/json")
  public List<Repository> search(@PathParam("q") String q, @PathParam("startPage") int startPage) {
    // Check Input
    this.checkInputParam("q", q);

    // Make sure page index starts with 1 (required by Github API)
    if (startPage < 1) {
      startPage = 1;
    }

    // Check Cache If Needed
    String cacheKey = "search_" + q + "_" + startPage;
    try {
      if (useCache) {
        List<Repository> cachedObject = Cache.get(cacheKey, List.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Cache Not Found - Hit Remote Service
    List<Repository> results = asArray(Repository.class, "repositories", searchPattern, q, String.valueOf(startPage));

    // Set Cache
    try {
      Cache.set(cacheKey, results, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Save Search
    try {
      this.saveSearchHistory(q);
    } catch (Throwable t) {
      // We don't want application failing because search history doesn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return Results
    return results;
  }

  /**
   * Coder impact.
   *
   * @param user
   *            the user
   * @param repository
   *            the repository
   * @return the map
   */
  @GET
  @Path("/repository/{user}/{repository}/coderImpacts")
  @Produces("application/json")
  public List<CoderImpact> coderImpacts(@PathParam("user") String user, @PathParam("repository") String repository) {
    // Check Input
    this.checkInputParam("user", user);
    this.checkInputParam("repository", repository);

    // Check Cache If Needed
    String cacheKey = "coderImpacts_" + user + "_" + repository;
    try {
      if (useCache) {
        List<CoderImpact> cachedObject = Cache.get(cacheKey, List.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Init map that will hold temporary values
    Map<String, Integer> map = new HashMap<String, Integer>();

    // Get last 100 commits
    List<Commit> commits = this.commits(user, repository);

    // Check list
    int max = 100;
    int count = 0;
    if ((commits != null) && (commits.size() > 0)) {
      // Loop on each commit
      for (Commit c : commits) {
        // Add Count
        count++;

        // If the map doesn't have an entry for the author, create one
        // with a zero value
        if (map.containsKey(c.getAuthor().getLogin()) == false) {
          map.put(c.getAuthor().getLogin(), 0);
        }

        // Add commit entry for the author
        Integer i = map.get(c.getAuthor().getLogin());
        i++;

        // Store value on temporary map
        map.put(c.getAuthor().getLogin(), i);

        // Check Max
        if (count == max) {
          break;
        }
      }
    }

    // Wrap values in list of impact
    List<CoderImpact> list = new ArrayList<CoderImpact>();
    for (Map.Entry<String, Integer> e : map.entrySet()) {
      list.add(new CoderImpact(e.getKey(), e.getValue(), count));
    }

    // Sort
    Collections.sort(list, new CoderImpactComparator());

    // Set Cache
    try {
      Cache.set(cacheKey, list, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return list
    return list;
  }

  /**
   * Commits.
   *
   * @param user
   *            the user
   * @param repository
   *            the repository
   * @return the json array
   */
  @GET
  @Path("/repository/{user}/{repository}/commits")
  @Produces("application/json")
  public List<Commit> commits(@PathParam("user") String user, @PathParam("repository") String repository) {
    // Check Input
    this.checkInputParam("user", user);
    this.checkInputParam("repository", repository);

    // Check Cache If Needed
    String cacheKey = "repository_commits_" + user + "_" + repository;
    try {
      if (useCache) {
        List<Commit> cachedObject = Cache.get(cacheKey, List.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Cache Not Found - Hit Remote Service
    List<Commit> results = new ArrayList<Commit>();
    Integer page = 1;
    while (results.size() < 100) {
      try {
        List<Commit> cs = asArray(Commit.class, "commits", commitsPattern, user, repository, String.valueOf(page));
        if ((cs != null) && (cs.size() > 0)) {
          results.addAll(cs);
        } else {
          break;
        }
      } catch (Throwable t) {
        Logger.warn(ExceptionUtil.getStackTrace(t));
        break;
      }
      page++;
    }

    // Set Cache
    try {
      Cache.set(cacheKey, results, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return Results
    return results;
  }

  /**
   * Contributors.
   *
   * @param user
   *            the user
   * @param repository
   *            the repository
   * @return the json array
   */
  @GET
  @Path("/repository/{user}/{repository}/contributors")
  @Produces("application/json")
  public List<User> contributors(@PathParam("user") String user, @PathParam("repository") String repository) {
    // Check Cache If Needed
    String cacheKey = "contributors_" + user + "_" + repository;
    try {
      if (useCache) {
        List<User> cachedObject = Cache.get(cacheKey, List.class);
        if (cachedObject != null) {
          return cachedObject;
        }
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Cache Remote Service - Hit Remote Services
    List<User> results = asArray(User.class, "contributors", contributorsCheckPattern, user, repository);

    // Set Cache
    try {
      Cache.set(cacheKey, results, cacheExpiration);
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }

    // Return Results
    return results;
  }

  /**
   * Latest searches.
   *
   * @return the list
   */
  public List<SearchHistory> latestSearches() {
    List<SearchHistory> list = new ArrayList<SearchHistory>();
    try {
      List<SearchHistory> data = SearchHistory.find("order by date desc").fetch(20);
      if (data != null) {
        list = data;
      }
    } catch (Throwable t) {
      // We don't want application failing because cache lookup didn't
      // work
      Logger.error(ExceptionUtil.getStackTrace(t));
    }
    return list;
  }

  /**
   * Save search history.
   *
   * @param searchTerm
   *            the search term
   */
  protected void saveSearchHistory(String searchTerm) {
    if (StringUtils.isNotBlank(searchTerm)) {
      SearchHistory s = new SearchHistory();
      s.date = new Date();
      s.searchTerm = searchTerm;
      s.save();
    } else {
      Logger.warn("Cannot save search history for invalid term: %s", searchTerm);
    }
  }
}
TOP

Related Classes of mashup.fm.github.GithubService

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.