001package org.gbif.api.util.iterables;
002
003import org.gbif.api.model.common.paging.PagingConstants;
004import org.gbif.api.model.registry.Dataset;
005import org.gbif.api.model.registry.Node;
006import org.gbif.api.model.registry.Organization;
007import org.gbif.api.service.registry.DatasetService;
008import org.gbif.api.service.registry.InstallationService;
009import org.gbif.api.service.registry.NetworkService;
010import org.gbif.api.service.registry.NodeService;
011import org.gbif.api.service.registry.OrganizationService;
012import org.gbif.api.vocabulary.Country;
013import org.gbif.api.vocabulary.DatasetType;
014
015import java.util.UUID;
016import javax.annotation.Nullable;
017
018import com.google.common.collect.ImmutableList;
019import org.slf4j.Logger;
020import org.slf4j.LoggerFactory;
021
022/**
023 * Factory constructing registry entity iterables using specific pagers under the hood.
024 */
025public class Iterables {
026    private static final Logger LOG = LoggerFactory.getLogger(Iterables.class);
027
028    /**
029     * Private default constructor.
030     */
031    private Iterables() {
032        //empty private constructor
033    }
034
035    /**
036     * @param key a valid dataset, organization or installation key. If null all datasets will be iterated over
037     * @throws IllegalArgumentException if given key is not existing
038     */
039    public static Iterable<Dataset> datasets(@Nullable UUID key, @Nullable DatasetType type,
040                                             DatasetService ds, OrganizationService os, InstallationService is,
041                                             NetworkService ns, NodeService nos) {
042        return datasets(key, type, ds, os, is, ns, nos, PagingConstants.DEFAULT_PARAM_LIMIT);
043    }
044
045    /**
046     * Returns a dataset iterable by testing the given registry key first to see whether it is a dataset, organization or installation.
047     * In case of an organization key the published datasets will be returned.
048     *
049     * @param key a valid dataset, organization or installation key. If null all datasets will be iterated over
050     * @param pageSize to use when talking to the registry
051     * @throws IllegalArgumentException if given key is not existing
052     */
053    public static Iterable<Dataset> datasets(@Nullable UUID key, @Nullable DatasetType type,
054                                             DatasetService ds, OrganizationService os, InstallationService is,
055                                             NetworkService ns, NodeService nos, int pageSize) {
056        if (key == null) {
057            LOG.info("Iterate over all {} datasets", type == null ? "" : type);
058            return new DatasetPager(ds, type, pageSize);
059
060        } else if (isDataset(key, ds)) {
061            LOG.info("Iterate over dataset {}", key);
062            return ImmutableList.of(ds.get(key));
063
064        } else if (isOrganization(key, os)) {
065            LOG.info("Iterate over all {} datasets published by {}", type == null ? "" : type, key);
066            return new OrgPublishingPager(os, key, type, pageSize);
067
068        } else if (isInstallation(key, is)) {
069            LOG.info("Iterate over all {} datasets hosted by installation {}", type == null ? "" : type, key);
070            return new InstallationPager(is, key, type, pageSize);
071
072        } else if (isNode(key, nos)) {
073            LOG.info("Iterate over all {} datasets endorsed by node {}", type == null ? "" : type, key);
074            return new NetworkPager(ns, key, type, pageSize);
075
076        } else if (isNetwork(key, ns)) {
077            LOG.info("Iterate over all {} datasets belonging to network {}", type == null ? "" : type, key);
078            return new NodeDatasetPager(nos, key, type, pageSize);
079        }
080        throw new IllegalArgumentException("Given key is no valid GBIF registry key: " + key);
081    }
082
083    /**
084     * @param type an optional filter to just include the given dataset type
085     */
086    public static Iterable<Dataset> datasets(@Nullable DatasetType type, DatasetService service) {
087        LOG.info("Iterate over all {} datasets", type == null ? "" : type);
088        return new DatasetPager(service, type, PagingConstants.DEFAULT_PARAM_LIMIT);
089    }
090
091    /**
092     * @param key a valid organization key
093     * @param type an optional filter to just include the given dataset type
094     */
095    public static Iterable<Dataset> publishedDatasets(UUID key, @Nullable DatasetType type, OrganizationService service) {
096        LOG.info("Iterate over all {} datasets published by {}", type == null ? "" : type, key);
097        return new OrgPublishingPager(service, key, type, PagingConstants.DEFAULT_PARAM_LIMIT);
098    }
099
100    /**
101     * @param key a valid organization key
102     * @param type an optional filter to just include the given dataset type
103     */
104    public static Iterable<Dataset> hostedDatasets(UUID key, @Nullable DatasetType type, OrganizationService service) {
105        LOG.info("Iterate over all {} datasets hosted by organization {}", type == null ? "" : type, key);
106        return new OrgHostingPager(service, key, type, PagingConstants.DEFAULT_PARAM_LIMIT);
107    }
108
109    /**
110     * @param key a valid installation key
111     * @param type an optional filter to just include the given dataset type
112     */
113    public static Iterable<Dataset> hostedDatasets(UUID key, @Nullable DatasetType type, InstallationService service) {
114        LOG.info("Iterate over all {} datasets hosted by installation {}", type == null ? "" : type, key);
115        return new InstallationPager(service, key, type, PagingConstants.DEFAULT_PARAM_LIMIT);
116    }
117
118    /**
119     * @param key a valid dataset key
120     */
121    public static Iterable<Dataset> constituentDatasets(UUID key, DatasetService service) {
122        LOG.info("Iterate over all constituent datasets of {}", key);
123        return new DatasetConstituentPager(service, key, PagingConstants.DEFAULT_PARAM_LIMIT);
124    }
125
126    /**
127     * Iterates over all constituents of a given network.
128     * @param key a valid network key
129     * @param type an optional filter to just include the given dataset type
130     */
131    public static Iterable<Dataset> networkDatasets(UUID key, @Nullable DatasetType type, NetworkService service) {
132        LOG.info("Iterate over all {} datasets belonging to network {}", type == null ? "" : type, key);
133        return new NetworkPager(service, key, type, PagingConstants.DEFAULT_PARAM_LIMIT);
134    }
135
136    /**
137     * @param nodeKey a valid endorsing node key
138     * @param type an optional filter to just include the given dataset type
139     */
140    public static Iterable<Dataset> endorsedDatasets(UUID nodeKey, @Nullable DatasetType type, NodeService service) {
141        LOG.info("Iterate over all {} datasets endorsed by node {}", type == null ? "" : type, nodeKey);
142        return new NodeDatasetPager(service, nodeKey, type, PagingConstants.DEFAULT_PARAM_LIMIT);
143    }
144
145    /**
146     * @param country an optional country filter
147     */
148    public static Iterable<Organization> organizations(@Nullable Country country, OrganizationService service) {
149        LOG.info("Iterate over all organizations {}", country == null ? "" : "from country "+country);
150        return new OrganizationPager(service, country, PagingConstants.DEFAULT_PARAM_LIMIT);
151    }
152
153    /**
154     * @param nodeKey a valid endorsing node key
155     */
156    public static Iterable<Organization> endorsedOrganizations(UUID nodeKey, NodeService service) {
157        LOG.info("Iterate over all organizations endorsed by node {}", nodeKey);
158        return new NodeOrganizationPager(service, nodeKey, PagingConstants.DEFAULT_PARAM_LIMIT);
159    }
160
161    /**
162     * Iterate over all endorsing nodes
163     */
164    public static Iterable<Node> nodes(NodeService service) {
165        LOG.info("Iterate over all nodes");
166        return new NodePager(service, PagingConstants.DEFAULT_PARAM_LIMIT);
167    }
168
169    private static boolean isDataset(UUID key, DatasetService ds) {
170        return ds.get(key) != null;
171    }
172
173    private static boolean isOrganization(UUID key, OrganizationService os) {
174        return os.get(key) != null;
175    }
176
177    private static boolean isInstallation(UUID key, InstallationService is) {
178        return is.get(key) != null;
179    }
180
181    private static boolean isNetwork(UUID key, NetworkService ns) {
182        return ns.get(key) != null;
183    }
184
185    private static boolean isNode(UUID key, NodeService ns) {
186        return ns.get(key) != null;
187    }
188}