001/*
002 * Licensed under the Apache License, Version 2.0 (the "License");
003 * you may not use this file except in compliance with the License.
004 * You may obtain a copy of the License at
005 *
006 *     http://www.apache.org/licenses/LICENSE-2.0
007 *
008 * Unless required by applicable law or agreed to in writing, software
009 * distributed under the License is distributed on an "AS IS" BASIS,
010 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
011 * See the License for the specific language governing permissions and
012 * limitations under the License.
013 */
014package org.gbif.api.model.event.search;
015
016import com.fasterxml.jackson.annotation.*;
017import com.fasterxml.jackson.core.JacksonException;
018import com.fasterxml.jackson.databind.DeserializationContext;
019import com.fasterxml.jackson.databind.JsonDeserializer;
020import com.fasterxml.jackson.databind.KeyDeserializer;
021import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
022import com.fasterxml.jackson.databind.node.ObjectNode;
023import io.swagger.v3.oas.annotations.Hidden;
024import java.io.IOException;
025import java.io.Serializable;
026import java.lang.reflect.Field;
027import java.util.ArrayList;
028import java.util.List;
029import java.util.Objects;
030import java.util.Optional;
031import lombok.extern.slf4j.Slf4j;
032import org.gbif.api.annotation.Experimental;
033import org.gbif.api.model.common.search.SearchParameter;
034import org.gbif.api.model.occurrence.search.OccurrenceSearchParameter;
035import org.gbif.api.vocabulary.DurationUnit;
036import org.gbif.api.vocabulary.EventIssue;
037
038/**
039 * Supported query parameters by the occurrence search and download service. For download predicates
040 * only the numerical types support comparisons other than equals.
041 */
042@Slf4j
043@JsonDeserialize(
044    as = EventSearchParameter.class,
045    using = EventSearchParameter.EventSearchParameterDeserializer.class)
046public class EventSearchParameter implements SearchParameter, Serializable {
047
048  /** See @link {@link OccurrenceSearchParameter#DATASET_KEY} */
049  public static final EventSearchParameter DATASET_KEY =
050      new EventSearchParameter(OccurrenceSearchParameter.DATASET_KEY);
051
052  /** See @link {@link OccurrenceSearchParameter#CHECKLIST_KEY} */
053  public static final EventSearchParameter CHECKLIST_KEY =
054      new EventSearchParameter(OccurrenceSearchParameter.CHECKLIST_KEY);
055
056  /** See @link {@link OccurrenceSearchParameter#YEAR} */
057  public static final EventSearchParameter YEAR =
058      new EventSearchParameter(OccurrenceSearchParameter.YEAR);
059
060  /** See @link {@link OccurrenceSearchParameter#MONTH} */
061  public static final EventSearchParameter MONTH =
062      new EventSearchParameter(OccurrenceSearchParameter.MONTH);
063
064  /** See @link {@link OccurrenceSearchParameter#DAY} */
065  public static final EventSearchParameter DAY =
066      new EventSearchParameter(OccurrenceSearchParameter.DAY);
067
068  /** See @link {@link OccurrenceSearchParameter#START_DAY_OF_YEAR} */
069  public static final EventSearchParameter START_DAY_OF_YEAR =
070      new EventSearchParameter(OccurrenceSearchParameter.START_DAY_OF_YEAR);
071
072  /** See @link {@link OccurrenceSearchParameter#END_DAY_OF_YEAR} */
073  public static final EventSearchParameter END_DAY_OF_YEAR =
074      new EventSearchParameter(OccurrenceSearchParameter.END_DAY_OF_YEAR);
075
076  /** See @link {@link OccurrenceSearchParameter#EVENT_DATE} */
077  public static final EventSearchParameter EVENT_DATE =
078      new EventSearchParameter(OccurrenceSearchParameter.EVENT_DATE);
079
080  /**
081   * An identifier for the set of information associated with an Event (something that occurs at a
082   * place and time). Maybe a global unique identifier or an identifier specific to the data set.
083   *
084   * @link {@link OccurrenceSearchParameter#EVENT_ID}
085   */
086  public static final EventSearchParameter EVENT_ID =
087      new EventSearchParameter(OccurrenceSearchParameter.EVENT_ID);
088
089  /** See @link {@link OccurrenceSearchParameter#PARENT_EVENT_ID} */
090  public static final EventSearchParameter PARENT_EVENT_ID =
091      new EventSearchParameter(OccurrenceSearchParameter.PARENT_EVENT_ID);
092
093  /** See @link {@link OccurrenceSearchParameter#SAMPLING_PROTOCOL} */
094  public static final EventSearchParameter SAMPLING_PROTOCOL =
095      new EventSearchParameter(OccurrenceSearchParameter.SAMPLING_PROTOCOL);
096
097  /** See @link {@link OccurrenceSearchParameter#LAST_INTERPRETED} */
098  public static final EventSearchParameter LAST_INTERPRETED =
099      new EventSearchParameter(OccurrenceSearchParameter.LAST_INTERPRETED);
100
101  /** See @link {@link OccurrenceSearchParameter#MODIFIED} */
102  public static final EventSearchParameter MODIFIED =
103      new EventSearchParameter(OccurrenceSearchParameter.MODIFIED);
104
105  /** See @link {@link OccurrenceSearchParameter#DECIMAL_LATITUDE} */
106  public static final EventSearchParameter DECIMAL_LATITUDE =
107      new EventSearchParameter(OccurrenceSearchParameter.DECIMAL_LATITUDE);
108
109  /** See @link {@link OccurrenceSearchParameter#DECIMAL_LONGITUDE} */
110  public static final EventSearchParameter DECIMAL_LONGITUDE =
111      new EventSearchParameter(OccurrenceSearchParameter.DECIMAL_LONGITUDE);
112
113  /** See @link {@link OccurrenceSearchParameter#COORDINATE_UNCERTAINTY_IN_METERS} */
114  public static final EventSearchParameter COORDINATE_UNCERTAINTY_IN_METERS =
115      new EventSearchParameter(OccurrenceSearchParameter.COORDINATE_UNCERTAINTY_IN_METERS);
116
117  /** See @link {@link OccurrenceSearchParameter#COUNTRY} */
118  public static final EventSearchParameter COUNTRY =
119      new EventSearchParameter(OccurrenceSearchParameter.COUNTRY);
120
121  /** See @link {@link OccurrenceSearchParameter#GBIF_REGION} */
122  public static final EventSearchParameter GBIF_REGION =
123      new EventSearchParameter(OccurrenceSearchParameter.GBIF_REGION);
124
125  /** See @link {@link OccurrenceSearchParameter#CONTINENT} */
126  public static final EventSearchParameter CONTINENT =
127      new EventSearchParameter(OccurrenceSearchParameter.CONTINENT);
128
129  /** See @link {@link OccurrenceSearchParameter#PUBLISHING_COUNTRY} */
130  public static final EventSearchParameter PUBLISHING_COUNTRY =
131      new EventSearchParameter(OccurrenceSearchParameter.PUBLISHING_COUNTRY);
132
133  /** See @link {@link OccurrenceSearchParameter#PUBLISHED_BY_GBIF_REGION} */
134  public static final EventSearchParameter PUBLISHED_BY_GBIF_REGION =
135      new EventSearchParameter(OccurrenceSearchParameter.PUBLISHED_BY_GBIF_REGION);
136
137  /** See @link {@link OccurrenceSearchParameter#ELEVATION} */
138  public static final EventSearchParameter ELEVATION =
139      new EventSearchParameter(OccurrenceSearchParameter.ELEVATION);
140
141  /** See @link {@link OccurrenceSearchParameter#DEPTH} */
142  public static final EventSearchParameter DEPTH =
143      new EventSearchParameter(OccurrenceSearchParameter.DEPTH);
144
145  /** See @link {@link OccurrenceSearchParameter#INSTITUTION_CODE} */
146  public static final EventSearchParameter INSTITUTION_CODE =
147      new EventSearchParameter(OccurrenceSearchParameter.INSTITUTION_CODE);
148
149  /** See @link {@link OccurrenceSearchParameter#COLLECTION_CODE} */
150  public static final EventSearchParameter COLLECTION_CODE =
151    new EventSearchParameter(OccurrenceSearchParameter.COLLECTION_CODE);
152
153  /** See @link {@link OccurrenceSearchParameter#TAXON_KEY} */
154  public static final EventSearchParameter TAXON_KEY =
155      new EventSearchParameter(OccurrenceSearchParameter.TAXON_KEY);
156
157  /** See @link {@link OccurrenceSearchParameter#ACCEPTED_TAXON_KEY} */
158  public static final EventSearchParameter ACCEPTED_TAXON_KEY =
159      new EventSearchParameter(OccurrenceSearchParameter.ACCEPTED_TAXON_KEY);
160
161  /** See @link {@link OccurrenceSearchParameter#SCIENTIFIC_NAME} */
162  public static final EventSearchParameter SCIENTIFIC_NAME =
163      new EventSearchParameter(OccurrenceSearchParameter.SCIENTIFIC_NAME);
164
165  /** See @link {@link OccurrenceSearchParameter#TAXON_ID} */
166  public static final EventSearchParameter TAXON_ID =
167      new EventSearchParameter(OccurrenceSearchParameter.TAXON_ID);
168
169  /** See @link {@link OccurrenceSearchParameter#TAXONOMIC_STATUS} */
170  public static final EventSearchParameter TAXONOMIC_STATUS =
171      new EventSearchParameter(OccurrenceSearchParameter.TAXONOMIC_STATUS);
172
173  /** See @link {@link OccurrenceSearchParameter#TAXONOMIC_ISSUE} */
174  public static final EventSearchParameter TAXONOMIC_ISSUE =
175      new EventSearchParameter(OccurrenceSearchParameter.TAXONOMIC_ISSUE);
176
177  /** See @link {@link OccurrenceSearchParameter#IUCN_RED_LIST_CATEGORY} */
178  public static final EventSearchParameter IUCN_RED_LIST_CATEGORY =
179      new EventSearchParameter(OccurrenceSearchParameter.IUCN_RED_LIST_CATEGORY);
180
181  /** See @link {@link OccurrenceSearchParameter#HAS_COORDINATE} */
182  public static final EventSearchParameter HAS_COORDINATE =
183      new EventSearchParameter(OccurrenceSearchParameter.HAS_COORDINATE);
184
185  /** See @link {@link OccurrenceSearchParameter#GEOMETRY} */
186  public static final EventSearchParameter GEOMETRY =
187      new EventSearchParameter(OccurrenceSearchParameter.GEOMETRY);
188
189  /** See @link {@link OccurrenceSearchParameter#GEO_DISTANCE} */
190  public static final EventSearchParameter GEO_DISTANCE =
191      new EventSearchParameter(OccurrenceSearchParameter.GEO_DISTANCE);
192
193  /** See @link {@link OccurrenceSearchParameter#HAS_GEOSPATIAL_ISSUE} */
194  public static final EventSearchParameter HAS_GEOSPATIAL_ISSUE =
195      new EventSearchParameter(OccurrenceSearchParameter.HAS_GEOSPATIAL_ISSUE);
196
197  /** See @link {@link OccurrenceSearchParameter#MEDIA_TYPE} */
198  public static final EventSearchParameter MEDIA_TYPE =
199      new EventSearchParameter(OccurrenceSearchParameter.MEDIA_TYPE);
200
201  /** See @link {@link OccurrenceSearchParameter#REPATRIATED} */
202  public static final EventSearchParameter REPATRIATED =
203      new EventSearchParameter(OccurrenceSearchParameter.REPATRIATED);
204
205  /** See @link {@link OccurrenceSearchParameter#STATE_PROVINCE} */
206  public static final EventSearchParameter STATE_PROVINCE =
207      new EventSearchParameter(OccurrenceSearchParameter.STATE_PROVINCE);
208
209  /** See @link {@link OccurrenceSearchParameter#WATER_BODY} */
210  public static final EventSearchParameter WATER_BODY =
211      new EventSearchParameter(OccurrenceSearchParameter.WATER_BODY);
212
213  /** See @link {@link OccurrenceSearchParameter#LOCALITY} */
214  public static final EventSearchParameter LOCALITY =
215      new EventSearchParameter(OccurrenceSearchParameter.LOCALITY);
216
217  /** See @link {@link OccurrenceSearchParameter#PROTOCOL} */
218  public static final EventSearchParameter PROTOCOL =
219      new EventSearchParameter(OccurrenceSearchParameter.PROTOCOL);
220
221  /** See @link {@link OccurrenceSearchParameter#LICENSE} */
222  public static final EventSearchParameter LICENSE =
223      new EventSearchParameter(OccurrenceSearchParameter.LICENSE);
224
225  /** See @link {@link OccurrenceSearchParameter#PUBLISHING_ORG} */
226  public static final EventSearchParameter PUBLISHING_ORG =
227      new EventSearchParameter(OccurrenceSearchParameter.PUBLISHING_ORG);
228
229  /** See @link {@link OccurrenceSearchParameter#NETWORK_KEY} */
230  public static final EventSearchParameter NETWORK_KEY =
231      new EventSearchParameter(OccurrenceSearchParameter.NETWORK_KEY);
232
233  /** See @link {@link OccurrenceSearchParameter#DATASET_CATEGORY} */
234  public static final EventSearchParameter DATASET_CATEGORY =
235      new EventSearchParameter(OccurrenceSearchParameter.DATASET_CATEGORY);
236
237  /** See @link {@link OccurrenceSearchParameter#INSTALLATION_KEY} */
238  public static final EventSearchParameter INSTALLATION_KEY =
239      new EventSearchParameter(OccurrenceSearchParameter.INSTALLATION_KEY);
240
241  /** See @link {@link OccurrenceSearchParameter#HOSTING_ORGANIZATION_KEY} */
242  public static final EventSearchParameter HOSTING_ORGANIZATION_KEY =
243      new EventSearchParameter(OccurrenceSearchParameter.HOSTING_ORGANIZATION_KEY);
244
245  /** See @link {@link OccurrenceSearchParameter#CRAWL_ID} */
246  public static final EventSearchParameter CRAWL_ID =
247      new EventSearchParameter(OccurrenceSearchParameter.CRAWL_ID);
248
249  /** See @link {@link OccurrenceSearchParameter#PROGRAMME} */
250  public static final EventSearchParameter PROGRAMME =
251      new EventSearchParameter(OccurrenceSearchParameter.PROGRAMME);
252
253  /** See @link {@link OccurrenceSearchParameter#SAMPLE_SIZE_UNIT} */
254  public static final EventSearchParameter SAMPLE_SIZE_UNIT =
255      new EventSearchParameter(OccurrenceSearchParameter.SAMPLE_SIZE_UNIT);
256
257  /** See @link {@link OccurrenceSearchParameter#SAMPLE_SIZE_VALUE} */
258  public static final EventSearchParameter SAMPLE_SIZE_VALUE =
259      new EventSearchParameter(OccurrenceSearchParameter.SAMPLE_SIZE_VALUE);
260
261  /** See @link {@link OccurrenceSearchParameter#GADM_GID} */
262  public static final EventSearchParameter GADM_GID =
263      new EventSearchParameter(OccurrenceSearchParameter.GADM_GID);
264
265  /** See @link {@link OccurrenceSearchParameter#GADM_LEVEL_0_GID} */
266  public static final EventSearchParameter GADM_LEVEL_0_GID =
267      new EventSearchParameter(OccurrenceSearchParameter.GADM_LEVEL_0_GID);
268
269  /** See @link {@link OccurrenceSearchParameter#GADM_LEVEL_1_GID} */
270  public static final EventSearchParameter GADM_LEVEL_1_GID =
271      new EventSearchParameter(OccurrenceSearchParameter.GADM_LEVEL_1_GID);
272
273  /** See @link {@link OccurrenceSearchParameter#GADM_LEVEL_2_GID} */
274  public static final EventSearchParameter GADM_LEVEL_2_GID =
275      new EventSearchParameter(OccurrenceSearchParameter.GADM_LEVEL_2_GID);
276
277  /** See @link {@link OccurrenceSearchParameter#GADM_LEVEL_3_GID} */
278  public static final EventSearchParameter GADM_LEVEL_3_GID =
279      new EventSearchParameter(OccurrenceSearchParameter.GADM_LEVEL_3_GID);
280
281  /** See @link {@link OccurrenceSearchParameter#DWCA_EXTENSION} */
282  public static final EventSearchParameter DWCA_EXTENSION =
283      new EventSearchParameter(OccurrenceSearchParameter.DWCA_EXTENSION);
284
285  /** See @link {@link OccurrenceSearchParameter#DATASET_ID} */
286  public static final EventSearchParameter DATASET_ID =
287      new EventSearchParameter(OccurrenceSearchParameter.DATASET_ID);
288
289  /** See @link {@link OccurrenceSearchParameter#DATASET_NAME} */
290  public static final EventSearchParameter DATASET_NAME =
291      new EventSearchParameter(OccurrenceSearchParameter.DATASET_NAME);
292
293  /** See @link {@link OccurrenceSearchParameter#ISLAND} */
294  public static final EventSearchParameter ISLAND =
295      new EventSearchParameter(OccurrenceSearchParameter.ISLAND);
296
297  /** See @link {@link OccurrenceSearchParameter#ISLAND_GROUP} */
298  public static final EventSearchParameter ISLAND_GROUP =
299      new EventSearchParameter(OccurrenceSearchParameter.ISLAND_GROUP);
300
301  /** See @link {@link OccurrenceSearchParameter#GEOREFERENCED_BY} */
302  public static final EventSearchParameter GEOREFERENCED_BY =
303      new EventSearchParameter(OccurrenceSearchParameter.GEOREFERENCED_BY);
304
305  /** See @link {@link OccurrenceSearchParameter#HIGHER_GEOGRAPHY} */
306  public static final EventSearchParameter HIGHER_GEOGRAPHY =
307      new EventSearchParameter(OccurrenceSearchParameter.HIGHER_GEOGRAPHY);
308
309  /** See @link {@link OccurrenceSearchParameter#FIELD_NUMBER} */
310  public static final EventSearchParameter FIELD_NUMBER =
311      new EventSearchParameter(OccurrenceSearchParameter.FIELD_NUMBER);
312
313  /** See @link {@link OccurrenceSearchParameter#GBIF_ID} */
314  public static final EventSearchParameter GBIF_ID =
315      new EventSearchParameter(OccurrenceSearchParameter.GBIF_ID);
316
317  /** An identifier for an Event and its children events. */
318  public static final EventSearchParameter EVENT_ID_HIERARCHY =
319      new EventSearchParameter("EVENT_ID_HIERARCHY", String.class);
320
321  /** An identifier for the vocabulary-backed Event Type. */
322  public static final EventSearchParameter EVENT_TYPE =
323      new EventSearchParameter("EVENT_TYPE", String.class);
324
325  /** An identifier for the verbatim Event Type. */
326  @Experimental
327  public static final EventSearchParameter VERBATIM_EVENT_TYPE =
328      new EventSearchParameter("VERBATIM_EVENT_TYPE", String.class);
329
330  /** Searches events for those that have a specific issue. */
331  public static final EventSearchParameter ISSUE =
332      new EventSearchParameter("ISSUE", EventIssue.class);
333
334  /** The event project ID.  */
335  public static final EventSearchParameter PROJECT_ID =
336    new EventSearchParameter("PROJECT_ID", String.class);
337
338  /** The event project title.  */
339  public static final EventSearchParameter PROJECT_TITLE =
340    new EventSearchParameter("PROJECT_TITLE", String.class);
341
342  /** The event funding attribution.  */
343  public static final EventSearchParameter FUNDING_ATTRIBUTION =
344    new EventSearchParameter("FUNDING_ATTRIBUTION", String.class);
345
346  /** The event funding attribution ID.  */
347  public static final EventSearchParameter FUNDING_ATTRIBUTION_ID =
348    new EventSearchParameter("FUNDING_ATTRIBUTION_ID", String.class);
349
350  /** The event location ID. */
351  public static final EventSearchParameter LOCATION_ID =
352      new EventSearchParameter("LOCATION_ID", String.class);
353
354  /** See @link {@link OccurrenceSearchParameter#MEASUREMENT_TYPE} */
355  public static final EventSearchParameter MEASUREMENT_TYPE =
356      new EventSearchParameter(OccurrenceSearchParameter.MEASUREMENT_TYPE);
357
358  /** See @link {@link OccurrenceSearchParameter#MEASUREMENT_TYPE_ID} */
359  public static final EventSearchParameter MEASUREMENT_TYPE_ID =
360      new EventSearchParameter(OccurrenceSearchParameter.MEASUREMENT_TYPE_ID);
361
362  /** Humboldt fields * */
363  public static final EventSearchParameter HUMBOLDT_SITE_COUNT =
364      new EventSearchParameter("HUMBOLDT_SITE_COUNT", Integer.class);
365
366  public static final EventSearchParameter HUMBOLDT_VERBATIM_SITE_NAMES =
367      new EventSearchParameter("HUMBOLDT_VERBATIM_SITE_NAMES", String.class);
368  public static final EventSearchParameter HUMBOLDT_GEOSPATIAL_SCOPE_AREA_VALUE =
369      new EventSearchParameter("HUMBOLDT_GEOSPATIAL_SCOPE_AREA_VALUE", Double.class);
370  public static final EventSearchParameter HUMBOLDT_GEOSPATIAL_SCOPE_AREA_UNIT =
371      new EventSearchParameter("HUMBOLDT_GEOSPATIAL_SCOPE_AREA_UNIT", String.class);
372  public static final EventSearchParameter HUMBOLDT_TOTAL_AREA_SAMPLED_VALUE =
373      new EventSearchParameter("HUMBOLDT_TOTAL_AREA_SAMPLED_VALUE", Double.class);
374  public static final EventSearchParameter HUMBOLDT_TOTAL_AREA_SAMPLED_UNIT =
375      new EventSearchParameter("HUMBOLDT_TOTAL_AREA_SAMPLED_UNIT", String.class);
376  public static final EventSearchParameter HUMBOLDT_TARGET_HABITAT_SCOPE =
377      new EventSearchParameter("HUMBOLDT_TARGET_HABITAT_SCOPE", String.class);
378  public static final EventSearchParameter HUMBOLDT_EVENT_DURATION =
379      new EventSearchParameter("HUMBOLDT_EVENT_DURATION", String.class);
380
381  @Hidden
382  public static final EventSearchParameter HUMBOLDT_EVENT_DURATION_VALUE_IN_MINUTES =
383      new EventSearchParameter("HUMBOLDT_EVENT_DURATION_VALUE_IN_MINUTES", Double.class);
384
385  public static final EventSearchParameter HUMBOLDT_EVENT_DURATION_VALUE =
386      new EventSearchParameter("HUMBOLDT_EVENT_DURATION_VALUE", Double.class);
387  public static final EventSearchParameter HUMBOLDT_EVENT_DURATION_UNIT =
388      new EventSearchParameter("HUMBOLDT_EVENT_DURATION_UNIT", DurationUnit.class);
389
390  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ISSUE =
391      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ISSUE", EventIssue.class);
392  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_USAGE_NAME =
393      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_USAGE_NAME", String.class);
394  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_USAGE_KEY =
395      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_USAGE_KEY", String.class);
396  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ACCEPTED_USAGE_NAME =
397      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ACCEPTED_USAGE_NAME", String.class);
398  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ACCEPTED_USAGE_KEY =
399      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_ACCEPTED_USAGE_KEY", String.class);
400  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_TAXON_KEY =
401      new EventSearchParameter("HUMBOLDT_TARGET_TAXONOMIC_SCOPE_TAXON_KEY", String.class);
402  public static final EventSearchParameter HUMBOLDT_TARGET_TAXONOMIC_SCOPE_IUCN_RED_LIST_CATEGORY =
403      new EventSearchParameter(
404          "HUMBOLDT_TARGET_TAXONOMIC_SCOPE_IUCN_RED_LIST_CATEGORY", String.class);
405  public static final EventSearchParameter HUMBOLDT_TAXON_COMPLETENESS_PROTOCOLS =
406      new EventSearchParameter("HUMBOLDT_TAXON_COMPLETENESS_PROTOCOLS", String.class);
407  public static final EventSearchParameter HUMBOLDT_IS_TAXONOMIC_SCOPE_FULLY_REPORTED =
408      new EventSearchParameter("HUMBOLDT_IS_TAXONOMIC_SCOPE_FULLY_REPORTED", Boolean.class);
409  public static final EventSearchParameter HUMBOLDT_IS_ABSENCE_REPORTED =
410      new EventSearchParameter("HUMBOLDT_IS_ABSENCE_REPORTED", Boolean.class);
411  public static final EventSearchParameter HUMBOLDT_HAS_NON_TARGET_TAXA =
412      new EventSearchParameter("HUMBOLDT_HAS_NON_TARGET_TAXA", Boolean.class);
413  public static final EventSearchParameter HUMBOLDT_ARE_NON_TARGET_TAXA_FULLY_REPORTED =
414      new EventSearchParameter("HUMBOLDT_ARE_NON_TARGET_TAXA_FULLY_REPORTED", Boolean.class);
415  public static final EventSearchParameter HUMBOLDT_TARGET_LIFE_STAGE_SCOPE =
416      new EventSearchParameter("HUMBOLDT_TARGET_LIFE_STAGE_SCOPE", String.class);
417  public static final EventSearchParameter HUMBOLDT_IS_LIFE_STAGE_SCOPE_FULLY_REPORTED =
418      new EventSearchParameter("HUMBOLDT_IS_LIFE_STAGE_SCOPE_FULLY_REPORTED", Boolean.class);
419  public static final EventSearchParameter HUMBOLDT_TARGET_DEGREE_OF_ESTABLISHMENT_SCOPE =
420      new EventSearchParameter("HUMBOLDT_TARGET_DEGREE_OF_ESTABLISHMENT_SCOPE", String.class);
421  public static final EventSearchParameter
422      HUMBOLDT_IS_DEGREE_OF_ESTABLISHMENT_SCOPE_FULLY_REPORTED =
423          new EventSearchParameter(
424              "HUMBOLDT_IS_DEGREE_OF_ESTABLISHMENT_SCOPE_FULLY_REPORTED", Boolean.class);
425  public static final EventSearchParameter HUMBOLDT_TARGET_GROWTH_FORM_SCOPE =
426      new EventSearchParameter("HUMBOLDT_TARGET_GROWTH_FORM_SCOPE", String.class);
427  public static final EventSearchParameter HUMBOLDT_IS_GROWTH_FORM_SCOPE_FULLY_REPORTED =
428      new EventSearchParameter("HUMBOLDT_IS_GROWTH_FORM_SCOPE_FULLY_REPORTED", Boolean.class);
429  public static final EventSearchParameter HUMBOLDT_HAS_NON_TARGET_ORGANISMS =
430      new EventSearchParameter("HUMBOLDT_HAS_NON_TARGET_ORGANISMS", Boolean.class);
431  public static final EventSearchParameter HUMBOLDT_COMPILATION_TYPES =
432      new EventSearchParameter("HUMBOLDT_COMPILATION_TYPES", String.class);
433  public static final EventSearchParameter HUMBOLDT_COMPILATION_SOURCE_TYPES =
434      new EventSearchParameter("HUMBOLDT_COMPILATION_SOURCE_TYPES", String.class);
435  public static final EventSearchParameter HUMBOLDT_INVENTORY_TYPES =
436      new EventSearchParameter("HUMBOLDT_INVENTORY_TYPES", String.class);
437  public static final EventSearchParameter HUMBOLDT_PROTOCOL_NAMES =
438      new EventSearchParameter("HUMBOLDT_PROTOCOL_NAMES", String.class);
439  public static final EventSearchParameter HUMBOLDT_IS_ABUNDANCE_REPORTED =
440      new EventSearchParameter("HUMBOLDT_IS_ABUNDANCE_REPORTED", Boolean.class);
441  public static final EventSearchParameter HUMBOLDT_IS_ABUNDANCE_CAP_REPORTED =
442      new EventSearchParameter("HUMBOLDT_IS_ABUNDANCE_CAP_REPORTED", Boolean.class);
443  public static final EventSearchParameter HUMBOLDT_ABUNDANCE_CAP =
444      new EventSearchParameter("HUMBOLDT_ABUNDANCE_CAP", Integer.class);
445  public static final EventSearchParameter HUMBOLDT_IS_VEGETATION_COVER_REPORTED =
446      new EventSearchParameter("HUMBOLDT_IS_VEGETATION_COVER_REPORTED", Boolean.class);
447  public static final EventSearchParameter
448      HUMBOLDT_IS_LEAST_SPECIFIC_TARGET_CATEGORY_QUANTITY_INCLUSIVE =
449          new EventSearchParameter(
450              "HUMBOLDT_IS_LEAST_SPECIFIC_TARGET_CATEGORY_QUANTITY_INCLUSIVE", Boolean.class);
451  public static final EventSearchParameter HUMBOLDT_HAS_VOUCHERS =
452      new EventSearchParameter("HUMBOLDT_HAS_VOUCHERS", Boolean.class);
453  public static final EventSearchParameter HUMBOLDT_VOUCHER_INSTITUTIONS =
454      new EventSearchParameter("HUMBOLDT_VOUCHER_INSTITUTIONS", String.class);
455  public static final EventSearchParameter HUMBOLDT_HAS_MATERIAL_SAMPLES =
456      new EventSearchParameter("HUMBOLDT_HAS_MATERIAL_SAMPLES", Boolean.class);
457  public static final EventSearchParameter HUMBOLDT_MATERIAL_SAMPLE_TYPES =
458      new EventSearchParameter("HUMBOLDT_MATERIAL_SAMPLE_TYPES", String.class);
459  public static final EventSearchParameter HUMBOLDT_SAMPLING_PERFORMED_BY =
460      new EventSearchParameter("HUMBOLDT_SAMPLING_PERFORMED_BY", String.class);
461  public static final EventSearchParameter HUMBOLDT_IS_SAMPLING_EFFORT_REPORTED =
462      new EventSearchParameter("HUMBOLDT_IS_SAMPLING_EFFORT_REPORTED", Boolean.class);
463  public static final EventSearchParameter HUMBOLDT_SAMPLING_EFFORT_VALUE =
464      new EventSearchParameter("HUMBOLDT_SAMPLING_EFFORT_VALUE", Double.class);
465  public static final EventSearchParameter HUMBOLDT_SAMPLING_EFFORT_UNIT =
466      new EventSearchParameter("HUMBOLDT_SAMPLING_EFFORT_UNIT", String.class);
467
468  public static EventSearchParameter[] values() {
469
470    Field[] values = EventSearchParameter.class.getFields();
471    List<EventSearchParameter> c = new ArrayList<>();
472    for (Field field : values) {
473      try {
474        c.add((EventSearchParameter) field.get(EventSearchParameter.class));
475      } catch (IllegalAccessException e) {
476        throw new RuntimeException(e);
477      }
478    }
479    return c.toArray(new EventSearchParameter[0]);
480  }
481
482  private Class<?> type;
483  private String name;
484
485  public EventSearchParameter() {}
486
487  public EventSearchParameter(OccurrenceSearchParameter occurrenceSearchParameter) {
488    this.name = occurrenceSearchParameter.getName();
489    this.type = occurrenceSearchParameter.getType();
490  }
491
492  public EventSearchParameter(String name, Class<?> type) {
493    this.name = name;
494    this.type = type;
495  }
496
497  @Override
498  public String name() {
499    return this.name;
500  }
501
502  public Class<?> getType() {
503    return type;
504  }
505
506  public String getName() {
507    return name;
508  }
509
510  @Override
511  public Class<?> type() {
512    return this.type;
513  }
514
515  @Override
516  public String toString() {
517    return name;
518  }
519
520  @Override
521  public boolean equals(Object o) {
522    if (this == o) return true;
523    if (o == null || getClass() != o.getClass()) return false;
524    EventSearchParameter that = (EventSearchParameter) o;
525    return Objects.equals(type, that.type) && Objects.equals(name, that.name);
526  }
527
528  @JsonValue
529  public String getSerializedValue() {
530    return name;
531  }
532
533  @Override
534  public int hashCode() {
535    return Objects.hash(type, name);
536  }
537
538  /**
539   * Lookup a parameter by its name.
540   *
541   * @param name the name of the parameter
542   * @return the parameter if found, otherwise empty
543   */
544  public static Optional<EventSearchParameter> lookupEventParam(String name) {
545    String normedType = name.toUpperCase().replaceAll("[. _-]", "");
546    Field[] values = EventSearchParameter.class.getFields();
547    for (Field field : values) {
548
549      String fieldName = field.getName();
550      String normedVal = fieldName.replaceAll("[. _-]", "");
551      if (normedType.equals(normedVal)) {
552        try {
553          return Optional.of((EventSearchParameter) field.get(EventSearchParameter.class));
554        } catch (IllegalAccessException e) {
555          throw new RuntimeException(e);
556        }
557      }
558    }
559    return Optional.empty();
560  }
561
562  public static class EventSearchParameterKeyDeserializer extends KeyDeserializer {
563
564    @Override
565    public Object deserializeKey(String value, DeserializationContext deserializationContext)
566        throws IOException {
567      Field[] values = EventSearchParameter.class.getFields();
568      try {
569        for (Field field : values) {
570          if (field.getName().equalsIgnoreCase(value)) {
571            return (EventSearchParameter) field.get(EventSearchParameter.class);
572          }
573        }
574      } catch (IllegalAccessException e) {
575        log.warn("Error deserializing event search parameter key", e);
576        // DO NOTHING
577      }
578      return null;
579    }
580  }
581
582  public static class EventSearchParameterDeserializer
583      extends JsonDeserializer<EventSearchParameter> {
584
585    @Override
586    public EventSearchParameter deserialize(
587        com.fasterxml.jackson.core.JsonParser jsonParser,
588        DeserializationContext deserializationContext)
589        throws IOException, JacksonException {
590
591      Field[] values = EventSearchParameter.class.getFields();
592      try {
593        String value = jsonParser.getText();
594        for (Field field : values) {
595          if (field.getName().equalsIgnoreCase(value)) {
596            return (EventSearchParameter) field.get(EventSearchParameter.class);
597          }
598        }
599
600      } catch (IllegalAccessException e) {
601        log.warn("Error deserializing event search parameter", e);
602      }
603
604      try {
605        ObjectNode node = jsonParser.getCodec().readTree(jsonParser);
606        String value = node.get("name").asText();
607        for (Field field : values) {
608          if (field.getName().equalsIgnoreCase(value)) {
609            return (EventSearchParameter) field.get(EventSearchParameter.class);
610          }
611        }
612      } catch (Exception e) {
613        log.warn("Error deserializing event search parameter from name", e);
614      }
615
616      return null;
617    }
618  }
619}