Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
com.emc.ia.sdk.configurer.PropertyBasedConfigurer Maven / Gradle / Ivy
Go to download
A library that makes it quick and easy to create SIPs in InfoArchive
/*
* Copyright (c) 2016 EMC Corporation. All Rights Reserved.
*/
package com.emc.ia.sdk.configurer;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
import com.emc.ia.sdk.sip.client.dto.Aic;
import com.emc.ia.sdk.sip.client.dto.Aics;
import com.emc.ia.sdk.sip.client.dto.Application;
import com.emc.ia.sdk.sip.client.dto.Applications;
import com.emc.ia.sdk.sip.client.dto.Contents;
import com.emc.ia.sdk.sip.client.dto.Criterion;
import com.emc.ia.sdk.sip.client.dto.Database;
import com.emc.ia.sdk.sip.client.dto.Databases;
import com.emc.ia.sdk.sip.client.dto.Federation;
import com.emc.ia.sdk.sip.client.dto.Federations;
import com.emc.ia.sdk.sip.client.dto.FileSystemFolder;
import com.emc.ia.sdk.sip.client.dto.FileSystemFolders;
import com.emc.ia.sdk.sip.client.dto.FileSystemRoots;
import com.emc.ia.sdk.sip.client.dto.Holding;
import com.emc.ia.sdk.sip.client.dto.Holdings;
import com.emc.ia.sdk.sip.client.dto.Ingest;
import com.emc.ia.sdk.sip.client.dto.IngestConfig;
import com.emc.ia.sdk.sip.client.dto.IngestNode;
import com.emc.ia.sdk.sip.client.dto.IngestNodes;
import com.emc.ia.sdk.sip.client.dto.Ingests;
import com.emc.ia.sdk.sip.client.dto.Libraries;
import com.emc.ia.sdk.sip.client.dto.Library;
import com.emc.ia.sdk.sip.client.dto.Namespace;
import com.emc.ia.sdk.sip.client.dto.Operand;
import com.emc.ia.sdk.sip.client.dto.Pdi;
import com.emc.ia.sdk.sip.client.dto.PdiConfig;
import com.emc.ia.sdk.sip.client.dto.PdiSchema;
import com.emc.ia.sdk.sip.client.dto.PdiSchemas;
import com.emc.ia.sdk.sip.client.dto.Pdis;
import com.emc.ia.sdk.sip.client.dto.Queries;
import com.emc.ia.sdk.sip.client.dto.Query;
import com.emc.ia.sdk.sip.client.dto.Quota;
import com.emc.ia.sdk.sip.client.dto.Quotas;
import com.emc.ia.sdk.sip.client.dto.ReceiverNode;
import com.emc.ia.sdk.sip.client.dto.ReceiverNodes;
import com.emc.ia.sdk.sip.client.dto.ResultConfigurationHelper;
import com.emc.ia.sdk.sip.client.dto.ResultConfigurationHelpers;
import com.emc.ia.sdk.sip.client.dto.RetentionClass;
import com.emc.ia.sdk.sip.client.dto.RetentionPolicies;
import com.emc.ia.sdk.sip.client.dto.RetentionPolicy;
import com.emc.ia.sdk.sip.client.dto.Search;
import com.emc.ia.sdk.sip.client.dto.SearchComposition;
import com.emc.ia.sdk.sip.client.dto.SearchCompositions;
import com.emc.ia.sdk.sip.client.dto.Searches;
import com.emc.ia.sdk.sip.client.dto.Services;
import com.emc.ia.sdk.sip.client.dto.Sip;
import com.emc.ia.sdk.sip.client.dto.Space;
import com.emc.ia.sdk.sip.client.dto.SpaceRootFolder;
import com.emc.ia.sdk.sip.client.dto.SpaceRootFolders;
import com.emc.ia.sdk.sip.client.dto.SpaceRootLibraries;
import com.emc.ia.sdk.sip.client.dto.SpaceRootLibrary;
import com.emc.ia.sdk.sip.client.dto.Spaces;
import com.emc.ia.sdk.sip.client.dto.Store;
import com.emc.ia.sdk.sip.client.dto.Stores;
import com.emc.ia.sdk.sip.client.dto.SubPriority;
import com.emc.ia.sdk.sip.client.dto.Tenant;
import com.emc.ia.sdk.sip.client.dto.XForm;
import com.emc.ia.sdk.sip.client.dto.XdbPdiConfig;
import com.emc.ia.sdk.sip.client.dto.export.ExportConfiguration;
import com.emc.ia.sdk.sip.client.dto.export.ExportConfigurations;
import com.emc.ia.sdk.sip.client.dto.export.ExportPipeline;
import com.emc.ia.sdk.sip.client.dto.export.ExportPipelines;
import com.emc.ia.sdk.sip.client.dto.export.ExportTransformation;
import com.emc.ia.sdk.sip.client.dto.export.ExportTransformations;
import com.emc.ia.sdk.sip.client.dto.result.Column;
import com.emc.ia.sdk.sip.client.dto.result.Column.DataType;
import com.emc.ia.sdk.sip.client.dto.result.Column.DefaultSort;
import com.emc.ia.sdk.sip.client.dto.result.ResultMaster;
import com.emc.ia.sdk.sip.client.dto.result.searchconfig.AllSearchComponents;
import com.emc.ia.sdk.sip.client.rest.InfoArchiveLinkRelations;
import com.emc.ia.sdk.sip.client.rest.RestCache;
import com.emc.ia.sdk.support.NewInstance;
import com.emc.ia.sdk.support.RepeatingConfigReader;
import com.emc.ia.sdk.support.datetime.Clock;
import com.emc.ia.sdk.support.datetime.DefaultClock;
import com.emc.ia.sdk.support.http.BinaryPart;
import com.emc.ia.sdk.support.http.HttpClient;
import com.emc.ia.sdk.support.http.HttpException;
import com.emc.ia.sdk.support.http.MediaTypes;
import com.emc.ia.sdk.support.http.TextPart;
import com.emc.ia.sdk.support.http.apache.ApacheHttpClient;
import com.emc.ia.sdk.support.io.RuntimeIoException;
import com.emc.ia.sdk.support.rest.AuthenticationStrategy;
import com.emc.ia.sdk.support.rest.LinkContainer;
import com.emc.ia.sdk.support.rest.RestClient;
@SuppressWarnings("PMD.ExcessiveClassLength")
public class PropertyBasedConfigurer implements InfoArchiveConfigurer, InfoArchiveLinkRelations,
InfoArchiveConfiguration {
private static final String TYPE_EXPORT_PIPELINE = "export-pipeline";
private static final String TYPE_EXPORT_TRANSFORMATION = "export-transformation";
private static final int MAX_RETRIES = 5;
private static final int RETRY_MS = 500;
private static final int WAIT_RACE_CONDITION_MS = 2000;
private static final String FORMAT_XML = "xml";
private static final String FORMAT_XSD = "xsd";
private static final String WORKING_FOLDER_NAME = "working/";
private static final String RECEIVER_NODE_NAME = "receiver_node_01";
private static final String INGEST_NAME = "ingest";
private static final String INGEST_NODE_NAME = "ingest_node_01";
private static final String DEFAULT_STORE_NAME = "filestore_01";
private static final String DEFAULT_RESULT_HELPER_NAME = "result_helper";
private final RestCache configurationState = new RestCache();
private Map configuration;
private RestClient restClient;
private final Clock clock;
public PropertyBasedConfigurer(Map configuration) {
this(null, configuration);
}
public PropertyBasedConfigurer(RestClient restClient, Map configuration) {
this(restClient, new DefaultClock(), configuration);
}
public PropertyBasedConfigurer(RestClient restClient, Clock clock, Map configuration) {
this.restClient = restClient;
this.clock = clock;
this.configuration = configuration;
}
@Override
public void configure() {
try {
initRestClient();
ensureTenant();
ensureFederation();
ensureDatabase();
ensureFileSystemRoot();
ensureTenantLevelExportPipelines();
ensureTenantLevelExportTransformations();
ensureTenantLevelExportConfigurations();
ensureApplication();
ensureSpace();
ensureSpaceRootLibrary();
ensureSpaceRootFolder();
ensureFileSystemFolder();
ensureStore();
ensureReceptionFolder();
ensureIngestionFolder();
ensureReceiverNode();
ensureIngestNode();
ensureRetentionPolicy();
ensurePdi();
ensurePdiSchema();
ensureIngest();
ensureLibrary();
ensureHolding();
ensureAic();
ensureQuota();
ensureQuery();
ensureResultConfigurationHelper();
ensureExportPipelines();
ensureExportTransformations();
ensureExportConfigurations();
ensureSearch();
} catch (IOException e) {
throw new RuntimeIoException(e);
}
}
protected RestCache getConfigurationState() {
return configurationState;
}
protected Map setConfiguration(Map config) {
return configuration = config;
}
private void initRestClient() throws IOException {
if (restClient == null) {
HttpClient httpClient =
NewInstance.fromConfiguration(configuration, HTTP_CLIENT_CLASSNAME, ApacheHttpClient.class.getName())
.as(HttpClient.class);
AuthenticationStrategy authentication = new AuthenticationStrategyFactory(configuration)
.getAuthenticationStrategy(() -> httpClient, () -> clock);
restClient = new RestClient(httpClient);
restClient.init(authentication);
}
configurationState.setServices(restClient.get(configured(SERVER_URI), Services.class));
}
public String configured(String name) {
String result = configuration.get(name);
Objects.requireNonNull(result, "Missing " + name);
return result;
}
private void ensureTenant() throws IOException {
configurationState.setTenant(restClient.follow(configurationState.getServices(), LINK_TENANT, Tenant.class));
}
private void ensureFederation() throws IOException {
String name = configuration.get(FEDERATION_NAME);
Federations federations = restClient.follow(configurationState.getServices(), LINK_FEDERATIONS, Federations.class);
configurationState.setFederation(federations.byName(name));
if (configurationState.getFederation() == null) {
createItem(federations, createFederation(name));
configurationState.setFederation(restClient.refresh(federations)
.byName(name));
Objects.requireNonNull(configurationState.getFederation(), "Could not create federation");
}
}
private Federation createFederation(String name) {
Federation result = new Federation();
result.setName(name);
result.setSuperUserPassword(configuration.get(FEDERATION_SUPERUSER_PASSWORD));
result.setBootstrap(configuration.get(FEDERATION_BOOTSTRAP));
return result;
}
private T createItem(LinkContainer collection, T item) throws IOException {
return createItem(collection, item, LINK_ADD, LINK_SELF);
}
public T createItem(LinkContainer collection, T item, String... linkRelations) throws IOException {
return perform(() -> restClient.createCollectionItem(collection, item, linkRelations));
}
private T perform(Operation operation) throws IOException {
int retry = 0;
while (retry < MAX_RETRIES) {
retry++;
try {
return operation.perform();
} catch (IOException e) {
if (isTemporarilyUnavailable(e)) {
clock.sleep(RETRY_MS * retry, TimeUnit.MILLISECONDS);
} else if (isDuplicateObjectException(e.getMessage())) {
clock.sleep(WAIT_RACE_CONDITION_MS, TimeUnit.MILLISECONDS);
break;
} else {
throw e;
}
}
}
return null;
}
private boolean isTemporarilyUnavailable(IOException exception) {
if (exception instanceof HttpException) {
HttpException httpException = (HttpException)exception;
return httpException.getStatusCode() == 503;
}
return false;
}
private boolean isDuplicateObjectException(String error) {
return error.contains("DUPLICATE_KEY") || error.contains("NAME_ALREADY_EXISTS");
}
private void ensureDatabase() throws IOException {
String name = configuration.get(DATABASE_NAME);
Databases databases = restClient.follow(configurationState.getFederation(), LINK_DATABASES, Databases.class);
Database database = databases.byName(name);
if (database == null) {
createItem(databases, createDatabase(name));
database = restClient.refresh(databases)
.byName(name);
Objects.requireNonNull(database, "Could not create database");
}
configurationState.setDatabaseUri(database.getSelfUri());
}
private Database createDatabase(String name) {
Database result = new Database();
result.setName(name);
result.setAdminPassword(configured(DATABASE_ADMIN_PASSWORD));
return result;
}
private void ensureFileSystemRoot() throws IOException {
FileSystemRoots fileSystemRoots =
restClient.follow(configurationState.getServices(), LINK_FILE_SYSTEM_ROOTS, FileSystemRoots.class);
configurationState.setFileSystemRootUri(fileSystemRoots.first()
.getSelfUri());
}
protected void ensureApplication() throws IOException {
String applicationName = configuration.get(APPLICATION_NAME);
Applications applications =
restClient.follow(configurationState.getTenant(), LINK_APPLICATIONS, Applications.class);
configurationState.setApplication(applications.byName(applicationName));
if (configurationState.getApplication() == null) {
createItem(applications, createApplication(applicationName));
configurationState.setApplication(restClient.refresh(applications)
.byName(applicationName));
Objects.requireNonNull(configurationState.getApplication(), "Could not create application");
}
}
private Application createApplication(String applicationName) {
Application result = new Application();
result.setName(applicationName);
return result;
}
private void ensureSpace() throws IOException {
String spaceName = configurationState.getApplication()
.getName();
Spaces spaces = restClient.follow(configurationState.getApplication(), LINK_SPACES, Spaces.class);
configurationState.setSpace(spaces.byName(spaceName));
if (configurationState.getSpace() == null) {
createItem(spaces, createSpace(spaceName));
configurationState.setSpace(restClient.refresh(spaces)
.byName(spaceName));
Objects.requireNonNull(configurationState.getSpace(), "Could not create space");
}
}
private Space createSpace(String name) {
Space result = new Space();
result.setName(name);
return result;
}
private void ensureSpaceRootLibrary() throws IOException {
String name = configured(HOLDING_NAME);
SpaceRootLibraries spaceRootLibraries =
restClient.follow(configurationState.getSpace(), LINK_SPACE_ROOT_LIBRARIES, SpaceRootLibraries.class);
configurationState.setSpaceRootLibrary(spaceRootLibraries.byName(name));
if (configurationState.getSpaceRootLibrary() == null) {
createItem(spaceRootLibraries, createSpaceRootLibrary(name));
configurationState.setSpaceRootLibrary(restClient.refresh(spaceRootLibraries)
.byName(name));
Objects.requireNonNull(configurationState.getSpaceRootLibrary(), "Could not create space root library");
}
}
private SpaceRootLibrary createSpaceRootLibrary(String name) {
SpaceRootLibrary result = new SpaceRootLibrary();
result.setName(name);
result.setXdbDatabase(configurationState.getDatabaseUri());
return result;
}
private void ensureSpaceRootFolder() throws IOException {
String name = configurationState.getSpace()
.getName();
SpaceRootFolders spaceRootFolders =
restClient.follow(configurationState.getSpace(), LINK_SPACE_ROOT_FOLDERS, SpaceRootFolders.class);
configurationState.setSpaceRootFolder(spaceRootFolders.byName(name));
if (configurationState.getSpaceRootFolder() == null) {
createItem(spaceRootFolders, createSpaceRootFolder(name));
configurationState.setSpaceRootFolder(restClient.refresh(spaceRootFolders)
.byName(name));
Objects.requireNonNull(configurationState.getSpaceRootFolder(), "Could not create space root folder");
}
}
private SpaceRootFolder createSpaceRootFolder(String name) {
SpaceRootFolder result = new SpaceRootFolder();
result.setName(name);
result.setFileSystemRoot(configurationState.getFileSystemRootUri());
return result;
}
private void ensureFileSystemFolder() throws IOException {
// Create the default file system folder.
FileSystemFolder defaultFolder = ensureFileSystemFolder(configured(HOLDING_NAME));
configurationState.setFileSystemFolderUri(defaultFolder.getSelfUri());
// Any extra folders
String rawFolderNames = configuration.get(FILE_SYSTEM_FOLDER);
if (rawFolderNames != null && !rawFolderNames.isEmpty()) {
String[] folderNames = rawFolderNames.split(",");
for (String folderName : folderNames) {
ensureFileSystemFolder(folderName.trim());
}
}
}
private FileSystemFolder ensureFileSystemFolder(String name) throws IOException {
FileSystemFolders fileSystemFolders =
restClient.follow(configurationState.getSpaceRootFolder(), LINK_FILE_SYSTEM_FOLDERS, FileSystemFolders.class);
FileSystemFolder fileSystemFolder = fileSystemFolders.byName(name);
if (fileSystemFolder == null) {
createItem(fileSystemFolders, createFileSystemFolder(name));
fileSystemFolder = restClient.refresh(fileSystemFolders)
.byName(name);
Objects.requireNonNull(fileSystemFolder, "Could not create file system folder " + name);
}
configurationState.setObjectUri("filesystemfolder", name, fileSystemFolder.getSelfUri());
return fileSystemFolder;
}
private FileSystemFolder createFileSystemFolder(String name) {
FileSystemFolder result = new FileSystemFolder();
result.setName(name);
result.setParentSpaceRootFolder(configurationState.getSpaceRootFolder()
.getSelfUri());
result.setSubPath("stores/" + DEFAULT_STORE_NAME);
return result;
}
private void ensureStore() throws IOException {
Store defaultStore = ensureStore(DEFAULT_STORE_NAME, null, configurationState.getFileSystemFolderUri());
configurationState.setStoreUri(defaultStore.getSelfUri());
RepeatingConfigReader reader =
new RepeatingConfigReader("stores", Arrays.asList(STORE_NAME, STORE_FOLDER, STORE_STORETYPE));
List> storeConfigurations = reader.read(configuration);
for (Map cfg : storeConfigurations) {
ensureStore(cfg.get(STORE_NAME), cfg.get(STORE_STORETYPE),
configurationState.getObjectUri("filesystemfolder", cfg.get(STORE_FOLDER)));
}
}
private Store ensureStore(String name, String storeType, String fileSystemFolderUri) throws IOException {
Stores stores = restClient.follow(configurationState.getApplication(), LINK_STORES, Stores.class);
Store store = stores.byName(name);
if (store == null) {
createItem(stores, createStore(name, storeType, fileSystemFolderUri));
store = restClient.refresh(stores)
.byName(name);
Objects.requireNonNull(store, "Could not create store");
}
configurationState.setObjectUri("store", name, store.getSelfUri());
return store;
}
private Store createStore(String storeName, String storeType, String fileSystemFolderUri) {
Store store = new Store();
store.setName(storeName);
if (storeType != null && !storeType.isEmpty()) {
store.setStoreType(storeType);
}
store.setFileSystemFolder(fileSystemFolderUri);
return store;
}
private void ensureReceptionFolder() throws IOException {
String name = "reception-folder";
FileSystemFolders receptionFolders =
restClient.follow(configurationState.getSpaceRootFolder(), LINK_FILE_SYSTEM_FOLDERS, FileSystemFolders.class);
FileSystemFolder receptionFolder = receptionFolders.byName(name);
if (receptionFolder == null) {
createItem(receptionFolders, createReceptionFolder(name));
receptionFolder = restClient.refresh(receptionFolders)
.byName(name);
Objects.requireNonNull(receptionFolder, "Could not create reception folder");
}
configurationState.setReceptionFolderUri(receptionFolder.getSelfUri());
}
private FileSystemFolder createReceptionFolder(String name) {
FileSystemFolder result = new FileSystemFolder();
result.setName(name);
result.setParentSpaceRootFolder(configurationState.getSpaceRootFolder()
.getSelfUri());
result.setSubPath(WORKING_FOLDER_NAME + RECEIVER_NODE_NAME);
return result;
}
private void ensureIngestionFolder() throws IOException {
String name = "ingestion-folder";
FileSystemFolders fileSystemFolders =
restClient.follow(configurationState.getSpaceRootFolder(), LINK_FILE_SYSTEM_FOLDERS, FileSystemFolders.class);
FileSystemFolder fileSystemFolder = fileSystemFolders.byName(name);
if (fileSystemFolder == null) {
createItem(fileSystemFolders, createIngestionFolder(name));
fileSystemFolder = restClient.refresh(fileSystemFolders)
.byName(name);
Objects.requireNonNull(fileSystemFolder, "Could not create ingestion folder");
}
}
private FileSystemFolder createIngestionFolder(String name) {
FileSystemFolder result = new FileSystemFolder();
result.setName(name);
result.setParentSpaceRootFolder(configurationState.getSpaceRootFolder()
.getSelfUri());
result.setSubPath(WORKING_FOLDER_NAME + INGEST_NODE_NAME);
return result;
}
private void ensureReceiverNode() throws IOException {
String name = RECEIVER_NODE_NAME;
ReceiverNodes receiverNodes =
restClient.follow(configurationState.getApplication(), LINK_RECEIVER_NODES, ReceiverNodes.class);
ReceiverNode receiverNode = receiverNodes.byName(name);
if (receiverNode == null) {
createItem(receiverNodes, createReceiverNode(name));
receiverNode = restClient.refresh(receiverNodes)
.byName(name);
Objects.requireNonNull(receiverNode, "Could not create receiver node");
}
}
private ReceiverNode createReceiverNode(String name) {
ReceiverNode result = new ReceiverNode();
result.setName(name);
result.setWorkingDirectory(configurationState.getReceptionFolderUri());
result.setLogsStore(configurationState.getStoreUri());
result.getSips()
.add(new Sip());
return result;
}
private void ensureTenantLevelExportPipelines() throws IOException {
String defaultPipelineName = "search-results-csv-gzip";
ExportPipelines pipelines =
restClient.follow(configurationState.getTenant(), LINK_EXPORT_PIPELINE, ExportPipelines.class);
ExportPipeline pipeline = pipelines.byName(defaultPipelineName);
if (pipeline == null) {
pipeline = new ExportPipeline();
pipeline.setName(defaultPipelineName);
pipeline.setDescription("gzip envelope for csv export");
pipeline.setIncludesContent(false);
pipeline.setInputFormat("ROW_COLUMN");
pipeline.setOutputFormat("csv");
pipeline.setEnvelopeFormat("gz");
pipeline.setType("XPROC");
pipeline.setComposite(true);
pipeline.setCollectionBasedExport(false);
pipeline.setContent(
"\n \n \n \n \n ");
createItem(pipelines, pipeline);
pipeline = restClient.refresh(pipelines)
.byName(defaultPipelineName);
Objects.requireNonNull(pipeline, "Could not create export pipeline");
}
configurationState.setObjectUri(TYPE_EXPORT_PIPELINE, defaultPipelineName, pipeline.getSelfUri());
}
private void ensureTenantLevelExportConfigurations() throws IOException {
String defaultName = "gzip_csv";
ExportConfigurations configurations =
restClient.follow(configurationState.getTenant(), LINK_EXPORT_CONFIG, ExportConfigurations.class);
ExportConfiguration exportConfiguration = configurations.byName(defaultName);
if (exportConfiguration == null) {
exportConfiguration = new ExportConfiguration();
exportConfiguration.setName(defaultName);
exportConfiguration.setDescription("configurations");
exportConfiguration.setExportType("ASYNCHRONOUS");
exportConfiguration.setPipeline(configurationState.getObjectUri(TYPE_EXPORT_PIPELINE, "search-results-csv-gzip"));
ExportConfiguration.Transformation transformation = new ExportConfiguration.Transformation();
transformation.setPortName("stylesheet");
transformation.setTransformation(
configurationState.getObjectUri(TYPE_EXPORT_TRANSFORMATION, "csv_xsl"));
exportConfiguration.addTransformation(transformation);
exportConfiguration.addOption(ExportConfiguration.DefaultOptions.XSL_RESULT_FORMAT, "csv");
createItem(configurations, exportConfiguration);
exportConfiguration = restClient.refresh(configurations)
.byName(defaultName);
Objects.requireNonNull(exportConfiguration, "Could not create export configuration");
}
configurationState.setObjectUri("export-configuration", defaultName, exportConfiguration.getSelfUri());
}
private void ensureTenantLevelExportTransformations() throws IOException {
String defaultName = "csv_xsl";
ExportTransformations transformations =
restClient.follow(configurationState.getTenant(), LINK_EXPORT_TRANSFORMATION, ExportTransformations.class);
ExportTransformation exportTransformation = transformations.byName(defaultName);
if (exportTransformation == null) {
exportTransformation = new ExportTransformation();
exportTransformation.setName(defaultName);
exportTransformation.setDescription("csv xsl transformation");
exportTransformation.setType("XSLT");
exportTransformation.setMainPath("search-results-csv.xsl");
createItem(transformations, exportTransformation);
exportTransformation = restClient.refresh(transformations)
.byName(defaultName);
Objects.requireNonNull(exportTransformation, "Could not create export transformation");
}
configurationState.setObjectUri(TYPE_EXPORT_TRANSFORMATION, defaultName, exportTransformation.getSelfUri());
}
private void ensureExportPipelines() throws IOException {
String rawPipelineNames = configuration.get(EXPORT_PIPELINE_NAME);
if (rawPipelineNames != null && !rawPipelineNames.isEmpty()) {
String[] pipelineNames = rawPipelineNames.split(",");
ExportPipelines pipelines =
restClient.follow(configurationState.getApplication(), LINK_EXPORT_PIPELINE, ExportPipelines.class);
for (String pipelineName : pipelineNames) {
ExportPipeline pipeline = pipelines.byName(pipelineName);
if (pipeline == null) {
createItem(pipelines, createExportPipeline(pipelineName));
pipeline = restClient.refresh(pipelines)
.byName(pipelineName);
Objects.requireNonNull(pipeline, "Could not create export pipeline");
}
configurationState.setObjectUri(TYPE_EXPORT_PIPELINE, pipelineName, pipeline.getSelfUri());
}
}
}
private void ensureExportConfigurations() throws IOException {
String rawConfigurationNames = configuration.get(EXPORT_CONFIG_NAME);
if (rawConfigurationNames != null && !rawConfigurationNames.isEmpty()) {
String[] configurationNames = rawConfigurationNames.split(",");
ExportConfigurations configurations =
restClient.follow(configurationState.getApplication(), LINK_EXPORT_CONFIG, ExportConfigurations.class);
for (String configurationName : configurationNames) {
ExportConfiguration exportConfiguration = configurations.byName(configurationName);
if (exportConfiguration == null) {
createItem(configurations, createExportConfiguration(configurationName));
exportConfiguration = restClient.refresh(configurations)
.byName(configurationName);
Objects.requireNonNull(configuration, "Could not create export configuration");
}
configurationState.setObjectUri("export-configuration", configurationName, exportConfiguration.getSelfUri());
}
}
}
private void ensureExportTransformations() throws IOException {
String rawTransformationNames = configuration.get(EXPORT_TRANSFORMATION_NAME);
if (rawTransformationNames != null && !rawTransformationNames.isEmpty()) {
String[] transformationNames = rawTransformationNames.split(",");
ExportTransformations transformations =
restClient.follow(configurationState.getApplication(), LINK_EXPORT_TRANSFORMATION, ExportTransformations.class);
for (String transformationName : transformationNames) {
ExportTransformation exportTransformation = transformations.byName(transformationName);
if (exportTransformation == null) {
createItem(transformations, createExportTransformation(transformationName));
exportTransformation = restClient.refresh(transformations)
.byName(transformationName);
Objects.requireNonNull(configuration, "Could not create export transformation");
}
configurationState.setObjectUri(TYPE_EXPORT_TRANSFORMATION, transformationName, exportTransformation.getSelfUri());
}
}
}
private ExportConfiguration createExportConfiguration(String name) {
ExportConfiguration conf = new ExportConfiguration();
conf.setName(name);
conf.setExportType(getString(EXPORT_CONFIG_TYPE_TEMPLATE, name));
conf.setPipeline(configurationState.getObjectUri(TYPE_EXPORT_PIPELINE,
getString(EXPORT_CONFIG_PIPELINE_TEMPLATE, name)));
fillExportConfigurationTransformations(name, conf);
fillExportConfigurationOptions(name, conf);
fillExportConfigurationEncryptedOptions(name, conf);
return conf;
}
private void fillExportConfigurationTransformations(String name, ExportConfiguration conf) {
String rawConfigTransformationNames = configuration.get(resolveTemplatedKey(EXPORT_CONFIG_TRANSFORMATIONS_TEMPLATE_NAME, name));
if (rawConfigTransformationNames != null && !rawConfigTransformationNames.isEmpty()) {
String[] configTransformationNames = rawConfigTransformationNames.split(",");
for (String configTransformationName : configTransformationNames) {
ExportConfiguration.Transformation transformation = new ExportConfiguration.Transformation();
transformation.setPortName(configuration.get(
resolveTemplatedKey(EXPORT_CONFIG_TRANSFORMATIONS_TEMPLATE_PORTNAME_TEMPLATE, name, configTransformationName)));
transformation.setTransformation(configurationState.getObjectUri(TYPE_EXPORT_TRANSFORMATION,
configuration.get(resolveTemplatedKey(
EXPORT_CONFIG_TRANSFORMATIONS_TEMPLATE_TRANSFORMATION_TEMPLATE, name, configTransformationName))));
conf.addTransformation(transformation);
}
}
}
private void fillExportConfigurationOptions(String name, ExportConfiguration conf) {
conf.addOption(ExportConfiguration.DefaultOptions.XSL_RESULT_FORMAT,
getString(EXPORT_CONFIG_OPTIONS_TEMPLATE_XSL_RESULTFORMAT_TEMPLATE, name));
conf.addOption(ExportConfiguration.DefaultOptions.XQUERY_RESULT_FORMAT,
getString(EXPORT_CONFIG_OPTIONS_TEMPLATE_XQUERY_RESULTFORMAT_TEMPLATE, name));
String rawConfigOptionNames = configuration.get(resolveTemplatedKey(EXPORT_CONFIG_OPTIONS_TEMPLATE_NAME, name));
if (rawConfigOptionNames != null && !rawConfigOptionNames.isEmpty()) {
String[] configOptionNames = rawConfigOptionNames.split(",");
for (String configOptionName : configOptionNames) {
conf.addOption(configOptionName,
configuration.get(resolveTemplatedKey(EXPORT_CONFIG_OPTIONS_TEMPLATE_VALUE_TEMPLATE, name, configOptionName)));
}
}
}
private void fillExportConfigurationEncryptedOptions(String name, ExportConfiguration conf) {
String rawConfigEncryptedOptionNames = configuration.get(resolveTemplatedKey(EXPORT_CONFIG_ENCRYPTED_OPTIONS_TEMPLATE_NAME, name));
if (rawConfigEncryptedOptionNames != null && !rawConfigEncryptedOptionNames.isEmpty()) {
String[] configEncryptedOptionNames = rawConfigEncryptedOptionNames.split(",");
for (String configEncryptedOptionName : configEncryptedOptionNames) {
conf.addEncryptedOption(configEncryptedOptionName,
configuration.get(resolveTemplatedKey(
EXPORT_CONFIG_ENCRYPTED_OPTIONS_TEMPLATE_VALUE_TEMPLATE, name, configEncryptedOptionName)));
}
}
}
private ExportPipeline createExportPipeline(String name) {
ExportPipeline pipeline = new ExportPipeline();
pipeline.setName(name);
pipeline.setComposite(getBoolean(EXPORT_PIPELINE_COMPOSITE_TEMPLATE, name));
pipeline.setContent(getString(EXPORT_PIPELINE_CONTENT_TEMPLATE, name));
pipeline.setDescription(getString(EXPORT_PIPELINE_DESCRIPTION_TEMPLATE, name));
pipeline.setEnvelopeFormat(getString(EXPORT_PIPELINE_ENVELOPE_FORMAT_TEMPLATE, name));
pipeline.setIncludesContent(getBoolean(EXPORT_PIPELINE_INCLUDES_CONTENT_TEMPLATE, name));
pipeline.setInputFormat(getString(EXPORT_PIPELINE_INPUT_FORMAT_TEMPLATE, name));
pipeline.setOutputFormat(getString(EXPORT_PIPELINE_OUTPUT_FORMAT_TEMPLATE, name));
pipeline.setType(getString(EXPORT_PIPELINE_TYPE_TEMPLATE, name));
pipeline.setCollectionBasedExport(getBoolean(EXPORT_PIPELINE_COLLECTION_BASED_TEMPLATE, name));
return pipeline;
}
private ExportTransformation createExportTransformation(String name) {
ExportTransformation transformation = new ExportTransformation();
transformation.setName(name);
transformation.setDescription(getString(EXPORT_TRANSFORMATION_DESCRIPTION_TEMPLATE, name));
transformation.setType(getString(EXPORT_TRANSFORMATION_TYPE_TEMPLATE, name));
transformation.setMainPath(getString(EXPORT_TRANSFORMATION_MAIN_PATH_TEMPLATE, name));
return transformation;
}
private boolean getBoolean(String key, String name) {
return Boolean.parseBoolean(getString(key, name));
}
private String getString(String key, String name) {
return configuration.get(resolveTemplatedKey(key, name));
}
private void ensureIngestNode() throws IOException {
String name = INGEST_NODE_NAME;
IngestNodes ingestNodes =
restClient.follow(configurationState.getApplication(), LINK_INGEST_NODES, IngestNodes.class);
IngestNode ingestNode = ingestNodes.byName(name);
if (ingestNode == null) {
createItem(ingestNodes, createIngestionNode(name));
ingestNode = restClient.refresh(ingestNodes)
.byName(name);
Objects.requireNonNull(ingestNode, "Could not create ingest node");
}
configurationState.setIngestNodeUri(ingestNode.getSelfUri());
}
private IngestNode createIngestionNode(String name) {
IngestNode result = new IngestNode();
result.setName(name);
result.setWorkingDirectory(configurationState.getFileSystemFolderUri());
return result;
}
private void ensureRetentionPolicy() throws IOException {
String name = configured(RETENTION_POLICY_NAME);
RetentionPolicies retentionPolicies =
restClient.follow(configurationState.getTenant(), LINK_RETENTION_POLICIES, RetentionPolicies.class);
RetentionPolicy retentionPolicy = retentionPolicies.byName(name);
if (retentionPolicy == null) {
createItem(retentionPolicies, createRetentionPolicy(name));
retentionPolicy = restClient.refresh(retentionPolicies)
.byName(name);
Objects.requireNonNull(retentionPolicy, "Could not create retention policy");
}
}
private RetentionPolicy createRetentionPolicy(String name) {
RetentionPolicy result = new RetentionPolicy();
result.setName(name);
return result;
}
private void ensurePdi() throws IOException {
String name = configured(RETENTION_POLICY_NAME);
Pdis pdis = restClient.follow(configurationState.getApplication(), LINK_PDIS, Pdis.class);
Pdi pdi = pdis.byName(name);
if (pdi == null) {
createItem(pdis, createPdi(name));
pdi = restClient.refresh(pdis)
.byName(name);
Objects.requireNonNull(pdi, "Could not create PDI");
}
ensureContents(pdi, PDI_XML, FORMAT_XML);
configurationState.setPdiUri(pdi.getSelfUri());
}
private void ensureContents(LinkContainer state, String configurationName, String format) throws IOException {
Contents contents = restClient.follow(state, LINK_CONTENTS, Contents.class);
if (contents.hasContent()) {
return;
}
String content = configured(configurationName);
try (InputStream stream = new ByteArrayInputStream(content.getBytes(StandardCharsets.UTF_8))) {
perform(() -> restClient.post(state.getUri(LINK_CONTENTS), null,
new TextPart("content", MediaTypes.HAL, "{ \"format\": \"" + format + "\" }"),
new BinaryPart("file", stream, configurationName)));
}
}
private Pdi createPdi(String name) {
Pdi result = new Pdi();
result.setName(name);
return result;
}
private void ensurePdiSchema() throws IOException {
String name = configured(PDI_SCHEMA_NAME);
PdiSchemas pdiSchemas = restClient.follow(configurationState.getApplication(), LINK_PDI_SCHEMAS, PdiSchemas.class);
PdiSchema pdiSchema = pdiSchemas.byName(name);
if (pdiSchema == null) {
createItem(pdiSchemas, createPdiSchema(name));
pdiSchema = restClient.refresh(pdiSchemas)
.byName(name);
Objects.requireNonNull(pdiSchema, "Could not create PDI schema");
}
ensureContents(pdiSchema, PDI_SCHEMA, FORMAT_XSD);
}
private PdiSchema createPdiSchema(String name) {
PdiSchema result = new PdiSchema();
result.setName(name);
return result;
}
private void ensureIngest() throws IOException {
String name = INGEST_NAME;
Ingests ingests = restClient.follow(configurationState.getApplication(), LINK_INGESTS, Ingests.class);
Ingest ingest = ingests.byName(name);
if (ingest == null) {
createItem(ingests, createIngest(name));
ingest = restClient.refresh(ingests)
.byName(name);
Objects.requireNonNull(ingest, "Could not create ingest");
}
configurationState.setIngestUri(ingest.getSelfUri());
ensureContents(ingest, INGEST_XML, FORMAT_XML);
}
private Ingest createIngest(String name) {
Ingest result = new Ingest();
result.setName(name);
return result;
}
private void ensureLibrary() throws IOException {
String name = configured(HOLDING_NAME);
Libraries libraries = restClient.follow(configurationState.getSpaceRootLibrary(), LINK_LIBRARIES, Libraries.class);
Library library = libraries.byName(name);
if (library == null) {
createItem(libraries, createLibrary(name));
library = restClient.refresh(libraries)
.byName(name);
Objects.requireNonNull(library, "Could not create library");
}
configurationState.setLibraryUri(library.getSelfUri());
}
private Library createLibrary(String name) {
Library result = new Library();
result.setName(name);
result.setSubPath("aips/" + configured(APPLICATION_NAME).replace(' ', '-'));
return result;
}
private void ensureHolding() throws IOException {
String name = configuration.get(HOLDING_NAME);
Holdings holdings = restClient.follow(configurationState.getApplication(), LINK_HOLDINGS, Holdings.class);
Holding holding = holdings.byName(name);
if (holding == null) {
createItem(holdings, createHolding(name));
holding = restClient.refresh(holdings)
.byName(name);
Objects.requireNonNull(holding, "Could not create holding");
}
configurationState.setHoldingUri(holding.getSelfUri());
}
private void ensureAic() throws IOException {
String name = configuration.get(AIC_NAME);
Aics aics = restClient.follow(configurationState.getApplication(), LINK_AICS, Aics.class);
Aic aic = aics.byName(name);
if (aic == null) {
createItem(aics, createAic(name));
aic = restClient.refresh(aics)
.byName(name);
Objects.requireNonNull(aic, "Could not create aic");
}
configurationState.setAicUri(aic.getSelfUri());
configurationState.setAicUriByName(name, aic.getSelfUri());
}
private Aic createAic(String name) {
Aic aic = new Aic();
aic.setName(name);
aic.setCriterias(createCriteria());
aic.getHoldings()
.add(configurationState.getHoldingUri());
return aic;
}
private List createCriteria() {
List criteria = new ArrayList<>();
RepeatingConfigReader reader = new RepeatingConfigReader("criteria", Arrays.asList(CRITERIA_NAME, CRITERIA_LABEL,
CRITERIA_TYPE, CRITERIA_PKEYMINATTR, CRITERIA_PKEYMAXATTR, CRITERIA_PKEYVALUESATTR, CRITERIA_INDEXED));
List> criterionConfigurations = reader.read(configuration);
for (Map cfg : criterionConfigurations) {
Criterion criterion = new Criterion();
criterion.setIndexed(Boolean.parseBoolean(cfg.get(CRITERIA_INDEXED)));
criterion.setLabel(cfg.get(CRITERIA_LABEL));
criterion.setName(cfg.get(CRITERIA_NAME));
String minAttr = cfg.get(CRITERIA_PKEYMINATTR)
.trim();
if (!minAttr.isEmpty()) {
criterion.setpKeyMinAttr(minAttr);
}
String maxAttr = cfg.get(CRITERIA_PKEYMAXATTR)
.trim();
if (!maxAttr.isEmpty()) {
criterion.setpKeyMaxAttr(maxAttr);
}
String valueAttr = cfg.get(CRITERIA_PKEYVALUESATTR)
.trim();
if (!valueAttr.isEmpty()) {
criterion.setpKeyValuesAttr(valueAttr);
}
criterion.setType(cfg.get(CRITERIA_TYPE));
criteria.add(criterion);
}
return criteria;
}
private void ensureQuery() throws IOException {
String rawQueryNames = configuration.get(QUERY_NAME);
List queryUris = new ArrayList<>();
if (rawQueryNames != null && !rawQueryNames.isEmpty()) {
String[] queryNames = rawQueryNames.split(",");
for (String queryName : queryNames) {
Queries queries = restClient.follow(configurationState.getApplication(), LINK_QUERIES, Queries.class);
Query query = queries.byName(queryName);
if (query == null) {
createItem(queries, createQuery(queryName));
query = restClient.refresh(queries)
.byName(queryName);
Objects.requireNonNull(query, "Could not create query");
}
queryUris.add(query.getSelfUri());
configurationState.setQueryUriByName(queryName, query.getSelfUri());
}
configurationState.setQueryUris(queryUris);
}
}
private void ensureQuota() throws IOException {
String name = configuration.get(QUOTA_NAME);
Quotas quotas = restClient.follow(configurationState.getApplication(), LINK_QUERY_QUOTAS, Quotas.class);
Quota quota = quotas.byName(name);
if (quota == null) {
createItem(quotas, createQuota(name));
quota = restClient.refresh(quotas)
.byName(name);
Objects.requireNonNull(quota, "Could not create query");
}
configurationState.setQuotaUri(quota.getSelfUri());
}
private Quota createQuota(String name) {
Quota quota = new Quota();
quota.setName(name);
int aipQuota = getOptionalInt(QUOTA_AIP, 0);
quota.setAipQuota(aipQuota);
int aiuQuota = getOptionalInt(QUOTA_AIU, 0);
quota.setAiuQuota(aiuQuota);
int dipQuota = getOptionalInt(QUOTA_DIP, 0);
quota.setDipQuota(dipQuota);
return quota;
}
private int getOptionalInt(String name, int defaultValue) {
String value = configuration.get(name);
if (value == null || value.isEmpty()) {
return defaultValue;
} else {
return Integer.parseInt(value);
}
}
private Query createQuery(String name) {
Query query = new Query();
query.setName(name);
query.setResultRootElement(configuration.get(resolveTemplatedKey(QUERY_RESULT_ROOT_ELEMENT_TEMPLATE, name)));
query.setResultRootNsEnabled(
Boolean.parseBoolean(configuration.get(resolveTemplatedKey(QUERY_RESULT_ROOT_NS_ENABLED_TEMPLATE, name))));
query.setResultSchema(configuration.get(resolveTemplatedKey(QUERY_RESULT_SCHEMA_TEMPLATE, name)));
query.setNamespaces(createNamespaces(name));
query.setXdbPdiConfigs(createXdbPdiConfigs(name));
query.setQuota(configurationState.getQuotaUri());
query.setQuotaAsync(configurationState.getQuotaUri());
query.getAics()
.add(configurationState.getAicUri());
return query;
}
private List createNamespaces(String name) {
RepeatingConfigReader reader = new RepeatingConfigReader("namespace",
resolveTemplatedKeys(Arrays.asList(QUERY_NAMESPACE_PREFIX_TEMPLATE, QUERY_NAMESPACE_URI_TEMPLATE), name));
List> namespaceCfgs = reader.read(configuration);
List namespaces = new ArrayList<>();
for (Map cfg : namespaceCfgs) {
Namespace namespace = new Namespace();
namespace.setPrefix(cfg.get(resolveTemplatedKey(QUERY_NAMESPACE_PREFIX_TEMPLATE, name)));
namespace.setUri(cfg.get(resolveTemplatedKey(QUERY_NAMESPACE_URI_TEMPLATE, name)));
namespaces.add(namespace);
}
return namespaces;
}
private List createXdbPdiConfigs(String name) {
RepeatingConfigReader reader = new RepeatingConfigReader("xdbpdiconfigs", resolveTemplatedKeys(
Arrays.asList(QUERY_XDBPDI_ENTITY_PATH_TEMPLATE, QUERY_XDBPDI_SCHEMA_TEMPLATE, QUERY_XDBPDI_TEMPLATE_TEMPLATE),
name));
List> xdbPdiCfgs = reader.read(configuration);
List xdbPdis = new ArrayList<>();
for (Map cfg : xdbPdiCfgs) {
XdbPdiConfig xdbPdi = new XdbPdiConfig();
xdbPdi.setEntityPath(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_ENTITY_PATH_TEMPLATE, name)));
xdbPdi.setSchema(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_SCHEMA_TEMPLATE, name)));
xdbPdi.setTemplate(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_TEMPLATE_TEMPLATE, name)));
xdbPdi.setOperands(createOperands(name, xdbPdi.getSchema()));
xdbPdis.add(xdbPdi);
}
return xdbPdis;
}
private List createOperands(String name, String schema) {
RepeatingConfigReader reader =
new RepeatingConfigReader("operands", resolveTemplatedKeys(Arrays.asList(QUERY_XDBPDI_OPERAND_NAME,
QUERY_XDBPDI_OPERAND_PATH, QUERY_XDBPDI_OPERAND_TYPE, QUERY_XDBPDI_OPERAND_INDEX), name, schema));
List> operandCfgs = reader.read(configuration);
List operands = new ArrayList<>();
for (Map cfg : operandCfgs) {
Operand operand = new Operand();
operand.setIndex(Boolean.parseBoolean(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_OPERAND_INDEX, name, schema))));
operand.setType(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_OPERAND_TYPE, name, schema)));
operand.setName(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_OPERAND_NAME, name, schema)));
operand.setPath(cfg.get(resolveTemplatedKey(QUERY_XDBPDI_OPERAND_PATH, name, schema)));
operands.add(operand);
}
return operands;
}
private List resolveTemplatedKeys(List templatedKeys, Object... vars) {
return templatedKeys.stream()
.map(key -> resolveTemplatedKey(key, vars))
.collect(Collectors.toList());
}
private String resolveTemplatedKey(String key, Object... vars) {
return String.format(key, vars);
}
private Holding createHolding(String holdingName) {
Holding result = new Holding();
result.setName(holdingName);
result.setAllStores(configurationState.getStoreUri());
IngestConfig ingestConfig = new IngestConfig();
ingestConfig.setIngest(configurationState.getIngestUri());
result.getIngestConfigs()
.add(ingestConfig);
result.getIngestNodes()
.add(configurationState.getIngestNodeUri());
SubPriority priority = new SubPriority();
priority.setPriority(0);
priority.setDeadline(100);
result.getSubPriorities()
.add(priority);
priority = new SubPriority();
priority.setPriority(1);
priority.setDeadline(200);
result.getSubPriorities()
.add(priority);
result.setXdbLibraryParent(configurationState.getLibraryUri());
RetentionClass retentionClass = new RetentionClass();
retentionClass.getPolicies()
.add(configured(RETENTION_POLICY_NAME));
result.getRetentionClasses()
.add(retentionClass);
PdiConfig pdiConfig = new PdiConfig();
pdiConfig.setPdi(configurationState.getPdiUri());
pdiConfig.setSchema(configured(PDI_SCHEMA_NAME));
result.getPdiConfigs()
.add(pdiConfig);
return result;
}
private void ensureResultConfigurationHelper() throws IOException {
String name = configuration.getOrDefault(RESULT_HELPER_NAME, DEFAULT_RESULT_HELPER_NAME);
if (configuration.containsKey(resolveTemplatedKey(RESULT_HELPER_XML, name))) {
ResultConfigurationHelpers helpers = restClient.follow(configurationState.getApplication(),
LINK_RESULT_CONFIGURATION_HELPERS, ResultConfigurationHelpers.class);
ResultConfigurationHelper helper = helpers.byName(name);
if (helper == null) {
createItem(helpers, createResultConfigurationHelper(name));
helper = restClient.refresh(helpers)
.byName(name);
Objects.requireNonNull(helper, "Could not create Result configuration helper");
}
ensureContents(helper, resolveTemplatedKey(RESULT_HELPER_XML, name), FORMAT_XML);
configurationState.setResultConfigHelperUri(helper.getSelfUri());
}
}
private ResultConfigurationHelper createResultConfigurationHelper(String name) {
ResultConfigurationHelper helper = new ResultConfigurationHelper();
helper.setName(name);
helper.setResultSchema(createResultSchema(name));
return helper;
}
private List createResultSchema(String name) {
String schema = configuration.get(resolveTemplatedKey(RESULT_HELPER_SCHEMA_TEMPLATE, name));
List schemas = new ArrayList<>();
schemas.add(schema);
return schemas;
}
private void ensureSearch() throws IOException {
String[] searchNames = configuration.get(SEARCH_NAME)
.split(",");
for (String name : searchNames) {
Searches searches = restClient.follow(configurationState.getApplication(), LINK_SEARCHES, Searches.class);
configurationState.setSearch(searches.byName(name));
if (configurationState.getSearch() == null) {
createItem(searches, createSearch(name));
configurationState.setSearch(restClient.refresh(searches)
.byName(name));
Objects.requireNonNull(configurationState.getSearch(), "Could not create Search");
ensureSearchComposition(name);
}
}
}
private Search createSearch(String name) {
Search search = new Search();
search.setName(name);
search.setDescription(configuration.get(resolveTemplatedKey(SEARCH_DESCRIPTION, name)));
search.setNestedSearch(Boolean.parseBoolean(configuration.get(resolveTemplatedKey(SEARCH_NESTED, name))));
search.setState(configuration.get(resolveTemplatedKey(SEARCH_STATE, name)));
search.setInUse(Boolean.parseBoolean(configuration.get(resolveTemplatedKey(SEARCH_INUSE, name))));
search.setAic(configurationState.getAicUriByName(configuration.get(resolveTemplatedKey(SEARCH_AIC, name))));
search.setQuery(configurationState.getQueryUriByName(configuration.get(resolveTemplatedKey(SEARCH_QUERY, name))));
return search;
}
private void ensureSearchComposition(String searchName) throws IOException {
String name = configuration.get(resolveTemplatedKey(SEARCH_COMPOSITION_NAME, searchName));
if (name == null || name.isEmpty()) {
name = "Set 1";
}
SearchCompositions compositions =
restClient.follow(configurationState.getSearch(), LINK_SEARCH_COMPOSITIONS, SearchCompositions.class);
configurationState.setSearchComposition(compositions.byName(name));
if (configurationState.getSearchComposition() == null) {
createItem(compositions, createSearchComposition(name), LINK_SELF);
SearchComposition composition = restClient.refresh(compositions)
.byName(name);
Objects.requireNonNull(composition, "Could not create Search compostion");
ensureAllSearchComponents(searchName, composition);
}
}
private SearchComposition createSearchComposition(String name) {
SearchComposition composition = new SearchComposition();
composition.setName(name);
composition.setSearchName(SEARCH_NAME);
return composition;
}
private void ensureAllSearchComponents(String searchName, SearchComposition composition) throws IOException {
AllSearchComponents components = new AllSearchComponents();
components.setSearchComposition(composition);
components.setXform(createXForm(searchName, composition.getName()));
components.setResultMaster(createResultMaster(searchName, composition.getName()));
SearchComposition updatedComposition =
restClient.put(composition.getUri(LINK_ALLCOMPONENTS), SearchComposition.class, components);
Objects.requireNonNull(updatedComposition, "Failed to update search composition");
}
private XForm createXForm(String searchName, String compositionName) throws IOException {
XForm xForm = new XForm();
String form = configuration.get(resolveTemplatedKey(SEARCH_COMPOSITION_XFORM, searchName, compositionName));
Objects.requireNonNull(form, "XForm XML is missing.");
xForm.setForm(form);
return xForm;
}
private ResultMaster createResultMaster(String searchName, String compositionName) throws IOException {
ResultMaster resultMaster = new ResultMaster();
resultMaster.setNamespaces(createNamespaces(configuration.get(resolveTemplatedKey(SEARCH_QUERY, searchName))));
List columns = resultMaster.getDefaultTab()
.getColumns();
resultMaster.getDefaultTab()
.setExportEnabled(getBoolean(SEARCH_COMPOSITION_RESULT_MAIN_EXPORT_ENABLED_TEMPLATE, searchName));
resultMaster.getDefaultTab()
.getExportConfigurations()
.addAll(uriFromNamesAndType("export-configuration",
getStrings(SEARCH_COMPOSITION_RESULT_MAIN_EXPORT_CONFIG_TEMPLATE, searchName)));
RepeatingConfigReader reader = new RepeatingConfigReader("maincolumns",
resolveTemplatedKeys(Arrays.asList(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_NAME,
SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_LABEL, SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_PATH,
SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_TYPE, SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_SORT), searchName,
compositionName));
List> columnCfgs = reader.read(configuration);
for (Map columnCfg : columnCfgs) {
String name =
columnCfg.get(resolveTemplatedKey(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_NAME, searchName, compositionName));
String label =
columnCfg.get(resolveTemplatedKey(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_LABEL, searchName, compositionName));
String path =
columnCfg.get(resolveTemplatedKey(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_PATH, searchName, compositionName));
DataType dataType = DataType.valueOf(
columnCfg.get(resolveTemplatedKey(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_TYPE, searchName, compositionName)));
DefaultSort sortOrder = DefaultSort.valueOf(
columnCfg.get(resolveTemplatedKey(SEARCH_COMPOSITION_RESULT_MAIN_COLUMN_SORT, searchName, compositionName)));
Column column = Column.fromSchema(name, label, path, dataType, sortOrder);
columns.add(column);
}
return resultMaster;
}
private List uriFromNamesAndType(String type, Collection strings) {
return strings.stream()
.map(it -> configurationState.getObjectUri(type, it))
.collect(Collectors.toList());
}
private List getStrings(String key, String variable) {
String rawString = getString(key, variable);
if (rawString != null) {
String[] values = rawString.split(",");
List normalizedStrings = new ArrayList<>();
for (String value : values) {
if (value != null) {
String normalizedValue = value.trim();
if (!normalizedValue.isEmpty()) {
normalizedStrings.add(normalizedValue);
}
}
}
return normalizedStrings;
}
return Collections.emptyList();
}
@FunctionalInterface
interface Operation {
T perform() throws IOException;
}
}