diff --git a/service/src/main/java/gov/nasa/pds/api/registry/ConnectionContext.java b/service/src/main/java/gov/nasa/pds/api/registry/ConnectionContext.java deleted file mode 100644 index 65be5786..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/ConnectionContext.java +++ /dev/null @@ -1,24 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.util.List; -import org.opensearch.client.opensearch.OpenSearchClient; -import org.opensearch.client.opensearch.generic.OpenSearchGenericClient; - -public interface ConnectionContext { - - public OpenSearchClient getOpenSearchClient(); - - public OpenSearchGenericClient getOpenSearchGenericClient(); - - public String getHost(); - - public List getRegistryIndices(); - - public List getRegistryRefIndices(); - - public int getTimeOutSeconds(); - - public List getArchiveStatus(); - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/GroupConstraint.java b/service/src/main/java/gov/nasa/pds/api/registry/GroupConstraint.java deleted file mode 100644 index 0e0e64df..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/GroupConstraint.java +++ /dev/null @@ -1,39 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.util.List; -import java.util.Map; - -import com.google.errorprone.annotations.Immutable; - -/** - * A set of search constraints specifying three collections of keyword/value match conditions: FILTERTOANY, MUST and NOT. - *

- * Taken as a whole, GroupConstraint matches any element that matches any value in FILTERTOANY for the given keyword, matches every condition in MUST, and fails every condition in MUSTNOT. - */ -@Immutable -public interface GroupConstraint { - - /** - * A single PDS keyword and a set of corresponding values, resulting in a match if a PDS item contains one or more - * values from the set in its property corresponding to the keyword. - */ - public Map> filterToAny(); - - /** - * A set of PDS keywords/values that ALL must be true to define just PDS items that make up this - * Group. - */ - public Map> must(); - - /** - * A set of PDS keywords/values that NONE must be true to define just PDS items that make up this - * Group. - */ - public Map> mustNot(); - - /** - * Return the union of this GroupConstraint and another. Equivalent to taking the union of both FILTER sets, the union of both MUST sets, and the union of both MUSTNOT sets - */ - - public GroupConstraint union(GroupConstraint otherConstraint); -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/LidvidsContext.java b/service/src/main/java/gov/nasa/pds/api/registry/LidvidsContext.java deleted file mode 100644 index ec072084..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/LidvidsContext.java +++ /dev/null @@ -1,15 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.util.List; - -public interface LidvidsContext { - public String getProductIdentifierStr(); - - public Integer getLimit(); - - public List getSortFields(); - - public List getSearchAfterValues(); - - public boolean getSingletonResultExpected(); -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/RequestBuildContext.java b/service/src/main/java/gov/nasa/pds/api/registry/RequestBuildContext.java deleted file mode 100644 index b1c93bf8..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/RequestBuildContext.java +++ /dev/null @@ -1,13 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.util.List; - -public interface RequestBuildContext { - public boolean justLatest(); // return just the latest LIDVIDs. return false if request is made - // for a - // specific version - - public List getFields(); // must not return null but an empty list - - public GroupConstraint getPresetCriteria(); // must not return null but an empty list -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/RequestConstructionContext.java b/service/src/main/java/gov/nasa/pds/api/registry/RequestConstructionContext.java deleted file mode 100644 index adbe5ceb..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/RequestConstructionContext.java +++ /dev/null @@ -1,21 +0,0 @@ -package gov.nasa.pds.api.registry; - -import gov.nasa.pds.api.registry.model.identifiers.PdsProductIdentifier; - -import java.util.List; -import java.util.Map; - -public interface RequestConstructionContext { - public List getKeywords(); // must not return null but an empty list - - public Map> getKeyValuePairs(); // must not return null but an empty map - - public PdsProductIdentifier getProductIdentifier(); - - public String getProductIdentifierString(); // must not return null but an empty string - - public String getQueryString(); // must not return null but an empty string - - public boolean isTerm(); // if true, then use QueryBuilders.termQuery otherwise use - // QueryBuilders.matchQuery -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/SpringBootMain.java b/service/src/main/java/gov/nasa/pds/api/registry/SpringBootMain.java deleted file mode 100644 index 965cb82b..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/SpringBootMain.java +++ /dev/null @@ -1,61 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.lang.IllegalArgumentException; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.boot.CommandLineRunner; -import org.springframework.boot.ExitCodeGenerator; -import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.SpringBootApplication; -import org.springframework.scheduling.annotation.EnableScheduling; -import org.springframework.context.annotation.AnnotationConfigApplicationContext; -import org.springframework.context.annotation.ComponentScan; -import io.swagger.v3.oas.annotations.OpenAPIDefinition; - -// TODO -// add archive status filter -// add other resolver endpoints - -@SpringBootApplication -@OpenAPIDefinition -@EnableScheduling -@ComponentScan(basePackages = {"gov.nasa.pds.api.registry.configuration", - "gov.nasa.pds.api.registry.controllers", "gov.nasa.pds.api.registry.model", - "gov.nasa.pds.api.registry.search", "javax.servlet.http"}) -public class SpringBootMain implements CommandLineRunner { - - private static final Logger log = LoggerFactory.getLogger(SpringBootMain.class); - - - - @Override - public void run(String... arg0) throws Exception { - if (arg0.length > 0 && arg0[0].equals("exitcode")) { - throw new ExitException(); - } - } - - public static void main(String[] args) throws Exception { - try { - AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(); - ctx.refresh(); - - new SpringApplication(SpringBootMain.class).run(args); - ctx.close(); - } catch (IllegalArgumentException e) { - log.error( - "Illegal springboot argument in the start command. Restart the application differently.", - e.getMessage(), e); - } - } - - class ExitException extends RuntimeException implements ExitCodeGenerator { - private static final long serialVersionUID = 1L; - - @Override - public int getExitCode() { - return 10; - } - - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/SystemConstants.java b/service/src/main/java/gov/nasa/pds/api/registry/SystemConstants.java deleted file mode 100644 index 06d218f2..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/SystemConstants.java +++ /dev/null @@ -1,18 +0,0 @@ -package gov.nasa.pds.api.registry; - -public class SystemConstants { - - /* - * Environment variables - values are retrieved using System.getEnv() under specific configuration - * states. - */ - - // Those in this section are expected to be value-only. - // For AWS deployments they are set through the Systems Manager Parameter Store - public static final String ES_HOSTS_ENV_VAR = "ES_HOSTS"; // es URLs - - private SystemConstants() { - throw new IllegalStateException("Objects of this class cannot be instantiated."); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/UserContext.java b/service/src/main/java/gov/nasa/pds/api/registry/UserContext.java deleted file mode 100644 index a238bab3..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/UserContext.java +++ /dev/null @@ -1,28 +0,0 @@ -package gov.nasa.pds.api.registry; - -import java.util.List; - -import gov.nasa.pds.api.registry.model.ProductVersionSelector; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductIdentifier; - -public interface UserContext extends LidvidsContext { - public String getAccept(); - - public List getFields(); - - public String getGroup(); - - public PdsProductIdentifier getIdentifier(); - - public List getKeywords(); - - public String getQuery(); - - public ProductVersionSelector getSelector(); - - public List getSortFields(); - - public List getSearchAfterValues(); - - public String getVersion(); -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/configuration/AWSSecretsAccess.java b/service/src/main/java/gov/nasa/pds/api/registry/configuration/AWSSecretsAccess.java deleted file mode 100644 index a834b859..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/configuration/AWSSecretsAccess.java +++ /dev/null @@ -1,129 +0,0 @@ -package gov.nasa.pds.api.registry.configuration; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.util.Iterator; - -import org.apache.commons.collections4.keyvalue.DefaultKeyValue; - -import com.fasterxml.jackson.databind.ObjectMapper; -import com.fasterxml.jackson.core.JsonProcessingException; -import com.fasterxml.jackson.databind.JsonMappingException; -import com.fasterxml.jackson.databind.JsonNode; - -import com.amazonaws.services.secretsmanager.AWSSecretsManagerClientBuilder; -import com.amazonaws.services.secretsmanager.AWSSecretsManager; -import com.amazonaws.services.secretsmanager.model.GetSecretValueRequest; -import com.amazonaws.services.secretsmanager.model.GetSecretValueResult; -import com.amazonaws.services.secretsmanager.model.DecryptionFailureException; -import com.amazonaws.services.secretsmanager.model.InternalServiceErrorException; -import com.amazonaws.services.secretsmanager.model.InvalidParameterException; -import com.amazonaws.services.secretsmanager.model.InvalidRequestException; -import com.amazonaws.services.secretsmanager.model.ResourceNotFoundException; - -public class AWSSecretsAccess { - - public static final String REGISTRY_DEFAULT_AWS_REGION = "us-west-2"; - - private static final ObjectMapper objectMapper = new ObjectMapper(); - private static final Logger log = LoggerFactory.getLogger(AWSSecretsAccess.class); - - // Get the secret using the default region - public DefaultKeyValue getSecret(String secretName) { - return getSecret(secretName, null); - } - - // Get the secret from an explicit region - // This code is a slight modification of that provided by the AWS SecretsManager - // console. - public DefaultKeyValue getSecret(String secretName, String region) { - - if (region == null || "".equals(region)) { - region = REGISTRY_DEFAULT_AWS_REGION; - } - - log.debug(String.format("Looking up secret in non-default region %s", region)); - - // Create a Secrets Manager client - AWSSecretsManager client = AWSSecretsManagerClientBuilder.standard().withRegion(region).build(); - - // In this sample we only handle the specific exceptions for the - // 'GetSecretValue' API. - // See - // https://docs.aws.amazon.com/secretsmanager/latest/apireference/API_GetSecretValue.html - // We rethrow the exception by default. - - GetSecretValueRequest getSecretValueRequest = - new GetSecretValueRequest().withSecretId(secretName); - GetSecretValueResult getSecretValueResult = null; - - try { - log.debug("Submitting getSecretValueRequest."); - getSecretValueResult = client.getSecretValue(getSecretValueRequest); - } catch (DecryptionFailureException e) { - // Secrets Manager can't decrypt the protected secret text using the provided - // KMS key. - // Deal with the exception here, and/or rethrow at your discretion. - log.error("DecryptionFailureException (%s)", e.getMessage()); - throw e; - } catch (InternalServiceErrorException e) { - // An error occurred on the server side. - // Deal with the exception here, and/or rethrow at your discretion. - log.error("InternalServiceErrorException (%s)", e.getMessage()); - throw e; - } catch (InvalidParameterException e) { - // You provided an invalid value for a parameter. - // Deal with the exception here, and/or rethrow at your discretion. - log.error("InvalidParameterException (%s)", e.getMessage()); - throw e; - } catch (InvalidRequestException e) { - // You provided a parameter value that is not valid for the current state of the - // resource. - // Deal with the exception here, and/or rethrow at your discretion. - log.error("InvalidRequestException (%s)", e.getMessage()); - throw e; - } catch (ResourceNotFoundException e) { - // We can't find the resource that you asked for. - // Deal with the exception here, and/or rethrow at your discretion. - log.error("ResourceNotFoundException (%s)", e.getMessage()); - throw e; - } - - return parseSecret(getSecretValueResult.getSecretString()); - - } - - // Given a String JSON representation, parse the secret key/value and return - public static DefaultKeyValue parseSecret(String secretString) { - DefaultKeyValue result = null; - - try { - JsonNode jsonObj = objectMapper.readTree(secretString); - String secretId = null; - String secretValue = null; - - Iterator fieldIter = jsonObj.fieldNames(); - while (fieldIter.hasNext()) { - if (secretId != null) { - // more than field name? This shouldn't happen - throw new RuntimeException( - String.format("Received multiple fields in secret value (%s)", secretString)); - } - secretId = fieldIter.next(); - secretValue = jsonObj.get(secretId).asText(); - - result = new DefaultKeyValue(secretId, secretValue); - log.debug("Secret string successfully parsed."); - } - } catch (JsonMappingException jmEx) { - log.error("Could not parse secret JSON value (%s)", jmEx.getMessage()); - throw new RuntimeException(jmEx); - } catch (JsonProcessingException jpEx) { - log.error("Could not process secret JSON value (%s)", jpEx.getMessage()); - throw new RuntimeException(jpEx); - } - - return result; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/configuration/ApiDocumentation.java b/service/src/main/java/gov/nasa/pds/api/registry/configuration/ApiDocumentation.java deleted file mode 100644 index 5ce83838..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/configuration/ApiDocumentation.java +++ /dev/null @@ -1,27 +0,0 @@ -package gov.nasa.pds.api.registry.configuration; - -import org.springframework.beans.factory.annotation.Value; -import org.springframework.stereotype.Controller; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RequestMethod; -import io.swagger.v3.oas.annotations.tags.Tag; - -/** - * Home redirection to swagger api documentation - */ -@Tag(name = "Registry Search API Documentation") -@Controller -public class ApiDocumentation { - - @Value("${server.contextPath}") - private String contextPath; - - @RequestMapping(method = RequestMethod.GET, produces = {"text/html"}, value = "/") - public String index() { - - String contextPath = this.contextPath.endsWith("/") ? this.contextPath : this.contextPath + "/"; - - System.out.println(contextPath + "swagger-ui/index.html"); - return "redirect:" + contextPath + "swagger-ui/index.html"; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenAPIClearedTags.java b/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenAPIClearedTags.java deleted file mode 100644 index 1723eaeb..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenAPIClearedTags.java +++ /dev/null @@ -1,62 +0,0 @@ -package gov.nasa.pds.api.registry.configuration; - -import java.util.ArrayList; -import java.util.List; -import java.util.Map; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springdoc.core.customizers.OpenApiCustomizer; -import org.springframework.stereotype.Component; -import io.swagger.v3.oas.models.OpenAPI; -import io.swagger.v3.oas.models.Operation; -import io.swagger.v3.oas.models.PathItem; -import io.swagger.v3.oas.models.Paths; -import io.swagger.v3.oas.models.tags.Tag; - -@Component -// this component is needed until https://github.com/OpenAPITools/openapi-generator/pull/13434 is -// fixed/merged -public class OpenAPIClearedTags implements OpenApiCustomizer { - protected static final Logger log = LoggerFactory.getLogger(OpenAPIClearedTags.class); - - private static final String FILTERED_TAGS = - "collections|bundles|products|classes|healthcheck|properties|docs"; - - @Override - public void customise(OpenAPI openApi) { - OpenAPIClearedTags.log.info("Removing products tag from operations"); - - - - List tags = openApi.getTags(); - ArrayList filteredTags = new ArrayList(); - - - for (Tag tag : tags) { - if (!tag.getName().matches(OpenAPIClearedTags.FILTERED_TAGS)) { - filteredTags.add(tag); - } - } - openApi.setTags(filteredTags); - - - Paths paths = openApi.getPaths(); - for (Map.Entry path : paths.entrySet()) { - PathItem pathItem = path.getValue(); - ArrayList filteredTagStrings = new ArrayList(); - for (Operation operation : pathItem.readOperations()) { - for (String tag : operation.getTags()) { - if (!tag.matches(OpenAPIClearedTags.FILTERED_TAGS)) { - filteredTagStrings.add(tag); - } - } - operation.setTags(filteredTagStrings); - } - - } - - } - - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenApiConfiguration.java b/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenApiConfiguration.java deleted file mode 100644 index 1fa153d3..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/configuration/OpenApiConfiguration.java +++ /dev/null @@ -1,51 +0,0 @@ -package gov.nasa.pds.api.registry.configuration; - -import org.springframework.beans.factory.annotation.Value; -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.Configuration; -import org.springframework.web.filter.ForwardedHeaderFilter; -import io.swagger.v3.oas.models.ExternalDocumentation; -import io.swagger.v3.oas.models.OpenAPI; -import io.swagger.v3.oas.models.info.Contact; -import io.swagger.v3.oas.models.info.Info; -import io.swagger.v3.oas.models.info.License; - - - -@Configuration -public class OpenApiConfiguration { - - @Value("${registry.service.version:undefined}") - private String version; - - - @Bean - public OpenAPI customOpenAPI() { - OpenAPI customOpenAPI = new OpenAPI() - .info(new Info().title("PDS Registry Search API") - .description( - "RestFul web API provided to search all classes of products in the PDS registries.") - .version(this.version) - .contact(new Contact().name("Contact PDS Engineering Node Support") - .email("pds_operator@jpl.nasa.gov")) - .license(new License().name("Apache 2.0") - .url("http://www.apache.org/licenses/LICENSE-2.0.html"))) - .externalDocs(new ExternalDocumentation().description("User's Guide") - .url("https://nasa-pds.github.io/pds-api/guides/search.html")); - - - return customOpenAPI; - } - - - - @Bean - ForwardedHeaderFilter forwardedHeaderFilter() { - return new ForwardedHeaderFilter(); - } - - - -} - - diff --git a/service/src/main/java/gov/nasa/pds/api/registry/configuration/WebMVCConfig.java b/service/src/main/java/gov/nasa/pds/api/registry/configuration/WebMVCConfig.java deleted file mode 100644 index fc9a55a7..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/configuration/WebMVCConfig.java +++ /dev/null @@ -1,123 +0,0 @@ -package gov.nasa.pds.api.registry.configuration; - -import java.util.List; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Value; -import org.springframework.context.annotation.ComponentScan; -import org.springframework.context.annotation.Configuration; -import org.springframework.http.MediaType; -import org.springframework.http.converter.ByteArrayHttpMessageConverter; -import org.springframework.http.converter.HttpMessageConverter; -import org.springframework.http.converter.StringHttpMessageConverter; -import org.springframework.web.servlet.config.annotation.ContentNegotiationConfigurer; -import org.springframework.web.servlet.config.annotation.EnableWebMvc; -import org.springframework.web.servlet.config.annotation.PathMatchConfigurer; -import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry; -import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; -import gov.nasa.pds.api.registry.view.CsvErrorMessageSerializer; -import gov.nasa.pds.api.registry.view.CsvPluralSerializer; -import gov.nasa.pds.api.registry.view.CsvSingularSerializer; -import gov.nasa.pds.api.registry.view.JsonErrorMessageSerializer; -import gov.nasa.pds.api.registry.view.JsonPluralSerializer; -import gov.nasa.pds.api.registry.view.JsonProductSerializer; -import gov.nasa.pds.api.registry.view.JsonSingularSerializer; -import gov.nasa.pds.api.registry.view.Pds4JsonProductSerializer; -import gov.nasa.pds.api.registry.view.Pds4JsonProductsSerializer; -import gov.nasa.pds.api.registry.view.Pds4XmlProductSerializer; -import gov.nasa.pds.api.registry.view.Pds4XmlProductsSerializer; -import gov.nasa.pds.api.registry.view.PdsProductTextHtmlSerializer; -import gov.nasa.pds.api.registry.view.PdsProductsTextHtmlSerializer; -import gov.nasa.pds.api.registry.view.PdsProductXMLSerializer; -import gov.nasa.pds.api.registry.view.PdsProductsXMLSerializer; -import gov.nasa.pds.api.registry.view.XmlErrorMessageSerializer; - -@Configuration -@EnableWebMvc -@ComponentScan(basePackages = {"gov.nasa.pds.api.registry.configuration ", - "gov.nasa.pds.api.registry.controller", "gov.nasa.pds.api.registry.search"}) -public class WebMVCConfig implements WebMvcConfigurer { - private static final Logger log = LoggerFactory.getLogger(WebMVCConfig.class); - - @Value("${server.contextPath}") - private String contextPath; - - @Override - public void addResourceHandlers(ResourceHandlerRegistry registry) { - String contextPath = this.contextPath.endsWith("/") ? this.contextPath : this.contextPath + "/"; - - registry.addResourceHandler(contextPath + "webjars/**") - .addResourceLocations("classpath:/META-INF/resources/webjars/"); - registry.addResourceHandler(contextPath + "static/**") - .addResourceLocations("classpath:/static/"); - - - registry.addResourceHandler(contextPath + "swagger-ui/pds.*") - .addResourceLocations("classpath:/swagger-ui/"); - registry.addResourceHandler(contextPath + "swagger-ui/index.htm*") - .addResourceLocations("classpath:/swagger-ui/"); - - - } - - @Override - @SuppressWarnings("deprecation") - public void configurePathMatch(PathMatchConfigurer configurer) { - // this is important to avoid that parameters (e.g lidvid) are truncated after . - configurer.setUseSuffixPatternMatch(false); - } - - /** - * Setup a simple strategy: use all the defaults and return JSON by default when not sure. - */ - public void configureContentNegotiation(ContentNegotiationConfigurer configurer) { - configurer.defaultContentType(MediaType.APPLICATION_JSON); - } - - @Override - public void configureMessageConverters(List> converters) { - WebMVCConfig.log - .info("Number of converters available at start " + Integer.toString(converters.size())); - - // csv converters - converters.add(new CsvErrorMessageSerializer()); - converters.add(new CsvPluralSerializer()); - converters.add(new CsvSingularSerializer()); - - // json+kvp converters - converters.add(new JsonPluralSerializer()); - converters.add(new JsonSingularSerializer()); - - // json+pds4 converters - converters.add(new Pds4JsonProductSerializer()); - converters.add(new Pds4JsonProductsSerializer()); - - // xml+pds4 converters - converters.add(new Pds4XmlProductSerializer()); - converters.add(new Pds4XmlProductsSerializer()); - - // default xml converters - converters.add(new PdsProductXMLSerializer()); - converters.add(new PdsProductsXMLSerializer()); - converters.add(new XmlErrorMessageSerializer()); - - // text converters for PdsProduct(s) - converters.add(new PdsProductTextHtmlSerializer()); - converters.add(new PdsProductsTextHtmlSerializer()); - - // Introduce basics that are not PDS related but may overload MediaType - // Put them after the PDS so that it always has priority except JSON below because it has */* - // basic converter for /api-docs end-point, new with springdoc 2 - converters.add(new ByteArrayHttpMessageConverter()); - - // basic converter for swagger-ui resources - converters.add(new StringHttpMessageConverter()); - - // default json converters - converters.add(new JsonErrorMessageSerializer()); - converters.add(new JsonProductSerializer()); // this one must be last because it contains */* - - WebMVCConfig.log.info("Number of converters available after adding locals " - + Integer.toString(converters.size())); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/controllers/DocsController.java b/service/src/main/java/gov/nasa/pds/api/registry/controllers/DocsController.java deleted file mode 100644 index 392842c1..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/controllers/DocsController.java +++ /dev/null @@ -1,84 +0,0 @@ -package gov.nasa.pds.api.registry.controllers; - -import java.lang.Object; -import java.util.List; -import java.util.Map; -import java.util.HashMap; -import java.util.AbstractMap; -import java.util.Collection; -import java.util.ArrayList; -import jakarta.validation.Valid; -import jakarta.validation.constraints.NotNull; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.stereotype.Controller; -import org.springframework.web.bind.annotation.RequestBody; -import org.springframework.web.bind.annotation.RequestParam; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.api.base.DocsApi; -import gov.nasa.pds.api.registry.ConnectionContext; -import gov.nasa.pds.api.registry.model.ErrorMessageFactory; -import io.swagger.v3.oas.annotations.Parameter; -import io.swagger.v3.oas.annotations.enums.ParameterIn; -import org.opensearch.client.opensearch.generic.OpenSearchGenericClient; -import org.opensearch.client.opensearch.generic.Requests; -import org.opensearch.client.opensearch.generic.Request; -import org.opensearch.client.opensearch.generic.Bodies; -import org.opensearch.client.opensearch.generic.Response; - - -@Controller -public class DocsController implements DocsApi { - - private static final Logger log = LoggerFactory.getLogger(DocsController.class); - - private final ConnectionContext connectionContext; - private final String host; - - @Autowired - public DocsController(ConnectionContext connectionContext) { - - this.connectionContext = connectionContext; - - this.host = connectionContext.getHost(); - - - } - - @Override - public ResponseEntity docs( - @NotNull @Parameter(name = "indices", - description = "syntax: indices=index1,index2... notes: OpenSearch indices ", - required = true, in = ParameterIn.QUERY) @Valid @RequestParam(value = "indices", - required = true) List indices, - @Parameter(name = "body", description = "OpenSearch DSL query", - required = true) @Valid @RequestBody String body) - throws Exception { - - String endPoint = this.host + "/" + String.join(",", indices) + "/_search"; - - Collection> headers = new ArrayList>(); - Map.Entry acceptHeader = - new AbstractMap.SimpleEntry("Accept", "application/json"); - headers.add(acceptHeader); - Request request = Requests.create("POST", endPoint, headers, new HashMap(), - Bodies.json(body)); - - - OpenSearchGenericClient openSearchGenericClient = - this.connectionContext.getOpenSearchGenericClient(); - // TODO make that work, it does not now, - // but I have to keep that development aside for now - Response response = openSearchGenericClient.execute(request); - - log.info("Request status response is " + response.getStatus()); - log.debug("Request response body is " + response.getBody()); - - - return new ResponseEntity(HttpStatus.OK); - - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/controllers/HealthCheckController.java b/service/src/main/java/gov/nasa/pds/api/registry/controllers/HealthCheckController.java deleted file mode 100644 index de78e364..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/controllers/HealthCheckController.java +++ /dev/null @@ -1,19 +0,0 @@ -package gov.nasa.pds.api.registry.controllers; - -import java.util.Map; -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.stereotype.Controller; -import gov.nasa.pds.api.base.HealthcheckApi; - -@Controller -public class HealthCheckController implements HealthcheckApi { - - @Override - public ResponseEntity> healthcheck() { - // To Be Completed - return new ResponseEntity<>(HttpStatus.OK); - - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/controllers/ProductsController.java b/service/src/main/java/gov/nasa/pds/api/registry/controllers/ProductsController.java deleted file mode 100644 index 85d1fdde..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/controllers/ProductsController.java +++ /dev/null @@ -1,627 +0,0 @@ -package gov.nasa.pds.api.registry.controllers; - -import java.lang.reflect.InvocationTargetException; -import java.io.IOException; -import java.util.*; - -import gov.nasa.pds.api.base.ClassesApi; -import gov.nasa.pds.api.registry.model.exceptions.*; -import gov.nasa.pds.api.registry.model.identifiers.PdsLid; -import gov.nasa.pds.api.registry.model.identifiers.PdsLidVid; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductClasses; -import jakarta.servlet.http.HttpServletRequest; -import com.fasterxml.jackson.databind.ObjectMapper; -import org.opensearch.client.opensearch.OpenSearchClient; -import org.opensearch.client.opensearch._types.OpenSearchException; -import org.opensearch.client.opensearch.core.SearchRequest; -import org.opensearch.client.opensearch.core.SearchResponse; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.http.HttpStatus; -import org.springframework.http.HttpStatusCode; -import org.springframework.http.ResponseEntity; -import org.springframework.stereotype.Controller; -import org.springframework.web.context.request.NativeWebRequest; -import org.springframework.web.context.request.RequestContextHolder; -import org.springframework.web.context.request.ServletRequestAttributes; -import gov.nasa.pds.api.base.ProductsApi; -import gov.nasa.pds.api.registry.ConnectionContext; -import gov.nasa.pds.api.registry.model.ErrorMessageFactory; -import gov.nasa.pds.api.registry.model.api_responses.PdsProductBusinessObject; -import gov.nasa.pds.api.registry.model.api_responses.ProductBusinessLogic; -import gov.nasa.pds.api.registry.model.api_responses.ProductBusinessLogicImpl; -import gov.nasa.pds.api.registry.model.api_responses.RawMultipleProductResponse; -import gov.nasa.pds.api.registry.model.api_responses.WyriwygBusinessObject; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductIdentifier; -import gov.nasa.pds.api.registry.search.RegistrySearchRequestBuilder; - - - -@Controller -// TODO: Refactor common controller code out of ProductsController and split the additional API implementations out into -// corresponding controllers -public class ProductsController implements ProductsApi, ClassesApi { - - @Override - // TODO: Remove this when the common controller code is refactored out - it is only necessary because additional - // interfaces have been implemented as a stopgap - public Optional getRequest() { - return ProductsApi.super.getRequest(); - } - - private static final Logger log = LoggerFactory.getLogger(ProductsController.class); - - private final ConnectionContext connectionContext; - private final ErrorMessageFactory errorMessageFactory; - private final ObjectMapper objectMapper; - private OpenSearchClient openSearchClient; - private SearchRequest presetSearchRequest; - - // TODO move that at a better place, it is not specific to this controller - private static Map> formatters = - new HashMap>(); - - static Map> getFormatters() { - return formatters; - } - - static Integer DEFAULT_LIMIT = 100; - - static { - // TODO move that at a better place, it is not specific to this controller - formatters.put("*", PdsProductBusinessObject.class); - formatters.put("*/*", PdsProductBusinessObject.class); - formatters.put("application/csv", WyriwygBusinessObject.class); - formatters.put("application/json", PdsProductBusinessObject.class); - formatters.put("application/kvp+json", WyriwygBusinessObject.class); - // this.formatters.put("application/vnd.nasa.pds.pds4+json", new - // Pds4ProductBusinessObject(true)); - // this.formatters.put("application/vnd.nasa.pds.pds4+xml", new - // Pds4ProductBusinessObject(false)); - formatters.put("application/xml", PdsProductBusinessObject.class); - formatters.put("text/csv", WyriwygBusinessObject.class); - formatters.put("text/html", PdsProductBusinessObject.class); - formatters.put("text/xml", PdsProductBusinessObject.class); - } - - - @Autowired - public ProductsController(ConnectionContext connectionContext, - ErrorMessageFactory errorMessageFactory, ObjectMapper objectMapper) { - - this.errorMessageFactory = errorMessageFactory; - this.objectMapper = objectMapper; - this.connectionContext = connectionContext; - this.openSearchClient = this.connectionContext.getOpenSearchClient(); - - } - - private ResponseEntity formatSingleProduct(HashMap product, - List fields) throws AcceptFormatNotSupportedException, UnhandledException { - // TODO add case when Accept is not available, default application/json - HttpServletRequest curRequest = - ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest(); - String acceptHeaderValue = curRequest.getHeader("Accept"); - - if (!ProductsController.formatters.containsKey(acceptHeaderValue)) { - throw new AcceptFormatNotSupportedException( - "format " + acceptHeaderValue + "is not supported."); - } - - Class formatterClass = - ProductsController.formatters.get(acceptHeaderValue); - - try { - // TODO replace URLs from the request path - ProductBusinessLogicImpl formatter = - (ProductBusinessLogicImpl) formatterClass.getConstructor().newInstance(); - // TODO check if that is applicable to all formatters. - // Would there be a better place to assign the object mapper ? I don't understand why we have - // only one assigned at the controller level. - formatter.setObjectMapper(this.objectMapper); - formatter.setResponse(product, fields); - - return new ResponseEntity(formatter.getResponse(), HttpStatus.OK); - - } catch (NoSuchMethodException | InvocationTargetException | IllegalAccessException - | InstantiationException e) { - throw new UnhandledException(e); - } - } - - private ResponseEntity formatMultipleProducts(RawMultipleProductResponse response, - List fields) throws AcceptFormatNotSupportedException, UnhandledException { - // TODO add case when Accept is not available, default application/json - HttpServletRequest curRequest = - ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest(); - String acceptHeaderValue = curRequest.getHeader("Accept"); - - if (!ProductsController.formatters.containsKey(acceptHeaderValue)) { - throw new AcceptFormatNotSupportedException( - "format " + acceptHeaderValue + " is not supported."); - } - - Class formatterClass = - ProductsController.formatters.get(acceptHeaderValue); - - try { - // TODO replace URLs from the request path - ProductBusinessLogicImpl formatter = - (ProductBusinessLogicImpl) formatterClass.getConstructor().newInstance(); - // TODO check if that is applicable to all formatters. - // Would there be a better place to assign the object mapper ? I don't understand why we have - // only one assigned at the controller level. - formatter.setObjectMapper(this.objectMapper); - formatter.setResponse(response.getProducts(), response.getSummary(), fields); - - return new ResponseEntity(formatter.getResponse(), HttpStatus.OK); - - } catch (NoSuchMethodException | InvocationTargetException | IllegalAccessException - | InstantiationException e) { - throw new UnhandledException(e); - } - } - - - - // 6 cases: - // lidvid, no suffix we want the exact match with the lidvid (case exact) - // lid, no suffix we want the latest lidvid which lid matches (case latest) - // lidvid, suffix latest, we want the latest lidvid which lid matches (case latest) - // lid, suffix latest, we want the latest lidvid which lid matches (case latest) - // lid suffix all, we want all the lidvid which lid matches (case all) - // lidvid, suffix all, we want the exact match with the lidvid (case exact) - - @Override - public ResponseEntity selectByLidvid(String identifier, List fields) - throws UnhandledException, NotFoundException, AcceptFormatNotSupportedException { - - HashMap product; - - try { - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - - if (pdsIdentifier.isLidvid()) { - product = this.getLidVid(pdsIdentifier, fields); - } else { - product = this.getLatestLidVid(pdsIdentifier, fields); - } - } catch (IOException | OpenSearchException e) { - throw new UnhandledException(e); - } - - return formatSingleProduct(product, fields); - - - - } - - - @Override - public ResponseEntity selectByLidvidLatest(String identifier, List fields) - throws UnhandledException, NotFoundException, AcceptFormatNotSupportedException { - - HashMap product; - - try { - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - product = this.getLatestLidVid(pdsIdentifier, fields); - } catch (IOException | OpenSearchException e) { - throw new UnhandledException(e); - } - - return formatSingleProduct(product, fields); - - } - - @Override - public ResponseEntity selectByLidvidAll(String identifier, List fields, - Integer limit, List sort, List searchAfter) throws UnhandledException, - NotFoundException, AcceptFormatNotSupportedException, SortSearchAfterMismatchException { - - RawMultipleProductResponse response; - - try { - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - - if (pdsIdentifier.isLidvid()) { - response = new RawMultipleProductResponse(this.getLidVid(pdsIdentifier, fields)); - - } else { - limit = (limit == null) ? DEFAULT_LIMIT : limit; - response = this.getAllLidVid(pdsIdentifier, fields, limit, sort, searchAfter); - } - - - - } catch (IOException | OpenSearchException e) { - throw new UnhandledException(e); - } - - return formatMultipleProducts(response, fields); - - - } - - @Override - public ResponseEntity productList(List fields, List keywords, - Integer limit, String q, List sort, List searchAfter) throws Exception { - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .applyMultipleProductsDefaults(fields, q, keywords, limit, sort, searchAfter, true) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - - - } - - - - @SuppressWarnings("unchecked") - private HashMap getLidVid(PdsProductIdentifier identifier, List fields) - throws OpenSearchException, IOException, NotFoundException { - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLidvid(identifier) - .fieldsFromStrings(fields) - .build(); - - // useless to detail here that the HashMap is parameterized - // because of compilation features, see - // https://stackoverflow.com/questions/2390662/java-how-do-i-get-a-class-literal-from-a-generic-type - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No product found with identifier " + identifier.toString()); - } - HashMap product = searchResponse.hits().hits().get(0).source(); - ProductsController.log.debug("Found product with lid=" + product.get("lid")); - return product; - - } - - - @SuppressWarnings("unchecked") - private HashMap getLatestLidVid(PdsProductIdentifier identifier, - List fields) throws OpenSearchException, IOException, NotFoundException { - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLid(identifier) - .fieldsFromStrings(fields) - .noSupersededProducts() - .build(); - - // useless to detail here that the HashMap is parameterized - // because of compilation features, see - // https://stackoverflow.com/questions/2390662/java-how-do-i-get-a-class-literal-from-a-generic-type - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No product found with identifier " + identifier.toString()); - } - - HashMap product = searchResponse.hits().hits().get(0).source(); - ProductsController.log.debug("Found product with lid=" + product.get("lid")); - return (HashMap) searchResponse.hits().hits().get(0).source(); - - } - - - private RawMultipleProductResponse getAllLidVid(PdsProductIdentifier identifier, - List fields, Integer limit, List sort, List searchAfter) - throws OpenSearchException, IOException, NotFoundException, SortSearchAfterMismatchException { - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLid(identifier).fieldsFromStrings(fields) - .paginate(limit, sort, searchAfter) - .build(); - - // useless to detail here that the HashMap is parameterized - // because of compilation features, see - // https://stackoverflow.com/questions/2390662/java-how-do-i-get-a-class-literal-from-a-generic-type - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No product found with identifier " + identifier.toString()); - } - - return new RawMultipleProductResponse(searchResponse); - - } - - private PdsProductClasses resolveProductClass(PdsProductIdentifier identifier) - throws OpenSearchException, IOException, NotFoundException{ - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLid(identifier) - .fieldsFromStrings(List.of(PdsProductClasses.getPropertyName())) - .noSupersededProducts() - .build(); - - SearchResponse searchResponse = this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No product found with identifier " + identifier.toString()); - } - - String productClassStr = searchResponse.hits().hits().get(0).source().get(PdsProductClasses.getPropertyName()).toString(); - return PdsProductClasses.valueOf(productClassStr); - } - - - private PdsLidVid resolveLatestLidvid(PdsProductIdentifier identifier) - throws OpenSearchException, IOException, NotFoundException { - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLid(identifier.getLid()) - .fieldsFromStrings(List.of()) - .noSupersededProducts() - .build(); - - SearchResponse searchResponse = this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No lidvids found with lid " + identifier.getLid().toString()); - } - - // TODO: Determine how to handle multiple hits due to sweepers lag - - return PdsLidVid.fromString(searchResponse.hits().hits().get(0).id()); - } - - - private List resolveExtantLidvids(PdsLid lid) - throws OpenSearchException, IOException, NotFoundException{ - - String lidvidKey = "_id"; - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .matchLid(lid) - .fieldsFromStrings(List.of(lidvidKey)) - .build(); - - SearchResponse searchResponse = this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No lidvids found with lid " + lid.toString()); - } - - return searchResponse.hits().hits().stream().map(hit -> hit.source().get(lidvidKey).toString()).map(PdsLidVid::fromString).toList(); - } - - /** - * Resolve a PdsProductIdentifier to a PdsLidVid according to the common rules of the API. - * The rules are currently trivial, but may incorporate additional behaviour later - * @param identifier a LID or LIDVID - * @return a LIDVID - */ - private PdsLidVid resolveIdentifierToLidvid(PdsProductIdentifier identifier) throws NotFoundException, IOException { - return identifier.isLidvid() ? (PdsLidVid) identifier : resolveLatestLidvid(identifier); - } - - @Override - public ResponseEntity productMembers( - String identifier, List fields, Integer limit, List sort, List searchAfter) - throws NotFoundException, UnhandledException, SortSearchAfterMismatchException, BadRequestException, - AcceptFormatNotSupportedException{ - - try{ - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - PdsProductClasses productClass = resolveProductClass(pdsIdentifier); - PdsLidVid lidvid = resolveIdentifierToLidvid(pdsIdentifier); - - RegistrySearchRequestBuilder searchRequestBuilder = new RegistrySearchRequestBuilder(this.connectionContext); - - if (productClass.isBundle()) { - searchRequestBuilder.matchMembersOfBundle(lidvid); - searchRequestBuilder.onlyCollections(); - } else if (productClass.isCollection()) { - searchRequestBuilder.matchMembersOfCollection(lidvid); - searchRequestBuilder.onlyBasicProducts(); - } else { - throw new BadRequestException("productMembers endpoint is only valid for products with Product_Class '" + - PdsProductClasses.Product_Bundle + "' or '" + PdsProductClasses.Product_Collection + - "' (got '" + productClass + "')"); - } - - SearchRequest searchRequest = searchRequestBuilder - .applyMultipleProductsDefaults(fields, "", List.of(), limit, sort, searchAfter, true) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - - } catch (IOException | OpenSearchException | UnparsableQParamException e) { - throw new UnhandledException(e); - } - } - - @Override - public ResponseEntity productMembersMembers( - String identifier, List fields, Integer limit, List sort, List searchAfter) - throws NotFoundException, UnhandledException, SortSearchAfterMismatchException, BadRequestException, - AcceptFormatNotSupportedException{ - - try{ - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - PdsProductClasses productClass = resolveProductClass(pdsIdentifier); - PdsLidVid lidvid = resolveIdentifierToLidvid(pdsIdentifier); - - RegistrySearchRequestBuilder searchRequestBuilder = new RegistrySearchRequestBuilder(this.connectionContext); - - if (productClass.isBundle()) { - searchRequestBuilder.matchMembersOfBundle(lidvid); - searchRequestBuilder.onlyBasicProducts(); - } else { - throw new BadRequestException("productMembers endpoint is only valid for products with Product_Class '" + - PdsProductClasses.Product_Bundle + "' (got '" + productClass + "')"); - } - - SearchRequest searchRequest = searchRequestBuilder - .applyMultipleProductsDefaults(fields, "", List.of(), limit, sort, searchAfter, true) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - - } catch (IOException | OpenSearchException | UnparsableQParamException e) { - throw new UnhandledException(e); - } - } - - /** - * Given a PdsProductIdentifier and the name of a document field which is expected to contain an array of LIDVID - * strings, return the chained contents of that field from all documents matching the identifier (multiple docs are - * possible if the identifier is a LID). - * @param identifier the LID/LIDVID for which to retrieve documents - * @param fieldName the name of the document _source property/field from which to extract results - * @return a deduplicated list of the aggregated property/field contents, converted to PdsProductLidvids - */ - private List resolveLidVidsFromProductField(PdsProductIdentifier identifier, String fieldName) - throws OpenSearchException, IOException, NotFoundException, UnhandledException { - - RegistrySearchRequestBuilder searchRequestBuilder = new RegistrySearchRequestBuilder(this.connectionContext); - - if (identifier.isLid()) { - searchRequestBuilder.matchLid(identifier); - } else if (identifier.isLidvid()) { - searchRequestBuilder.matchLidvid(identifier); - } else { - throw new UnhandledException("PdsProductIdentifier identifier is neither LID nor LIDVID. This should never occur"); - } - - SearchRequest searchRequest = searchRequestBuilder - .matchLid(identifier) - .fieldsFromStrings(List.of(fieldName)) - .build(); - - SearchResponse searchResponse = this.openSearchClient.search(searchRequest, HashMap.class); - - if (searchResponse.hits().total().value() == 0) { - throw new NotFoundException("No product found with identifier " + identifier); - } - - return searchResponse.hits().hits().stream().map(hit -> (List) hit.source().get(fieldName)).filter(Objects::nonNull).flatMap(Collection::stream).map(PdsLidVid::fromString).toList(); - } - - - @Override - public ResponseEntity productMemberOf( - String identifier, List fields, Integer limit, List sort, List searchAfter) - throws NotFoundException, UnhandledException, SortSearchAfterMismatchException, BadRequestException, - AcceptFormatNotSupportedException, UnparsableQParamException { - - try{ - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - PdsProductClasses productClass = resolveProductClass(pdsIdentifier); - PdsLidVid lidvid = resolveIdentifierToLidvid(pdsIdentifier); - - List parentIds; - if (productClass.isCollection()) { - parentIds = resolveLidVidsFromProductField(lidvid, "ops:Provenance/ops:parent_bundle_identifier"); - } else if (productClass.isBasicProduct()) { - parentIds = resolveLidVidsFromProductField(lidvid, "ops:Provenance/ops:parent_collection_identifier"); - } else { - throw new BadRequestException("productMembersOf endpoint is not valid for products with Product_Class '" + - PdsProductClasses.Product_Bundle + "' (got '" + productClass + "')"); - } - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .applyMultipleProductsDefaults(fields, "", List.of(), limit, sort, searchAfter, true) - .matchFieldAnyOfIdentifiers("_id", parentIds) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - - } catch (IOException | OpenSearchException e) { - throw new UnhandledException(e); - } - } - - @Override - public ResponseEntity productMemberOfOf( - String identifier, List fields, Integer limit, List sort, List searchAfter) - throws NotFoundException, UnhandledException, SortSearchAfterMismatchException, BadRequestException, - AcceptFormatNotSupportedException, UnparsableQParamException { - - try{ - PdsProductIdentifier pdsIdentifier = PdsProductIdentifier.fromString(identifier); - PdsProductClasses productClass = resolveProductClass(pdsIdentifier); - PdsLidVid lidvid = resolveIdentifierToLidvid(pdsIdentifier); - - List parentIds; - if (productClass.isBasicProduct()) { - parentIds = resolveLidVidsFromProductField(lidvid, "ops:Provenance/ops:parent_bundle_identifier"); - } else { -// TODO: replace with enumeration of acceptable values later - throw new BadRequestException("productMembersOf endpoint is not valid for products with Product_Class '" + - PdsProductClasses.Product_Bundle + "' or '" + PdsProductClasses.Product_Collection + "' (got '" + productClass + "')"); - } - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .applyMultipleProductsDefaults(fields, "", List.of(), limit, sort, searchAfter, true) - .matchFieldAnyOfIdentifiers("_id", parentIds) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - - } catch (IOException | OpenSearchException e) { - throw new UnhandledException(e); - } - } - - @Override - // TODO: Relocate this to ClassesController once common controller code has been extracted/refactored - public ResponseEntity classList(String propertyClass, List fields, List keywords, Integer limit, String q, List sort, List searchAfter) throws Exception { - PdsProductClasses pdsProductClass; - try { - pdsProductClass = PdsProductClasses.fromSwaggerName(propertyClass); - } catch (IllegalArgumentException err) { - throw new BadRequestException(err.getMessage()); - } - - SearchRequest searchRequest = new RegistrySearchRequestBuilder(this.connectionContext) - .applyMultipleProductsDefaults(fields, q, keywords, limit, sort, searchAfter, true) - .matchProductClass(pdsProductClass) - .build(); - - SearchResponse searchResponse = - this.openSearchClient.search(searchRequest, HashMap.class); - - RawMultipleProductResponse products = new RawMultipleProductResponse(searchResponse); - - return formatMultipleProducts(products, fields); - } - - @Override - // TODO: Relocate this to ClassesController once common controller code has been extracted/refactored - public ResponseEntity> classes() throws Exception { - return new ResponseEntity<>(Arrays.stream(PdsProductClasses.values()).map(PdsProductClasses::getSwaggerName).toList(), HttpStatusCode.valueOf(200)); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/controllers/RegistryApiResponseEntityExceptionHandler.java b/service/src/main/java/gov/nasa/pds/api/registry/controllers/RegistryApiResponseEntityExceptionHandler.java deleted file mode 100644 index 2de03b14..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/controllers/RegistryApiResponseEntityExceptionHandler.java +++ /dev/null @@ -1,83 +0,0 @@ -package gov.nasa.pds.api.registry.controllers; - - -import java.util.Set; - -import gov.nasa.pds.api.registry.model.exceptions.*; -import org.springframework.http.HttpHeaders; -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.ControllerAdvice; -import org.springframework.web.bind.annotation.ExceptionHandler; -import org.springframework.web.context.request.WebRequest; -import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler; - - -@ControllerAdvice -public class RegistryApiResponseEntityExceptionHandler extends ResponseEntityExceptionHandler { - - private String errorDisclaimerHeader = "An error occured.\n"; - private String errorDisclaimerFooter = - "For assistance, forward this error message to pds-operator@jpl.nasa.org"; - - // TODO refactor code to avoid repeating oneself. - - private ResponseEntity genericExceptionHandler(RegistryApiException ex, - WebRequest request, String errorDescrpitionSuffix, HttpStatus status) { - - String requestDescription = request.getDescription(false); - String errorDescription = ex.getMessage() + errorDescrpitionSuffix; - String errorIdentifier = ex.getUuid(); - - - String bodyOfResponse = - status.toString() + "\n Request " + requestDescription + " failed with message:\n" - + errorDescription + "(ref:" + errorIdentifier + ")\n" + errorDisclaimerFooter; - return handleExceptionInternal(ex, bodyOfResponse, new HttpHeaders(), status, request); - - } - - - @ExceptionHandler(value = {NotFoundException.class}) - protected ResponseEntity notFound(NotFoundException ex, WebRequest request) { - return genericExceptionHandler(ex, request, "", HttpStatus.NOT_FOUND); - - } - - @ExceptionHandler(value = {BadRequestException.class}) - protected ResponseEntity badRequest(BadRequestException ex, WebRequest request) { - return genericExceptionHandler(ex, request, "", HttpStatus.BAD_REQUEST); - - } - - @ExceptionHandler(value = {UnhandledException.class}) - protected ResponseEntity unhandled(UnhandledException ex, WebRequest request) { - return genericExceptionHandler(ex, request, "", HttpStatus.INTERNAL_SERVER_ERROR); - } - - - @ExceptionHandler(value = {AcceptFormatNotSupportedException.class}) - protected ResponseEntity notAcceptable(AcceptFormatNotSupportedException ex, - WebRequest request) { - Set supportedFormats = ProductsController.getFormatters().keySet(); - String errorDescriptionSuffix = - " Supported formats (in Accept header) are: " + String.join(", ", supportedFormats); - - return genericExceptionHandler(ex, request, errorDescriptionSuffix, HttpStatus.NOT_ACCEPTABLE); - - } - - @ExceptionHandler(value = {SortSearchAfterMismatchException.class}) - protected ResponseEntity missSort(SortSearchAfterMismatchException ex, - WebRequest request) { - return genericExceptionHandler(ex, request, "", HttpStatus.BAD_REQUEST); - } - - @ExceptionHandler(value = {UnparsableQParamException.class}) - protected ResponseEntity unparsableQParam(UnparsableQParamException ex, - WebRequest request) { - return genericExceptionHandler(ex, request, "", HttpStatus.BAD_REQUEST); - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/ApplicationTypeException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/ApplicationTypeException.java deleted file mode 100644 index c390db3a..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/ApplicationTypeException.java +++ /dev/null @@ -1,9 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class ApplicationTypeException extends Exception { - private static final long serialVersionUID = 4336719956245071997L; - - public ApplicationTypeException(String message) { - super(message); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidMismatchException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidMismatchException.java deleted file mode 100644 index 8599aafc..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidMismatchException.java +++ /dev/null @@ -1,12 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class LidVidMismatchException extends Exception { - /** - * - */ - private static final long serialVersionUID = -4675409702552965562L; - - public LidVidMismatchException(String lidvid, String expected, String found) { - super("The lidvid " + lidvid + " was of type " + found + " not of type " + expected); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidNotFoundException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidNotFoundException.java deleted file mode 100644 index b8753e2b..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/LidVidNotFoundException.java +++ /dev/null @@ -1,12 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class LidVidNotFoundException extends Exception { - /** - * - */ - private static final long serialVersionUID = -4675409702552965562L; - - public LidVidNotFoundException(String lidvid) { - super("The lidvid " + lidvid + " was not found"); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/MembershipException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/MembershipException.java deleted file mode 100644 index a87f6dd6..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/MembershipException.java +++ /dev/null @@ -1,10 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class MembershipException extends Exception { - private static final long serialVersionUID = 4619792009605522154L; - - public MembershipException(String lidvid, String membership, String type) { - super("The lidvid '" + lidvid + "' of type " + type + " does not support " + membership - + " membership"); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/NothingFoundException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/NothingFoundException.java deleted file mode 100644 index a55bec36..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/NothingFoundException.java +++ /dev/null @@ -1,8 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class NothingFoundException extends Exception { - /** - * - */ - private static final long serialVersionUID = -987644388715945160L; -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnknownGroupNameException.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnknownGroupNameException.java deleted file mode 100644 index 10d3ab0b..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnknownGroupNameException.java +++ /dev/null @@ -1,11 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -import java.util.Set; - -public class UnknownGroupNameException extends Exception { - private static final long serialVersionUID = -5630215762959235121L; - - public UnknownGroupNameException(String group, Set known) { - super("Unknown group '" + group + "'. All known groups: " + String.join(", ", known)); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnsupportedSearchProperty.java b/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnsupportedSearchProperty.java deleted file mode 100644 index 06f6ca37..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/exceptions/UnsupportedSearchProperty.java +++ /dev/null @@ -1,16 +0,0 @@ -package gov.nasa.pds.api.registry.exceptions; - -public class UnsupportedSearchProperty extends Exception { - - /** - * - */ - private static final long serialVersionUID = 1L; - - public UnsupportedSearchProperty(String msg) { - - super(msg); - - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/Antlr4SearchListener.java b/service/src/main/java/gov/nasa/pds/api/registry/model/Antlr4SearchListener.java deleted file mode 100644 index f5fb4fd3..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/Antlr4SearchListener.java +++ /dev/null @@ -1,231 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import gov.nasa.pds.api.registry.lexer.SearchBaseListener; -import gov.nasa.pds.api.registry.lexer.SearchParser; - -import java.util.ArrayDeque; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Deque; -import java.util.List; -import java.util.stream.Collectors; -import org.antlr.v4.runtime.misc.ParseCancellationException; -import org.opensearch.client.json.JsonData; -import org.opensearch.client.opensearch._types.FieldValue; -import org.opensearch.client.opensearch._types.query_dsl.BoolQuery; -import org.opensearch.client.opensearch._types.query_dsl.MatchQuery; -import org.opensearch.client.opensearch._types.query_dsl.Query; -import org.opensearch.client.opensearch._types.query_dsl.RangeQuery; -import org.opensearch.client.opensearch._types.query_dsl.SimpleQueryStringQuery; -import org.opensearch.client.opensearch._types.query_dsl.TermsQuery; -import org.opensearch.client.opensearch._types.query_dsl.TermsQueryField; -import org.opensearch.client.opensearch._types.query_dsl.TermsSetQuery; -import org.opensearch.client.opensearch._types.query_dsl.WildcardQuery; -import org.opensearch.client.opensearch._types.query_dsl.Operator; -import org.opensearch.index.query.RangeQueryBuilder; -import org.opensearch.index.query.SimpleQueryStringBuilder; -import org.opensearch.index.query.TermQueryBuilder; -import org.opensearch.index.query.QueryBuilder; - -public class Antlr4SearchListener extends SearchBaseListener { - enum conjunctions { - AND, OR - }; - - enum operation { - eq, ge, gt, le, lt, ne - }; - - private static final Logger log = LoggerFactory.getLogger(Antlr4SearchListener.class); - - private BoolQuery.Builder queryBuilder = new BoolQuery.Builder(); - private conjunctions conjunction = conjunctions.AND; // DEFAULT - - final private Deque stackQueryBuilders = new ArrayDeque(); - final private Deque stack_conjunction = new ArrayDeque(); - - private operation operator = null; - - public Antlr4SearchListener() { - super(); - } - - - @Override - public void exitQuery(SearchParser.QueryContext ctx) {} - - @Override - public void enterGroup(SearchParser.GroupContext ctx) { - log.debug("Enter Group"); - - this.stack_conjunction.push(this.conjunction); - this.conjunction = conjunctions.AND; // DEFAULT - - this.stackQueryBuilders.push(this.queryBuilder); - this.queryBuilder = new BoolQuery.Builder(); - - } - - @Override - public void exitGroup(SearchParser.GroupContext ctx) { - - log.debug("Exit Group"); - - BoolQuery.Builder upperBoolQueryBuilder = this.stackQueryBuilders.pop(); - this.conjunction = this.stack_conjunction.pop(); - - Query innerQuery = this.queryBuilder.build().toQuery(); - if (ctx.NOT() != null) { - upperBoolQueryBuilder.mustNot(innerQuery); - } else { - if (this.conjunction == conjunctions.AND) { - upperBoolQueryBuilder.must(innerQuery); - } else { - upperBoolQueryBuilder.should(innerQuery); - } - } - - this.queryBuilder = upperBoolQueryBuilder; - - } - - @Override - public void enterAndStatement(SearchParser.AndStatementContext ctx) { - log.debug("Enter AndStatement"); - this.conjunction = conjunctions.AND; - } - - @Override - public void enterOrStatement(SearchParser.OrStatementContext ctx) { - log.debug("Enter OrStatement"); - this.conjunction = conjunctions.OR; - } - - @Override - public void exitOrStatement(SearchParser.OrStatementContext ctx) { - log.debug("Exit OrStatement"); - this.queryBuilder.minimumShouldMatch("1"); - } - - - @Override - public void enterComparison(SearchParser.ComparisonContext ctx) {} - - @Override - public void exitComparison(SearchParser.ComparisonContext ctx) { - log.debug("Exit comparison"); - final String left = SearchUtil.jsonPropertyToOpenProperty(ctx.FIELD().getSymbol().getText()); - - String right; - Query comparatorQuery = null; - - - if (ctx.NUMBER() != null) { - right = ctx.NUMBER().getSymbol().getText(); - } else if (ctx.STRINGVAL() != null) { - right = ctx.STRINGVAL().getSymbol().getText(); - right = right.replaceAll("^\"|\"$", ""); - } else { - throw new ParseCancellationException( - "A right component (literal) of a comparison is neither a number or a string. Number and String are the only types supported for literals."); - } - - if (this.operator == operation.eq || this.operator == operation.ne) { - - - FieldValue fieldValue = new FieldValue.Builder().stringValue(right).build(); - - MatchQuery matchQueryBuilder = new MatchQuery.Builder().field(left).query(fieldValue).build(); - - comparatorQuery = matchQueryBuilder.toQuery(); - - if (this.operator == operation.ne) { - comparatorQuery = new BoolQuery.Builder().mustNot(comparatorQuery).build().toQuery(); - } - - - - } else { - RangeQuery.Builder rangeQueryBuilder = new RangeQuery.Builder(); - - rangeQueryBuilder = rangeQueryBuilder.field(left); - - if (this.operator == operation.ge) - rangeQueryBuilder.gte(JsonData.of(right)); - else if (this.operator == operation.gt) - rangeQueryBuilder.gt(JsonData.of(right)); - else if (this.operator == operation.le) - rangeQueryBuilder.lte(JsonData.of(right)); - else if (this.operator == operation.lt) - rangeQueryBuilder.lt(JsonData.of(right)); - else { - throw new ParseCancellationException("Operator " + this.operator.name() - + " is not supported. Supported comparison operators are eq, ne, gt, gte, lt, lte."); - } - - comparatorQuery = rangeQueryBuilder.build().toQuery(); - - } - - if (this.conjunction == conjunctions.AND) { - this.queryBuilder.must(comparatorQuery); - } else { - this.queryBuilder.should(comparatorQuery); - } - - } - - @Override - public void enterLikeComparison(SearchParser.LikeComparisonContext ctx) {} - - @Override - public void exitLikeComparison(SearchParser.LikeComparisonContext ctx) { - log.debug("Exit likeComparison"); - final String left = SearchUtil.jsonPropertyToOpenProperty(ctx.FIELD().getSymbol().getText()); - - String right = ctx.STRINGVAL().getText(); - // remove quotes - right = right.replaceAll("^\"|\"$", ""); - - SimpleQueryStringQuery simpleQueryString = new SimpleQueryStringQuery.Builder().fields(left) - .query(right).fuzzyMaxExpansions(0).build(); - - Query query = simpleQueryString.toQuery(); - log.debug("Exit Like comparison: left member is " + left + " right member is " + right); - - if (this.conjunction == conjunctions.AND) { - this.queryBuilder.must(query); - } else { - this.queryBuilder.should(query); - } - - } - - @Override - public void enterOperator(SearchParser.OperatorContext ctx) { - if (ctx.EQ() != null) - this.operator = operation.eq; - else if (ctx.GE() != null) - this.operator = operation.ge; - else if (ctx.GT() != null) - this.operator = operation.gt; - else if (ctx.LE() != null) - this.operator = operation.le; - else if (ctx.LT() != null) - this.operator = operation.lt; - else if (ctx.NE() != null) - this.operator = operation.ne; - else { - log.error("Panic, there are more operators than this versionof the lexer knows about"); - throw new ParseCancellationException(); // PANIC: listener out of sync with the grammar - } - } - - public BoolQuery getBoolQuery() { - log.debug("Get boolQuery"); - return this.queryBuilder.build(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/BlobUtil.java b/service/src/main/java/gov/nasa/pds/api/registry/model/BlobUtil.java deleted file mode 100644 index 717faa86..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/BlobUtil.java +++ /dev/null @@ -1,66 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.InputStream; -import java.io.OutputStream; -import java.util.Base64; -import java.util.zip.InflaterInputStream; - -/** - * Utility class to extract BLOBs stored in DB - * - * @author karpenko - */ -public class BlobUtil { - public static final String JSON_BLOB_PROPERTY = "ops:Label_File_Info/ops:json_blob"; - public static final String XML_BLOB_PROPERTY = "ops:Label_File_Info/ops:blob"; - - /** - * Decompress base64 encoded BLOB. - * - * @param blob Base64 encoded compressed BLOB - * @return Original BLOB value as a string - * @throws Exception an exception - */ - public static String blobToString(String blob) throws Exception { - byte[] data = Base64.getDecoder().decode(blob); - return blobToString(data); - } - - /** - * Decompress binary BLOB. - * - * @param blob compressed BLOB - * @return Original BLOB value as a string - * @throws Exception an exception - */ - public static String blobToString(byte[] blob) throws Exception { - ByteArrayInputStream is = new ByteArrayInputStream(blob); - // Decompress ("inflate") the BLOB - InflaterInputStream source = new InflaterInputStream(is); - - ByteArrayOutputStream dest = new ByteArrayOutputStream(); - copy(source, dest); - dest.close(); - - return dest.toString("utf-8"); - } - - /** - * Copy data from input to output stream - * - * @param source source stream - * @param dest destination stream - * @throws Exception an exception - */ - private static void copy(InputStream source, OutputStream dest) throws Exception { - byte[] buf = new byte[1024]; - - int count = 0; - while ((count = source.read(buf)) >= 0) { - dest.write(buf, 0, count); - } - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/EntityProduct.java b/service/src/main/java/gov/nasa/pds/api/registry/model/EntityProduct.java deleted file mode 100644 index c0aee1a3..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/EntityProduct.java +++ /dev/null @@ -1,146 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import com.fasterxml.jackson.annotation.JsonFormat; -import com.fasterxml.jackson.annotation.JsonProperty; - -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; -import java.util.Map; - -public class EntityProduct { - public static final String[] JSON_PROPERTIES = new String[] {"lidvid", "title", "product_class", - "pds:Time_Coordinates/pds:start_date_time", "pds:Time_Coordinates/pds:stop_date_time", - "pds:Modification_Detail/pds:modification_date", "pds:File/pds:creation_date_time", - "ref_lid_instrument_host", "ref_lid_instrument", "ref_lid_investigation", "ref_lid_target", - "vid", "ops:Label_File_Info/ops:file_ref", "ops:Tracking_Meta/ops:archive_status"}; - - @JsonProperty("lidvid") - private String lidvid; - - @JsonProperty("title") - private String title; - - @JsonProperty("product_class") - private String productClass; - - // for compliance with data loaded with version of harvest < 3.7.4 - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("pds:Time_Coordinates/pds:start_date_time") - private List start_date_time; - - // for compliance with data loaded with version of harvest < 3.7.4 - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("pds:Time_Coordinates/pds:stop_date_time") - private List stop_date_time; - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("pds:Modification_Detail/pds:modification_date") - private List modification_date; - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("pds:File/pds:creation_date_time") - private List creation_date; - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ref_lid_instrument_host") - private List ref_lid_instrument_host = new ArrayList(); - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ref_lid_instrument") - private List ref_lid_instrument = new ArrayList(); - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ref_lid_investigation") - private List ref_lid_investigation = new ArrayList(); - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ref_lid_target") - private List ref_lid_target = new ArrayList(); - - @JsonProperty("vid") - private String version; - - // for compliance with data loaded with version of harvest < 3.7.4 - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ops:Label_File_Info/ops:file_ref") - private List pds4FileReference; - - @JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY) - @JsonProperty("ops:Tracking_Meta/ops:archive_status") - private List archive_status; - - private Map properties; - - public void setProperties(Map properties) { - this.properties = properties; - } - - public Map getProperties() { - return properties; - } - - public String getLidVid() { - return this.lidvid; - } - - public String getTitle() { - return this.title; - } - - public String getProductClass() { - return this.productClass; - } - - public static Iterable emptyIfNull(Iterable iterable) { - return iterable == null ? Collections.emptyList() : iterable; - } - - public List getRef_lid_instrument() { - return ref_lid_instrument; - } - - public List getRef_lid_instrument_host() { - return ref_lid_instrument_host; - } - - public List getRef_lid_investigation() { - return ref_lid_investigation; - } - - public List getRef_lid_target() { - return ref_lid_target; - } - - private static String getFirstElmentOrNull(List l) { - return l != null ? l.get(0) : null; - } - - public String getPDS4FileRef() { - return EntityProduct.getFirstElmentOrNull(this.pds4FileReference); - } - - public String getStartDateTime() { - return EntityProduct.getFirstElmentOrNull(this.start_date_time); - } - - public String getStopDateTime() { - return EntityProduct.getFirstElmentOrNull(this.stop_date_time); - } - - public List getModificationDate() { - return modification_date; - } - - public List getCreationDate() { - return creation_date; - } - - public String getVersion() { - return version; - } - - public List getArchiveStatus() { - return this.archive_status; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/ErrorMessageFactory.java b/service/src/main/java/gov/nasa/pds/api/registry/model/ErrorMessageFactory.java deleted file mode 100644 index fee441db..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/ErrorMessageFactory.java +++ /dev/null @@ -1,36 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import java.util.ArrayList; -import jakarta.servlet.http.HttpServletRequest; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.stereotype.Component; -import gov.nasa.pds.model.ErrorMessage; - -@Component -// TODO replace that with a default error manangement in spring-boot, -// see https://github.com/NASA-PDS/registry-api/issues/286 -public class ErrorMessageFactory { - - @Autowired - HttpServletRequest request; - - public Object get(Exception err) { - ErrorMessage em = new ErrorMessage(); - - ArrayList requestArray = new ArrayList(); - - requestArray.add(this.request.getRequestURL().toString()); - - String queryString; - if ((queryString = this.request.getQueryString()) != null) { - requestArray.add(queryString); - } - - em.setRequest(String.join("?", requestArray)); - - em.setMessage(err.getMessage() == null || err.getMessage().length() == 0 ? err.toString() - : err.getMessage()); - return em; - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/Pds4ProductFactory.java b/service/src/main/java/gov/nasa/pds/api/registry/model/Pds4ProductFactory.java deleted file mode 100644 index 4f97c059..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/Pds4ProductFactory.java +++ /dev/null @@ -1,167 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import java.util.ArrayList; -import java.util.List; -import java.util.Map; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import gov.nasa.pds.model.Pds4Metadata; -import gov.nasa.pds.model.Pds4MetadataOpsDataFile; -import gov.nasa.pds.model.Pds4MetadataOpsLabelFileInfo; -import gov.nasa.pds.model.Pds4MetadataOpsTrackingMeta; -import gov.nasa.pds.model.Pds4Product; - -/** - * Creates Pds4Product object from opensearch key-value field map. - * - * @author karpenko - */ -public class Pds4ProductFactory { - private static final Logger log = LoggerFactory.getLogger(Pds4ProductFactory.class); - - // JSON BLOB - public static final String FLD_JSON_BLOB = BlobUtil.JSON_BLOB_PROPERTY; - public static final String FLD_XML_BLOB = BlobUtil.XML_BLOB_PROPERTY; - - // Data File Info - public static final String FLD_DATA_FILE_NAME = "ops:Data_File_Info/ops:file_name"; - public static final String FLD_DATA_FILE_CREATION = "ops:Data_File_Info/ops:creation_date_time"; - public static final String FLD_DATA_FILE_REF = "ops:Data_File_Info/ops:file_ref"; - public static final String FLD_DATA_FILE_SIZE = "ops:Data_File_Info/ops:file_size"; - public static final String FLD_DATA_FILE_MD5 = "ops:Data_File_Info/ops:md5_checksum"; - public static final String FLD_DATA_FILE_MIME_TYPE = "ops:Data_File_Info/ops:mime_type"; - - // Label Info - public static final String FLD_LABEL_FILE_NAME = "ops:Label_File_Info/ops:file_name"; - public static final String FLD_LABEL_FILE_CREATION = "ops:Label_File_Info/ops:creation_date_time"; - public static final String FLD_LABEL_FILE_REF = "ops:Label_File_Info/ops:file_ref"; - public static final String FLD_LABEL_FILE_SIZE = "ops:Label_File_Info/ops:file_size"; - public static final String FLD_LABEL_FILE_MD5 = "ops:Label_File_Info/ops:md5_checksum"; - - // Tracking_Meta - public static final String FLD_TRACK_META_ARCHIVE_STATUS = "ops:Tracking_Meta/ops:archive_status"; - - // Node Name - public static final String FLD_NODE_NAME = "ops:Harvest_Info/ops:node_name"; - - /** - * Create Pds4Product object from opensearch key-value field map. - * - * @param lidvid product LIDVID - * @param fieldMap key-value field map - * @return new Pds4Product object - */ - public static Pds4Product createProduct(String lidvid, Map fieldMap, - boolean isJSON) { - Pds4Product prod = new Pds4Product(); - prod.setId(lidvid); - - if (fieldMap == null) - return prod; - - // Pds4 JSON BLOB - String blob = null; - String decoded_blob = null; - try { - - if (isJSON) { - blob = getVal(fieldMap, FLD_JSON_BLOB); - decoded_blob = BlobUtil.blobToString(String.valueOf(blob)); - } else { - int first, last; - blob = getVal(fieldMap, FLD_XML_BLOB); - decoded_blob = BlobUtil.blobToString(String.valueOf(blob)); - decoded_blob = decoded_blob.replaceAll("\r", ""); - first = decoded_blob.indexOf("", first + 2); - decoded_blob = decoded_blob.replace(decoded_blob.substring(first, last + 2), ""); - first = decoded_blob.indexOf(" fieldMap) { - Pds4Metadata meta = new Pds4Metadata(); - - ArrayList nodeNames = (ArrayList) fieldMap.get(FLD_NODE_NAME); - String nodeName = nodeNames.get(0); - meta.setNodeName(nodeName); - meta.setOpsColonLabelFileInfo(createLabelFile(fieldMap)); - meta.setOpsColonDataFiles(createDataFiles(fieldMap)); - meta.setOpsColonTrackingMeta(createTrackingMeta(fieldMap)); - return meta; - } - - @SuppressWarnings("unchecked") - private static String getVal(Map fieldMap, String fieldName) { - return ((ArrayList) fieldMap.get(fieldName)).get(0); - } - - private static Pds4MetadataOpsLabelFileInfo createLabelFile(Map fieldMap) { - ArrayList vals = (ArrayList) fieldMap.get(FLD_LABEL_FILE_NAME); - - if (vals == null) - return null; - - Pds4MetadataOpsLabelFileInfo item = new Pds4MetadataOpsLabelFileInfo(); - - String val = vals.get(0); - - item.setOpsColonFileName(val); - - val = getVal(fieldMap, FLD_LABEL_FILE_CREATION); - item.setOpsColonCreationDate(val); - - val = getVal(fieldMap, FLD_LABEL_FILE_REF); - item.setOpsColonFileRef(val); - - val = getVal(fieldMap, FLD_LABEL_FILE_SIZE); - item.setOpsColonFileSize(val); - - val = getVal(fieldMap, FLD_LABEL_FILE_MD5); - item.setOpsColonMd5Checksum(val); - - return item; - } - - @SuppressWarnings("rawtypes") - private static List createDataFiles(Map fieldMap) { - ArrayList vals = (ArrayList) fieldMap.get(FLD_DATA_FILE_NAME); - if (vals == null) { - return new ArrayList(); - } - - List items = new ArrayList(); - - for (int i = 0; i < ((List) vals).size(); i++) { - Pds4MetadataOpsDataFile item = new Pds4MetadataOpsDataFile(); - item.setOpsColonFileName((String) ((List) fieldMap.get(FLD_DATA_FILE_CREATION)).get(i)); - item.setOpsColonCreationDate((String) ((List) fieldMap.get(FLD_DATA_FILE_CREATION)).get(i)); - item.opsColonFileRef((String) ((List) fieldMap.get(FLD_DATA_FILE_REF)).get(i)); - item.setOpsColonFileSize((String) ((List) fieldMap.get(FLD_DATA_FILE_SIZE)).get(i)); - item.setOpsColonMd5Checksum((String) ((List) fieldMap.get(FLD_DATA_FILE_MD5)).get(i)); - item.setOpsColonMimeType((String) ((List) fieldMap.get(FLD_DATA_FILE_MIME_TYPE)).get(i)); - items.add(item); - } - - return items; - } - - private static Pds4MetadataOpsTrackingMeta createTrackingMeta(Map fieldMap) { - Pds4MetadataOpsTrackingMeta item = new Pds4MetadataOpsTrackingMeta(); - - item.setOpsColonArchiveStatus((String) fieldMap.get(FLD_TRACK_META_ARCHIVE_STATUS)); - return item; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/ProductQueryBuilderUtil.java b/service/src/main/java/gov/nasa/pds/api/registry/model/ProductQueryBuilderUtil.java deleted file mode 100644 index 759ba779..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/ProductQueryBuilderUtil.java +++ /dev/null @@ -1,95 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import java.util.ArrayList; -import java.util.List; -import java.util.StringTokenizer; - -import jakarta.annotation.PostConstruct; - -import org.antlr.v4.runtime.BailErrorStrategy; -import org.antlr.v4.runtime.CharStreams; -import org.antlr.v4.runtime.CodePointCharStream; -import org.antlr.v4.runtime.CommonTokenStream; -import org.antlr.v4.runtime.tree.ParseTree; -import org.antlr.v4.runtime.tree.ParseTreeWalker; -import org.opensearch.index.query.BoolQueryBuilder; -import org.opensearch.index.query.QueryBuilders; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Value; -import org.springframework.stereotype.Component; - -import gov.nasa.pds.api.registry.GroupConstraint; -import gov.nasa.pds.api.registry.lexer.SearchLexer; -import gov.nasa.pds.api.registry.lexer.SearchParser; - -@Component -public class ProductQueryBuilderUtil { - private static final Logger log = LoggerFactory.getLogger(ProductQueryBuilderUtil.class); - - @Value("${filter.archiveStatus}") - private String propArchiveStatusFilter; - private static List archiveStatusFilter; - - - /** - * Init archive status filter - */ - @PostConstruct - public void init() { - if (propArchiveStatusFilter == null) - return; - - List list = new ArrayList<>(); - - StringTokenizer tkz = new StringTokenizer(propArchiveStatusFilter, ",; "); - while (tkz.hasMoreTokens()) { - String token = tkz.nextToken(); - list.add(token); - } - - if (!list.isEmpty()) { - archiveStatusFilter = list; - } - } - - public static void addArchiveStatusFilter(BoolQueryBuilder boolQuery) { - log.debug("addArchiveStatusFilter: " + archiveStatusFilter); - - if (archiveStatusFilter == null || archiveStatusFilter.isEmpty()) - return; - - boolQuery.must( - QueryBuilders.termsQuery("ops:Tracking_Meta/ops:archive_status", archiveStatusFilter)); - } - - public static void addHistoryStopband(BoolQueryBuilder boolQuery) { - boolQuery.mustNot(QueryBuilders.existsQuery("ops:Provenance/ops:superseded_by")); - } - - public static void addPresetCriteria(BoolQueryBuilder boolQuery, GroupConstraint presetCriteria) { - if (presetCriteria != null) { - int filterTermsKeysCount = presetCriteria.filterToAny().keySet().size(); - if (filterTermsKeysCount > 1) { - throw new RuntimeException( - "Filtering on multiple keys is undefined and not supported by OpenSearch terms query"); - } - - presetCriteria.must().forEach((key, list) -> { - list.forEach(value -> { - boolQuery.must(QueryBuilders.termQuery(key, value)); - }); - }); - presetCriteria.filterToAny().forEach((key, list) -> { - boolQuery.filter(QueryBuilders.termsQuery(key, list)); - }); - presetCriteria.mustNot().forEach((key, list) -> { - list.forEach(value -> { - boolQuery.mustNot(QueryBuilders.termQuery(key, value)); - }); - }); - } - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/ProductVersionSelector.java b/service/src/main/java/gov/nasa/pds/api/registry/model/ProductVersionSelector.java deleted file mode 100644 index 84938e50..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/ProductVersionSelector.java +++ /dev/null @@ -1,27 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -/** - * Used by API calls, such as "/bundles/{lidvid}/collections", - * "/bundles/{lidvid}/collections/latest", "/bundles/{lidvid}/collections/all", etc., to select - * product versions. - * - * @author karpenko - */ -public enum ProductVersionSelector { - /** - * Original version of a product, e.g., from LIDVID reference field - */ - ORIGINAL, - /** - * All versions of a product - */ - ALL, - /** - * Latest version of a product - */ - LATEST, - /** - * A specified version of a product - */ - TYPED -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/SearchUtil.java b/service/src/main/java/gov/nasa/pds/api/registry/model/SearchUtil.java deleted file mode 100644 index d7b617c4..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/SearchUtil.java +++ /dev/null @@ -1,155 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import java.net.URI; -import java.net.URISyntaxException; -import java.net.URL; -import java.util.ArrayList; -import java.util.List; -import org.apache.http.client.utils.URIBuilder; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import gov.nasa.pds.api.registry.exceptions.UnsupportedSearchProperty; -import gov.nasa.pds.model.Metadata; -import gov.nasa.pds.model.PdsProduct; -import gov.nasa.pds.model.Reference; - -public class SearchUtil { - - private static final Logger log = LoggerFactory.getLogger(SearchUtil.class); - - static public String jsonPropertyToOpenProperty(String jsonProperty) { - return jsonProperty.replace(".", "/"); - } - - static public String[] jsonPropertyToOpenProperty(String[] jsonProperties) { - if (jsonProperties != null && jsonProperties.length > 0) { - for (int i = 0; i < jsonProperties.length; i++) { - jsonProperties[i] = jsonPropertyToOpenProperty(jsonProperties[i]); - } - } - return jsonProperties; - } - - static public List jsonPropertyToOpenProperty(List jsonProperties) { - if (jsonProperties != null && jsonProperties.size() > 0) { - for (int i = 0; i < jsonProperties.size(); i++) { - jsonProperties.set(i, jsonPropertyToOpenProperty(jsonProperties.get(i))); - } - } - return jsonProperties; - } - - static public String openPropertyToJsonProperty(String openProperty) - throws UnsupportedSearchProperty { - - return openProperty.replace('/', '.'); - } - - static private void addReference(ArrayList to, String ID, URL baseURL) { - Reference reference = new Reference(); - reference.setId(ID); - - String spec = "/products/" + reference.getId(); - - try { - - URIBuilder uriBuilder = new URIBuilder(baseURL.toURI()); - - log.debug("Reference base path is: " + uriBuilder.getPath()); - if (uriBuilder.getPath() == null) { - uriBuilder.setPath(spec); - } else { - uriBuilder.setPath(uriBuilder.getPath() + spec); - } - - URI uri = uriBuilder.build().normalize(); - - log.debug("Reference path is: " + uri.toString()); - reference.setHref(uri.toString()); - - } catch (URISyntaxException e) { - log.warn("Unable to create external URL for reference "); - e.printStackTrace(); - reference.setHref(spec); - } - - to.add(reference); - } - - static private PdsProduct addPropertiesFromESEntity(PdsProduct product, EntityProduct ep, - URL baseURL) { - product.setId(ep.getLidVid()); - product.setType(ep.getProductClass()); - - String title = ep.getTitle(); - if (title != null) { - product.setTitle(ep.getTitle()); - } - - String startDateTime = ep.getStartDateTime(); - if (startDateTime != null) { - product.setStartDateTime(startDateTime); - } - - String stopDateTime = ep.getStopDateTime(); - if (stopDateTime != null) { - product.setStopDateTime(ep.getStopDateTime()); - } - - ArrayList investigations = new ArrayList(); - ArrayList observationSystemComponent = new ArrayList(); - ArrayList targets = new ArrayList(); - Metadata meta = new Metadata(); - // String baseURL = - // ServletUriComponentsBuilder.fromCurrentContextPath().build().toUriString(); - - String version = ep.getVersion(); - if (version != null) { - meta.setVersion(ep.getVersion()); - } - - List creationDateTime = ep.getCreationDate(); - if (creationDateTime != null && !creationDateTime.isEmpty()) { - meta.setCreationDateTime(creationDateTime.get(0)); - } - - List updateDateTime = ep.getModificationDate(); - if (updateDateTime != null && !updateDateTime.isEmpty()) { - // TODO check which modification time to use when there are more than one - meta.setUpdateDateTime(updateDateTime.get(0)); - } - - String labelUrl = ep.getPDS4FileRef(); - if (labelUrl != null) { - meta.setLabelUrl(labelUrl); - } - - for (String id : ep.getRef_lid_instrument_host()) { - SearchUtil.addReference(observationSystemComponent, id, baseURL); - } - for (String id : ep.getRef_lid_instrument()) { - SearchUtil.addReference(observationSystemComponent, id, baseURL); - } - for (String id : ep.getRef_lid_investigation()) { - SearchUtil.addReference(investigations, id, baseURL); - } - for (String id : ep.getRef_lid_target()) { - SearchUtil.addReference(targets, id, baseURL); - } - - product.setInvestigations(investigations); - product.setMetadata(meta); - product.setObservingSystemComponents(observationSystemComponent); - product.setTargets(targets); - - return product; - } - - static public PdsProduct entityProductToAPIProduct(EntityProduct ep, URL baseURL) { - log.debug("convert EntityProduct (ep) to API object without XML label"); - - PdsProduct product = new PdsProduct(); - - return addPropertiesFromESEntity(product, ep, baseURL); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/Unlimited.java b/service/src/main/java/gov/nasa/pds/api/registry/model/Unlimited.java deleted file mode 100644 index 3136c346..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/Unlimited.java +++ /dev/null @@ -1,38 +0,0 @@ -package gov.nasa.pds.api.registry.model; - -import gov.nasa.pds.api.registry.LidvidsContext; - -import java.util.List; - -class Unlimited implements LidvidsContext { - final private String lidvid; - - Unlimited(String id) { - this.lidvid = id; - } - - @Override - public String getProductIdentifierStr() { - return this.lidvid; - } - - @Override - public Integer getLimit() { - return Integer.MAX_VALUE; - } - - @Override - public List getSortFields() { - return List.of("ops:Harvest_Info/ops:harvest_date_time"); - } - - @Override - public List getSearchAfterValues() { - return List.of(""); // TODO: Check whether this actually works or if it needs to be set per-page in the contexts in which Unlimited is used - } - - @Override - public boolean getSingletonResultExpected() { - return false; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/Pds4ProductBusinessObject.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/Pds4ProductBusinessObject.java deleted file mode 100644 index fb30a4df..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/Pds4ProductBusinessObject.java +++ /dev/null @@ -1,178 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.net.URL; -import java.util.ArrayList; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.TreeSet; -import org.opensearch.search.SearchHit; -import org.opensearch.search.SearchHits; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.api.registry.model.Pds4ProductFactory; -import gov.nasa.pds.api.registry.search.HitIterator; -import gov.nasa.pds.model.Pds4Product; -import gov.nasa.pds.model.Pds4Products; -import gov.nasa.pds.model.Summary; - - -public class Pds4ProductBusinessObject extends ProductBusinessLogicImpl { - private static final Logger log = LoggerFactory.getLogger(Pds4ProductBusinessObject.class); - @SuppressWarnings("unused") - private ObjectMapper objectMapper; - private Pds4Product product = null; - private Pds4Products products = null; - @SuppressWarnings("unused") - private URL baseURL; - - public final boolean isJSON; - public final String[] PDS4_PRODUCT_FIELDS; - - public Pds4ProductBusinessObject(boolean isJSON) { - super(); - String temp[] = { - // BLOB - (isJSON ? Pds4ProductFactory.FLD_JSON_BLOB : Pds4ProductFactory.FLD_XML_BLOB), - - // Data File Info - Pds4ProductFactory.FLD_DATA_FILE_NAME, Pds4ProductFactory.FLD_DATA_FILE_CREATION, - Pds4ProductFactory.FLD_DATA_FILE_REF, Pds4ProductFactory.FLD_DATA_FILE_SIZE, - Pds4ProductFactory.FLD_DATA_FILE_MD5, Pds4ProductFactory.FLD_DATA_FILE_MIME_TYPE, - - // Label Info - Pds4ProductFactory.FLD_LABEL_FILE_NAME, Pds4ProductFactory.FLD_LABEL_FILE_CREATION, - Pds4ProductFactory.FLD_LABEL_FILE_REF, Pds4ProductFactory.FLD_LABEL_FILE_SIZE, - Pds4ProductFactory.FLD_LABEL_FILE_MD5, - - // Tracking Meta - Pds4ProductFactory.FLD_TRACK_META_ARCHIVE_STATUS, - - // Node Name - Pds4ProductFactory.FLD_NODE_NAME}; - - this.PDS4_PRODUCT_FIELDS = temp; - this.isJSON = isJSON; - } - - @Override - public String[] getMaximallyRequiredFields() { - return this.PDS4_PRODUCT_FIELDS; - } - - @Override - public String[] getMinimallyRequiredFields() { - return this.PDS4_PRODUCT_FIELDS; - } - - @Override - public Object getResponse() { - return this.product == null ? this.products : this.product; - } - - @Override - public void setObjectMapper(ObjectMapper om) { - this.objectMapper = om; - } - - - @Override - public void setResponse(Map kvp, List fields) { - // TODO: to be implemented - this.product = null; - } - - @Override - public void setResponse(SearchHit hit, List fields) { - this.product = Pds4ProductFactory.createProduct(hit.getId(), hit.getSourceAsMap(), this.isJSON); - } - - @Override - public int setResponse(HitIterator hits, Summary summary, List fields) { - List list = new ArrayList(); - Pds4Products products = new Pds4Products(); - Set uniqueProperties = new TreeSet(); - - for (Map kvp : hits) { - - uniqueProperties.addAll(getFilteredProperties(kvp, fields, null).keySet()); - - try { - Pds4Product prod = Pds4ProductFactory.createProduct(hits.getCurrentId(), kvp, this.isJSON); - list.add(prod); - } catch (Throwable t) { - String lidvid = "unknown"; - if (kvp.containsKey("lidvid")) { - lidvid = kvp.get("lidvid").toString(); - } - log.error("DATA ERROR: could not convert opensearch document to Pds4Product for lidvid: " - + lidvid, t); - } - } - - products.setData(list); - products.setSummary(summary); - summary.setProperties(new ArrayList(uniqueProperties)); - this.products = products; - return list.size(); - } - - @Override - public int setResponse(SearchHits hits, Summary summary, List fields) { - List list = new ArrayList(); - Pds4Products products = new Pds4Products(); - Set uniqueProperties = new TreeSet(); - - // Products - for (SearchHit hit : hits) { - String id = hit.getId(); - Map fieldMap = hit.getSourceAsMap(); - - uniqueProperties.addAll(getFilteredProperties(fieldMap, fields, null).keySet()); - - try { - Pds4Product prod = Pds4ProductFactory.createProduct(id, fieldMap, this.isJSON); - list.add(prod); - } catch (Throwable t) { - log.error("DATA ERROR: could not convert opensearch document to Pds4Product for lidvid: " - + hit.getId(), t); - } - } - products.setData(list); - products.setSummary(summary); - summary.setProperties(new ArrayList(uniqueProperties)); - this.products = products; - return (int) hits.getTotalHits().value; - } - - - @Override - public void setResponse(List> hits, Summary summary, List fields) { - List list = new ArrayList(); - Pds4Products products = new Pds4Products(); - Set uniqueProperties = new TreeSet(); - String id; - // Products - for (Map hit : hits) { - // TODO complete that - id = (String) hit.get("_id"); - uniqueProperties.addAll(getFilteredProperties(hit, fields, null).keySet()); - - try { - Pds4Product prod = Pds4ProductFactory.createProduct(id, hit, this.isJSON); - list.add(prod); - } catch (Throwable t) { - log.error( - "DATA ERROR: could not convert opensearch document to Pds4Product for lidvid: " + id, - t); - } - } - products.setData(list); - products.setSummary(summary); - summary.setProperties(new ArrayList(uniqueProperties)); - this.products = products; - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/PdsProductBusinessObject.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/PdsProductBusinessObject.java deleted file mode 100644 index 8845d73d..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/PdsProductBusinessObject.java +++ /dev/null @@ -1,172 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.TreeSet; -import org.opensearch.search.SearchHit; -import org.opensearch.search.SearchHits; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.api.registry.model.EntityProduct; -import gov.nasa.pds.api.registry.model.SearchUtil; -import gov.nasa.pds.api.registry.search.HitIterator; -import gov.nasa.pds.model.PdsProduct; -import gov.nasa.pds.model.PdsProducts; -import gov.nasa.pds.model.Summary; - - -public class PdsProductBusinessObject extends ProductBusinessLogicImpl { - private static final Logger log = LoggerFactory.getLogger(PdsProductBusinessObject.class); - private ObjectMapper objectMapper; - private PdsProduct product = null; - private PdsProducts products = null; - - - @Override - public String[] getMaximallyRequiredFields() { - return new String[0]; - } - - @Override - public String[] getMinimallyRequiredFields() { - return EntityProduct.JSON_PROPERTIES; - } - - @Override - public Object getResponse() { - return this.product == null ? this.products : this.product; - } - - @Override - public void setObjectMapper(ObjectMapper om) { - this.objectMapper = om; - } - - - @Override - public void setResponse(Map kvp, List fields) { - EntityProduct ep = objectMapper.convertValue(kvp, EntityProduct.class); - product = SearchUtil.entityProductToAPIProduct(ep, this.baseURL); - PdsProduct product = SearchUtil.entityProductToAPIProduct( - objectMapper.convertValue(kvp, EntityProduct.class), this.baseURL); - - - // TODO: findout why the getFilteredProperties method is used here. Should we add fields as a - // second argument instead of null ? - - product.setProperties( - (Map>) getFilteredProperties(kvp, fields, excludedProperties)); - this.product = product; - } - - - @Override - @SuppressWarnings("unchecked") - public void setResponse(SearchHit hit, List fields) { - Map kvp = hit.getSourceAsMap();; - - this.setResponse(kvp, fields); - - } - - - @Override - @SuppressWarnings("unchecked") - public void setResponse(List> hits, Summary summary, List fields) { - PdsProducts products = new PdsProducts(); - Set uniqueProperties = new TreeSet(); - - for (Map kvp : hits) { - try { - uniqueProperties.addAll(getFilteredProperties(kvp, fields, excludedProperties).keySet()); - - products.addDataItem(SearchUtil.entityProductToAPIProduct( - objectMapper.convertValue(kvp, EntityProduct.class), this.baseURL)); - products.getData().get(products.getData().size() - 1) - .setProperties((Map>) (Map) getFilteredProperties(kvp, - fields, excludedProperties)); - } catch (Throwable t) { - String lidvid = "unknown"; - if (kvp.containsKey("lidvid")) { - lidvid = kvp.get("lidvid").toString(); - } - log.error("DATA ERROR: could not convert opensearch document to EntityProduct for lidvid: " - + lidvid, t); - } - } - - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - } - - - - @Override - @SuppressWarnings("unchecked") - public int setResponse(HitIterator hits, Summary summary, List fields) { - int count; - PdsProducts products = new PdsProducts(); - Set uniqueProperties = new TreeSet(); - - for (Map kvp : hits) { - try { - uniqueProperties.addAll(getFilteredProperties(kvp, fields, excludedProperties).keySet()); - - products.addDataItem(SearchUtil.entityProductToAPIProduct( - objectMapper.convertValue(kvp, EntityProduct.class), this.baseURL)); - products.getData().get(products.getData().size() - 1) - .setProperties((Map>) (Map) getFilteredProperties(kvp, - fields, excludedProperties)); - } catch (Throwable t) { - String lidvid = "unknown"; - if (kvp.containsKey("lidvid")) { - lidvid = kvp.get("lidvid").toString(); - } - log.error("DATA ERROR: could not convert opensearch document to EntityProduct for lidvid: " - + lidvid, t); - } - } - count = products.getData().size(); - - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - return count; - } - - @Override - @SuppressWarnings("unchecked") - public int setResponse(SearchHits hits, Summary summary, List fields) { - Map kvp; - PdsProducts products = new PdsProducts(); - Set uniqueProperties = new TreeSet(); - - for (SearchHit hit : hits) { - try { - kvp = hit.getSourceAsMap(); - uniqueProperties.addAll(getFilteredProperties(kvp, fields, excludedProperties).keySet()); - - products.addDataItem(SearchUtil.entityProductToAPIProduct( - objectMapper.convertValue(kvp, EntityProduct.class), this.baseURL)); - // TODO: understand why the getFilteredProperties method is called with null arguments, - // should we add fields or not call the method at all ? - products.getData().get(products.getData().size() - 1) - .setProperties((Map>) (Map) getFilteredProperties(kvp, - null, excludedProperties)); - } catch (Throwable t) { - log.error("DATA ERROR: could not convert opensearch document to EntityProduct for lidvid: " - + hit.getId(), t); - } - } - - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - return (int) hits.getTotalHits().value; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogic.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogic.java deleted file mode 100644 index 74fe49a7..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogic.java +++ /dev/null @@ -1,29 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.util.List; -import java.util.Map; -import org.opensearch.search.SearchHit; -import org.opensearch.search.SearchHits; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.api.registry.search.HitIterator; -import gov.nasa.pds.model.Summary; - -public interface ProductBusinessLogic { - public String[] getMinimallyRequiredFields(); - - public String[] getMaximallyRequiredFields(); - - public Object getResponse(); - - public void setObjectMapper(ObjectMapper om); - - public void setResponse(Map hit, List fields); - - public void setResponse(List> hits, Summary summary, List fields); - - public void setResponse(SearchHit hit, List fields); - - public int setResponse(HitIterator hits, Summary summary, List fields); - - public int setResponse(SearchHits hits, Summary summary, List fields); -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogicImpl.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogicImpl.java deleted file mode 100644 index 00792a66..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/ProductBusinessLogicImpl.java +++ /dev/null @@ -1,139 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.net.MalformedURLException; -import java.net.URL; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import jakarta.servlet.http.HttpServletRequest; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.stereotype.Component; -import org.springframework.web.context.annotation.RequestScope; -import org.springframework.web.context.request.RequestContextHolder; -import org.springframework.web.context.request.ServletRequestAttributes; -import gov.nasa.pds.api.registry.exceptions.UnsupportedSearchProperty; -import gov.nasa.pds.api.registry.model.BlobUtil; -import gov.nasa.pds.api.registry.model.SearchUtil; - -@Component -@RequestScope -public abstract class ProductBusinessLogicImpl implements ProductBusinessLogic { - private static final Logger log = LoggerFactory.getLogger(ProductBusinessLogicImpl.class); - - private static final String DEFAULT_NULL_VALUE = null; - - protected URL baseURL; - - protected List excludedProperties = getExcludedProperties(); - - private static List getExcludedProperties() { - List excludedProperties = new ArrayList(); - try { - excludedProperties.add(SearchUtil.openPropertyToJsonProperty(BlobUtil.JSON_BLOB_PROPERTY)); - excludedProperties.add(SearchUtil.openPropertyToJsonProperty(BlobUtil.XML_BLOB_PROPERTY)); - } catch (UnsupportedSearchProperty e) { - log.error("That should not happen, unless there is an error in the code"); - } - log.info("The following properties will not be sent in the API response " + excludedProperties); - return excludedProperties; - } - - - public ProductBusinessLogicImpl() { - try { - - HttpServletRequest request = - ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest(); - - String proxyContextPath = request.getContextPath(); - ProductBusinessLogicImpl.log.debug("contextPath is: '" + proxyContextPath + "'"); - - if (ProductBusinessLogicImpl.proxyRunsOnDefaultPort(request)) { - this.baseURL = new URL(request.getScheme(), request.getServerName(), proxyContextPath); - } else { - this.baseURL = new URL(request.getScheme(), request.getServerName(), - request.getServerPort(), proxyContextPath); - } - - log.debug("baseUrl is " + this.baseURL.toString()); - - - } catch (MalformedURLException e) { - log.error("Server URL was not retrieved"); - - } - } - - - private static boolean proxyRunsOnDefaultPort(HttpServletRequest request) { - return (("https".equals(request.getScheme()) && (request.getServerPort() == 443)) - || ("http".equals(request.getScheme()) && (request.getServerPort() == 80))); - } - - - private static List object2PropertyValue(Object o) { - ArrayList pv = new ArrayList(); - - if (o instanceof List) { - for (Object p : (List) o) { - ((ArrayList) pv).add(String.valueOf(p)); - } - - } else { - // TODO find a type which make String castable in PropertyValue, - // currently I am desperate so I transform String in a List - ((ArrayList) pv).add(String.valueOf(o)); - } - - return pv; - - } - - /** - * @param sourceAsMap source map coming from openSearch - * @param included_fields, in API syntax, with . - * @param excluded_fields is ignored is included_fields is not null and not empty, in API syntax - * @return - */ - public static Map> getFilteredProperties(Map sourceAsMap, // in - // ES - // syntax - List included_fields, // in API syntax - List excluded_fields) { // in API syntax - - Map> filteredMapJsonProperties = new HashMap>(); - - if ((included_fields == null) || (included_fields.size() == 0)) { - String apiProperty; - log.debug("Excluded fields are " + excluded_fields); - for (Map.Entry entry : sourceAsMap.entrySet()) { - try { - apiProperty = SearchUtil.openPropertyToJsonProperty(entry.getKey()); - if ((excluded_fields == null) || !excluded_fields.contains(apiProperty)) { - filteredMapJsonProperties.put(apiProperty, object2PropertyValue(entry.getValue())); - } - } catch (UnsupportedSearchProperty e) { - log.warn("openSearch property " + entry.getKey() + " is not supported, ignored"); - } - } - } else { - String esField; - for (String field : included_fields) { - esField = SearchUtil.jsonPropertyToOpenProperty(field); - - if (sourceAsMap.containsKey(esField)) { - filteredMapJsonProperties.put(field, object2PropertyValue(sourceAsMap.get(esField))); - } else { - filteredMapJsonProperties.put(field, - object2PropertyValue(ProductBusinessLogicImpl.DEFAULT_NULL_VALUE)); - } - } - } - return filteredMapJsonProperties; - } -} - - diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/RawMultipleProductResponse.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/RawMultipleProductResponse.java deleted file mode 100644 index 9aaeae92..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/RawMultipleProductResponse.java +++ /dev/null @@ -1,42 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.stream.Collectors; -import org.opensearch.client.opensearch.core.SearchResponse; -import gov.nasa.pds.model.Summary; - -public class RawMultipleProductResponse { - private Summary summary; - private List> products; - - public RawMultipleProductResponse(SearchResponse searchResponse) { - this.summary = new Summary(); - this.summary.setHits((int) searchResponse.hits().total().value()); - this.products = searchResponse.hits().hits().stream().map(p -> (Map) p.source()) - .collect(Collectors.toList()); - - } - - public RawMultipleProductResponse(HashMap product) { - this.summary = new Summary(); - this.summary.setHits(1); - this.products = new ArrayList>(); - this.products.add(product); - - } - - - - public Summary getSummary() { - return summary; - } - - public List> getProducts() { - return products; - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/WyriwygBusinessObject.java b/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/WyriwygBusinessObject.java deleted file mode 100644 index bf0e5a85..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/api_responses/WyriwygBusinessObject.java +++ /dev/null @@ -1,187 +0,0 @@ -package gov.nasa.pds.api.registry.model.api_responses; - -import java.net.URL; -import java.util.ArrayList; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; -import java.util.TreeSet; -import org.opensearch.search.SearchHit; -import org.opensearch.search.SearchHits; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.api.registry.exceptions.UnsupportedSearchProperty; -import gov.nasa.pds.api.registry.model.SearchUtil; -import gov.nasa.pds.api.registry.search.HitIterator; -import gov.nasa.pds.model.Summary; -import gov.nasa.pds.model.WyriwygProduct; -import gov.nasa.pds.model.WyriwygProductKeyValuePair; -import gov.nasa.pds.model.WyriwygProducts; - -public class WyriwygBusinessObject extends ProductBusinessLogicImpl { - private static final Logger log = LoggerFactory.getLogger(WyriwygBusinessObject.class); - - @SuppressWarnings("unused") - private ObjectMapper om; - @SuppressWarnings("unused") - private URL baseURL; - private WyriwygProduct product = null; - private WyriwygProducts products = null; - - - @Override - public String[] getMaximallyRequiredFields() { - return new String[0]; - } - - @Override - public String[] getMinimallyRequiredFields() { - return new String[0]; - } - - @Override - public Object getResponse() { - return this.product == null ? this.products : this.product; - } - - @Override - public void setObjectMapper(ObjectMapper om) { - this.om = om; - } - - - @Override - public void setResponse(Map kvps, List fields) { - // TODO: to be implemented - - - this.product = generateWyriwygProduct(kvps, fields); - } - - @Override - public void setResponse(SearchHit hit, List fields) { - this.setResponse(hit.getSourceAsMap(), fields); - } - - @Override - public int setResponse(HitIterator hits, Summary summary, List fields) { - Set uniqueProperties = new TreeSet(); - WyriwygProducts products = new WyriwygProducts(); - - for (Map kvps : hits) { - uniqueProperties.addAll(getFilteredProperties(kvps, fields, null).keySet()); - - WyriwygProduct product = new WyriwygProduct(); - for (Entry pair : kvps.entrySet()) { - WyriwygProductKeyValuePair kvp = new WyriwygProductKeyValuePair(); - try { - kvp.setKey(SearchUtil.openPropertyToJsonProperty(pair.getKey())); - kvp.setValue(getStringValueOf(pair.getValue())); - product.addKeyValuePairsItem(kvp); - } catch (UnsupportedSearchProperty e) { - log.warn("openSearch property " + pair.getKey() + " is not supported, ignored"); - } - } - products.addDataItem(product); - - } - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - return products.getData().size(); - } - - @Override - public int setResponse(SearchHits hits, Summary summary, List fields) { - - Set uniqueProperties = new TreeSet(); - WyriwygProducts products = new WyriwygProducts(); - - for (SearchHit hit : hits.getHits()) { - Map kvps = hit.getSourceAsMap(); - uniqueProperties.addAll(getFilteredProperties(kvps, fields, null).keySet()); - - WyriwygProduct product = new WyriwygProduct(); - for (Entry pair : kvps.entrySet()) { - WyriwygProductKeyValuePair kvp = new WyriwygProductKeyValuePair(); - try { - kvp.setKey(SearchUtil.openPropertyToJsonProperty(pair.getKey())); - kvp.setValue(getStringValueOf(pair.getValue())); - product.addKeyValuePairsItem(kvp); - } catch (UnsupportedSearchProperty e) { - log.warn("openSearch property " + pair.getKey() + " is not supported, ignored"); - } - } - products.addDataItem(product); - } - - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - return (int) (hits.getTotalHits().value); - } - - - @Override - public void setResponse(List> hits, Summary summary, List fields) { - - Set uniqueProperties = new TreeSet(); - WyriwygProducts products = new WyriwygProducts(); - - for (Map hit : hits) { - - uniqueProperties.addAll(getFilteredProperties(hit, fields, excludedProperties).keySet()); - WyriwygProduct product = generateWyriwygProduct(hit, fields); - products.addDataItem(product); - } - - summary.setProperties(new ArrayList(uniqueProperties)); - products.setSummary(summary); - this.products = products; - } - - - private WyriwygProduct generateWyriwygProduct(Map hit, - List included_fields) { - WyriwygProduct product = new WyriwygProduct(); - String jsonProperty; - for (Entry pair : hit.entrySet()) { - WyriwygProductKeyValuePair kvp = new WyriwygProductKeyValuePair(); - try { - jsonProperty = SearchUtil.openPropertyToJsonProperty(pair.getKey()); - if (!excludedProperties.contains(jsonProperty)) { - kvp.setKey(jsonProperty); - kvp.setValue(getStringValueOf(pair.getValue())); - product.addKeyValuePairsItem(kvp); - } - } catch (UnsupportedSearchProperty e) { - log.warn("openSearch property " + pair.getKey() + " is not supported, ignored"); - } - - } - - return product; - - - } - - - private String getStringValueOf(Object o) { - String valueOf; - if (o instanceof Iterable) { - List stringRepresentations = new ArrayList<>(); - for (Object el : (Iterable) o) { - stringRepresentations.add(String.valueOf(el)); - } - - String delimiter = "|"; - valueOf = String.join(delimiter, stringRepresentations); - } else { - valueOf = String.valueOf(o); - } - - return valueOf; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/AcceptFormatNotSupportedException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/AcceptFormatNotSupportedException.java deleted file mode 100644 index e25c9648..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/AcceptFormatNotSupportedException.java +++ /dev/null @@ -1,10 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -public class AcceptFormatNotSupportedException extends RegistryApiException { - private static final long serialVersionUID = -2118295915069330607L; - - public AcceptFormatNotSupportedException(String msg) { - super("AcceptFormatNotSupportedException: " + msg); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/BadRequestException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/BadRequestException.java deleted file mode 100644 index 55345724..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/BadRequestException.java +++ /dev/null @@ -1,17 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.Serial; - -public class BadRequestException extends RegistryApiException { - private static final Logger log = LoggerFactory.getLogger(BadRequestException.class); - @Serial - private static final long serialVersionUID = 2026697251322082840L; - - public BadRequestException(String msg) { - super("BadRequestException: " + msg); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/NotFoundException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/NotFoundException.java deleted file mode 100644 index ff8491a8..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/NotFoundException.java +++ /dev/null @@ -1,15 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -public class NotFoundException extends RegistryApiException { - - private static final long serialVersionUID = -6704894264788325051L; - private static final Logger log = LoggerFactory.getLogger(NotFoundException.class); - - public NotFoundException(String msg) { - super("NotFoundException: " + msg); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/RegistryApiException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/RegistryApiException.java deleted file mode 100644 index 3873560e..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/RegistryApiException.java +++ /dev/null @@ -1,33 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -import java.util.UUID; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - - -public class RegistryApiException extends Exception { - private static final long serialVersionUID = 202822323640754980L; - - - private static final Logger log = LoggerFactory.getLogger(RegistryApiException.class); - - - private String uuid; - - public RegistryApiException(String msg) { - - super(msg); - UUID uuidObj = UUID.randomUUID(); - this.uuid = uuidObj.toString(); - - log.info(this.uuid + " " + msg); - - - - } - - public String getUuid() { - return this.uuid; - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/SortSearchAfterMismatchException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/SortSearchAfterMismatchException.java deleted file mode 100644 index 3c5d6367..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/SortSearchAfterMismatchException.java +++ /dev/null @@ -1,8 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -public class SortSearchAfterMismatchException extends RegistryApiException { - - public SortSearchAfterMismatchException(String detail) { - super("Invalid combination of sort and searchAfter values: " + detail); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnhandledException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnhandledException.java deleted file mode 100644 index 3b3d069d..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnhandledException.java +++ /dev/null @@ -1,22 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -public class UnhandledException extends RegistryApiException { - - private static final long serialVersionUID = -2108508968768896105L; - private static final Logger log = LoggerFactory.getLogger(UnhandledException.class); - - - public UnhandledException(String msg) { - super("Unhandled Exception:" + msg); - } - - public UnhandledException(Exception e) { - super("Unhandled Exception: " + e.getMessage()); - - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnparsableQParamException.java b/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnparsableQParamException.java deleted file mode 100644 index 4935068a..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/exceptions/UnparsableQParamException.java +++ /dev/null @@ -1,17 +0,0 @@ -package gov.nasa.pds.api.registry.model.exceptions; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - - - -public class UnparsableQParamException extends RegistryApiException { - - private static final long serialVersionUID = -6704894264788325051L; - private static final Logger log = LoggerFactory.getLogger(UnparsableQParamException.class); - - public UnparsableQParamException(String msg) { - super("UnparsableQParamException: Unable to parse the q parameter:" + msg); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLid.java b/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLid.java deleted file mode 100644 index e14d9fc5..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLid.java +++ /dev/null @@ -1,46 +0,0 @@ -package gov.nasa.pds.api.registry.model.identifiers; - -public class PdsLid extends PdsProductIdentifier { - private String value; - - public PdsLid(String value) { - this.value = value; - } - - public String getValue() { - return this.value; - } - - @Override - public PdsLid getLid() { - return this; - } - - @Override - public String toString() { - return this.value; - } - - public static PdsLid fromString(String lid) { - return new PdsLid(lid); - } - - @Override - public boolean equals(Object other) { - if (this == other) { - return true; - } - - if (!(other instanceof PdsLid)) { - return false; - } - - PdsLid otherAsLid = (PdsLid) other; - return this.value.equals(otherAsLid.getValue()); - } - - @Override - public int hashCode() { - return this.value.hashCode(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLidVid.java b/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLidVid.java deleted file mode 100644 index df9b045c..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsLidVid.java +++ /dev/null @@ -1,73 +0,0 @@ -package gov.nasa.pds.api.registry.model.identifiers; - -public class PdsLidVid extends PdsProductIdentifier implements Comparable { - private final PdsLid lid; - private final PdsVid vid; - - public PdsLid getLid() { - return lid; - } - - public PdsVid getVid() { - return vid; - } - - public PdsLidVid(PdsLid lid, PdsVid vid) { - this.lid = lid; - this.vid = vid; - } - - public static PdsLidVid fromString(String lidVidString) { - String[] chunks = lidVidString.split(LIDVID_SEPARATOR); - - if (chunks.length != 2) { - String errMsg = String.format("Provided value '%s' is not a valid LIDVID", lidVidString); - throw new IllegalArgumentException(errMsg); - } - - PdsLid lid = new PdsLid(chunks[0]); - PdsVid vid = PdsVid.fromString(chunks[1]); - - return new PdsLidVid(lid, vid); - } - - @Override - public int hashCode() { - return this.toString().hashCode(); - } - - @Override - public boolean equals(Object other) { - if (this == other) { - return true; - } - - if (!(other instanceof PdsLidVid)) { - return false; - } - - PdsLidVid otherAsLidVid = (PdsLidVid) other; - return this.lid.equals(otherAsLidVid.lid) && this.vid.equals(otherAsLidVid.vid); - } - - @Override - public String toString() { - return String.format("%s::%s", this.lid, this.vid); - } - - @Override - public int compareTo(PdsLidVid other) { - if (this.equals(other)) { - return 0; - } - - if (!this.lid.equals(other.lid)) { - String errMsg = String.format( - "Comparison is only defined between LIDVIDs with identical LIDs (got '%s', '%s')", - this.lid, other.lid); - throw new IllegalArgumentException(errMsg); - } - - return this.vid.compareTo(other.vid); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductClasses.java b/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductClasses.java deleted file mode 100644 index fbbda05f..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductClasses.java +++ /dev/null @@ -1,115 +0,0 @@ -package gov.nasa.pds.api.registry.model.identifiers; - -import java.util.Arrays; -import java.util.List; - -/** - * An enumeration of the valid product_class values from the PDS4 Data Dictionary - * ... - */ -public enum PdsProductClasses { - Product_AIP("Product_AIP"), - Product_Ancillary("Product_Ancillary"), - Product_Attribute_Definition("Product_Attribute_Definition"), - Product_Browse("Product_Browse"), - Product_Bundle("Product_Bundle"), - Product_Class_Definition("Product_Class_Definition"), - Product_Collection("Product_Collection"), - Product_Context("Product_Context"), - Product_DIP("Product_DIP"), - Product_DIP_Deep_Archive("Product_DIP_Deep_Archive"), - Product_Data_Set_PDS3("Product_Data_Set_PDS3"), - Product_Document("Product_Document"), - Product_External("Product_External"), - Product_File_Repository("Product_File_Repository"), - Product_File_Text("Product_File_Text"), - Product_Instrument_Host_PDS3("Product_Instrument_Host_PDS3"), - Product_Instrument_PDS3("Product_Instrument_PDS3"), - Product_Metadata_Supplemental("Product_Metadata_Supplemental"), - Product_Mission_PDS3("Product_Mission_PDS3"), - Product_Native("Product_Native"), - Product_Observational("Product_Observational"), - Product_Proxy_PDS3("Product_Proxy_PDS3"), - Product_SIP("Product_SIP"), - Product_SIP_Deep_Archive("Product_SIP_Deep_Archive"), - Product_SPICE_Kernel("Product_SPICE_Kernel"), - Product_Service("Product_Service"), - Product_Software("Product_Software"), - Product_Subscription_PDS3("Product_Subscription_PDS3"), - Product_Target_PDS3("Product_Target_PDS3"), - Product_Thumbnail("Product_Thumbnail"), - Product_Update("Product_Update"), - Product_Volume_PDS3("Product_Volume_PDS3"), - Product_Volume_Set_PDS3("Product_Volume_Set_PDS3"), - Product_XML_Schema("Product_XML_Schema"), - Product_Zipped("Product_Zipped"); - - private final String value; - - PdsProductClasses(String value) { - this.value = value; - } - - public String getValue() { - return value; - } - - /** - * @return the database property/field these string values appear in. Provided for convenience. - */ - public static String getPropertyName() { - return "product_class"; - } - - public static List getValidSwaggerNames() { - return Arrays.stream(PdsProductClasses.values()).map(PdsProductClasses::getSwaggerName).toList(); - } - - /** - * @return the shorthand name used for convenience in API routes, ex. "Product_Bundle" -> "bundle" - */ - public String getSwaggerName() { - List chunks = Arrays.asList(this.value.split("_")); - - if (chunks.size() < 2 || !chunks.get(0).equals("Product")) { - throw new IllegalArgumentException("Could not generate swagger name for PDSProductClasses value '" + this.value + "'"); - } - - List relevantChunks = chunks.subList(1, chunks.size()); - - return String.join("-", relevantChunks).toLowerCase(); - } - - /** - * @return the PdsProductClass which is equivalent to a given swagger-formatted product class name - */ - public static PdsProductClasses fromSwaggerName(String swaggerName) { - List matches = Arrays.stream(PdsProductClasses.values()) - .filter(value -> value.getSwaggerName().equals(swaggerName)) - .toList(); - - if (matches.isEmpty()) { - throw new IllegalArgumentException("No PdsProductClass matches swagger name '" + swaggerName + "'" - + "'. Valid names are: " + String.join(", ", getValidSwaggerNames())); - } - - if (matches.size() > 1) { -// This should never be possible and indicates an error in the enum value definitions - throw new IllegalArgumentException("Multiple PdsProductClass matches swagger name '" + swaggerName + "'"); - } - - return matches.get(0); - } - - public Boolean isBundle() { - return this == Product_Bundle; - } - - public Boolean isCollection() { - return this == Product_Collection; - } - - public Boolean isBasicProduct() { - return !(isBundle() || isCollection()); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductIdentifier.java b/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductIdentifier.java deleted file mode 100644 index 759a387d..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsProductIdentifier.java +++ /dev/null @@ -1,44 +0,0 @@ -package gov.nasa.pds.api.registry.model.identifiers; - -public abstract class PdsProductIdentifier { - protected static final String LIDVID_SEPARATOR = "::"; - - public abstract PdsLid getLid(); - - @Override - public abstract String toString(); - - public static PdsProductIdentifier fromString(String identifier) { - if (identifier.length() == 0) - return null; - - try { - return identifier.contains(LIDVID_SEPARATOR) ? PdsLidVid.fromString(identifier) - : PdsLid.fromString(identifier); - } catch (IllegalArgumentException err) { - return resolvePartialLidVid(identifier); - } - } - - private static PdsLid resolvePartialLidVid(String identifier) { - return PdsLid.fromString(identifier.split(LIDVID_SEPARATOR)[0]); - } - - public boolean isLidvid() { - return this instanceof PdsLidVid; - } - - public boolean isLid() { - return this instanceof PdsLid; - } - - public static boolean stringIsLidvid(String identifierStr) { - PdsProductIdentifier identifierObj = PdsProductIdentifier.fromString(identifierStr); - return identifierObj != null && identifierObj.isLidvid(); - } - - public static boolean stringIsLid(String identifierStr) { - PdsProductIdentifier identifierObj = PdsProductIdentifier.fromString(identifierStr); - return identifierObj != null && identifierObj.isLid(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsVid.java b/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsVid.java deleted file mode 100644 index 9d530aad..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/model/identifiers/PdsVid.java +++ /dev/null @@ -1,81 +0,0 @@ -package gov.nasa.pds.api.registry.model.identifiers; - -public class PdsVid implements Comparable { - private final int majorVersion; - private final int minorVersion; - - public PdsVid(int majorVersion, int minorVersion) { - if (majorVersion < 0) { - String errMsg = String.format("majorVersion must be 0 or higher (got '%d'))", majorVersion); - throw new IllegalArgumentException(errMsg); - } - - if (minorVersion < 0) { - String errMsg = String.format("minorVersion must be 0 or higher (got '%d'))", minorVersion); - throw new IllegalArgumentException(errMsg); - } - - this.majorVersion = majorVersion; - this.minorVersion = minorVersion; - } - - public static PdsVid fromString(String vidString) { - String[] versionChunks = vidString.split("\\."); - - if (versionChunks.length != 2) { - String errMsg = String.format("Provided value '%s' is not a valid VID", vidString); - throw new IllegalArgumentException(errMsg); - } - - int majorVersion = Integer.parseInt(versionChunks[0]); - int minorVersion = Integer.parseInt(versionChunks[1]); - - return new PdsVid(majorVersion, minorVersion); - } - - public int getMajorVersion() { - return majorVersion; - } - - public int getMinorVersion() { - return minorVersion; - } - - @Override - public String toString() { - return String.format("%d.%d", majorVersion, minorVersion); - } - - @Override - public boolean equals(Object other) { - if (this == other) { - return true; - } - - if (!(other instanceof PdsVid)) { - return false; - } - - PdsVid otherAsVid = (PdsVid) other; - return this.majorVersion == otherAsVid.getMajorVersion() - && this.minorVersion == otherAsVid.getMinorVersion(); - } - - @Override - public int hashCode() { - return this.toString().hashCode(); - } - - @Override - public int compareTo(PdsVid o) { - if (this.equals(o)) { - return 0; - } - - if (this.majorVersion == o.getMajorVersion()) { - return Integer.compare(this.minorVersion, o.getMinorVersion()); - } else { - return Integer.compare(this.majorVersion, o.getMajorVersion()); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/HitIterator.java b/service/src/main/java/gov/nasa/pds/api/registry/search/HitIterator.java deleted file mode 100644 index 87ee07b8..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/HitIterator.java +++ /dev/null @@ -1,87 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.io.IOException; -import java.util.Iterator; -import java.util.Map; - -import org.opensearch.action.search.SearchRequest; -import org.opensearch.client.RequestOptions; -import org.opensearch.client.RestHighLevelClient; -import org.opensearch.search.SearchHit; -import org.opensearch.search.SearchHits; - -public class HitIterator implements Iterable>, Iterator> { - private int size = 500; // define size to use here to prevent page skipping if opensearch default - // size - // ever changes - private int at = 0, page = 0; - private SearchHits currentBatch; - private RestHighLevelClient client; - private SearchRequest request; - - public HitIterator(RestHighLevelClient client, SearchRequest request) throws IOException { - super(); - this.client = client; - this.request = request; - this.currentBatch = this.fetch(); - } - - public HitIterator(int size, RestHighLevelClient client, SearchRequest request) - throws IOException { - super(); - this.client = client; - this.request = request; - this.size = size; - this.currentBatch = this.fetch(); - } - - private SearchHits fetch() throws IOException { - this.request.source().from(this.page * this.size); - this.request.source().size(this.size); - return this.client.search(this.request, RequestOptions.DEFAULT).getHits(); - } - - private SearchHit getAt() throws IOException { - if (this.size <= this.at) { - this.page++; - this.at = 0; - this.currentBatch = this.fetch(); - } - - return this.currentBatch.getAt(this.at); - } - - public String getCurrentId() { - try { - return this.getAt().getId(); - } catch (IOException ioe) { - return null; - } - } - - @Override - public boolean hasNext() { - return this.currentBatch == null ? false - : (this.at + this.page * this.size) < this.currentBatch.getTotalHits().value; - } - - @Override - public Iterator> iterator() { - return this; - } - - @Override - public Map next() { - if (this.hasNext()) { - try { - SearchHit hit = this.getAt(); - at++; - return hit.getSourceAsMap(); - } catch (IOException ioe) { - return null; - } - } else { - return null; - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchConfig.java b/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchConfig.java deleted file mode 100644 index 1efb82fd..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchConfig.java +++ /dev/null @@ -1,140 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.List; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Value; -import org.springframework.context.annotation.Configuration; - -/* - * Keep this eventhough not directly referenced - * - * Seems to found and used via reflection rather than direct reference. When removed it causes - * spring to fail with an opensearch failure requiring EleasticSearchRegistryConnection. Not sure - * why the error indicates an interface that is already there when this class is missing but that is - * what happened. - */ - -@Configuration -public class OpenSearchConfig { - private static final Logger log = LoggerFactory.getLogger(OpenSearchConfig.class); - - // This default for ES hosts is set in the constructor since we first want to - // check - // the environment if not set in the application properties. This preserves the - // original behavior when the default was specified in the Value annotation. - - @Value("#{'${openSearch.host:}'.split(',')}") - private List hosts; - - @Value("${openSearch.registryIndex:registry}") - private String registryIndex; - - @Value("${openSearch.registryRefIndex:registry-refs}") - private String registryRefIndex; - - @Value("#{'${openSearch.disciplineNodes:}'.split(',')}") - private List disciplineNodes; - - @Value("${openSearch.timeOutSeconds:60}") - private int timeOutSeconds; - - public int getTimeOutSeconds() { - return timeOutSeconds; - } - - public void setTimeOutSeconds(int timeOutSeconds) { - this.timeOutSeconds = timeOutSeconds; - } - - @Value("${openSearch.CCSEnabled:true}") - private boolean CCSEnabled; - - public boolean getCCSEnabled() { - return CCSEnabled; - } - - @Value("${openSearch.username:}") - private String username; - - @Value("#{'${filter.archiveStatus:}'.split(',')}") - private List archiveStatus; - - public List getArchiveStatus() { - return archiveStatus; - } - - public char[] getPassword() { - return password; - } - - public void setPassword(char[] password) { - this.password = password; - } - - public String getUsername() { - return username; - } - - public void setUsername(String username) { - this.username = username; - } - - @Value("${openSearch.password:}") - private char[] password; - - @Value("${openSearch.ssl:false}") - private boolean ssl; - - @Value("${openSearch.sslCertificateCNVerification:false}") - private boolean sslCertificateCNVerification; - - - - public List getHosts() { - return hosts; - } - - public void setHost(List hosts) { - this.hosts = hosts; - } - - public String getRegistryIndex() { - return registryIndex; - } - - public void setRegistryIndex(String registryIndex) { - this.registryIndex = registryIndex; - } - - public String getRegistryRefIndex() { - return registryRefIndex; - } - - public void setRegistryRefIndex(String registryRefIndex) { - this.registryRefIndex = registryRefIndex; - } - - public List getDisciplineNodes() { - return disciplineNodes; - } - - public boolean isSsl() { - return ssl; - } - - public boolean doesSslCertificateVCNerification() { - return sslCertificateCNVerification; - } - - public void setSslCertificateCNVerification(boolean sslCertificateCNVerification) { - this.sslCertificateCNVerification = sslCertificateCNVerification; - } - - public void setSsl(boolean ssl) { - this.ssl = ssl; - } - - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionImplBuilder.java b/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionImplBuilder.java deleted file mode 100644 index 6f66b2ef..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionImplBuilder.java +++ /dev/null @@ -1,161 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.io.IOException; -import java.util.Arrays; -import java.util.List; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.beans.factory.config.ConfigurableBeanFactory; -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.Scope; -import org.springframework.stereotype.Component; -import gov.nasa.pds.api.registry.SystemConstants; -import gov.nasa.pds.api.registry.util.AWSCredentialsFetcher; - -@Component -class OpenSearchRegistryConnectionImplBuilder { - - private static final String DEFAULT_ES_HOST = "localhost:9200"; - - private static final Logger log = - LoggerFactory.getLogger(OpenSearchRegistryConnectionImplBuilder.class); - - private List hosts; - private final String registryIndex; - private final String registryRefIndex; - private final int timeOutSeconds; - private final boolean CCSEnabled; - private final List disciplineNodes; - private final boolean ssl; - private final boolean sslCertificateCNVerification; - private String username; - private char[] password; - private final List archiveStatus; - - public List getArchiveStatus() { - return archiveStatus; - } - - public List getHosts() { - return hosts; - } - - public void setHosts(List hosts) { - this.hosts = hosts; - } - - public String getUsername() { - return username; - } - - public void setUsername(String username) { - this.username = username; - } - - public char[] getPassword() { - return password; - } - - public void setPassword(char[] password) { - this.password = password; - } - - public String getRegistryIndex() { - return registryIndex; - } - - public String getRegistryRefIndex() { - return registryRefIndex; - } - - public List getDisciplineNodes() { - return disciplineNodes; - } - - public int getTimeOutSeconds() { - return timeOutSeconds; - } - - - public boolean getCCSEnabled() { - return CCSEnabled; - } - - public boolean isSsl() { - return ssl; - } - - public boolean isSslCertificateCNVerification() { - return sslCertificateCNVerification; - } - - - - public OpenSearchRegistryConnectionImplBuilder() { - // Default builder - this.hosts = Arrays.asList("localhost:9200"); - this.registryIndex = "registry"; - this.registryRefIndex = "registry-refs"; - this.timeOutSeconds = 5; - this.CCSEnabled = true; - this.disciplineNodes = Arrays.asList(new String[] {""}); - this.username = null; - this.password = null; - this.ssl = false; - this.sslCertificateCNVerification = true; - this.archiveStatus = null; - - } - - @Autowired - public OpenSearchRegistryConnectionImplBuilder(OpenSearchConfig openSearchConfig) { - - this.hosts = openSearchConfig.getHosts(); - - if (this.hosts == null || this.hosts.size() == 0 || this.hosts.get(0) == null - || "".equals(this.hosts.get(0))) { - this.setESHostsFromEnvOrDefault(); - } - - this.registryIndex = openSearchConfig.getRegistryIndex(); - this.registryRefIndex = openSearchConfig.getRegistryRefIndex(); - this.timeOutSeconds = openSearchConfig.getTimeOutSeconds(); - this.CCSEnabled = openSearchConfig.getCCSEnabled(); - this.disciplineNodes = openSearchConfig.getDisciplineNodes(); - this.ssl = openSearchConfig.isSsl(); - this.sslCertificateCNVerification = openSearchConfig.doesSslCertificateVCNerification(); - this.username = openSearchConfig.getUsername(); - this.password = openSearchConfig.getPassword(); - this.archiveStatus = openSearchConfig.getArchiveStatus(); - - this.awsCredentialsFetcher().fetchCredentials(); - - - } - - @Bean - @Scope(value = ConfigurableBeanFactory.SCOPE_SINGLETON) - public AWSCredentialsFetcher awsCredentialsFetcher() { - return new AWSCredentialsFetcher(); - } - - public void setESHostsFromEnvOrDefault() { - - String esHosts = System.getenv(SystemConstants.ES_HOSTS_ENV_VAR); - - if (esHosts != null && !"".equals(esHosts)) { - log.info("Received ES hosts from environment"); - } else { - log.info(String.format("ES hosts not set in config or environment, defaulting to %s", - DEFAULT_ES_HOST)); - esHosts = DEFAULT_ES_HOST; - } - - log.debug(String.format("esHosts : %s", esHosts)); - - this.hosts = List.of(esHosts.split(",")); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionNewImpl.java b/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionNewImpl.java deleted file mode 100644 index f2bb1359..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/OpenSearchRegistryConnectionNewImpl.java +++ /dev/null @@ -1,294 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.List; - -import javax.net.ssl.SSLContext; -import javax.net.ssl.SSLEngine; -import software.amazon.awssdk.http.SdkHttpClient; -import software.amazon.awssdk.http.apache.ApacheHttpClient; -import software.amazon.awssdk.regions.Region; - -import java.util.stream.Collectors; -import java.security.KeyManagementException; -import java.security.KeyStoreException; -import java.security.NoSuchAlgorithmException; -import java.util.ArrayList; -import java.util.Arrays; -import org.apache.hc.client5.http.auth.AuthScope; -import org.apache.hc.client5.http.auth.UsernamePasswordCredentials; -import org.apache.hc.client5.http.impl.async.HttpAsyncClientBuilder; -import org.apache.hc.client5.http.impl.auth.BasicCredentialsProvider; -import org.apache.hc.client5.http.impl.nio.PoolingAsyncClientConnectionManager; -import org.apache.hc.client5.http.impl.nio.PoolingAsyncClientConnectionManagerBuilder; -import org.apache.hc.client5.http.ssl.ClientTlsStrategyBuilder; -import org.apache.hc.client5.http.ssl.NoopHostnameVerifier; -import org.apache.hc.core5.function.Factory; -import org.apache.hc.core5.http.HttpHost; -import org.apache.hc.core5.http.nio.ssl.TlsStrategy; -import org.apache.hc.core5.reactor.ssl.TlsDetails; -import org.apache.hc.core5.ssl.SSLContextBuilder; - -import org.opensearch.client.transport.httpclient5.ApacheHttpClient5TransportBuilder; -import org.opensearch.client.transport.OpenSearchTransport; -import org.opensearch.client.transport.aws.AwsSdk2Transport; -import org.opensearch.client.transport.aws.AwsSdk2TransportOptions; -import org.opensearch.client.opensearch.OpenSearchClient; -import org.opensearch.client.opensearch.generic.OpenSearchGenericClient; -import org.opensearch.client.opensearch.core.InfoRequest; -import org.opensearch.client.opensearch.core.InfoResponse; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import com.google.common.base.Splitter; - -import gov.nasa.pds.api.registry.ConnectionContext; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.stereotype.Component; - - - -@Component -public class OpenSearchRegistryConnectionNewImpl implements ConnectionContext { - - // key for getting the remotes from cross cluster config - public static String CLUSTER_REMOTE_KEY = "cluster.remote"; - public static List SINGLE_EMPTY_STRING = Arrays.asList(""); - - private static final Logger log = - LoggerFactory.getLogger(OpenSearchRegistryConnectionNewImpl.class); - - private PoolingAsyncClientConnectionManager connectionManager = null; - private OpenSearchClient openSearchClient; - private OpenSearchGenericClient openSearchGenericClient; - private String host; - - public String getHost() { - return host; - } - - - private List registryIndices = new ArrayList(); - private List registryRefIndices = new ArrayList(); - private int timeOutSeconds; - private List archiveStatus; - - public OpenSearchRegistryConnectionNewImpl() throws java.security.NoSuchAlgorithmException, - java.security.KeyStoreException, java.security.KeyManagementException { - this(new OpenSearchRegistryConnectionImplBuilder()); - } - - private HttpAsyncClientBuilder clientBuilderForHttpTransport(HttpAsyncClientBuilder builder, - String userName, char[] password, HttpHost host, boolean ssl, - boolean sslCertificateCNVerification) { - - try { - PoolingAsyncClientConnectionManagerBuilder connectionManagerBuilder = - PoolingAsyncClientConnectionManagerBuilder.create(); - - final SSLContext sslContext = - SSLContextBuilder.create().loadTrustMaterial(null, (chains, authType) -> true).build(); - - if (ssl) { - OpenSearchRegistryConnectionNewImpl.log.info("Connection over SSL"); - - - ClientTlsStrategyBuilder clientTlsStrategyBuilder = - ClientTlsStrategyBuilder.create().setSslContext(sslContext) - // See https://issues.apache.org/jira/browse/HTTPCLIENT-2219 - .setTlsDetailsFactory(new Factory() { - @Override - public TlsDetails create(final SSLEngine sslEngine) { - return new TlsDetails(sslEngine.getSession(), - sslEngine.getApplicationProtocol()); - } - }); - - if (!sslCertificateCNVerification) { - clientTlsStrategyBuilder.setHostnameVerifier(NoopHostnameVerifier.INSTANCE); - } - final TlsStrategy tlsStrategy = clientTlsStrategyBuilder.build(); - connectionManagerBuilder = connectionManagerBuilder.setTlsStrategy(tlsStrategy); - - } - - this.connectionManager = connectionManagerBuilder.build(); - - if ((userName != null) && !userName.equals("")) { - OpenSearchRegistryConnectionNewImpl.log - .info("Set openSearch connection with username/password"); - final BasicCredentialsProvider credentialsProvider = new BasicCredentialsProvider(); - - - credentialsProvider.setCredentials(new AuthScope(host), - new UsernamePasswordCredentials(userName, password)); - - builder = builder.setDefaultCredentialsProvider(credentialsProvider); - } - - return builder.setConnectionManager(connectionManager); - - } catch (KeyManagementException | NoSuchAlgorithmException | KeyStoreException e) { - log.error("Ssl issue while connecting to openSearch" + e.getMessage()); - return null; - } - } - - private void setIndices(List disciplineNodes, String registrySuffix, - String registryRefsSuffix) { - // create indices strings from discipline nodes and index suffixes - log.info("Use disipline nodes: " + String.join(",", disciplineNodes) + "End discipline nodes"); - String prefix; - for (String disciplineNode : disciplineNodes) { - prefix = (disciplineNode.length() != 0) ? disciplineNode + "-" : ""; - this.registryIndices.add(prefix + registrySuffix); - this.registryRefIndices.add(prefix + registryRefsSuffix); - } - log.debug("Use registry indices:" + String.join(",", this.registryIndices) + "End indices"); - log.debug( - "Use registryRef indices:" + String.join(",", this.registryRefIndices) + "End indices"); - } - - private OpenSearchTransport getLocalTransport(List httpHosts, Boolean ssl, - Boolean sslCertificateCNVerification, String username, char[] password) { - - - - // TODO we only take the first of the hosts to create the AuthScope - // we should either take them all or make httpHosts a single element - // I have no idea not why httpHosts is a list in the first place, maybe because we are - // supposed to query a cluster. - - final ApacheHttpClient5TransportBuilder builder = ApacheHttpClient5TransportBuilder - .builder(httpHosts.toArray(new HttpHost[httpHosts.size()])); - - - builder.setHttpClientConfigCallback(httpClientBuilder -> { - return this.clientBuilderForHttpTransport(httpClientBuilder, username, password, - httpHosts.get(0), ssl, sslCertificateCNVerification); - }); - - return builder.build(); - } - - - private OpenSearchTransport getAWSTransport(String host) { - SdkHttpClient httpClient = ApacheHttpClient.builder().build(); - log.info("trying to connect to host:" + host); - return new AwsSdk2Transport(httpClient, host, "aoss", Region.US_WEST_2, - AwsSdk2TransportOptions.builder().build()); - - } - - @Autowired - public OpenSearchRegistryConnectionNewImpl( - OpenSearchRegistryConnectionImplBuilder connectionBuilder) - throws java.security.NoSuchAlgorithmException, java.security.KeyStoreException, - java.security.KeyManagementException { - - - - List httpHosts = new ArrayList(); - - OpenSearchRegistryConnectionNewImpl.log.info("Connection to open search"); - - final OpenSearchTransport transport; - - // test if we are running on ECS, - String env_value = System.getenv("ECS_CONTAINER_METADATA_URI_V4"); - if (env_value == null) { - // if environment variable does not exist, - // means we are trying to reach a regular OpenSearch - for (String host : connectionBuilder.getHosts()) { - this.host = host; - List hostAndPort = Splitter.on(':').splitToList(host); - OpenSearchRegistryConnectionNewImpl.log - .info("Host " + hostAndPort.get(0) + ":" + hostAndPort.get(1)); - log.info("Connection to host" + host); - httpHosts.add(new HttpHost((connectionBuilder.isSsl() ? "https" : "http"), - hostAndPort.get(0), Integer.parseInt(hostAndPort.get(1)))); - - } - - transport = getLocalTransport(httpHosts, connectionBuilder.isSsl(), - connectionBuilder.isSslCertificateCNVerification(), connectionBuilder.getUsername(), - connectionBuilder.getPassword()); - } else { - // otherwise, we try to connect to AWS opensearch serverless. - String host = connectionBuilder.getHosts().get(0); - transport = this.getAWSTransport(host); - } - - - - this.openSearchClient = new OpenSearchClient(transport); - this.openSearchGenericClient = new OpenSearchGenericClient(transport); - - /* - * fails with error 404 InfoResponse info = this.openSearchClient.info(); - * log.info("OpenSearch client info: " + info.version().distribution() + ": " + - * info.version().number()); log.info("OpenSearch client info, cluster name: " + - * info.clusterName()); log.info("OpenSearch client info, cluster uuid: " + info.clusterUuid()); - * log.info("OpenSearch client info, api name: " + info.name()); - * log.info("OpenSearch client info, tagline: " + info.tagline()); - */ - - this.setIndices(connectionBuilder.getDisciplineNodes(), connectionBuilder.getRegistryIndex(), - connectionBuilder.getRegistryRefIndex()); - - this.timeOutSeconds = connectionBuilder.getTimeOutSeconds(); - this.archiveStatus = connectionBuilder.getArchiveStatus(); - - - } - - - public OpenSearchClient getOpenSearchClient() { - return this.openSearchClient; - } - - public OpenSearchGenericClient getOpenSearchGenericClient() { - return this.openSearchGenericClient; - } - - public List getRegistryIndices() { - return registryIndices; - } - - public void setRegistryIndices(List registryRefIndices) { - this.registryRefIndices = registryRefIndices; - } - - public List getRegistryRefIndices() { - return registryRefIndices; - } - - public void setRegistryRefIndices(List registryRefIndices) { - this.registryRefIndices = registryRefIndices; - } - - public int getTimeOutSeconds() { - return timeOutSeconds; - } - - public void setTimeOutSeconds(int timeOutSeconds) { - this.timeOutSeconds = timeOutSeconds; - } - - public List getArchiveStatus() { - return archiveStatus; - } - - public void setArchiveStatus(List archiveStatus) { - this.archiveStatus = archiveStatus; - } - - - public void close() { - try { - // TODO verify if that is what we want to do here... - this.connectionManager.close(); - } catch (Exception ex) { - // Ignore - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/RegistrySearchRequestBuilder.java b/service/src/main/java/gov/nasa/pds/api/registry/search/RegistrySearchRequestBuilder.java deleted file mode 100644 index 13d70f64..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/RegistrySearchRequestBuilder.java +++ /dev/null @@ -1,402 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -import gov.nasa.pds.api.registry.model.identifiers.PdsLidVid; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductClasses; -import org.antlr.v4.runtime.BailErrorStrategy; -import org.antlr.v4.runtime.CharStreams; -import org.antlr.v4.runtime.CodePointCharStream; -import org.antlr.v4.runtime.CommonTokenStream; -import org.antlr.v4.runtime.tree.ParseTree; -import org.antlr.v4.runtime.tree.ParseTreeWalker; -import org.antlr.v4.runtime.RecognitionException; -import org.antlr.v4.runtime.misc.ParseCancellationException; -import org.opensearch.client.opensearch._types.FieldSort; -import org.opensearch.client.opensearch._types.FieldValue; -import org.opensearch.client.opensearch._types.SortOptions; -import org.opensearch.client.opensearch._types.SortOrder; -import org.opensearch.client.opensearch._types.query_dsl.BoolQuery; -import org.opensearch.client.opensearch._types.query_dsl.ExistsQuery; -import org.opensearch.client.opensearch._types.query_dsl.FieldAndFormat; -import org.opensearch.client.opensearch._types.query_dsl.MatchQuery; -import org.opensearch.client.opensearch._types.query_dsl.Query; -import org.opensearch.client.opensearch._types.query_dsl.TermsQuery; -import org.opensearch.client.opensearch._types.query_dsl.TermsQueryField; -import org.opensearch.client.opensearch.core.SearchRequest; -import org.opensearch.client.opensearch.core.search.SourceConfig; -import org.opensearch.client.opensearch.core.search.SourceFilter; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import gov.nasa.pds.api.registry.ConnectionContext; -import gov.nasa.pds.api.registry.lexer.SearchLexer; -import gov.nasa.pds.api.registry.lexer.SearchParser; -import gov.nasa.pds.api.registry.model.Antlr4SearchListener; -import gov.nasa.pds.api.registry.model.EntityProduct; -import gov.nasa.pds.api.registry.model.SearchUtil; -import gov.nasa.pds.api.registry.model.exceptions.SortSearchAfterMismatchException; -import gov.nasa.pds.api.registry.model.exceptions.UnparsableQParamException; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductIdentifier; - - -public class RegistrySearchRequestBuilder extends SearchRequest.Builder{ - - private static final Logger log = LoggerFactory.getLogger(RegistrySearchRequestBuilder.class); - - private static final ArrayList STATIC_FIELDANDFORMATS = - new ArrayList() { - { - for (String prop : EntityProduct.JSON_PROPERTIES) { - add(new FieldAndFormat.Builder().field(prop).build()); - } - } - }; - - private ConnectionContext connectionContext; - private List registryIndices; - private BoolQuery.Builder queryBuilder; - - public RegistrySearchRequestBuilder(ConnectionContext connectionContext) { -// edunn TODO: Evaluate what can be taken out of the constructor - - this.connectionContext = connectionContext; - - this.registryIndices = this.connectionContext.getRegistryIndices(); - log.info("Use indices: " + String.join(",", registryIndices) + "End indices"); - - this.index(registryIndices); - - Query baseQuery = getMandatoryBaselineQuery(connectionContext); - this.queryBuilder = new BoolQuery.Builder() - .must(baseQuery); - } - - /** - * Return a baseline, non-configurable query which applies to all search requests. Currently, this is just archive - * status, but this will likely be subject to extensive revision (may balloon, or disappear entirely) - * @param connectionContext - * @return the minimal match constraints applicable to all search requests - */ - private static Query getMandatoryBaselineQuery(ConnectionContext connectionContext) { - List archiveStatus = connectionContext.getArchiveStatus(); - List archiveStatusFieldValues = archiveStatus.stream().map(FieldValue::of).toList(); - log.info("Only publishes archiveStatus: " + String.join(",", archiveStatus)); - TermsQueryField archiveStatusTerms = new TermsQueryField.Builder() - .value(archiveStatusFieldValues) - .build(); - - TermsQuery archiveStatusQuery = new TermsQuery.Builder() - .field("ops:Tracking_Meta/ops:archive_status") - .terms(archiveStatusTerms) - .build(); - - return archiveStatusQuery.toQuery(); - } - - /** - * Access the internal BoolQuery.Builder instance which is used to build a query during - * RegistrySearchRequestBuilder.build() - * Before accessing the query builder directly, consider whether the behaviour is common enough that it should be - * abstracted as a method of RegistrySearchRequestBuilder. - * @return the query builder instance for this search-request builder - */ - public BoolQuery.Builder getQueryBuilder() { - return this.queryBuilder; - } - - /** - * Applies a common set of constraints and other build options which generally apply to any endpoint which queries - * OpenSearch for a result-set of multiple products. - * @param includeFieldNames - which properties to include in the results (JSON format, not OpenSearch format) - * @param queryString - a querystring (q=) to constrain the result-set by - * @param keywords - a set of keyword matches to - * @param pageSize - the page size to use for pagination - * @param sortFieldNames - the fields by which results are sorted (ascending), from highest to lowest priority - * @param searchAfterFieldValues - the values corresponding to the sort fields, for pagination - * @param noSupersededProducts - whether to exclude superseded products from the result set - */ - public RegistrySearchRequestBuilder applyMultipleProductsDefaults( - List includeFieldNames, - String queryString, - List keywords, - Integer pageSize, - List sortFieldNames, - List searchAfterFieldValues, - Boolean noSupersededProducts - ) throws UnparsableQParamException, SortSearchAfterMismatchException { - this - .fieldsFromStrings(includeFieldNames) - .constrainByQueryString(queryString) - .addKeywordsParam(keywords) - .paginate(pageSize, sortFieldNames, searchAfterFieldValues); - - if (noSupersededProducts) { - this.noSupersededProducts(); - } - - return this; - } - - public SearchRequest build() { - this.query(this.queryBuilder.build().toQuery()); - this.trackTotalHits(t -> t.enabled(true)); - - return super.build(); - } - - /** - * Add a constraint that a given field name must match the given field value - * @param fieldName the name of the field in OpenSearch format - * @param value the value which must be present in the given field - */ - public RegistrySearchRequestBuilder matchField(String fieldName, String value) { - FieldValue fieldValue = new FieldValue.Builder().stringValue(value).build(); - MatchQuery lidvidMatch = new MatchQuery.Builder().field(fieldName).query(fieldValue).build(); - - this.queryBuilder.must(lidvidMatch.toQuery()); - - return this; - } - - /** - * Add a constraint that a given field name must match the given field value - * @param fieldName the name of the field in OpenSearch format - * @param identifier the PDS identifier whose string representation must be present in the given field - */ - public RegistrySearchRequestBuilder matchField(String fieldName, PdsProductIdentifier identifier) { - return this.matchField(fieldName, identifier.toString()); - } - - - /** - * Add a constraint that a given field name must match at least one of the given field values - * @param fieldName the name of the field in OpenSearch format - * @param values the values, one of which must be present in the given field - */ - public RegistrySearchRequestBuilder matchFieldAnyOf(String fieldName, List values) { - List fieldValues = values.stream().map(value -> new FieldValue.Builder().stringValue(value).build()).toList(); - TermsQueryField termsQueryField = new TermsQueryField.Builder().value(fieldValues).build(); - TermsQuery query = new TermsQuery.Builder().field(fieldName).terms(termsQueryField).build(); - - this.queryBuilder.must(query.toQuery()); - - return this; - } - - /** - * Add a constraint that a given field name must match at least one of the given field values - * @param fieldName the name of the field in OpenSearch format - * @param identifiers the PDS identifiers, one of whose string representation must be present in the given field - */ - public RegistrySearchRequestBuilder matchFieldAnyOfIdentifiers(String fieldName, List identifiers) { - return this.matchFieldAnyOf(fieldName, identifiers.stream().map(PdsProductIdentifier::toString).toList()); - } - - public RegistrySearchRequestBuilder matchLidvid(PdsProductIdentifier identifier) { - return this.matchField("_id", identifier); - } - - public RegistrySearchRequestBuilder matchLid(PdsProductIdentifier identifier) { - return this.matchField("lid", identifier.getLid()); - } - - public RegistrySearchRequestBuilder matchProductClass(PdsProductClasses productClass) { - return this.matchField(PdsProductClasses.getPropertyName(), productClass.getValue()); - } - - public RegistrySearchRequestBuilder matchMembersOfBundle(PdsLidVid identifier) { - return this.matchField("ops:Provenance/ops:parent_bundle_identifier", identifier); - } - - public RegistrySearchRequestBuilder matchMembersOfCollection(PdsLidVid identifier) { - return this.matchField("ops:Provenance/ops:parent_collection_identifier", identifier); - } - - public RegistrySearchRequestBuilder paginate(Integer pageSize, List sortFieldNames, - List searchAfterFieldValues) throws SortSearchAfterMismatchException { - if ((sortFieldNames != null) && (!sortFieldNames.isEmpty())) { - this.sortFromStrings(sortFieldNames); - } - - this.size(pageSize); - - if ((searchAfterFieldValues != null) && (!searchAfterFieldValues.isEmpty())) { - if (sortFieldNames == null) { - throw new SortSearchAfterMismatchException("sort argument must be provided if searchAfter argument is provided"); - } else if (searchAfterFieldValues.size() != sortFieldNames.size()) { - throw new SortSearchAfterMismatchException("sort and searchAfter arguments must be of equal length if provided"); - } - this.searchAfterFromStrings(searchAfterFieldValues); - } - - return this; - - } - - /** - * Implements an alternative to .sort() that accepts strings in API property format. - * Currently hardcoded to sort in ascending order only. - * @param sortFieldNames - */ - public RegistrySearchRequestBuilder sortFromStrings(List sortFieldNames) { - - String openSearchField; - - List sortOptionsList = new ArrayList(); - for (String field : sortFieldNames) { - openSearchField = SearchUtil.jsonPropertyToOpenProperty(field); - FieldSort fieldSort = - new FieldSort.Builder().field(openSearchField).order(SortOrder.Asc).build(); - sortOptionsList.add(new SortOptions.Builder().field(fieldSort).build()); - } - - this.sort(sortOptionsList); - - return this; - - } - - /** - * Implements an alternative to .searchAfter() that accepts values as strings. - * No-op in current version of OpenSearch client, but a later version will require the commented-out - * implementation to convert the Strings to FieldValues - * @param searchAfterValues - */ - public RegistrySearchRequestBuilder searchAfterFromStrings(List searchAfterValues) { - /* - * List fieldValues = new ArrayList(); - * - * for (String fieldValue : searchAfter) { fieldValues.add(new - // TODO check if the number value need to be handled specfically. Method stringValue() implies yes - * FieldValue.Builder().stringValue(fieldValue).build()); } - */ - this.searchAfter(searchAfterValues); - - - return this; - } - - - /** - * Implements an alternative to .fields() that accepts values as strings. - * @param fieldNames - */ - public RegistrySearchRequestBuilder fieldsFromStrings(List fieldNames) { - - if ((fieldNames == null) || (fieldNames.isEmpty())) { - return this; - } else { - log.info("restricting list of fields requested from OpenSearch."); - // TODO refine to only pull the static field when the output response requires it. - List openSearchField = - new ArrayList(Arrays.asList(EntityProduct.JSON_PROPERTIES)); - for (String field : fieldNames) { - openSearchField.add(SearchUtil.jsonPropertyToOpenProperty(field)); - } - - SourceFilter sourceFilter = new SourceFilter.Builder().includes(openSearchField).build(); - SourceConfig limitedSourceCfg = new SourceConfig.Builder().filter(sourceFilter).build(); - - this.source(limitedSourceCfg); - - return this; - } - - } - - private static BoolQuery parseQueryString(String queryString) { - CodePointCharStream input = CharStreams.fromString(queryString); - SearchLexer lex = new SearchLexer(input); - CommonTokenStream tokens = new CommonTokenStream(lex); - - SearchParser par = new SearchParser(tokens); - par.setErrorHandler(new BailErrorStrategy()); - ParseTree tree = par.query(); - - log.debug(tree.toStringTree(par)); - - // Walk it and attach our listener - ParseTreeWalker walker = new ParseTreeWalker(); - Antlr4SearchListener listener = new Antlr4SearchListener(); - walker.walk(listener, tree); - - return listener.getBoolQuery(); - } - - /** - * Constrain results with a query-string in PDS API Search Query syntax - * @param q a PDS API Search Query string - * @throws UnparsableQParamException if the string is not parseable - */ - public RegistrySearchRequestBuilder constrainByQueryString(String q) throws UnparsableQParamException { - - try { - if ((q != null) && (q.length() > 0)) { - BoolQuery qBoolQuery = RegistrySearchRequestBuilder.parseQueryString(q); - this.queryBuilder.must(qBoolQuery.toQuery()); - } - return this; - } catch (RecognitionException | ParseCancellationException e) { - log.info("Unable to parse q " + q + "error message is " + e); - throw new UnparsableQParamException( - "q string value:" + q + " Error message " + e.getMessage()); - } - - - } - - public RegistrySearchRequestBuilder addKeywordsParam(List keywords) { - - // TODO implement - return this; - } - - /** - * Limit results to the latest version of each LID in the result-set. - * N.B. this does *not* mean the latest version which satisfies other constraints, so application of this constraint - * can result in no hits being returned despite valid results existing. - */ - public RegistrySearchRequestBuilder noSupersededProducts() { - - ExistsQuery supersededByExists = new ExistsQuery.Builder() - .field("ops:Provenance/ops:superseded_by") - .build(); - - this.queryBuilder.mustNot(supersededByExists.toQuery()); - - return this; - } - - /** - * Limit results to bundle products - */ - public RegistrySearchRequestBuilder onlyBundles() { - return this.matchField(PdsProductClasses.getPropertyName(), PdsProductClasses.Product_Bundle.toString()); - } - - - /** - * Limit results to collection products - */public RegistrySearchRequestBuilder onlyCollections() { - return this.matchField(PdsProductClasses.getPropertyName(), PdsProductClasses.Product_Collection.toString()); - } - - - /** - * Limit results to basic (non-aggregate) products, i.e. exclude bundles/collections - */ - public RegistrySearchRequestBuilder onlyBasicProducts() { - List excludeValues = Arrays.stream(PdsProductClasses.values()) - .filter(cls -> !cls.isBasicProduct()) - .map(value -> new FieldValue.Builder().stringValue(value.toString()).build()).toList(); - TermsQueryField termsQueryField = new TermsQueryField.Builder().value(excludeValues).build(); - TermsQuery query = new TermsQuery.Builder().field(PdsProductClasses.getPropertyName()).terms(termsQueryField).build(); - - this.queryBuilder.mustNot(query.toQuery()); - return this; - } - -} - diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/RequestBuildContextFactory.java b/service/src/main/java/gov/nasa/pds/api/registry/search/RequestBuildContextFactory.java deleted file mode 100644 index 758fc020..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/RequestBuildContextFactory.java +++ /dev/null @@ -1,31 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.Arrays; -import java.util.List; - -import gov.nasa.pds.api.registry.GroupConstraint; -import gov.nasa.pds.api.registry.RequestBuildContext; - -public class RequestBuildContextFactory { - public static RequestBuildContext empty() { - return new SimpleRequestBuildContext(true); - } - - public static RequestBuildContext given(boolean justLatest, String field) { - return new SimpleRequestBuildContext(justLatest, Arrays.asList(field)); - } - - public static RequestBuildContext given(boolean justLatest, List fields) { - return new SimpleRequestBuildContext(justLatest, fields); - } - - public static RequestBuildContext given(boolean justLatest, String field, - GroupConstraint preset) { - return new SimpleRequestBuildContext(justLatest, Arrays.asList(field), preset); - } - - public static RequestBuildContext given(boolean justLatest, List fields, - GroupConstraint preset) { - return new SimpleRequestBuildContext(justLatest, fields, preset); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/RequestConstructionContextFactory.java b/service/src/main/java/gov/nasa/pds/api/registry/search/RequestConstructionContextFactory.java deleted file mode 100644 index 7cecad47..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/RequestConstructionContextFactory.java +++ /dev/null @@ -1,37 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.Arrays; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -import gov.nasa.pds.api.registry.RequestConstructionContext; - -public class RequestConstructionContextFactory { - - public static RequestConstructionContext minimal() { - return new SimpleRequestConstructionContext(new HashMap<>(), true); - } - public static RequestConstructionContext given(String lidvid) { - return new SimpleRequestConstructionContext(lidvid); - } - - public static RequestConstructionContext given(List lidvids) { - Map> kvps = new HashMap>(); - kvps.put("lidvid", lidvids); - return new SimpleRequestConstructionContext(kvps, true); - } - - public static RequestConstructionContext given(String key, String value, boolean asTerm) { - List values = Arrays.asList(value); - Map> kvps = new HashMap>(); - kvps.put(key, values); - return new SimpleRequestConstructionContext(kvps, asTerm); - } - - public static RequestConstructionContext given(String key, List values, boolean asTerm) { - Map> kvps = new HashMap>(); - kvps.put(key, values); - return new SimpleRequestConstructionContext(kvps, asTerm); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestBuildContext.java b/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestBuildContext.java deleted file mode 100644 index c5cdb780..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestBuildContext.java +++ /dev/null @@ -1,47 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.ArrayList; -import java.util.List; - -import gov.nasa.pds.api.registry.GroupConstraint; -import gov.nasa.pds.api.registry.RequestBuildContext; -import gov.nasa.pds.api.registry.util.GroupConstraintImpl; - -class SimpleRequestBuildContext implements RequestBuildContext { - final private boolean justLatest; - final private List fields; - final private GroupConstraint preset; - - SimpleRequestBuildContext(boolean justLatest) { - this.fields = new ArrayList(); - this.justLatest = justLatest; - this.preset = GroupConstraintImpl.empty(); - } - - SimpleRequestBuildContext(boolean justLatest, List fields) { - this.fields = fields; - this.justLatest = justLatest; - this.preset = GroupConstraintImpl.empty(); - } - - SimpleRequestBuildContext(boolean justLatest, List fields, GroupConstraint preset) { - this.fields = fields; - this.justLatest = justLatest; - this.preset = preset; - } - - @Override - public boolean justLatest() { - return this.justLatest; - } - - @Override - public List getFields() { - return this.fields; - } - - @Override - public GroupConstraint getPresetCriteria() { - return this.preset; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestConstructionContext.java b/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestConstructionContext.java deleted file mode 100644 index 71d06b3a..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/search/SimpleRequestConstructionContext.java +++ /dev/null @@ -1,69 +0,0 @@ -package gov.nasa.pds.api.registry.search; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -import gov.nasa.pds.api.registry.RequestConstructionContext; -import gov.nasa.pds.api.registry.model.identifiers.PdsProductIdentifier; - -class SimpleRequestConstructionContext implements RequestConstructionContext { - final private boolean isTerm; - final private Map> kvps; - final private PdsProductIdentifier productIdentifier; - - SimpleRequestConstructionContext(Map> kvps) { - this.isTerm = false; - this.kvps = kvps; - this.productIdentifier = null; - } - - SimpleRequestConstructionContext(Map> kvps, boolean asTerm) { - this.isTerm = asTerm; - this.kvps = kvps; - this.productIdentifier = null; - } - - SimpleRequestConstructionContext(String productIdentifier) { - this.isTerm = false; - this.kvps = new HashMap>(); - this.productIdentifier = PdsProductIdentifier.fromString(productIdentifier); - } - - SimpleRequestConstructionContext(String productIdentifier, boolean isTerm) { - this.isTerm = isTerm; - this.kvps = new HashMap>(); - this.productIdentifier = PdsProductIdentifier.fromString(productIdentifier); - } - - @Override - public List getKeywords() { - return new ArrayList(); - } - - @Override - public Map> getKeyValuePairs() { - return this.kvps; - } - - @Override - public PdsProductIdentifier getProductIdentifier() { - return this.productIdentifier; - } - - @Override - public String getProductIdentifierString() { - return this.productIdentifier == null ? "" : this.productIdentifier.toString(); - } - - @Override - public String getQueryString() { - return ""; - } - - @Override - public boolean isTerm() { - return this.isTerm; - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/util/AWSCredentialsFetcher.java b/service/src/main/java/gov/nasa/pds/api/registry/util/AWSCredentialsFetcher.java deleted file mode 100644 index 5b2213ff..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/util/AWSCredentialsFetcher.java +++ /dev/null @@ -1,100 +0,0 @@ -package gov.nasa.pds.api.registry.util; - -import java.io.IOException; -import java.io.InputStream; -import java.net.HttpURLConnection; -import java.net.URL; -import java.util.Properties; -import java.util.concurrent.TimeUnit; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.stereotype.Component; -import org.springframework.scheduling.annotation.Scheduled; -import com.fasterxml.jackson.annotation.JsonProperty; -import com.fasterxml.jackson.databind.ObjectMapper; - - -class AWSCredentials { - @JsonProperty("RoleArn") - String roleArn; - - @JsonProperty("AccessKeyId") - String accessKeyId; - - @JsonProperty("SecretAccessKey") - String secretAccessKey; - - @JsonProperty("Token") - String token; - - @JsonProperty("Expiration") - String expiration; - - public String getRoleArn() { - return roleArn; - } - - public String getAccessKeyId() { - return accessKeyId; - } - - public String getSecretAccessKey() { - return secretAccessKey; - } - - public String getToken() { - return token; - } - - public String getExpiration() { - return expiration; - } - - -} - - -@Component -public class AWSCredentialsFetcher { - - private static final Logger log = LoggerFactory.getLogger(AWSCredentialsFetcher.class); - - private final String AWS_CONTAINER_CREDENTIALS_RELATIVE_URI = - "AWS_CONTAINER_CREDENTIALS_RELATIVE_URI"; - private final String CREDENTIAL_SERVER_IP = "169.254.170.2"; - - - @Scheduled(fixedDelay = 5, timeUnit = TimeUnit.HOURS) - public void fetchCredentials() { - - String credentialRelativeURI = System.getenv(this.AWS_CONTAINER_CREDENTIALS_RELATIVE_URI); - - if (credentialRelativeURI != null) { - try { - log.info("Getting/Renewing AWS Credentials"); - String credentialURL = "http://" + this.CREDENTIAL_SERVER_IP + credentialRelativeURI; - URL url = new URL(credentialURL); - HttpURLConnection con = (HttpURLConnection) url.openConnection(); - con.setRequestMethod("GET"); - InputStream credentialStream = con.getInputStream(); - AWSCredentials awsCredentials = - new ObjectMapper().readValue(credentialStream, AWSCredentials.class); - Properties awsCredProperties = new Properties(System.getProperties()); - awsCredProperties.setProperty("aws.accessKeyId", awsCredentials.getAccessKeyId()); - awsCredProperties.setProperty("aws.secretAccessKey", awsCredentials.getSecretAccessKey()); - awsCredProperties.setProperty("aws.sessionToken", awsCredentials.getToken()); - System.setProperties(awsCredProperties); - log.info("Expiration of the AWS token is scheduled in " + awsCredentials.expiration); - } catch (IOException e) { - log.error("Unable to get or renew AWS Credentials", e); - } - - } else { - log.info("Nothing to do, we don't need AWS Credentials"); - } - - - } - - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/util/GroupConstraintImpl.java b/service/src/main/java/gov/nasa/pds/api/registry/util/GroupConstraintImpl.java deleted file mode 100644 index 47556d35..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/util/GroupConstraintImpl.java +++ /dev/null @@ -1,136 +0,0 @@ -package gov.nasa.pds.api.registry.util; - -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import com.google.errorprone.annotations.Immutable; - -import gov.nasa.pds.api.registry.GroupConstraint; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -@Immutable -public class GroupConstraintImpl implements GroupConstraint { - - private static final Logger log = LoggerFactory.getLogger(GroupConstraintImpl.class); - - final private Map> filterToAny; - final private Map> must; - final private Map> mustNot; - - private GroupConstraintImpl(Map> must, Map> filterToAny, - Map> mustNot) { - int filterTermsKeysCount = filterToAny.keySet().size(); - if (filterTermsKeysCount > 1) { - throw new RuntimeException( - "Filtering on multiple keys is not supported by OpenSearch terms query, so is undefined"); - } - - this.must = Map.copyOf(must); - this.filterToAny = Map.copyOf(filterToAny); - this.mustNot = Map.copyOf(mustNot); - } - - @Override - public Map> must() { - return must; - } - - @Override - public Map> filterToAny() { - return filterToAny; - } - - @Override - public Map> mustNot() { - return mustNot; - } - - - /** - * Perform a union on a pair of a single constraint type (filter, must or mustNot) - */ - private Map> performConstraintUnion(Map> constraint1, Map> constraint2) { - Map> unionConstraint = new HashMap<>(constraint1); - constraint2.forEach( - (key, value) -> { - if (unionConstraint.containsKey(key)) { - unionConstraint.get(key).addAll(value); - List deduplicatedValue = List.copyOf(Set.copyOf(unionConstraint.get(key))); - unionConstraint.put(key, deduplicatedValue); - } else { - unionConstraint.put(key, List.copyOf(value)); - } - }); - - return unionConstraint; - } - - private void logMutuallyExclusiveMustConditions(Map> mustConditions) { - mustConditions.forEach( - (key, value) -> { - if (value.size() > 1) { - log.warn( - "Multiple values for 'must' condition are mutually-exclusive and will always fail: property='" - + key - + "', values=['" - + String.join("', '", value) - + "']"); - } - }); - } - - @Override - public GroupConstraint union(GroupConstraint otherGroupConstraint) { - Map> unionFilter = - performConstraintUnion(this.filterToAny, otherGroupConstraint.filterToAny()); - Map> unionMust = - performConstraintUnion(this.must, otherGroupConstraint.must()); - Map> unionMustNot = - performConstraintUnion(this.mustNot, otherGroupConstraint.mustNot()); - - logMutuallyExclusiveMustConditions(unionMust); - - return new GroupConstraintImpl(unionMust, unionFilter, unionMustNot); - } - - final private static Map> EMPTY = new HashMap>(); - - public static GroupConstraint empty() { - return new GroupConstraintImpl(EMPTY, EMPTY, EMPTY); - } - - public static GroupConstraint buildAll(Map> map) { - return new GroupConstraintImpl(map, EMPTY, EMPTY); - } - - public static GroupConstraint buildAny(Map> map) { - return new GroupConstraintImpl(EMPTY, map, EMPTY); - } - - public static GroupConstraint buildNot(Map> map) { - return new GroupConstraintImpl(EMPTY, EMPTY, map); - } - - public static GroupConstraint buildAllAny(Map> allmap, - Map> anymap) { - return new GroupConstraintImpl(allmap, anymap, EMPTY); - } - - public static GroupConstraint buildAllNot(Map> allmap, - Map> notmap) { - return new GroupConstraintImpl(allmap, EMPTY, notmap); - } - - public static GroupConstraint buildAnyNot(Map> anymap, - Map> notmap) { - return new GroupConstraintImpl(EMPTY, anymap, notmap); - } - - public static GroupConstraint build(Map> allmap, - Map> anymap, Map> notmap) { - return new GroupConstraintImpl(allmap, anymap, notmap); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvErrorMessageSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/CsvErrorMessageSerializer.java deleted file mode 100644 index 27682b00..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvErrorMessageSerializer.java +++ /dev/null @@ -1,48 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import gov.nasa.pds.model.ErrorMessage; - -public class CsvErrorMessageSerializer extends AbstractHttpMessageConverter { - public CsvErrorMessageSerializer() { - super(new MediaType("application", "csv"), new MediaType("text", "csv")); - } - - @Override - protected boolean supports(Class clazz) { - return ErrorMessage.class.isAssignableFrom(clazz); - } - - @Override - protected ErrorMessage readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new ErrorMessage(); - } - - @Override - protected void writeInternal(ErrorMessage t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - outputMessage.getHeaders().setContentType(MediaType.TEXT_PLAIN); // must be before body is fetched - OutputStreamWriter osw = new OutputStreamWriter(outputMessage.getBody(), "UTF-8"); - try { - osw.write("request,message\n"); - osw.write('"'); - osw.write(t.getRequest()); - osw.write("\",\""); - osw.write(t.getMessage()); - osw.write('"'); - osw.write('\n'); - } finally { - osw.close(); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvPluralSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/CsvPluralSerializer.java deleted file mode 100644 index 83077c10..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvPluralSerializer.java +++ /dev/null @@ -1,45 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.model.WyriwygProducts; - - -public class CsvPluralSerializer extends AbstractHttpMessageConverter { - public CsvPluralSerializer() { - super(new MediaType("application", "csv"), new MediaType("text", "csv")); - } - - @Override - protected boolean supports(Class clazz) { - return WyriwygProducts.class.isAssignableFrom(clazz); - } - - @Override - protected WyriwygProducts readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new WyriwygProducts(); - } - - @Override - protected void writeInternal(WyriwygProducts t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - outputMessage.getHeaders().setContentType(MediaType.TEXT_PLAIN); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - Utilities.fix(t.getSummary()); - WyriwygSerializer.writeCSV(t, wr, mapper); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvSingularSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/CsvSingularSerializer.java deleted file mode 100644 index 0b1138df..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/CsvSingularSerializer.java +++ /dev/null @@ -1,45 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.WyriwygProduct; - -public class CsvSingularSerializer extends AbstractHttpMessageConverter { - public CsvSingularSerializer() { - super(new MediaType("application", "csv"), new MediaType("text", "csv")); - } - - @Override - protected boolean supports(Class clazz) { - return WyriwygProduct.class.isAssignableFrom(clazz); - } - - @Override - protected WyriwygProduct readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new WyriwygProduct(); - } - - @Override - protected void writeInternal(WyriwygProduct t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - outputMessage.getHeaders().setContentType(MediaType.TEXT_PLAIN); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - WyriwygSerializer.writeCSV(t, wr, mapper); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/HtmlErrorMessageSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/HtmlErrorMessageSerializer.java deleted file mode 100644 index 47f863e2..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/HtmlErrorMessageSerializer.java +++ /dev/null @@ -1,46 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import gov.nasa.pds.model.ErrorMessage; - -public class HtmlErrorMessageSerializer extends AbstractHttpMessageConverter { - public HtmlErrorMessageSerializer() { - super(MediaType.TEXT_HTML); - } - - @Override - protected boolean supports(Class clazz) { - return ErrorMessage.class.isAssignableFrom(clazz); - } - - @Override - protected ErrorMessage readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new ErrorMessage(); - } - - @Override - protected void writeInternal(ErrorMessage t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - outputMessage.getHeaders().setContentType(MediaType.TEXT_HTML); // must be before body is fetched - OutputStreamWriter osw = new OutputStreamWriter(outputMessage.getBody(), "UTF-8"); - try { - osw.write("

Error Message

From Request

"); - osw.write(t.getRequest()); - osw.write("

Message

"); - osw.write(t.getMessage()); - osw.write("

"); - } finally { - osw.close(); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonErrorMessageSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/JsonErrorMessageSerializer.java deleted file mode 100644 index 66655699..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonErrorMessageSerializer.java +++ /dev/null @@ -1,45 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStreamWriter; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; -import gov.nasa.pds.model.ErrorMessage; - -public class JsonErrorMessageSerializer extends AbstractHttpMessageConverter { - public JsonErrorMessageSerializer() { - super(MediaType.APPLICATION_JSON, new MediaType("application", "kvp+json"), - new MediaType("application", "vnd.nasa.pds.pds4+json"), MediaType.ALL, new MediaType("*")); - } - - @Override - protected boolean supports(Class clazz) { - return ErrorMessage.class.isAssignableFrom(clazz); - } - - @Override - protected ErrorMessage readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new ErrorMessage(); - } - - @Override - protected void writeInternal(ErrorMessage t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStreamWriter osw = new OutputStreamWriter(outputMessage.getBody(), "UTF-8"); - try { - osw.write("{\"request\":\""); - osw.write(t.getRequest()); - osw.write("\",\"message\":\""); - osw.write(t.getMessage()); - osw.write("\"}"); - } finally { - osw.close(); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonPluralSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/JsonPluralSerializer.java deleted file mode 100644 index 5cde984e..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonPluralSerializer.java +++ /dev/null @@ -1,44 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.model.WyriwygProducts; - -public class JsonPluralSerializer extends AbstractHttpMessageConverter { - public JsonPluralSerializer() { - super(new MediaType("application", "kvp+json")); - } - - @Override - protected boolean supports(Class clazz) { - return WyriwygProducts.class.isAssignableFrom(clazz); - } - - @Override - protected WyriwygProducts readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new WyriwygProducts(); - } - - @Override - protected void writeInternal(WyriwygProducts t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - Utilities.fix(t.getSummary()); - WyriwygSerializer.writeJSON(t, wr, mapper); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonProductSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/JsonProductSerializer.java deleted file mode 100644 index 80e1e6c5..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonProductSerializer.java +++ /dev/null @@ -1,38 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.util.ArrayList; -import java.util.List; -import org.springframework.http.ContentDisposition; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.HttpMessageNotWritableException; -import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -public class JsonProductSerializer extends MappingJackson2HttpMessageConverter { - public JsonProductSerializer() { - super(); - - List supportMediaTypes = new ArrayList(); - supportMediaTypes.add(MediaType.APPLICATION_JSON); - supportMediaTypes.add(MediaType.ALL); - supportMediaTypes.add(new MediaType("*")); - - this.setSupportedMediaTypes(supportMediaTypes); - - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - this.setObjectMapper(mapper); - } - - @Override - protected void writeInternal(Object object, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - outputMessage.getHeaders().setContentDisposition(ContentDisposition.empty()); - super.writeInternal(object, outputMessage); - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonSingularSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/JsonSingularSerializer.java deleted file mode 100644 index f4ed1c8c..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/JsonSingularSerializer.java +++ /dev/null @@ -1,45 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.WyriwygProduct; - -public class JsonSingularSerializer extends AbstractHttpMessageConverter { - public JsonSingularSerializer() { - super(new MediaType("application", "kvp+json")); - } - - @Override - protected boolean supports(Class clazz) { - return WyriwygProduct.class.isAssignableFrom(clazz); - } - - @Override - protected WyriwygProduct readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new WyriwygProduct(); - } - - @Override - protected void writeInternal(WyriwygProduct t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - WyriwygSerializer.writeJSON(t, wr, mapper); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductSerializer.java deleted file mode 100644 index af45943f..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductSerializer.java +++ /dev/null @@ -1,85 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.io.Writer; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.Pds4Metadata; -import gov.nasa.pds.model.Pds4Product; - -/** - * Custom serializer to write a Pds4Product in "pds4+json" format. - * - * @author karpenko - */ -public class Pds4JsonProductSerializer extends AbstractHttpMessageConverter { - private static final Logger log = LoggerFactory.getLogger(Pds4JsonProductSerializer.class); - - /** - * Constructor - */ - public Pds4JsonProductSerializer() { - super(new MediaType("application", "vnd.nasa.pds.pds4+json")); - } - - @Override - protected boolean supports(Class clazz) { - return Pds4Product.class.isAssignableFrom(clazz); - } - - @Override - protected Pds4Product readInternal(Class clazz, HttpInputMessage msg) - throws IOException, HttpMessageNotReadableException { - return new Pds4Product(); - } - - @Override - public void writeInternal(Pds4Product product, HttpOutputMessage msg) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - msg.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStream os = msg.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - writeProduct(product, wr, mapper); - wr.close(); - } - - public static void writeProduct(Pds4Product product, Writer wr, ObjectMapper mapper) - throws IOException { - wr.write("{\n"); - - String value = mapper.writeValueAsString(product.getId()); - wr.write("\"id\": " + value); - - Pds4Metadata meta = product.getMetadata(); - if (meta != null) { - value = mapper.writeValueAsString(meta); - wr.write(",\n\"meta\": " + value); - } - - if (product.getPds4() != null) { - try { - wr.write(",\n\"pds4\": "); - wr.write((String) product.getPds4()); - } catch (Exception ex) { - log.warn("Could not extract BLOB from product " + product.getId(), ex); - } - } - - wr.write("}\n"); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductsSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductsSerializer.java deleted file mode 100644 index 50a58bc3..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4JsonProductsSerializer.java +++ /dev/null @@ -1,90 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.io.Writer; -import java.util.List; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.Pds4Product; -import gov.nasa.pds.model.Pds4Products; - -/** - * Custom serializer to write a Pds4Product in "pds4+json" format. - * - * @author karpenko - */ -public class Pds4JsonProductsSerializer extends AbstractHttpMessageConverter { - /** - * Constructor - */ - public Pds4JsonProductsSerializer() { - super(new MediaType("application", "vnd.nasa.pds.pds4+json")); - } - - @Override - protected boolean supports(Class clazz) { - return Pds4Products.class.isAssignableFrom(clazz); - } - - @Override - protected Pds4Products readInternal(Class clazz, HttpInputMessage msg) - throws IOException, HttpMessageNotReadableException { - return new Pds4Products(); - } - - @Override - public void writeInternal(Pds4Products products, HttpOutputMessage msg) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - mapper.setSerializationInclusion(Include.NON_NULL); - msg.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - - OutputStream os = msg.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os); - - Utilities.fix(products.getSummary()); - wr.write("{\n"); - - // Summary - wr.write("\"summary\":"); - String value = mapper.writeValueAsString(products.getSummary()); - wr.write(value); - wr.write(",\n"); - - // Data - wr.write("\"data\":["); - writeProducts(products.getData(), wr, mapper); - wr.write("]\n"); - - wr.write("}\n"); - wr.close(); - } - - private void writeProducts(List list, Writer wr, ObjectMapper mapper) - throws IOException { - if (list == null) - return; - - int size = list.size(); - for (int i = 0; i < size; i++) { - Pds4Product prod = list.get(i); - Pds4JsonProductSerializer.writeProduct(prod, wr, mapper); - - if (i < size - 1) { - wr.write(",\n"); - } - } - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductSerializer.java deleted file mode 100644 index 688c1c66..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductSerializer.java +++ /dev/null @@ -1,90 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import gov.nasa.pds.model.Pds4Product; - -import java.io.IOException; -import java.io.OutputStream; - -import javax.xml.stream.XMLOutputFactory; -import javax.xml.stream.XMLStreamException; -import javax.xml.stream.XMLStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.dataformat.xml.XmlMapper; - -public class Pds4XmlProductSerializer extends AbstractHttpMessageConverter { - static final public String NAMESPACE_PREFIX = "pds_api"; - static final public String NAMESPACE_PREFIX_OPS = "ops"; - static final public String NAMESPACE_URL = "http://pds.nasa.gov/api"; - static final public String NAMESPACE_URL_OPS = "https://pds.nasa.gov/pds4/ops/v1"; - - public Pds4XmlProductSerializer() { - super(new MediaType("application", "vnd.nasa.pds.pds4+xml")); - } - - @Override - protected boolean supports(Class clazz) { - return Pds4Product.class.isAssignableFrom(clazz); - } - - @Override - protected Pds4Product readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new Pds4Product(); - } - - @Override - protected void writeInternal(Pds4Product product, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - try { - outputMessage.getHeaders().setContentType(MediaType.TEXT_XML); // must be before body is fetched - OutputStream outputStream = outputMessage.getBody(); - XMLOutputFactory outputFactory = XMLOutputFactory.newFactory(); - outputFactory.setProperty("javax.xml.stream.isRepairingNamespaces", true); - XMLStreamWriter writer = outputFactory.createXMLStreamWriter(outputStream); - writer.setPrefix(Pds4XmlProductSerializer.NAMESPACE_PREFIX, - Pds4XmlProductSerializer.NAMESPACE_URL); - writer.setPrefix(NAMESPACE_PREFIX_OPS, NAMESPACE_URL_OPS); - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "product"); - writer.writeNamespace(Pds4XmlProductSerializer.NAMESPACE_PREFIX, - Pds4XmlProductSerializer.NAMESPACE_URL); - writer.writeNamespace(NAMESPACE_PREFIX_OPS, NAMESPACE_URL_OPS); - Pds4XmlProductSerializer.serialize(outputStream, writer, new XmlMapper(), product); - writer.writeEndElement(); - writer.close(); - } catch (ClassCastException e) { - this.logger.error( - "For XML serialization, the Product object must be extended as ProductWithXmlLabel: " - + e.getMessage()); - } catch (Exception e) { - this.logger.error("Unexpected for no known reason.", e); - } - } - - static public void serialize(OutputStream stream, XMLStreamWriter writer, XmlMapper mapper, - Pds4Product product) throws IOException, XMLStreamException { - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "id"); - writer.writeCharacters(product.getId()); - writer.writeEndElement(); - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "meta"); - writer.writeCharacters(""); - writer.flush(); - stream.write(mapper.writeValueAsString(product.getMetadata()).replace("", "") - .replace("", "").getBytes("UTF-8")); - stream.flush(); - writer.writeEndElement(); - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "pds4"); - writer.writeCharacters(""); - writer.flush(); - stream.write(String.valueOf(product.getPds4()).getBytes("UTF8")); - stream.flush(); - writer.writeEndElement(); - writer.flush(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductsSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductsSerializer.java deleted file mode 100644 index 1d4d578c..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/Pds4XmlProductsSerializer.java +++ /dev/null @@ -1,89 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; - -import javax.xml.stream.XMLOutputFactory; -import javax.xml.stream.XMLStreamWriter; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.dataformat.xml.XmlMapper; - -import gov.nasa.pds.model.Pds4Product; -import gov.nasa.pds.model.Pds4Products; -import gov.nasa.pds.model.Summary; - -public class Pds4XmlProductsSerializer extends AbstractHttpMessageConverter { - /*** - * OBSOLETE since we don't want to use the label in blob anymore to provide the pds4 original - * label for a list of products - * - */ - - private static final Logger log = LoggerFactory.getLogger(Pds4XmlProductsSerializer.class); - - public Pds4XmlProductsSerializer() { - super(new MediaType("application", "vnd.nasa.pds.pds4+xml")); - } - - @Override - protected boolean supports(Class clazz) { - return Pds4Products.class.isAssignableFrom(clazz); - } - - @Override - protected Pds4Products readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - // dummy method never used - return new Pds4Products(); - } - - @Override - protected void writeInternal(Pds4Products products, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - try { - outputMessage.getHeaders().setContentType(MediaType.TEXT_XML); // must be before body is fetched - OutputStream outputStream = outputMessage.getBody(); - XMLOutputFactory outputFactory = XMLOutputFactory.newFactory(); - outputFactory.setProperty("javax.xml.stream.isRepairingNamespaces", true); - XMLStreamWriter writer = outputFactory.createXMLStreamWriter(outputStream); - Utilities.fix(products.getSummary()); - writer.setPrefix(Pds4XmlProductSerializer.NAMESPACE_PREFIX, - Pds4XmlProductSerializer.NAMESPACE_URL); - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "products"); - writer.writeNamespace(Pds4XmlProductSerializer.NAMESPACE_PREFIX, - Pds4XmlProductSerializer.NAMESPACE_URL); - writer.writeNamespace(Pds4XmlProductSerializer.NAMESPACE_PREFIX_OPS, - Pds4XmlProductSerializer.NAMESPACE_URL_OPS); - Summary summary = products.getSummary(); - XmlMapper xmlMapper = new XmlMapper(); - xmlMapper.writeValue(writer, summary); - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "data"); - for (Pds4Product product : products.getData()) { - writer.writeStartElement(Pds4XmlProductSerializer.NAMESPACE_URL, "product"); - Pds4XmlProductSerializer.serialize(outputStream, writer, new XmlMapper(), product); - writer.writeEndElement(); - } - writer.writeEndElement(); // data - writer.writeEndElement(); // products - writer.close(); - outputStream.close(); - } catch (ClassCastException e) { - this.logger - .error("For XML serialization, Product object must be extended to ProductWithXmlLabel: " - + e.getMessage()); - } catch (Exception e) { - Pds4XmlProductsSerializer.log - .info("error while serializing products in xml " + e.getMessage()); - } - } - -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductTextHtmlSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductTextHtmlSerializer.java deleted file mode 100644 index 038c5c1e..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductTextHtmlSerializer.java +++ /dev/null @@ -1,46 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.nio.charset.Charset; -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.PdsProduct; - -public class PdsProductTextHtmlSerializer extends AbstractHttpMessageConverter { - public PdsProductTextHtmlSerializer() { - super(MediaType.TEXT_HTML); - } - - @Override - protected boolean supports(Class clazz) { - return PdsProduct.class.isAssignableFrom(clazz); - } - - @Override - protected PdsProduct readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new PdsProduct(); - } - - @Override - protected void writeInternal(PdsProduct t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os, Charset.defaultCharset()); - mapper.setSerializationInclusion(Include.NON_NULL); - wr.write(mapper.writerWithDefaultPrettyPrinter().writeValueAsString(t)); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductXMLSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductXMLSerializer.java deleted file mode 100644 index 8d35eceb..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductXMLSerializer.java +++ /dev/null @@ -1,60 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import gov.nasa.pds.model.PdsProduct; - -import java.io.IOException; -import java.io.OutputStream; - -import javax.xml.stream.XMLOutputFactory; -import javax.xml.stream.XMLStreamException; -import javax.xml.stream.XMLStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.ctc.wstx.api.WstxInputProperties; -import com.fasterxml.jackson.dataformat.xml.XmlMapper; - -public class PdsProductXMLSerializer extends AbstractHttpMessageConverter { - static final public String NAMESPACE_PREFIX = "pds_api"; - static final public String NAMESPACE_URL = "http://pds.nasa.gov/api"; - - public PdsProductXMLSerializer() { - super(MediaType.APPLICATION_XML, MediaType.TEXT_XML); - } - - @Override - protected boolean supports(Class clazz) { - return PdsProduct.class.isAssignableFrom(clazz); - } - - @Override - protected PdsProduct readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new PdsProduct(); - } - - @Override - protected void writeInternal(PdsProduct product, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - try { - outputMessage.getHeaders().setContentType(MediaType.TEXT_XML); // must be before body is fetched - OutputStream outputStream = outputMessage.getBody(); - XMLOutputFactory outputFactory = XMLOutputFactory.newFactory(); - outputFactory.setProperty("javax.xml.stream.isRepairingNamespaces", true); - outputFactory.setProperty(WstxInputProperties.P_RETURN_NULL_FOR_DEFAULT_NAMESPACE, true); - XMLStreamWriter writer = outputFactory.createXMLStreamWriter(outputStream); - new XmlMapper().writeValue(writer, product); - } catch (ClassCastException e) { - this.logger.error( - "For XML serialization, the Product object must be extended as ProductWithXmlLabel: " - + e.getMessage()); - } catch (XMLStreamException e) { - this.logger.error("XML serialization problem: " + e.getMessage()); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsTextHtmlSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsTextHtmlSerializer.java deleted file mode 100644 index 72701b01..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsTextHtmlSerializer.java +++ /dev/null @@ -1,48 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.nio.charset.Charset; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.fasterxml.jackson.annotation.JsonInclude.Include; -import com.fasterxml.jackson.databind.ObjectMapper; - -import gov.nasa.pds.model.PdsProducts; - -public class PdsProductsTextHtmlSerializer extends AbstractHttpMessageConverter { - public PdsProductsTextHtmlSerializer() { - super(MediaType.TEXT_HTML); - } - - @Override - protected boolean supports(Class clazz) { - return PdsProducts.class.isAssignableFrom(clazz); - } - - @Override - protected PdsProducts readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new PdsProducts(); - } - - @Override - protected void writeInternal(PdsProducts t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - ObjectMapper mapper = new ObjectMapper(); - outputMessage.getHeaders().setContentType(MediaType.APPLICATION_JSON); // must be before body is fetched - OutputStream os = outputMessage.getBody(); - OutputStreamWriter wr = new OutputStreamWriter(os, Charset.defaultCharset()); - mapper.setSerializationInclusion(Include.NON_NULL); - Utilities.fix(t.getSummary()); - wr.write(mapper.writerWithDefaultPrettyPrinter().writeValueAsString(t)); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsXMLSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsXMLSerializer.java deleted file mode 100644 index 84b4b104..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/PdsProductsXMLSerializer.java +++ /dev/null @@ -1,67 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import gov.nasa.pds.model.PdsProduct; -import gov.nasa.pds.model.PdsProducts; - -import java.io.IOException; -import java.io.OutputStream; - -import javax.xml.stream.XMLOutputFactory; -import javax.xml.stream.XMLStreamException; -import javax.xml.stream.XMLStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import com.ctc.wstx.api.WstxInputProperties; -import com.fasterxml.jackson.dataformat.xml.XmlMapper; - -public class PdsProductsXMLSerializer extends AbstractHttpMessageConverter { - public PdsProductsXMLSerializer() { - super(MediaType.APPLICATION_XML, MediaType.TEXT_XML); - } - - @Override - protected boolean supports(Class clazz) { - return PdsProducts.class.isAssignableFrom(clazz); - } - - @Override - protected PdsProducts readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new PdsProducts(); - } - - @Override - protected void writeInternal(PdsProducts products, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - try { - outputMessage.getHeaders().setContentType(MediaType.TEXT_XML); // must be before body is fetched - OutputStream outputStream = outputMessage.getBody(); - XmlMapper mapper = new XmlMapper(); - XMLOutputFactory outputFactory = XMLOutputFactory.newFactory(); - Utilities.fix(products.getSummary()); - outputFactory.setProperty("javax.xml.stream.isRepairingNamespaces", true); - outputFactory.setProperty(WstxInputProperties.P_RETURN_NULL_FOR_DEFAULT_NAMESPACE, true); - XMLStreamWriter writer = outputFactory.createXMLStreamWriter(outputStream); - writer.setDefaultNamespace(null); - writer.writeStartElement("PdsProducts"); - mapper.writeValue(writer, products.getSummary()); - for (PdsProduct product : products.getData()) - mapper.writeValue(writer, product); - writer.writeEndElement(); - writer.close(); - outputStream.close(); - } catch (ClassCastException e) { - this.logger.error( - "For XML serialization, the Product object must be extended as ProductWithXmlLabel: " - + e.getMessage()); - } catch (XMLStreamException e) { - this.logger.error("XML serialization problem: " + e.getMessage()); - } - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/Utilities.java b/service/src/main/java/gov/nasa/pds/api/registry/view/Utilities.java deleted file mode 100644 index 4a9347cb..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/Utilities.java +++ /dev/null @@ -1,22 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.util.ArrayList; -import java.util.List; - -import gov.nasa.pds.api.registry.exceptions.UnsupportedSearchProperty; -import gov.nasa.pds.api.registry.model.SearchUtil; -import gov.nasa.pds.model.Summary; - -class Utilities { - static void fix(Summary summary) { - List fixed = new ArrayList(summary.getProperties().size()); - for (String prop : summary.getProperties()) { - try { - fixed.add(SearchUtil.openPropertyToJsonProperty(prop)); - } catch (UnsupportedSearchProperty e) { - fixed.add(prop); - } - } - summary.setProperties(fixed); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/WyriwygSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/WyriwygSerializer.java deleted file mode 100644 index 87857b83..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/WyriwygSerializer.java +++ /dev/null @@ -1,101 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.Writer; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashMap; -import java.util.List; -import com.fasterxml.jackson.databind.ObjectMapper; -import gov.nasa.pds.model.WyriwygProduct; -import gov.nasa.pds.model.WyriwygProductKeyValuePair; -import gov.nasa.pds.model.WyriwygProducts; - -final class WyriwygSerializer { - private static void writeHeader(List labels, Writer wr) throws IOException { - int n = 0; - for (String label : labels) { - if (0 < n) - wr.write(","); - wr.write(label); - n++; - } - wr.write("\n"); - } - - private static void writeJSON(WyriwygProduct product, Writer wr, ObjectMapper mapper, - String indent) throws IOException { - int n = 0; - wr.write(indent + "{\n"); - for (WyriwygProductKeyValuePair kvp : product.getKeyValuePairs()) { - if (0 < n) - wr.write(",\n"); - wr.write(indent + " \"" + kvp.getKey() + "\":" + mapper.writeValueAsString(kvp.getValue())); - n++; - } - wr.write(indent + "}"); - } - - private static void writeRow(List labels, WyriwygProduct product, Writer wr, - ObjectMapper om) throws IOException { - HashMap row = new HashMap(); - int n = 0; - - for (WyriwygProductKeyValuePair kvp : product.getKeyValuePairs()) - row.put(kvp.getKey(), kvp.getValue()); - for (String label : labels) { - if (0 < n) - wr.write(","); - if (row.containsKey(label)) - wr.write("\"" + row.get(label) + "\""); - n++; - } - wr.write("\n"); - } - - public static void writeCSV(WyriwygProduct product, Writer wr, ObjectMapper mapper) - throws IOException { - List labels = new ArrayList(); - - for (WyriwygProductKeyValuePair kvp : product.getKeyValuePairs()) - labels.add(kvp.getKey()); - Collections.sort(labels); - WyriwygSerializer.writeHeader(labels, wr); - WyriwygSerializer.writeRow(labels, product, wr, mapper); - wr.close(); - } - - public static void writeCSV(WyriwygProducts products, Writer wr, ObjectMapper mapper) - throws IOException { - Collections.sort(products.getSummary().getProperties()); - WyriwygSerializer.writeHeader(products.getSummary().getProperties(), wr); - for (WyriwygProduct product : products.getData()) - WyriwygSerializer.writeRow(products.getSummary().getProperties(), product, wr, mapper); - wr.close(); - } - - public static void writeJSON(WyriwygProduct product, Writer wr, ObjectMapper mapper) - throws IOException { - WyriwygSerializer.writeJSON(product, wr, mapper, ""); - wr.write("\n"); - wr.close(); - } - - public static void writeJSON(WyriwygProducts products, Writer wr, ObjectMapper mapper) - throws IOException { - int n = 0; - // Summary - wr.write("{\n \"summary\":" + mapper.writeValueAsString(products.getSummary()) + ",\n"); - - // Data - wr.write(" \"data\":["); - for (WyriwygProduct product : products.getData()) { - if (0 < n) - wr.write(",\n"); - WyriwygSerializer.writeJSON(product, wr, mapper, " "); - n++; - } - wr.write("\n ]\n}\n"); - wr.close(); - } -} diff --git a/service/src/main/java/gov/nasa/pds/api/registry/view/XmlErrorMessageSerializer.java b/service/src/main/java/gov/nasa/pds/api/registry/view/XmlErrorMessageSerializer.java deleted file mode 100644 index 5c2dec56..00000000 --- a/service/src/main/java/gov/nasa/pds/api/registry/view/XmlErrorMessageSerializer.java +++ /dev/null @@ -1,47 +0,0 @@ -package gov.nasa.pds.api.registry.view; - -import java.io.IOException; -import java.io.OutputStreamWriter; - -import org.springframework.http.HttpInputMessage; -import org.springframework.http.HttpOutputMessage; -import org.springframework.http.MediaType; -import org.springframework.http.converter.AbstractHttpMessageConverter; -import org.springframework.http.converter.HttpMessageNotReadableException; -import org.springframework.http.converter.HttpMessageNotWritableException; - -import gov.nasa.pds.model.ErrorMessage; - -public class XmlErrorMessageSerializer extends AbstractHttpMessageConverter { - public XmlErrorMessageSerializer() { - super(MediaType.APPLICATION_XML, MediaType.TEXT_XML, - new MediaType("application", "vnd.nasa.pds.pds4+xml")); - } - - @Override - protected boolean supports(Class clazz) { - return ErrorMessage.class.isAssignableFrom(clazz); - } - - @Override - protected ErrorMessage readInternal(Class clazz, - HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException { - return new ErrorMessage(); - } - - @Override - protected void writeInternal(ErrorMessage t, HttpOutputMessage outputMessage) - throws IOException, HttpMessageNotWritableException { - outputMessage.getHeaders().setContentType(MediaType.TEXT_XML); // must be before body is fetched - OutputStreamWriter osw = new OutputStreamWriter(outputMessage.getBody(), "UTF-8"); - try { - osw.write(""); - osw.write(t.getRequest()); - osw.write(""); - osw.write(t.getMessage()); - osw.write(""); - } finally { - osw.close(); - } - } -}