Skip to content

Commit

Permalink
server: support for customizable data providers
Browse files Browse the repository at this point in the history
Signed-off-by: Bernd Hufmann <[email protected]>
  • Loading branch information
bhufmann committed Sep 23, 2024
1 parent 4a1c7dd commit 1a087fb
Show file tree
Hide file tree
Showing 2 changed files with 181 additions and 21 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -47,8 +47,10 @@
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.MARKER_SET_ID;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.MISSING_OUTPUTID;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.MISSING_PARAMETERS;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.MISSING_TYPE_ID;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.NO_PROVIDER;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.NO_SUCH_CONFIGURATION;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.NO_SUCH_PROVIDER;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.NO_SUCH_TRACE;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.OCG;
import static org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.services.EndpointConstants.ONE_OF;
Expand Down Expand Up @@ -139,10 +141,14 @@
import org.eclipse.tracecompass.tmf.analysis.xml.core.module.TmfXmlUtils;
import org.eclipse.tracecompass.tmf.core.analysis.IAnalysisModuleHelper;
import org.eclipse.tracecompass.tmf.core.analysis.TmfAnalysisManager;
import org.eclipse.tracecompass.tmf.core.config.ITmfConfigurationSourceType;
import org.eclipse.tracecompass.tmf.core.config.ITmfDataProviderSource;
import org.eclipse.tracecompass.tmf.core.dataprovider.DataProviderManager;
import org.eclipse.tracecompass.tmf.core.dataprovider.DataProviderParameterUtils;
import org.eclipse.tracecompass.tmf.core.dataprovider.IDataProviderDescriptor;
import org.eclipse.tracecompass.tmf.core.dataprovider.IDataProviderDescriptor.ProviderType;
import org.eclipse.tracecompass.tmf.core.dataprovider.IDataProviderFactory;
import org.eclipse.tracecompass.tmf.core.exceptions.TmfConfigurationException;
import org.eclipse.tracecompass.tmf.core.model.CommonStatusMessage;
import org.eclipse.tracecompass.tmf.core.model.DataProviderDescriptor;
import org.eclipse.tracecompass.tmf.core.model.IOutputStyleProvider;
Expand Down Expand Up @@ -252,16 +258,11 @@ public Response getProvider(
if (experiment == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_TRACE).build();
}
List<IDataProviderDescriptor> list = DataProviderManager.getInstance().getAvailableProviders(experiment);
list.addAll(getXmlDataProviderDescriptors(experiment, EnumSet.of(OutputType.TIME_GRAPH)));
list.addAll(getXmlDataProviderDescriptors(experiment, EnumSet.of(OutputType.XY)));

Optional<IDataProviderDescriptor> provider = list.stream().filter(p -> p.getId().equals(outputId)).findFirst();

if (provider.isPresent()) {
return Response.ok(provider.get()).build();
IDataProviderDescriptor provider = getDescriptor(experiment, outputId);
if (provider != null) {
return Response.ok(provider).build();
}

return Response.status(Status.NOT_FOUND).build();
}

Expand Down Expand Up @@ -1158,17 +1159,24 @@ public Response getConfigurationTypes(
@Parameter(description = EXP_UUID) @PathParam("expUUID") UUID expUUID,
@Parameter(description = OUTPUT_ID) @PathParam("outputId") String outputId
) {
return Response.status(Status.NOT_IMPLEMENTED).entity("Get all configuration types for a given output").build(); //$NON-NLS-1$
}

private static Response validateParameters(String outputId, QueryParameters queryParameters) {
if (outputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID).build();
TmfExperiment experiment = ExperimentManagerService.getExperimentByUUID(expUUID);
if (experiment == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_TRACE).build();
}
if (queryParameters == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_PARAMETERS).build();

IDataProviderDescriptor sourceDescriptor = getDescriptor(experiment, outputId);
IDataProviderFactory factory = manager.getFactory(outputId);
if (sourceDescriptor == null || factory == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}
return null;

ITmfDataProviderSource source = factory.getAdapter(ITmfDataProviderSource.class);

if (source != null) {
return Response.ok(source.getConfigurationSourceTypes()).build();
}
return Response.ok(Collections.emptyList()).build();
}

/**
Expand All @@ -1195,7 +1203,33 @@ public Response getConfigurationType(
@Parameter(description = EXP_UUID) @PathParam("expUUID") UUID expUUID,
@Parameter(description = OUTPUT_ID) @PathParam("outputId") String outputId,
@Parameter(description = CFG_TYPE_ID) @PathParam("typeId") String typeId) {
return Response.status(Status.NOT_IMPLEMENTED).entity("Get a configuration type for a given output").build(); //$NON-NLS-1$

TmfExperiment experiment = ExperimentManagerService.getExperimentByUUID(expUUID);
if (experiment == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_TRACE).build();
}

if (outputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID).build();
}

IDataProviderDescriptor sourceDescriptor = getDescriptor(experiment, outputId);
IDataProviderFactory factory = manager.getFactory(outputId);
if (sourceDescriptor == null || factory == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}
ITmfDataProviderSource source = factory.getAdapter(ITmfDataProviderSource.class);

if (source == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}

Optional<ITmfConfigurationSourceType> optional = source.getConfigurationSourceTypes().stream().filter(type -> type.getId().equals(typeId)).findAny();

if (!optional.isPresent()) {
return Response.status(Status.NOT_FOUND).entity("Configuration source type doesn't exist").build(); //$NON-NLS-1$
}
return Response.ok(optional.get()).build();
}

/**
Expand All @@ -1206,12 +1240,11 @@ public Response getConfigurationType(
* desired experiment UUID
* @param outputId
* Output ID for the data provider to query
* @param typeId
* the configuration source type ID
* @param queryParameters
* the query parameters used to create a data provider
* @return a list of data provider descriptors
*/
@SuppressWarnings("null")
@POST
@Path("/{outputId}")
@Tag(name = OCG)
Expand All @@ -1229,7 +1262,52 @@ public Response createDataProvider(
@RequestBody(description = CFG_CREATE_DESC + " " + CFG_KEYS_DESC, content = {
@Content(schema = @Schema(implementation = org.eclipse.tracecompass.incubator.internal.trace.server.jersey.rest.core.model.OutputConfigurationQueryParameters.class))
}, required = true) OutputConfigurationQueryParameters queryParameters) {
return Response.status(Status.NOT_IMPLEMENTED).entity("POST a configuration to a given output to create derived output").build(); //$NON-NLS-1$


try (FlowScopeLog scope = new FlowScopeLogBuilder(LOGGER, Level.FINE, "DataProviderService#createDataProvider") //$NON-NLS-1$
.setCategory(outputId).build()) {
TmfExperiment experiment = ExperimentManagerService.getExperimentByUUID(expUUID);
if (experiment == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_TRACE).build();
}

Response errorResponse = validateOutputConfigParameters(outputId, queryParameters);
if (errorResponse != null) {
return errorResponse;
}

IDataProviderFactory factory = manager.getFactory(outputId);
if (factory == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}

String typeId = queryParameters.getTypeId();

ITmfDataProviderSource source = factory.getAdapter(ITmfDataProviderSource.class);

if (source == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}

Optional<ITmfConfigurationSourceType> optional = source.getConfigurationSourceTypes().stream().filter(type -> type.getId().equals(typeId)).findAny();
if (!optional.isPresent()) {
return Response.status(Status.NOT_FOUND).entity("Configuration source type doesn't exist").build(); //$NON-NLS-1$
}
ITmfConfigurationSourceType sourceType = optional.get();
// @NonNull Map<@NonNull String, @NonNull Object> params = new HashMap<>();
// if (sourceType.getSchemaFile() != null) {
// // Pass JSON object as json string
// params.put(TmfConfiguration.JSON_STRING_KEY, queryParameters.getParameters().toString());
// } else {
// // Convert it to a Map<String, Object>
// ObjectMapper mapper = new ObjectMapper();
// params = mapper.convertValue(queryParameters.getParameters(), new TypeReference<Map<String,Object>>(){});
// }
List<IDataProviderDescriptor> returnDescr = source.createDataProviderDescriptors(typeId, experiment, queryParameters.getParameters().toString());
return Response.ok(returnDescr).build();
} catch (TmfConfigurationException e) {
return Response.status(Status.BAD_REQUEST).entity(e.getMessage()).build();
}
}

/**
Expand Down Expand Up @@ -1257,7 +1335,83 @@ public Response deleteDerivedOutput(
@Parameter(description = EXP_UUID) @PathParam("expUUID") UUID expUUID,
@Parameter(description = OUTPUT_ID) @PathParam("outputId") String outputId,
@Parameter(description = OUTPUT_ID) @PathParam("derivedOutputId") String derivedOutputId) {
return Response.status(Status.NOT_IMPLEMENTED).entity("DELETE derived output").build(); //$NON-NLS-1$

if (outputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID + " (source)").build(); //$NON-NLS-1$
}

if (derivedOutputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID + " (derived)").build(); //$NON-NLS-1$
}

try (FlowScopeLog scope = new FlowScopeLogBuilder(LOGGER, Level.FINE, "DataProviderService#removeDataProvider") //$NON-NLS-1$
.setCategory(outputId).build()) {
TmfExperiment experiment = ExperimentManagerService.getExperimentByUUID(expUUID);
if (experiment == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_TRACE).build();
}

IDataProviderDescriptor sourceDescriptor = getDescriptor(experiment, outputId);
if (sourceDescriptor == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_PROVIDER + " (source): " + outputId).build(); //$NON-NLS-1$
}

IDataProviderDescriptor derivedDescriptor = getDescriptor(experiment, derivedOutputId);
if (derivedDescriptor == null) {
return Response.status(Status.NOT_FOUND).entity(NO_SUCH_PROVIDER + " (derived): " + derivedOutputId).build(); //$NON-NLS-1$
}

IDataProviderFactory factory = manager.getFactory(outputId);
if (factory == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}

ITmfDataProviderSource source = factory.getAdapter(ITmfDataProviderSource.class);

if (source == null) {
return Response.status(Status.METHOD_NOT_ALLOWED).entity(NO_SUCH_PROVIDER).build();
}
source.removeDataProviderDescriptor(experiment, derivedDescriptor);
return Response.ok().build();
} catch (TmfConfigurationException e) {
return Response.status(Status.BAD_REQUEST).entity(e.getMessage()).build();
}
}

private static Response validateParameters(String outputId, QueryParameters queryParameters) {
if (outputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID).build();
}
if (queryParameters == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_PARAMETERS).build();
}
return null;
}

private static Response validateOutputConfigParameters(String outputId, OutputConfigurationQueryParameters queryParameters) {
if (outputId == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_OUTPUTID).build();
}
if (queryParameters == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_PARAMETERS).build();
}
if (queryParameters.getTypeId() == null) {
return Response.status(Status.BAD_REQUEST).entity(MISSING_TYPE_ID).build();
}
return null;
}

private static @Nullable IDataProviderDescriptor getDescriptor(@NonNull ITmfTrace experiment, @NonNull String outputId) {
List<IDataProviderDescriptor> list = DataProviderManager.getInstance().getAvailableProviders(experiment);
list.addAll(getXmlDataProviderDescriptors(experiment, EnumSet.of(OutputType.TIME_GRAPH)));
list.addAll(getXmlDataProviderDescriptors(experiment, EnumSet.of(OutputType.XY)));

Optional<IDataProviderDescriptor> provider = list.stream().filter(p -> p.getId().equals(outputId)).findFirst();
if (provider.isPresent()) {
return provider.get();
}
return null;
}


}
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,18 @@ public final class EndpointConstants {
/** Error message returned for a request with missing parameters */
public static final String MISSING_PARAMETERS = "Missing query parameters"; //$NON-NLS-1$

/** Error message returned for a request with configuration type ID */
public static final String MISSING_TYPE_ID = "Missing configuration type ID"; //$NON-NLS-1$

/** Error message returned for a request with invalid parameters */
public static final String INVALID_PARAMETERS = "Invalid query parameters"; //$NON-NLS-1$

/** Error message returned for a request for a non-existing data provider */
public static final String NO_PROVIDER = "Analysis cannot run"; //$NON-NLS-1$

/** Error message returned for a request for a non-existing data provider */
public static final String NO_SUCH_PROVIDER = "Data provider doesn't exist"; //$NON-NLS-1$

/** Error message returned for a request for trace that doesn't exist */
public static final String NO_SUCH_TRACE = "No such trace"; //$NON-NLS-1$

Expand Down

0 comments on commit 1a087fb

Please sign in to comment.