com.jdroid.github.service.RepositoryService Maven / Gradle / Ivy
/*******************************************************************************
* Copyright (c) 2011 GitHub Inc.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Kevin Sawicki (GitHub Inc.) - initial API and implementation
*******************************************************************************/
package com.jdroid.github.service;
import static com.jdroid.github.client.IGitHubConstants.CHARSET_UTF8;
import static com.jdroid.github.client.IGitHubConstants.PARAM_LANGUAGE;
import static com.jdroid.github.client.IGitHubConstants.PARAM_START_PAGE;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_BRANCHES;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_CONTRIBUTORS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_FORKS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_HOOKS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_LANGUAGES;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_LEGACY;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_ORGS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_REPOS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_REPOSITORIES;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_SEARCH;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_TAGS;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_TEST;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_USER;
import static com.jdroid.github.client.IGitHubConstants.SEGMENT_USERS;
import static com.jdroid.github.client.PagedRequest.PAGE_FIRST;
import static com.jdroid.github.client.PagedRequest.PAGE_SIZE;
import com.google.gson.reflect.TypeToken;
import java.io.IOException;
import java.net.URLEncoder;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import com.jdroid.github.Contributor;
import com.jdroid.github.IRepositoryIdProvider;
import com.jdroid.github.IResourceProvider;
import com.jdroid.github.Repository;
import com.jdroid.github.RepositoryBranch;
import com.jdroid.github.RepositoryHook;
import com.jdroid.github.RepositoryId;
import com.jdroid.github.RepositoryTag;
import com.jdroid.github.SearchRepository;
import com.jdroid.github.client.GitHubClient;
import com.jdroid.github.client.GitHubRequest;
import com.jdroid.github.client.PageIterator;
import com.jdroid.github.client.PagedRequest;
/**
* Repository service class.
*
* @see GitHub repository API
* documentation
* @see GitHub forks API
* documentation
*/
public class RepositoryService extends GitHubService {
/**
* FIELD_NAME
*/
public static final String FIELD_NAME = "name"; //$NON-NLS-1$
/**
* FIELD_DESCRIPTION
*/
public static final String FIELD_DESCRIPTION = "description"; //$NON-NLS-1$
/**
* FIELD_HOMEPAGE
*/
public static final String FIELD_HOMEPAGE = "homepage"; //$NON-NLS-1$
/**
* FIELD_PUBLIC
*/
public static final String FIELD_PUBLIC = "public"; //$NON-NLS-1$
/**
* Type filter key
*/
public static final String FILTER_TYPE = "type"; //$NON-NLS-1$
/**
* Public repository filter type
*/
public static final String TYPE_PUBLIC = "public"; //$NON-NLS-1$
/**
* Private repository filter type
*/
public static final String TYPE_PRIVATE = "private"; //$NON-NLS-1$
/**
* Member repository filter type
*/
public static final String TYPE_MEMBER = "member"; //$NON-NLS-1$
/**
* All repositories filter type
*/
public static final String TYPE_ALL = "all"; //$NON-NLS-1$
private static class RepositoryContainer implements
IResourceProvider {
private List repositories;
/**
* @see IResourceProvider#getResources()
*/
public List getResources() {
return repositories;
}
}
/**
* Create repository service
*/
public RepositoryService() {
super();
}
/**
* Create repository service
*
* @param client
* cannot be null
*/
public RepositoryService(GitHubClient client) {
super(client);
}
/**
* Get repositories for the currently authenticated user
*
* @return list of repositories
* @throws IOException
*/
public List getRepositories() throws IOException {
return getRepositories((Map) null);
}
/**
* Get repositories for the currently authenticated user
*
* @param filterData
* @return list of repositories
* @throws IOException
*/
public List getRepositories(Map filterData)
throws IOException {
return getAll(pageRepositories(filterData));
}
/**
* Page repositories for currently authenticated user
*
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories() {
return pageRepositories(PAGE_SIZE);
}
/**
* Page repositories for currently authenticated user
*
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(int size) {
return pageRepositories(PAGE_FIRST, size);
}
/**
* Page repositories for currently authenticated user
*
* @param start
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(int start, int size) {
return pageRepositories((Map) null, start, size);
}
/**
* Page repositories for currently authenticated user
*
* @param filterData
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(
Map filterData) {
return pageRepositories(filterData, PAGE_SIZE);
}
/**
* Page repositories for currently authenticated user
*
* @param filterData
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(
Map filterData, int size) {
return pageRepositories(filterData, PAGE_FIRST, size);
}
/**
* Page repositories for currently authenticated user
*
* @param filterData
* @param start
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(
Map filterData, int start, int size) {
PagedRequest request = createPagedRequest(start, size);
request.setUri(SEGMENT_USER + SEGMENT_REPOS);
request.setParams(filterData);
request.setType(new TypeToken>() {
}.getType());
return createPageIterator(request);
}
/**
* Page all repositories
*
* @return iterator over pages of repositories
*/
public PageIterator pageAllRepositories() {
return pageAllRepositories(-1);
}
/**
* Page all repositories
*
* @param since
* @return iterator over pages of repositories
*/
public PageIterator pageAllRepositories(final long since) {
PagedRequest request = createPagedRequest();
request.setUri(SEGMENT_REPOSITORIES);
if (since > 0)
request.setParams(Collections.singletonMap("since",
Long.toString(since)));
request.setType(new TypeToken>() {
}.getType());
return createPageIterator(request);
}
/**
* Get repositories for the given user
*
* @param user
* @return list of repositories
* @throws IOException
*/
public List getRepositories(String user) throws IOException {
return getAll(pageRepositories(user));
}
/**
* Page repositories for given user
*
* @param user
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(String user) {
return pageRepositories(user, PAGE_SIZE);
}
/**
* Page repositories for given user
*
* @param user
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageRepositories(String user, int size) {
return pageRepositories(user, PAGE_FIRST, size);
}
/**
* Page repositories for given user
*
* @param user
* @param start
* @param size
* @return iterator over repository page
*/
public PageIterator pageRepositories(String user, int start,
int size) {
if (user == null)
throw new IllegalArgumentException("User cannot be null"); //$NON-NLS-1$
if (user.length() == 0)
throw new IllegalArgumentException("User cannot be empty"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_USERS);
uri.append('/').append(user);
uri.append(SEGMENT_REPOS);
PagedRequest request = createPagedRequest(start, size);
request.setUri(uri);
request.setType(new TypeToken>() {
}.getType());
return createPageIterator(request);
}
/**
* Get organization repositories for the given organization
*
* @param organization
* @return list of repositories
* @throws IOException
*/
public List getOrgRepositories(String organization)
throws IOException {
return getOrgRepositories(organization, null);
}
/**
* Page repositories for the given organization
*
* @param organization
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization) {
return pageOrgRepositories(organization, PAGE_SIZE);
}
/**
* Page repositories for the given organization
*
* @param organization
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization,
int size) {
return pageOrgRepositories(organization, PAGE_FIRST, size);
}
/**
* Page repositories for the given organization
*
* @param organization
* @param start
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization,
int start, int size) {
return pageOrgRepositories(organization, null, start, size);
}
/**
* Get organization repositories for the given organization
*
* @param organization
* @param filterData
* @return list of repositories
* @throws IOException
*/
public List getOrgRepositories(String organization,
Map filterData) throws IOException {
return getAll(pageOrgRepositories(organization, filterData));
}
/**
* Page repositories for the given organization
*
* @param organization
* @param filterData
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization,
Map filterData) {
return pageOrgRepositories(organization, filterData, PAGE_SIZE);
}
/**
* Page repositories for the given organization
*
* @param organization
* @param filterData
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization,
Map filterData, int size) {
return pageOrgRepositories(organization, filterData, PAGE_FIRST, size);
}
/**
* Page repositories for the given organization
*
* @param organization
* @param filterData
* @param start
* @param size
* @return iterator over pages of repositories
*/
public PageIterator pageOrgRepositories(String organization,
Map filterData, int start, int size) {
if (organization == null)
throw new IllegalArgumentException("Organization cannot be null"); //$NON-NLS-1$
if (organization.length() == 0)
throw new IllegalArgumentException("Organization cannot be empty"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_ORGS);
uri.append('/').append(organization);
uri.append(SEGMENT_REPOS);
PagedRequest request = createPagedRequest(start, size);
request.setParams(filterData);
request.setUri(uri);
request.setType(new TypeToken>() {
}.getType());
return createPageIterator(request);
}
/**
* Search for repositories matching query.
*
* @param query
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(final String query)
throws IOException {
return searchRepositories(query, -1);
}
/**
* Search for repositories matching query.
*
* @param query
* @param startPage
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(final String query,
final int startPage) throws IOException {
return searchRepositories(query, null, startPage);
}
/**
* Search for repositories matching language and query.
*
* @param query
* @param language
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(final String query,
final String language) throws IOException {
return searchRepositories(query, language, -1);
}
/**
* Search for repositories matching language and query.
*
* @param query
* @param language
* @param startPage
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(final String query,
final String language, final int startPage) throws IOException {
if (query == null)
throw new IllegalArgumentException("Query cannot be null"); //$NON-NLS-1$
if (query.length() == 0)
throw new IllegalArgumentException("Query cannot be empty"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_LEGACY + SEGMENT_REPOS
+ SEGMENT_SEARCH);
final String encodedQuery = URLEncoder.encode(query, CHARSET_UTF8)
.replace("+", "%20") //$NON-NLS-1$ //$NON-NLS-2$
.replace(".", "%2E"); //$NON-NLS-1$ //$NON-NLS-2$
uri.append('/').append(encodedQuery);
PagedRequest request = createPagedRequest();
Map params = new HashMap(2, 1);
if (language != null && language.length() > 0)
params.put(PARAM_LANGUAGE, language);
if (startPage > 0)
params.put(PARAM_START_PAGE, Integer.toString(startPage));
if (!params.isEmpty())
request.setParams(params);
request.setUri(uri);
request.setType(RepositoryContainer.class);
return getAll(request);
}
/**
* Search for repositories matching search parameters.
*
* @param params
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(
final Map params) throws IOException {
return searchRepositories(params, -1);
}
/**
* Search for repositories matching search parameters.
*
* @param queryParams
* @param startPage
* @return list of repositories
* @throws IOException
*/
public List searchRepositories(
final Map queryParams, final int startPage)
throws IOException {
if (queryParams == null)
throw new IllegalArgumentException("Params cannot be null"); //$NON-NLS-1$
if (queryParams.isEmpty())
throw new IllegalArgumentException("Params cannot be empty"); //$NON-NLS-1$
StringBuilder query = new StringBuilder();
for (Entry param : queryParams.entrySet())
query.append(param.getKey()).append(':').append(param.getValue())
.append(' ');
return searchRepositories(query.toString(), startPage);
}
/**
* Create a new repository
*
* @param repository
* @return created repository
* @throws IOException
*/
public Repository createRepository(Repository repository)
throws IOException {
if (repository == null)
throw new IllegalArgumentException("Repository cannot be null"); //$NON-NLS-1$
return client.post(SEGMENT_USER + SEGMENT_REPOS, repository,
Repository.class);
}
/**
* Create a new repository
*
* @param organization
* @param repository
* @return created repository
* @throws IOException
*/
public Repository createRepository(String organization,
Repository repository) throws IOException {
if (organization == null)
throw new IllegalArgumentException("Organization cannot be null"); //$NON-NLS-1$
if (organization.length() == 0)
throw new IllegalArgumentException("Organization cannot be empty"); //$NON-NLS-1$
if (repository == null)
throw new IllegalArgumentException("Repository cannot be null"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_ORGS);
uri.append('/').append(organization);
uri.append(SEGMENT_REPOS);
return client.post(uri.toString(), repository, Repository.class);
}
/**
* Get repository
*
* @param owner
* @param name
* @return repository
* @throws IOException
*/
public Repository getRepository(final String owner, final String name)
throws IOException {
return getRepository(RepositoryId.create(owner, name));
}
/**
* Get repository
*
* @param provider
* @return repository
* @throws IOException
*/
public Repository getRepository(final IRepositoryIdProvider provider)
throws IOException {
final String id = getId(provider);
GitHubRequest request = createRequest();
request.setUri(SEGMENT_REPOS + '/' + id);
request.setType(Repository.class);
return (Repository) client.get(request).getBody();
}
/**
* Create paged request for iterating over repositories forks
*
* @param repository
* @param start
* @param size
* @return paged request
*/
protected PagedRequest createPagedForkRequest(
IRepositoryIdProvider repository, int start, int size) {
final String id = getId(repository);
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(id);
uri.append(SEGMENT_FORKS);
PagedRequest request = createPagedRequest(start, size);
request.setUri(uri);
request.setType(new TypeToken>() {
}.getType());
return request;
}
/**
* Get all the forks of the given repository
*
* @param repository
* @return non-null but possibly empty list of repository
* @throws IOException
*/
public List getForks(IRepositoryIdProvider repository)
throws IOException {
return getAll(pageForks(repository));
}
/**
* Page forks of given repository
*
* @param repository
* @return iterator over repositories
*/
public PageIterator pageForks(IRepositoryIdProvider repository) {
return pageForks(repository, PAGE_SIZE);
}
/**
* Page forks of given repository
*
* @param repository
* @param size
* @return iterator over repositories
*/
public PageIterator pageForks(IRepositoryIdProvider repository,
int size) {
return pageForks(repository, PAGE_FIRST, size);
}
/**
* Page forks of given repository
*
* @param repository
* @param start
* @param size
* @return iterator over repositories
*/
public PageIterator pageForks(IRepositoryIdProvider repository,
int start, int size) {
PagedRequest request = createPagedForkRequest(repository,
start, size);
return createPageIterator(request);
}
/**
* Edit given repository
*
* @param repository
* @return edited repository
* @throws IOException
*/
public Repository editRepository(Repository repository) throws IOException {
if (repository == null)
throw new IllegalArgumentException("Repository cannot be null"); //$NON-NLS-1$
final String repoId = getId(repository);
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(repoId);
return client.post(uri.toString(), repository, Repository.class);
}
/**
* Edit given fields in repository
*
* Only values in the given fields map will be updated on the repository
*
* @param owner
* @param name
* @param fields
* @return edited repository
* @throws IOException
*/
public Repository editRepository(String owner, String name,
Map fields) throws IOException {
verifyRepository(owner, name);
if (fields == null)
throw new IllegalArgumentException("Fields cannot be null"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(owner).append('/').append(name);
return client.post(uri.toString(), fields, Repository.class);
}
/**
* Edit given fields in repository
*
* Only values in the given fields map will be updated on the repository
*
* @param provider
* @param fields
* @return edited repository
* @throws IOException
*/
public Repository editRepository(IRepositoryIdProvider provider,
Map fields) throws IOException {
String id = getId(provider);
if (fields == null)
throw new IllegalArgumentException("Fields cannot be null"); //$NON-NLS-1$
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(id);
return client.post(uri.toString(), fields, Repository.class);
}
/**
* Fork given repository into new repository under the currently
* authenticated user.
*
* @param repository
* @return forked repository
* @throws IOException
*/
public Repository forkRepository(IRepositoryIdProvider repository)
throws IOException {
return forkRepository(repository, null);
}
/**
* Fork given repository into new repository.
*
* The new repository will be under the given organization if non-null, else
* it will be under the currently authenticated user.
*
* @param repository
* @param organization
* @return forked repository
* @throws IOException
*/
public Repository forkRepository(IRepositoryIdProvider repository,
String organization) throws IOException {
final String id = getId(repository);
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(id);
uri.append(SEGMENT_FORKS);
if (organization != null)
uri.append("?org=").append(organization);
return client.post(uri.toString(), null, Repository.class);
}
/**
* Get languages used in given repository
*
* @param repository
* @return map of language names mapped to line counts
* @throws IOException
*/
@SuppressWarnings({ "unchecked" })
public Map getLanguages(IRepositoryIdProvider repository)
throws IOException {
String id = getId(repository);
StringBuilder uri = new StringBuilder(SEGMENT_REPOS);
uri.append('/').append(id);
uri.append(SEGMENT_LANGUAGES);
GitHubRequest request = createRequest();
request.setUri(uri);
request.setType(new TypeToken