Merge branch 'master' into Artifiact_upload_directory_upload
This commit is contained in:
43
README.md
43
README.md
@@ -10,15 +10,31 @@ Build: [](htt
|
||||
* You can also check out our [Project Homepage](https://projects.eclipse.org/projects/iot.hawkbit) for further contact options.
|
||||
|
||||
|
||||
# Compile
|
||||
```
|
||||
mvn install
|
||||
```
|
||||
|
||||
# Run and use
|
||||
# Compile, Run and Getting Started
|
||||
|
||||
We are not providing an off the shelf installation ready hawkBit update server. However, we recommend to check out the [Example Application](examples/hawkbit-example-app) for a runtime ready Spring Boot based update server that is empowered by hawkBit.
|
||||
|
||||
#### Clone and build hawkBit
|
||||
```
|
||||
$ git clone https://github.com/eclipse/hawkbit.git
|
||||
$ mvn clean install
|
||||
```
|
||||
#### Start hawkBit example app
|
||||
[Example Application](examples/hawkbit-example-app)
|
||||
```
|
||||
$ java –jar ./examples/hawkbit-example-app/target/hawkbit-example-app-#version#.jar
|
||||
```
|
||||
#### Start hawkBit device simulator
|
||||
[Device Simulator](examples/hawkbit-device-simulator)
|
||||
```
|
||||
$ java –jar ./examples/hawkbit-device-simulator/target/hawkbit-device-simulator-#version#.jar
|
||||
```
|
||||
#### Generate Getting Started data
|
||||
[Example Management API Client](examples/hawkbit-mgmt-api-client)
|
||||
```
|
||||
$ java –jar ./examples/hawkbit-mgmt-api-client/target/hawkbit-mgmt-api-client-#version#.jar
|
||||
```
|
||||
|
||||
# Releases and Roadmap
|
||||
|
||||
* We are currently working on the first formal release under the Eclipse banner: 0.1 (see [Release 0.1 branch](https://github.com/eclipse/hawkbit/tree/release-train-0.1)).
|
||||
@@ -29,11 +45,10 @@ We are not providing an off the shelf installation ready hawkBit update server.
|
||||
* And of course tons of usability improvements and bug fixes.
|
||||
|
||||
|
||||
## Try out examples
|
||||
#### Standalone Test Application Server
|
||||
[Example Application](examples/hawkbit-example-app)
|
||||
#### Device Simulator using the DMF AMQP API
|
||||
[Device Simulator](examples/hawkbit-device-simulator)
|
||||
# Device Integration
|
||||
There are two device integration APIs provided by the hawkbit update server.
|
||||
* [Direct Device Integration API (HTTP)](DDIA.md)
|
||||
* [Device Management Federation API (AMQP)](DMFA.md)
|
||||
|
||||
# Modules
|
||||
`hawkbit-core` : core elements.
|
||||
@@ -49,9 +64,3 @@ We are not providing an off the shelf installation ready hawkBit update server.
|
||||
`hawkbit-rest-resource` : HTTP REST endpoints for the Management and the Direct Device API.
|
||||
`hawkbit-ui` : Vaadin UI.
|
||||
`hawkbit-cache-redis` : spring cache manager configuration and implementation with redis, distributed cache and distributed events.
|
||||
|
||||
|
||||
# Device Integration
|
||||
There are two device integration APIs provided by the hawkbit update server.
|
||||
* [Direct Device Integration API (HTTP)](DDIA.md)
|
||||
* [Device Management Federation API (AMQP)](DMFA.md)
|
||||
|
||||
@@ -10,7 +10,6 @@ package org.eclipse.hawkbit.simulator;
|
||||
|
||||
import java.util.concurrent.ScheduledExecutorService;
|
||||
|
||||
import org.eclipse.hawkbit.simulator.DeviceSimulatorUpdater.UpdaterCallback;
|
||||
import org.eclipse.hawkbit.simulator.http.ControllerResource;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
@@ -82,28 +81,27 @@ public class DDISimulatedDevice extends AbstractSimulatedDevice {
|
||||
final String deploymentJson = controllerResource.getDeployment(getTenant(), getId(), actionId);
|
||||
final String swVersion = JsonPath.parse(deploymentJson).read("deployment.chunks[0].version");
|
||||
currentActionId = actionId;
|
||||
deviceUpdater.startUpdate(getTenant(), getId(), actionId, swVersion, new UpdaterCallback() {
|
||||
@Override
|
||||
public void updateFinished(final AbstractSimulatedDevice device, final Long actionId) {
|
||||
switch (device.getResponseStatus()) {
|
||||
case SUCCESSFUL:
|
||||
controllerResource.postSuccessFeedback(getTenant(), getId(), actionId);
|
||||
break;
|
||||
case ERROR:
|
||||
controllerResource.postErrorFeedback(getTenant(), getId(), actionId);
|
||||
break;
|
||||
default:
|
||||
throw new IllegalStateException("simulated device has an unknown response status + "
|
||||
+ device.getResponseStatus());
|
||||
}
|
||||
currentActionId = null;
|
||||
deviceUpdater.startUpdate(getTenant(), getId(), actionId, swVersion, (device, actionId1) -> {
|
||||
switch (device.getResponseStatus()) {
|
||||
case SUCCESSFUL:
|
||||
controllerResource.postSuccessFeedback(getTenant(), getId(),
|
||||
actionId1);
|
||||
break;
|
||||
case ERROR:
|
||||
controllerResource.postErrorFeedback(getTenant(), getId(),
|
||||
actionId1);
|
||||
break;
|
||||
default:
|
||||
throw new IllegalStateException(
|
||||
"simulated device has an unknown response status + " + device.getResponseStatus());
|
||||
}
|
||||
currentActionId = null;
|
||||
});
|
||||
}
|
||||
} catch (final PathNotFoundException e) {
|
||||
// href might not be in the json response, so ignore
|
||||
// exception here.
|
||||
LOGGER.trace("Response does not contain a deploymentbase href link, ignoring.");
|
||||
LOGGER.trace("Response does not contain a deploymentbase href link, ignoring.", e);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.simulator;
|
||||
|
||||
import java.security.SecureRandom;
|
||||
import java.util.Random;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.concurrent.ScheduledExecutorService;
|
||||
@@ -41,7 +42,7 @@ public class DeviceSimulatorUpdater {
|
||||
|
||||
/**
|
||||
* Starting an simulated update process of an simulated device.
|
||||
*
|
||||
*
|
||||
* @param tenant
|
||||
* the tenant of the device
|
||||
* @param id
|
||||
@@ -66,7 +67,7 @@ public class DeviceSimulatorUpdater {
|
||||
}
|
||||
|
||||
private static final class DeviceSimulatorUpdateThread implements Runnable {
|
||||
private static final Random rndSleep = new Random();
|
||||
private static final Random rndSleep = new SecureRandom();
|
||||
|
||||
private final AbstractSimulatedDevice device;
|
||||
private final SpSenderService spSenderService;
|
||||
@@ -74,9 +75,8 @@ public class DeviceSimulatorUpdater {
|
||||
private final EventBus eventbus;
|
||||
private final UpdaterCallback callback;
|
||||
|
||||
private DeviceSimulatorUpdateThread(final AbstractSimulatedDevice device,
|
||||
final SpSenderService spSenderService, final long actionId, final EventBus eventbus,
|
||||
final UpdaterCallback callback) {
|
||||
private DeviceSimulatorUpdateThread(final AbstractSimulatedDevice device, final SpSenderService spSenderService,
|
||||
final long actionId, final EventBus eventbus, final UpdaterCallback callback) {
|
||||
this.device = device;
|
||||
this.spSenderService = spSenderService;
|
||||
this.actionId = actionId;
|
||||
@@ -89,8 +89,9 @@ public class DeviceSimulatorUpdater {
|
||||
final double newProgress = device.getProgress() + 0.2;
|
||||
device.setProgress(newProgress);
|
||||
if (newProgress < 1.0) {
|
||||
threadPool.schedule(new DeviceSimulatorUpdateThread(device, spSenderService, actionId, eventbus,
|
||||
callback), rndSleep.nextInt(3000), TimeUnit.MILLISECONDS);
|
||||
threadPool.schedule(
|
||||
new DeviceSimulatorUpdateThread(device, spSenderService, actionId, eventbus, callback),
|
||||
rndSleep.nextInt(3000), TimeUnit.MILLISECONDS);
|
||||
} else {
|
||||
callback.updateFinished(device, actionId);
|
||||
}
|
||||
@@ -102,7 +103,7 @@ public class DeviceSimulatorUpdater {
|
||||
* Callback interface which is called when the simulated update process has
|
||||
* been finished and the caller of starting the simulated update process can
|
||||
* send the result to the hawkbit update server back.
|
||||
*
|
||||
*
|
||||
* @author Michael Hirsch
|
||||
*
|
||||
*/
|
||||
@@ -111,7 +112,7 @@ public class DeviceSimulatorUpdater {
|
||||
/**
|
||||
* Callback method to indicate that the simulated update process has
|
||||
* been finished.
|
||||
*
|
||||
*
|
||||
* @param device
|
||||
* the device which has been updated
|
||||
* @param actionId
|
||||
|
||||
@@ -16,6 +16,8 @@ import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.eclipse.hawkbit.simulator.event.NextPollCounterUpdate;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@@ -24,13 +26,15 @@ import com.google.common.eventbus.EventBus;
|
||||
/**
|
||||
* Poll time trigger which executes the {@link DDISimulatedDevice#poll()} every
|
||||
* second.
|
||||
*
|
||||
*
|
||||
* @author Michael Hirsch
|
||||
*
|
||||
*/
|
||||
@Component
|
||||
public class NextPollTimeController {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(NextPollTimeController.class);
|
||||
|
||||
private static final ScheduledExecutorService executorService = Executors.newScheduledThreadPool(1);
|
||||
private static final ExecutorService pollService = Executors.newFixedThreadPool(1);
|
||||
|
||||
@@ -58,14 +62,9 @@ public class NextPollTimeController {
|
||||
if (nextCounter < 0) {
|
||||
if (device instanceof DDISimulatedDevice) {
|
||||
try {
|
||||
pollService.submit(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
((DDISimulatedDevice) device).poll();
|
||||
}
|
||||
});
|
||||
} catch (final Exception e) {
|
||||
|
||||
pollService.submit(() -> ((DDISimulatedDevice) device).poll());
|
||||
} catch (final IllegalStateException e) {
|
||||
LOGGER.trace("Device could not be polled", e);
|
||||
}
|
||||
nextCounter = ((DDISimulatedDevice) device).getPollDelaySec();
|
||||
}
|
||||
|
||||
@@ -1,3 +1,39 @@
|
||||
# HawkBit management API example
|
||||
|
||||
Example client that shows how to efficiently use the hawkBit management API.
|
||||
|
||||
Powered by [Feign](https://github.com/Netflix/feign).
|
||||
Powered by [Feign](https://github.com/Netflix/feign).
|
||||
|
||||
## How to run the example client
|
||||
|
||||
Run getting started example
|
||||
|
||||
|
||||
|
||||
$ java -jar hawkbit-mgmt-api-client-#version#.jar
|
||||
|
||||
|
||||
Run create and start rollout example
|
||||
|
||||
|
||||
$ java -jar hawkbit-mgmt-api-client-#version#.jar --createrollout
|
||||
|
||||
|
||||
## This example shows
|
||||
|
||||
In getting started example:
|
||||
* creating software modules type
|
||||
* creating distribution set type
|
||||
* creating distribution sets
|
||||
* creating software modules
|
||||
* assigning software modules to distribution sets
|
||||
|
||||
In rollout mode:
|
||||
* creating software modules type
|
||||
* creating distribution set type
|
||||
* creating distribution sets
|
||||
* creating software modules
|
||||
* assigning software modules to distribution sets
|
||||
* creating a rollout
|
||||
* starting a rollout
|
||||
|
||||
|
||||
@@ -16,9 +16,43 @@
|
||||
<artifactId>hawkbit-examples-parent</artifactId>
|
||||
<version>0.2.0-SNAPSHOT</version>
|
||||
</parent>
|
||||
<packaging>jar</packaging>
|
||||
<artifactId>hawkbit-mgmt-api-client</artifactId>
|
||||
<name>hawkBit Management API example client</name>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>repackage</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<outputDirectory>${baseDir}</outputDirectory>
|
||||
<addResources>false</addResources>
|
||||
<mainClass>org.eclipse.hawkbit.mgmt.client.Application</mainClass>
|
||||
<layout>JAR</layout>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-netflix</artifactId>
|
||||
<version>1.0.7.RELEASE</version>
|
||||
<type>pom</type>
|
||||
<scope>import</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
@@ -26,45 +60,32 @@
|
||||
<artifactId>hawkbit-rest-api</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.netflix.feign</groupId>
|
||||
<artifactId>feign-jackson</artifactId>
|
||||
<version>8.12.1</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.netflix.feign</groupId>
|
||||
<artifactId>feign-core</artifactId>
|
||||
<version>8.12.1</version>
|
||||
<!-- need to overwrite for the interface inheritance feature of feign-core -->
|
||||
<version>8.14.2</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Test -->
|
||||
<dependency>
|
||||
<groupId>org.eclipse.hawkbit</groupId>
|
||||
<artifactId>hawkbit-example-app</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<scope>test</scope>
|
||||
<artifactId>hibernate-validator</artifactId>
|
||||
<groupId>org.hibernate</groupId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
<artifactId>spring-boot-starter</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>ru.yandex.qatools.allure</groupId>
|
||||
<artifactId>allure-junit-adaptor</artifactId>
|
||||
<scope>test</scope>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-feign</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.easytesting</groupId>
|
||||
<artifactId>fest-assert-core</artifactId>
|
||||
<scope>test</scope>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-logging</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.easytesting</groupId>
|
||||
<artifactId>fest-assert</artifactId>
|
||||
<scope>test</scope>
|
||||
<groupId>com.google.collections</groupId>
|
||||
<artifactId>google-collections</artifactId>
|
||||
<version>1.0-rc2</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
|
||||
</project>
|
||||
@@ -1,38 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
|
||||
import feign.Headers;
|
||||
import feign.RequestLine;
|
||||
|
||||
/**
|
||||
* Client binding for the Distribution resource of the management API.
|
||||
*/
|
||||
@FunctionalInterface
|
||||
public interface DistributionSetResource {
|
||||
|
||||
/**
|
||||
* Creates a list of distribution sets.
|
||||
*
|
||||
* @param sets
|
||||
* the request body java bean containing the necessary attributes
|
||||
* for creating a distribution set.
|
||||
* @return the list of targets which have been created
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.DISTRIBUTIONSET_V1_REQUEST_MAPPING)
|
||||
@Headers("Content-Type: application/json")
|
||||
DistributionSetsRest createDistributionSets(final List<DistributionSetRequestBodyPost> sets);
|
||||
|
||||
}
|
||||
@@ -1,138 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedDistributionSetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.DistributionSetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
|
||||
import feign.Headers;
|
||||
import feign.Param;
|
||||
import feign.RequestLine;
|
||||
|
||||
/**
|
||||
* Client binding for the DistributionSetTag resource of the management API.
|
||||
*/
|
||||
public interface DistrubutionSetTagResource {
|
||||
|
||||
/**
|
||||
* Retrieves a single distributionset tag based on the given ID.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to retrieve
|
||||
* @return a deserialized java bean containing the attributes of the
|
||||
* returned distributionset tag
|
||||
*/
|
||||
@RequestLine("GET " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING + "/{dsTagId}")
|
||||
TagRest getDistributionSetTag(@Param("dsTagId") Long dsTagId);
|
||||
|
||||
/**
|
||||
* Creates a list of distributionset tags.
|
||||
*
|
||||
* @param tags
|
||||
* the tags to be created
|
||||
* @return the created tag list
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING)
|
||||
@Headers("Content-Type: application/json")
|
||||
TagsRest createDistributionSetTags(List<TagRequestBodyPut> tags);
|
||||
|
||||
/**
|
||||
* Update attributes of a distributionset tag.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the distributionset tag id to be updated
|
||||
* @param tag
|
||||
* the request body
|
||||
* @return the updated distributionset tag
|
||||
*/
|
||||
@RequestLine("PUT " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING + "/{dsTagId}")
|
||||
@Headers("Content-Type: application/json")
|
||||
TagRest updateDistributionSetTag(@Param("dsTagId") Long dsTagId, TagRequestBodyPut tag);
|
||||
|
||||
/**
|
||||
* Deletes given distributionset tag on given ID.
|
||||
*
|
||||
* @param dsTagId
|
||||
* to be deleted
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING + "/{dsTagId}")
|
||||
void deleteDistributionSetTag(@Param("dsTagId") final Long dsTagId);
|
||||
|
||||
/**
|
||||
* Retrieves a all assigned targets on the given distributionset tag id.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to retrieve
|
||||
* @return a list of targets
|
||||
*/
|
||||
@RequestLine("GET " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
DistributionSetsRest getAssignedDistributionSets(@Param("dsTagId") final Long dsTagId);
|
||||
|
||||
/**
|
||||
* Toggle the tag assignment all assigned targets will be unassigned and all
|
||||
* unassigned targets will be assigned.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to toggle
|
||||
* @param assignedTargetRequestBodies
|
||||
* a list of controller ids
|
||||
* @return a list of assigned and unassigned targets
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING + "/toggleTagAssignment")
|
||||
@Headers("Content-Type: application/json")
|
||||
DistributionSetTagAssigmentResultRest toggleTagAssignment(@Param("dsTagId") final Long dsTagId,
|
||||
final List<AssignedDistributionSetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Assign targets to a given distributionset tag id.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to add the targets
|
||||
* @param assignedTargetRequestBodies
|
||||
* a list of controller ids
|
||||
* @return a list of assigned targets
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
@Headers("Content-Type: application/json")
|
||||
TargetsRest assignDistributionSets(@Param("dsTagId") final Long dsTagId,
|
||||
final List<AssignedDistributionSetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Unassign targets to a given distributionset tag id.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to add the targets
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
void unassignDistributionSets(@Param("dsTagId") final Long dsTagId);
|
||||
|
||||
/**
|
||||
* Unassign one target to a given distributionset tag id.
|
||||
*
|
||||
* @param dsTagId
|
||||
* the ID of the distributionset tag to add the targets param
|
||||
* @param dsId
|
||||
* the distributionset id
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING + "/{dsId}")
|
||||
void unassignDistributionSet(@Param("dsTagId") final Long dsTagId, @Param("dsId") final Long dsId);
|
||||
}
|
||||
@@ -1,80 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
|
||||
import feign.Headers;
|
||||
import feign.Param;
|
||||
import feign.RequestLine;
|
||||
|
||||
/**
|
||||
* Client binding for the Target resource of the management API.
|
||||
*/
|
||||
public interface TargetResource {
|
||||
|
||||
/**
|
||||
* Retrieves a single target based on the given ID.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve
|
||||
* @return a deserialized java bean containing the attributes of the
|
||||
* returned target
|
||||
*/
|
||||
@RequestLine("GET /rest/v1/targets/{targetId}")
|
||||
TargetRest getTarget(@Param("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Paged query of targets resource.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* of the paged query
|
||||
* @param pagingLimitParam
|
||||
* of the paged query
|
||||
* @return paged list of target entries
|
||||
*/
|
||||
@RequestLine("GET /rest/v1/targets?offset={pagingOffsetParam}&limit={pagingLimitParam}")
|
||||
TargetPagedList getTargets(@Param("pagingOffsetParam") int pagingOffsetParam,
|
||||
@Param("pagingLimitParam") int pagingLimitParam);
|
||||
|
||||
/**
|
||||
* Paged query of targets resource with default offset and limit.
|
||||
*
|
||||
* @return paged list of target entries
|
||||
*/
|
||||
@RequestLine("GET /rest/v1/targets")
|
||||
TargetPagedList getTargets();
|
||||
|
||||
/**
|
||||
* Deletes given target based on given ID.
|
||||
*
|
||||
* @param targetId
|
||||
* to be deleted
|
||||
*/
|
||||
@RequestLine("DELETE /rest/v1/targets/{targetId}")
|
||||
void deleteTarget(@Param("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Creates a list of targets.
|
||||
*
|
||||
* @param targets
|
||||
* the request body java bean containing the necessary attributes
|
||||
* for creating a target.
|
||||
* @return the list of targets which have been created
|
||||
*/
|
||||
@RequestLine("POST /rest/v1/targets/")
|
||||
@Headers("Content-Type: application/json")
|
||||
TargetsRest createTargets(List<TargetRequestBody> targets);
|
||||
|
||||
}
|
||||
@@ -1,137 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedTargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TargetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
|
||||
import feign.Headers;
|
||||
import feign.Param;
|
||||
import feign.RequestLine;
|
||||
|
||||
/**
|
||||
* Client binding for the Target resource of the management API.
|
||||
*/
|
||||
public interface TargetTagResource {
|
||||
|
||||
/**
|
||||
* Retrieves a single target tag based on the given ID.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @return a deserialized java bean containing the attributes of the
|
||||
* returned target tag
|
||||
*/
|
||||
@RequestLine("GET " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING + "/{targetTagId}")
|
||||
TagRest getTargetTag(@Param("targetTagId") Long targetTagId);
|
||||
|
||||
/**
|
||||
* Creates a list of target tags.
|
||||
*
|
||||
* @param tags
|
||||
* the tags to be created
|
||||
* @return the created tag list
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING)
|
||||
@Headers("Content-Type: application/json")
|
||||
TagsRest createTargetTag(List<TagRequestBodyPut> tags);
|
||||
|
||||
/**
|
||||
* Update attributes of a target tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the target tag id to be updated
|
||||
* @param tag
|
||||
* the request body
|
||||
* @return the updated target tag
|
||||
*/
|
||||
@RequestLine("PUT " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING + "/{targetTagId}")
|
||||
@Headers("Content-Type: application/json")
|
||||
TagRest updateTagretTag(@Param("targetTagId") Long targetTagId, TagRequestBodyPut tag);
|
||||
|
||||
/**
|
||||
* Deletes given target tag on given ID.
|
||||
*
|
||||
* @param targetTagId
|
||||
* to be deleted
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING + "/{targetTagId}")
|
||||
void deleteTargetTag(@Param("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Retrieves a all assigned targets on the given target tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @return a list of targets
|
||||
*/
|
||||
@RequestLine("GET " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
TargetsRest getAssignedTargets(@Param("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Toggle the tag assignment all assigned targets will be unassigned and all
|
||||
* unassigned targets will be assigned.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to toggle
|
||||
* @param assignedTargetRequestBodies
|
||||
* a list of controller ids
|
||||
* @return a list of assigned and unassigned targets
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING + "/toggleTagAssignment")
|
||||
@Headers("Content-Type: application/json")
|
||||
TargetTagAssigmentResultRest toggleTagAssignment(@Param("targetTagId") final Long targetTagId,
|
||||
final List<AssignedTargetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Assign targets to a given target tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to add the targets
|
||||
* @param assignedTargetRequestBodies
|
||||
* a list of controller ids
|
||||
* @return a list of assigned targets
|
||||
*/
|
||||
@RequestLine("POST " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
@Headers("Content-Type: application/json")
|
||||
TargetsRest assignTargets(@Param("targetTagId") final Long targetTagId,
|
||||
final List<AssignedTargetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Unassign targets to a given target tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to add the targets
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
void unassignTargets(@Param("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Unassign one target to a given target tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to add the targets param
|
||||
* @param controllerId
|
||||
* the controller id
|
||||
*/
|
||||
@RequestLine("DELETE " + RestConstants.TARGET_TAG_V1_REQUEST_MAPPING
|
||||
+ RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING + "/{controllerId}")
|
||||
void unassignTarget(@Param("targetTagId") final Long targetTagId, @Param("controllerId") final String controllerId);
|
||||
}
|
||||
@@ -0,0 +1,77 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client;
|
||||
|
||||
import org.eclipse.hawkbit.mgmt.client.scenarios.CreateStartedRolloutExample;
|
||||
import org.eclipse.hawkbit.mgmt.client.scenarios.GettingStartedDefaultScenario;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.CommandLineRunner;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.boot.builder.SpringApplicationBuilder;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.cloud.netflix.feign.EnableFeignClients;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
|
||||
import feign.Contract;
|
||||
import feign.auth.BasicAuthRequestInterceptor;
|
||||
|
||||
@SpringBootApplication
|
||||
@EnableFeignClients
|
||||
@EnableConfigurationProperties(ClientConfigurationProperties.class)
|
||||
public class Application implements CommandLineRunner {
|
||||
|
||||
@Autowired
|
||||
private ClientConfigurationProperties configuration;
|
||||
|
||||
@Autowired
|
||||
private GettingStartedDefaultScenario gettingStarted;
|
||||
|
||||
@Autowired
|
||||
private CreateStartedRolloutExample gettingStartedRolloutScenario;
|
||||
|
||||
public static void main(final String[] args) {
|
||||
new SpringApplicationBuilder().showBanner(false).sources(Application.class).run(args);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run(final String... args) throws Exception {
|
||||
if (containsArg("--createrollout", args)) {
|
||||
// run the create and start rollout example
|
||||
gettingStartedRolloutScenario.run();
|
||||
} else {
|
||||
// run the getting started scenario which creates a setup of
|
||||
// distribution set and software modules to be used
|
||||
gettingStarted.run();
|
||||
}
|
||||
}
|
||||
|
||||
@Bean
|
||||
public BasicAuthRequestInterceptor basicAuthRequestInterceptor() {
|
||||
return new BasicAuthRequestInterceptor(configuration.getUsername(), configuration.getPassword());
|
||||
}
|
||||
|
||||
@Bean
|
||||
public ApplicationJsonRequestHeaderInterceptor jsonHeaderInterceptor() {
|
||||
return new ApplicationJsonRequestHeaderInterceptor();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public Contract feignContract() {
|
||||
return new IgnoreMultipleConsumersProducersSpringMvcContract();
|
||||
}
|
||||
|
||||
private boolean containsArg(final String containsArg, final String... args) {
|
||||
for (final String arg : args) {
|
||||
if (arg.equalsIgnoreCase(containsArg)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client;
|
||||
|
||||
import org.springframework.http.MediaType;
|
||||
|
||||
import feign.RequestInterceptor;
|
||||
import feign.RequestTemplate;
|
||||
|
||||
/**
|
||||
* An feign request interceptor to set the defined {@code Accept} and
|
||||
* {@code Content-Type} headers for each request to {@code application/json}.
|
||||
*/
|
||||
public class ApplicationJsonRequestHeaderInterceptor implements RequestInterceptor {
|
||||
|
||||
@Override
|
||||
public void apply(final RequestTemplate template) {
|
||||
template.header("Accept", MediaType.APPLICATION_JSON_VALUE);
|
||||
template.header("Content-Type", MediaType.APPLICATION_JSON_VALUE);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client;
|
||||
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
|
||||
/**
|
||||
* Configuration bean which holds the configuration of the client e.g. the base
|
||||
* URL of the hawkbit-server and the credentials to use the RESTful Management
|
||||
* API.
|
||||
*/
|
||||
@ConfigurationProperties(prefix = "hawkbit")
|
||||
public class ClientConfigurationProperties {
|
||||
|
||||
private String url = "localhost:8080";
|
||||
private String username = "admin";
|
||||
private String password = "admin"; // NOSONAR this password is only used for
|
||||
// examples
|
||||
|
||||
public String getUrl() {
|
||||
return url;
|
||||
}
|
||||
|
||||
public void setUrl(final String url) {
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
public String getUsername() {
|
||||
return username;
|
||||
}
|
||||
|
||||
public void setUsername(final String username) {
|
||||
this.username = username;
|
||||
}
|
||||
|
||||
public String getPassword() {
|
||||
return password;
|
||||
}
|
||||
|
||||
public void setPassword(final String password) {
|
||||
this.password = password;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client;
|
||||
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.cloud.netflix.feign.support.SpringMvcContract;
|
||||
|
||||
import feign.MethodMetadata;
|
||||
|
||||
/**
|
||||
* Own implementation of the {@link SpringMvcContract} which catches the
|
||||
* {@link IllegalStateException} which occurs due multiple produces and consumes
|
||||
* values in the request-mapping
|
||||
* annoation.https://github.com/spring-cloud/spring-cloud-netflix/issues/808
|
||||
*/
|
||||
public class IgnoreMultipleConsumersProducersSpringMvcContract extends SpringMvcContract {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory
|
||||
.getLogger(IgnoreMultipleConsumersProducersSpringMvcContract.class);
|
||||
|
||||
@Override
|
||||
protected void processAnnotationOnMethod(final MethodMetadata data, final Annotation methodAnnotation,
|
||||
final Method method) {
|
||||
try {
|
||||
super.processAnnotationOnMethod(data, methodAnnotation, method);
|
||||
} catch (final IllegalStateException e) {
|
||||
// ignore illegalstateexception here because it's thrown because of
|
||||
// multiple consumers and produces, see
|
||||
// https://github.com/spring-cloud/spring-cloud-netflix/issues/808
|
||||
LOGGER.trace(e.getMessage(), e);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the DistributionSet resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/distributionsets")
|
||||
public interface DistributionSetResourceClient extends DistributionSetRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTagRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the DistributionSetTag resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/distributionsettags")
|
||||
public interface DistributionSetTagResourceClient extends DistributionSetTagRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTypeRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the DistributionSetType resource of the management API.
|
||||
*
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/distributionsettypes")
|
||||
public interface DistributionSetTypeResourceClient extends DistributionSetTypeRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.RolloutRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the Rollout resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/rollouts")
|
||||
public interface RolloutResourceClient extends RolloutRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleRestAPI;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the SoftwareModule resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/softwaremodules")
|
||||
public interface SoftwareModuleResourceClient extends SoftwareModuleRestAPI {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleTypeRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the oftwareModuleType resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/softwaremoduletypes")
|
||||
public interface SoftwareModuleTypeResourceClient extends SoftwareModuleTypeRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the Target resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/targets")
|
||||
public interface TargetResourceClient extends TargetRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetTagRestApi;
|
||||
import org.springframework.cloud.netflix.feign.FeignClient;
|
||||
|
||||
/**
|
||||
* Client binding for the TargetTag resource of the management API.
|
||||
*/
|
||||
@FeignClient(url = "${hawkbit.endpoint.url:localhost:8080}/rest/v1/targettags")
|
||||
public interface TargetTagResourceClient extends TargetTagRestApi {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,99 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPost;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link DistributionSetRequestBodyPost}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class DistributionSetBuilder {
|
||||
|
||||
private String name;
|
||||
private String version;
|
||||
private String type;
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the distribution set
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param version
|
||||
* the version of the distribution set
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetBuilder version(final String version) {
|
||||
this.version = version;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param type
|
||||
* the distribution set type name for this distribution set
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetBuilder type(final String type) {
|
||||
this.type = type;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of
|
||||
* {@link DistributionSetRequestBodyPost} which can directly be used to post
|
||||
* on the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link DistributionSetRequestBodyPost}
|
||||
*/
|
||||
public List<DistributionSetRequestBodyPost> build() {
|
||||
return Lists.newArrayList(doBuild(name));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link DistributionSetRequestBodyPost} to
|
||||
* create multiple distribution sets at once. An increasing number will be
|
||||
* added to the name of the distribution set. The version and type will
|
||||
* remain the same.
|
||||
*
|
||||
* @param count
|
||||
* the amount of distribution sets body which should be created
|
||||
* @return a list of {@link DistributionSetRequestBodyPost}
|
||||
*/
|
||||
public List<DistributionSetRequestBodyPost> buildAsList(final int count) {
|
||||
final ArrayList<DistributionSetRequestBodyPost> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(name + index));
|
||||
}
|
||||
|
||||
return bodyList;
|
||||
}
|
||||
|
||||
private DistributionSetRequestBodyPost doBuild(final String prefixName) {
|
||||
final DistributionSetRequestBodyPost body = new DistributionSetRequestBodyPost();
|
||||
body.setName(prefixName);
|
||||
body.setVersion(version);
|
||||
body.setType(type);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,124 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeAssigmentRest;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link DistributionSetTypeRequestBodyPost}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class DistributionSetTypeBuilder {
|
||||
|
||||
private String key;
|
||||
private String name;
|
||||
private final List<SoftwareModuleTypeAssigmentRest> mandatorymodules = Lists.newArrayList();
|
||||
private final List<SoftwareModuleTypeAssigmentRest> optionalmodules = Lists.newArrayList();
|
||||
|
||||
/**
|
||||
* @param key
|
||||
* the key of the distribution set type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetTypeBuilder key(final String key) {
|
||||
this.key = key;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the distribution set type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetTypeBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param softwareModuleTypeIds
|
||||
* the IDs of the software module types which should be mandatory
|
||||
* for the distribution set type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetTypeBuilder mandatorymodules(final Long... softwareModuleTypeIds) {
|
||||
for (final Long id : softwareModuleTypeIds) {
|
||||
final SoftwareModuleTypeAssigmentRest softwareModuleTypeAssigmentRest = new SoftwareModuleTypeAssigmentRest();
|
||||
softwareModuleTypeAssigmentRest.setId(id);
|
||||
this.mandatorymodules.add(softwareModuleTypeAssigmentRest);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* @param softwareModuleTypeIds
|
||||
* the IDs of the software module types which should be optional
|
||||
* for the distribution set type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public DistributionSetTypeBuilder optionalmodules(final Long... softwareModuleTypeIds) {
|
||||
for (final Long id : softwareModuleTypeIds) {
|
||||
final SoftwareModuleTypeAssigmentRest softwareModuleTypeAssigmentRest = new SoftwareModuleTypeAssigmentRest();
|
||||
softwareModuleTypeAssigmentRest.setId(id);
|
||||
this.optionalmodules.add(softwareModuleTypeAssigmentRest);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of
|
||||
* {@link DistributionSetTypeRequestBodyPost} which can directly be used in
|
||||
* the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link DistributionSetTypeRequestBodyPost}
|
||||
*/
|
||||
public List<DistributionSetTypeRequestBodyPost> build() {
|
||||
return Lists.newArrayList(doBuild(name, key));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link DistributionSetTypeRequestBodyPost} to
|
||||
* create multiple distribution set types at once. An increasing number will
|
||||
* be added to the name and key of the distribution set type. The optional
|
||||
* and mandatory software module types will remain the same.
|
||||
*
|
||||
* @param count
|
||||
* the amount of distribution sets type body which should be
|
||||
* created
|
||||
* @return a list of {@link DistributionSetTypeRequestBodyPost}
|
||||
*/
|
||||
public List<DistributionSetTypeRequestBodyPost> buildAsList(final int count) {
|
||||
final ArrayList<DistributionSetTypeRequestBodyPost> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(name + index, key + index));
|
||||
}
|
||||
return bodyList;
|
||||
|
||||
}
|
||||
|
||||
private DistributionSetTypeRequestBodyPost doBuild(final String prefixName, final String prefixKey) {
|
||||
final DistributionSetTypeRequestBodyPost body = new DistributionSetTypeRequestBodyPost();
|
||||
body.setKey(prefixKey);
|
||||
body.setName(prefixName);
|
||||
body.setMandatorymodules(mandatorymodules);
|
||||
body.setOptionalmodules(optionalmodules);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,115 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutCondition;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutCondition.Condition;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutRestRequestBody;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link RolloutRestRequestBody}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class RolloutBuilder {
|
||||
|
||||
private String name;
|
||||
private int groupSize;
|
||||
private String targetFilterQuery;
|
||||
private long distributionSetId;
|
||||
private String successThreshold;
|
||||
private String errorThreshold;
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the rollout
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param groupSize
|
||||
* the amount of groups the rollout should be split into
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder groupSize(final int groupSize) {
|
||||
this.groupSize = groupSize;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param targetFilterQuery
|
||||
* the FIQL query language to filter targets to contain in the
|
||||
* rollout
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder targetFilterQuery(final String targetFilterQuery) {
|
||||
this.targetFilterQuery = targetFilterQuery;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to assign to the target in the
|
||||
* rollout
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder distributionSetId(final long distributionSetId) {
|
||||
this.distributionSetId = distributionSetId;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param successThreshold
|
||||
* the threshold to be used to indicate if a deployment group is
|
||||
* successful, to trigger the success action
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder successThreshold(final String successThreshold) {
|
||||
this.successThreshold = successThreshold;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param errorThreshold
|
||||
* the threshold to be used to indicate if a deployment group is
|
||||
* failing, to trigger the error action
|
||||
* @return the builder itself
|
||||
*/
|
||||
public RolloutBuilder errorThreshold(final String errorThreshold) {
|
||||
this.errorThreshold = errorThreshold;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds the rollout rest body to creating a rollout.
|
||||
*
|
||||
* @return the rest request body for creating a rollout
|
||||
*/
|
||||
public RolloutRestRequestBody build() {
|
||||
return doBuild();
|
||||
}
|
||||
|
||||
private RolloutRestRequestBody doBuild() {
|
||||
final RolloutRestRequestBody body = new RolloutRestRequestBody();
|
||||
body.setName(name);
|
||||
body.setAmountGroups(groupSize);
|
||||
body.setTargetFilterQuery(targetFilterQuery);
|
||||
body.setDistributionSetId(distributionSetId);
|
||||
body.setSuccessCondition(new RolloutCondition(Condition.THRESHOLD, successThreshold));
|
||||
body.setErrorCondition(new RolloutCondition(Condition.THRESHOLD, errorThreshold));
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleAssigmentRest;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link SoftwareModuleAssigmentRest}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class SoftwareModuleAssigmentBuilder {
|
||||
|
||||
private final List<Long> ids;
|
||||
|
||||
public SoftwareModuleAssigmentBuilder() {
|
||||
ids = new ArrayList<Long>();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param id
|
||||
* the id of the software module
|
||||
* @return the builder itself
|
||||
*/
|
||||
public SoftwareModuleAssigmentBuilder id(final Long id) {
|
||||
ids.add(id);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of {@link SoftwareModuleAssigmentRest}
|
||||
* which can directly be used in the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link SoftwareModuleAssigmentRest}
|
||||
*/
|
||||
public List<SoftwareModuleAssigmentRest> build() {
|
||||
final List<SoftwareModuleAssigmentRest> softwareModuleAssigmentRestList = new ArrayList<>();
|
||||
for (final Long id : ids) {
|
||||
final SoftwareModuleAssigmentRest softwareModuleAssigmentRest = new SoftwareModuleAssigmentRest();
|
||||
softwareModuleAssigmentRest.setId(id);
|
||||
softwareModuleAssigmentRestList.add(softwareModuleAssigmentRest);
|
||||
}
|
||||
return softwareModuleAssigmentRestList;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,101 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleRequestBodyPost;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link SoftwareModuleRequestBodyPost}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class SoftwareModuleBuilder {
|
||||
|
||||
private String name;
|
||||
private String version;
|
||||
private String type;
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the software module
|
||||
* @return the builder itself
|
||||
*/
|
||||
public SoftwareModuleBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param version
|
||||
* the version of the software module
|
||||
* @return the builder itsefl
|
||||
*/
|
||||
public SoftwareModuleBuilder version(final String version) {
|
||||
this.version = version;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param type
|
||||
* the key of the software module type to be used for this
|
||||
* software module
|
||||
* @return the builder itself
|
||||
*/
|
||||
public SoftwareModuleBuilder type(final String type) {
|
||||
this.type = type;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of
|
||||
* {@link SoftwareModuleRequestBodyPost} which can directly be used in the
|
||||
* RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link SoftwareModuleRequestBodyPost}
|
||||
*/
|
||||
public List<SoftwareModuleRequestBodyPost> build() {
|
||||
return Lists.newArrayList(doBuild(name));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link SoftwareModuleRequestBodyPost} to create
|
||||
* multiple software module at once. An increasing number will be added to
|
||||
* the name of the software module. The version and type will remain the
|
||||
* same.
|
||||
*
|
||||
* @param count
|
||||
* the amount of software module body which should be created
|
||||
* @return a list of {@link DistributionSetTypeRequestBodyPost}
|
||||
*/
|
||||
public List<SoftwareModuleRequestBodyPost> buildAsList(final int count) {
|
||||
final ArrayList<SoftwareModuleRequestBodyPost> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(name + index));
|
||||
}
|
||||
|
||||
return bodyList;
|
||||
}
|
||||
|
||||
private SoftwareModuleRequestBodyPost doBuild(final String prefixName) {
|
||||
final SoftwareModuleRequestBodyPost body = new SoftwareModuleRequestBodyPost();
|
||||
body.setName(prefixName);
|
||||
body.setVersion(version);
|
||||
body.setType(type);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,101 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPost;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link SoftwareModuleRequestBodyPost}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class SoftwareModuleTypeBuilder {
|
||||
|
||||
private String key;
|
||||
private String name;
|
||||
private String description;
|
||||
private int maxAssignments;
|
||||
|
||||
/**
|
||||
* @param key
|
||||
* the key of the software module type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public SoftwareModuleTypeBuilder key(final String key) {
|
||||
this.key = key;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the software module type
|
||||
* @return the builder itself
|
||||
*/
|
||||
public SoftwareModuleTypeBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
public SoftwareModuleTypeBuilder description(final String description) {
|
||||
this.description = description;
|
||||
return this;
|
||||
}
|
||||
|
||||
public SoftwareModuleTypeBuilder maxAssignments(final int maxAssignments) {
|
||||
this.maxAssignments = maxAssignments;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of
|
||||
* {@link SoftwareModuleTypeRequestBodyPost} which can directly be used in
|
||||
* the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link SoftwareModuleTypeRequestBodyPost}
|
||||
*/
|
||||
public List<SoftwareModuleTypeRequestBodyPost> build() {
|
||||
return Lists.newArrayList(doBuild(key, name));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link SoftwareModuleTypeRequestBodyPost} to
|
||||
* create multiple software module types at once. An increasing number will
|
||||
* be added to the name and key of the software module type.
|
||||
*
|
||||
* @param count
|
||||
* the amount of software module type bodies which should be
|
||||
* created
|
||||
* @return a list of {@link SoftwareModuleTypeRequestBodyPost}
|
||||
*/
|
||||
public List<SoftwareModuleTypeRequestBodyPost> buildAsList(final int count) {
|
||||
final ArrayList<SoftwareModuleTypeRequestBodyPost> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(key + index, name + index));
|
||||
}
|
||||
return bodyList;
|
||||
}
|
||||
|
||||
private SoftwareModuleTypeRequestBodyPost doBuild(final String prefixKey, final String prefixName) {
|
||||
final SoftwareModuleTypeRequestBodyPost body = new SoftwareModuleTypeRequestBodyPost();
|
||||
body.setKey(prefixKey);
|
||||
body.setName(prefixName);
|
||||
body.setDescription(description);
|
||||
body.setMaxAssignments(maxAssignments);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,96 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
* Builder pattern for building {@link TagRequestBodyPut}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class TagBuilder {
|
||||
|
||||
private String name;
|
||||
private String description;
|
||||
private String color;
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the tag
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TagBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param description
|
||||
* the description of the tag
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TagBuilder description(final String description) {
|
||||
this.description = description;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param color
|
||||
* the colour of the tag
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TagBuilder color(final String color) {
|
||||
this.color = color;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of {@link TagRequestBodyPut} which can
|
||||
* directly be used in the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link TagRequestBodyPut}
|
||||
*/
|
||||
public List<TagRequestBodyPut> build() {
|
||||
return Lists.newArrayList(doBuild(name));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link TagRequestBodyPut} to create multiple
|
||||
* tags at once. An increasing number will be added to the name of the tag.
|
||||
* The color and description will remain the same.
|
||||
*
|
||||
* @param count
|
||||
* the amount of distribution sets body which should be created
|
||||
* @return a list of {@link TagRequestBodyPut}
|
||||
*/
|
||||
public List<TagRequestBodyPut> buildAsList(final int count) {
|
||||
final ArrayList<TagRequestBodyPut> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(name + index));
|
||||
}
|
||||
|
||||
return bodyList;
|
||||
}
|
||||
|
||||
private TagRequestBodyPut doBuild(final String prefixName) {
|
||||
final TagRequestBodyPut body = new TagRequestBodyPut();
|
||||
body.setName(prefixName);
|
||||
body.setDescription(description);
|
||||
body.setColour(color);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.resource.builder;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRequestBody;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
/**
|
||||
*
|
||||
* Builder pattern for building {@link TargetRequestBody}.
|
||||
*
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
public class TargetBuilder {
|
||||
|
||||
private String controllerId;
|
||||
private String name;
|
||||
private String description;
|
||||
|
||||
/**
|
||||
* @param controllerId
|
||||
* the ID of the controller/target
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TargetBuilder controllerId(final String controllerId) {
|
||||
this.controllerId = controllerId;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* the name of the target
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TargetBuilder name(final String name) {
|
||||
this.name = name;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param description
|
||||
* the description of the target
|
||||
* @return the builder itself
|
||||
*/
|
||||
public TargetBuilder description(final String description) {
|
||||
this.description = description;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list with a single entry of {@link TargetRequestBody} which can
|
||||
* directly be used in the RESTful-API.
|
||||
*
|
||||
* @return a single entry list of {@link TargetRequestBody}
|
||||
*/
|
||||
public List<TargetRequestBody> build() {
|
||||
return Lists.newArrayList(doBuild(controllerId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a list of multiple {@link TargetRequestBody} to create multiple
|
||||
* targets at once. An increasing number will be added to the controllerId
|
||||
* of the target. The name and description will remain.
|
||||
*
|
||||
* @param count
|
||||
* the amount of software module type bodies which should be
|
||||
* created
|
||||
* @return a list of {@link SoftwareModuleTypeRequestBodyPost}
|
||||
*/
|
||||
public List<TargetRequestBody> buildAsList(final int count) {
|
||||
final ArrayList<TargetRequestBody> bodyList = Lists.newArrayList();
|
||||
for (int index = 0; index < count; index++) {
|
||||
bodyList.add(doBuild(controllerId + index));
|
||||
}
|
||||
return bodyList;
|
||||
}
|
||||
|
||||
private TargetRequestBody doBuild(final String prefixControllerId) {
|
||||
final TargetRequestBody body = new TargetRequestBody();
|
||||
body.setControllerId(prefixControllerId);
|
||||
body.setName(name);
|
||||
body.setDescription(description);
|
||||
return body;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.scenarios;
|
||||
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.DistributionSetResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.DistributionSetTypeResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.RolloutResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.SoftwareModuleResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.SoftwareModuleTypeResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.TargetResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.DistributionSetBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.DistributionSetTypeBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.RolloutBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleAssigmentBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleTypeBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.TargetBuilder;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutResponseBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModulesRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypesRest;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
* Example for creating and starting a Rollout.
|
||||
*
|
||||
*/
|
||||
@Component
|
||||
public class CreateStartedRolloutExample {
|
||||
|
||||
/* known software module type name and key */
|
||||
private static final String SM_MODULE_TYPE = "firmware";
|
||||
|
||||
/* known distribution set type name and key */
|
||||
private static final String DS_MODULE_TYPE = "firmware";
|
||||
|
||||
@Autowired
|
||||
private DistributionSetResourceClient distributionSetResource;
|
||||
|
||||
@Autowired
|
||||
private SoftwareModuleResourceClient softwareModuleResource;
|
||||
|
||||
@Autowired
|
||||
private TargetResourceClient targetResource;
|
||||
|
||||
@Autowired
|
||||
private RolloutResourceClient rolloutResource;
|
||||
|
||||
@Autowired
|
||||
private DistributionSetTypeResourceClient distributionSetTypeResource;
|
||||
|
||||
@Autowired
|
||||
private SoftwareModuleTypeResourceClient softwareModuleTypeResource;
|
||||
|
||||
/**
|
||||
* Run the Rollout scenario.
|
||||
*/
|
||||
public void run() {
|
||||
|
||||
// create three SoftwareModuleTypes
|
||||
final SoftwareModuleTypesRest createdSoftwareModuleTypes = softwareModuleTypeResource.createSoftwareModuleTypes(
|
||||
new SoftwareModuleTypeBuilder().key(SM_MODULE_TYPE).name(SM_MODULE_TYPE).maxAssignments(1).build())
|
||||
.getBody();
|
||||
|
||||
// create one DistributionSetType
|
||||
distributionSetTypeResource.createDistributionSetTypes(new DistributionSetTypeBuilder().key(DS_MODULE_TYPE)
|
||||
.name(DS_MODULE_TYPE).mandatorymodules(createdSoftwareModuleTypes.get(0).getModuleId()).build())
|
||||
.getBody();
|
||||
|
||||
// create one DistributionSet
|
||||
final DistributionSetsRest distributionSetsRest = distributionSetResource.createDistributionSets(
|
||||
new DistributionSetBuilder().name("rollout-example").version("1.0.0").type(DS_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
// create three SoftwareModules
|
||||
final SoftwareModulesRest softwareModulesRest = softwareModuleResource
|
||||
.createSoftwareModules(
|
||||
new SoftwareModuleBuilder().name("firmware").version("1.0.0").type(SM_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
// Assign SoftwareModule to DistributionSet
|
||||
distributionSetResource.assignSoftwareModules(distributionSetsRest.get(0).getDsId(),
|
||||
new SoftwareModuleAssigmentBuilder().id(softwareModulesRest.get(0).getModuleId()).build());
|
||||
|
||||
// create ten targets
|
||||
targetResource.createTargets(new TargetBuilder().controllerId("00-FF-AA-0").name("00-FF-AA-0")
|
||||
.description("Targets used for rollout example").buildAsList(10));
|
||||
|
||||
// create a Rollout
|
||||
final RolloutResponseBody rolloutResponseBody = rolloutResource
|
||||
.create(new RolloutBuilder().name("MyRollout").groupSize(2).targetFilterQuery("name==00-FF-AA-0*")
|
||||
.distributionSetId(distributionSetsRest.get(0).getDsId()).successThreshold("80")
|
||||
.errorThreshold("50").build())
|
||||
.getBody();
|
||||
|
||||
// start the created Rollout
|
||||
rolloutResource.start(rolloutResponseBody.getRolloutId(), false);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,134 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.client.scenarios;
|
||||
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.DistributionSetResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.DistributionSetTypeResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.SoftwareModuleResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.SoftwareModuleTypeResourceClient;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.DistributionSetBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.DistributionSetTypeBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleAssigmentBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleBuilder;
|
||||
import org.eclipse.hawkbit.mgmt.client.resource.builder.SoftwareModuleTypeBuilder;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModulesRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypesRest;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
*
|
||||
* Default getting started scenario.
|
||||
*
|
||||
*/
|
||||
@Component
|
||||
public class GettingStartedDefaultScenario {
|
||||
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(GettingStartedDefaultScenario.class);
|
||||
|
||||
/* known software module type name and key */
|
||||
private static final String SM_MODULE_TYPE = "gettingstarted";
|
||||
|
||||
/* known distribution set type name and key */
|
||||
private static final String DS_MODULE_TYPE = "gettingstarted";
|
||||
|
||||
/* known distribution name of this getting started example */
|
||||
private static final String SM_EXAMPLE_NAME = "gettingstarted-example";
|
||||
|
||||
/* known distribution name of this getting started example */
|
||||
private static final String DS_EXAMPLE_NAME = "gettingstarted-example";
|
||||
|
||||
@Autowired
|
||||
private DistributionSetResourceClient distributionSetResource;
|
||||
|
||||
@Autowired
|
||||
private DistributionSetTypeResourceClient distributionSetTypeResource;
|
||||
|
||||
@Autowired
|
||||
private SoftwareModuleResourceClient softwareModuleResource;
|
||||
|
||||
@Autowired
|
||||
private SoftwareModuleTypeResourceClient softwareModuleTypeResource;
|
||||
|
||||
/**
|
||||
* Run the default getting started scenario.
|
||||
*/
|
||||
public void run() {
|
||||
|
||||
LOGGER.info("Running Getting-Started-Scenario...");
|
||||
|
||||
// create one SoftwareModuleTypes
|
||||
LOGGER.info("Creating software module type {}", SM_MODULE_TYPE);
|
||||
final SoftwareModuleTypesRest createdSoftwareModuleTypes = softwareModuleTypeResource.createSoftwareModuleTypes(
|
||||
new SoftwareModuleTypeBuilder().key(SM_MODULE_TYPE).name(SM_MODULE_TYPE).maxAssignments(1).build())
|
||||
.getBody();
|
||||
|
||||
// create one DistributionSetType
|
||||
LOGGER.info("Creating distribution set type {}", DS_MODULE_TYPE);
|
||||
distributionSetTypeResource.createDistributionSetTypes(new DistributionSetTypeBuilder().key(DS_MODULE_TYPE)
|
||||
.name(DS_MODULE_TYPE).mandatorymodules(createdSoftwareModuleTypes.get(0).getModuleId()).build());
|
||||
|
||||
// create three DistributionSet
|
||||
final String dsVersion1 = "1.0.0";
|
||||
final String dsVersion2 = "2.0.0";
|
||||
final String dsVersion3 = "2.1.0";
|
||||
|
||||
LOGGER.info("Creating distribution set {}:{}", DS_EXAMPLE_NAME, dsVersion1);
|
||||
final DistributionSetsRest distributionSetsRest1 = distributionSetResource.createDistributionSets(
|
||||
new DistributionSetBuilder().name(DS_EXAMPLE_NAME).version(dsVersion1).type(DS_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
LOGGER.info("Creating distribution set {}:{}", DS_EXAMPLE_NAME, dsVersion2);
|
||||
final DistributionSetsRest distributionSetsRest2 = distributionSetResource.createDistributionSets(
|
||||
new DistributionSetBuilder().name(DS_EXAMPLE_NAME).version(dsVersion2).type(DS_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
LOGGER.info("Creating distribution set {}:{}", DS_EXAMPLE_NAME, dsVersion3);
|
||||
final DistributionSetsRest distributionSetsRest3 = distributionSetResource.createDistributionSets(
|
||||
new DistributionSetBuilder().name(DS_EXAMPLE_NAME).version(dsVersion3).type(DS_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
// create three SoftwareModules
|
||||
final String swVersion1 = "1";
|
||||
final String swVersion2 = "2";
|
||||
final String swVersion3 = "3";
|
||||
|
||||
LOGGER.info("Creating distribution set {}:{}", SM_EXAMPLE_NAME, swVersion1);
|
||||
final SoftwareModulesRest softwareModulesRest1 = softwareModuleResource.createSoftwareModules(
|
||||
new SoftwareModuleBuilder().name(SM_EXAMPLE_NAME).version(swVersion1).type(SM_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
LOGGER.info("Creating distribution set {}:{}", SM_EXAMPLE_NAME, swVersion2);
|
||||
final SoftwareModulesRest softwareModulesRest2 = softwareModuleResource.createSoftwareModules(
|
||||
new SoftwareModuleBuilder().name(SM_EXAMPLE_NAME).version(swVersion2).type(SM_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
LOGGER.info("Creating distribution set {}:{}", SM_EXAMPLE_NAME, swVersion3);
|
||||
final SoftwareModulesRest softwareModulesRest3 = softwareModuleResource.createSoftwareModules(
|
||||
new SoftwareModuleBuilder().name(SM_EXAMPLE_NAME).version(swVersion3).type(SM_MODULE_TYPE).build())
|
||||
.getBody();
|
||||
|
||||
// Assign SoftwareModules to DistributionSet
|
||||
LOGGER.info("Assign software module {}:{} to distribution set {}:{}", SM_EXAMPLE_NAME, swVersion1,
|
||||
DS_EXAMPLE_NAME, dsVersion1);
|
||||
distributionSetResource.assignSoftwareModules(distributionSetsRest1.get(0).getDsId(),
|
||||
new SoftwareModuleAssigmentBuilder().id(softwareModulesRest1.get(0).getModuleId()).build());
|
||||
|
||||
LOGGER.info("Assign software module {}:{} to distribution set {}:{}", SM_EXAMPLE_NAME, swVersion2,
|
||||
DS_EXAMPLE_NAME, dsVersion2);
|
||||
distributionSetResource.assignSoftwareModules(distributionSetsRest2.get(0).getDsId(),
|
||||
new SoftwareModuleAssigmentBuilder().id(softwareModulesRest2.get(0).getModuleId()).build());
|
||||
|
||||
LOGGER.info("Assign software module {}:{} to distribution set {}:{}", SM_EXAMPLE_NAME, swVersion3,
|
||||
DS_EXAMPLE_NAME, dsVersion3);
|
||||
distributionSetResource.assignSoftwareModules(distributionSetsRest3.get(0).getDsId(),
|
||||
new SoftwareModuleAssigmentBuilder().id(softwareModulesRest3.get(0).getModuleId()).build());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
#
|
||||
# Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
#
|
||||
# All rights reserved. This program and the accompanying materials
|
||||
# are made available under the terms of the Eclipse Public License v1.0
|
||||
# which accompanies this distribution, and is available at
|
||||
# http://www.eclipse.org/legal/epl-v10.html
|
||||
#
|
||||
|
||||
hawkbit.url=localhost:8080
|
||||
hawkbit.username=admin
|
||||
hawkbit.password=admin
|
||||
|
||||
spring.main.banner-mode=OFF
|
||||
@@ -0,0 +1,30 @@
|
||||
<!-- Copyright (c) 2015 Bosch Software Innovations GmbH and others. All rights reserved. This program and the accompanying
|
||||
materials are made available under the terms of the Eclipse Public License v1.0 which accompanies this distribution, and
|
||||
is available at http://www.eclipse.org/legal/epl-v10.html -->
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
|
||||
Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
which accompanies this distribution, and is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
|
||||
-->
|
||||
<configuration>
|
||||
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
|
||||
<!-- Log message format -->
|
||||
<encoder>
|
||||
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
|
||||
</pattern>
|
||||
</encoder>
|
||||
</appender>
|
||||
|
||||
<logger name="org.eclipse.hawkbit" level="info" />
|
||||
|
||||
<root level="error">
|
||||
<appender-ref ref="STDOUT" />
|
||||
</root>
|
||||
|
||||
</configuration>
|
||||
@@ -1,186 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.app.Start;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedDistributionSetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.DistributionSetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.junit.Before;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Ignore;
|
||||
import org.junit.Test;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.context.annotation.Description;
|
||||
|
||||
import ru.yandex.qatools.allure.annotations.Features;
|
||||
import ru.yandex.qatools.allure.annotations.Stories;
|
||||
import feign.Feign;
|
||||
import feign.Logger;
|
||||
import feign.auth.BasicAuthRequestInterceptor;
|
||||
import feign.jackson.JacksonDecoder;
|
||||
import feign.jackson.JacksonEncoder;
|
||||
|
||||
@Features("Example Tests - Management RESTful API Client")
|
||||
@Stories("DistrubutionSet Tag Resource")
|
||||
public class DistributionSetTagTest {
|
||||
|
||||
private DistrubutionSetTagResource distrubutionSetTagResource;
|
||||
|
||||
private static List<AssignedDistributionSetRequestBody> assignedTargetRequestBodies;
|
||||
|
||||
@BeforeClass
|
||||
public static void startupServer() {
|
||||
SpringApplication.run(Start.class, new String[0]);
|
||||
createTargetsAssignment();
|
||||
assignedTargetRequestBodies.add(new AssignedDistributionSetRequestBody().setDistributionSetId(100L));
|
||||
}
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
this.distrubutionSetTagResource = createDistrubutionSetTagResource();
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of distrubutionset tag by ID")
|
||||
@Ignore
|
||||
public void getDistributionSetTag() {
|
||||
final TagsRest result = createDistributionSetTags(2);
|
||||
|
||||
assertThat(distrubutionSetTagResource.getDistributionSetTag(result.get(0).getTagId()).getName()).isEqualTo(
|
||||
"Tag0");
|
||||
|
||||
deleteDistributionSets(result);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple update of a distrubutionset tag")
|
||||
@Ignore
|
||||
public void updateDistributionSetTag() {
|
||||
final TagsRest created = createDistributionSetTags(10);
|
||||
|
||||
distrubutionSetTagResource.updateDistributionSetTag(created.get(0).getTagId(), new TagRequestBodyPut()
|
||||
.setDescription("Test").setName("Test").setColour("Green"));
|
||||
|
||||
final TagRest targetTag = distrubutionSetTagResource.getDistributionSetTag(created.get(0).getTagId());
|
||||
assertThat(targetTag.getName()).isEqualTo("Test");
|
||||
assertThat(targetTag.getDescription()).isEqualTo("Test");
|
||||
assertThat(targetTag.getColour()).isEqualTo("Green");
|
||||
|
||||
deleteDistributionSets(created);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of all assigned distrubutionsets by a distrubutionset tag.")
|
||||
@Ignore
|
||||
public void getDistributionSetByTagId() {
|
||||
final TagsRest created = createDistributionSetTags(10);
|
||||
distrubutionSetTagResource.assignDistributionSets(created.get(2).getTagId(), assignedTargetRequestBodies);
|
||||
|
||||
final DistributionSetsRest distributionSetsRest = distrubutionSetTagResource
|
||||
.getAssignedDistributionSets(created.get(2).getTagId());
|
||||
assertThat(distributionSetsRest).hasSize(5);
|
||||
|
||||
distrubutionSetTagResource.unassignDistributionSets(created.get(2).getTagId());
|
||||
deleteDistributionSets(created);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Toggle request to unassigned all assigned distrubutionset and assign all unassigned distrubutionset.")
|
||||
@Ignore
|
||||
public void toggleTagAssignment() {
|
||||
final TagsRest created = createDistributionSetTags(10);
|
||||
final Long id = created.get(2).getTagId();
|
||||
|
||||
distrubutionSetTagResource.assignDistributionSets(id, assignedTargetRequestBodies);
|
||||
distrubutionSetTagResource.unassignDistributionSet(id, assignedTargetRequestBodies.get(0)
|
||||
.getDistributionSetId());
|
||||
|
||||
DistributionSetTagAssigmentResultRest assigmentResultRest = distrubutionSetTagResource.toggleTagAssignment(id,
|
||||
assignedTargetRequestBodies);
|
||||
|
||||
final TagRest targetTag = distrubutionSetTagResource.getDistributionSetTag(created.get(2).getTagId());
|
||||
assertThat(assigmentResultRest.getAssignedDistributionSets()).hasSize(1);
|
||||
assertThat(assigmentResultRest.getUnassignedDistributionSets()).hasSize(0);
|
||||
|
||||
assigmentResultRest = distrubutionSetTagResource.toggleTagAssignment(id, assignedTargetRequestBodies);
|
||||
assertThat(assigmentResultRest.getAssignedDistributionSets()).hasSize(0);
|
||||
assertThat(assigmentResultRest.getUnassignedDistributionSets()).hasSize(5);
|
||||
|
||||
distrubutionSetTagResource.unassignDistributionSets(targetTag.getTagId());
|
||||
deleteDistributionSets(created);
|
||||
}
|
||||
|
||||
private void deleteDistributionSets(final List<TagRest> tags) {
|
||||
for (final TagRest tag : tags) {
|
||||
distrubutionSetTagResource.deleteDistributionSetTag(tag.getTagId());
|
||||
}
|
||||
}
|
||||
|
||||
private TagsRest createDistributionSetTags(final int number) {
|
||||
|
||||
final List<TagRequestBodyPut> tags = new ArrayList<>();
|
||||
for (int i = 0; i < number; i++) {
|
||||
tags.add(new TagRequestBodyPut().setDescription("Tag " + i).setName("Tag" + i).setColour("Red"));
|
||||
}
|
||||
|
||||
final TagsRest result = distrubutionSetTagResource.createDistributionSetTags(tags);
|
||||
|
||||
assertThat(result).hasSize(number);
|
||||
return result;
|
||||
}
|
||||
|
||||
private DistrubutionSetTagResource createDistrubutionSetTagResource() {
|
||||
final DistrubutionSetTagResource distrubutionSetTagResource = Feign.builder().logger(new Logger.ErrorLogger())
|
||||
.logLevel(Logger.Level.BASIC).decoder(new JacksonDecoder()).encoder(new JacksonEncoder())
|
||||
.requestInterceptor(new BasicAuthRequestInterceptor("admin", "admin"))
|
||||
.target(DistrubutionSetTagResource.class, "http://localhost:8080");
|
||||
return distrubutionSetTagResource;
|
||||
}
|
||||
|
||||
private static void createTargetsAssignment() {
|
||||
|
||||
final List<DistributionSetRequestBodyPost> sets = new ArrayList<>();
|
||||
assignedTargetRequestBodies = new ArrayList<>();
|
||||
for (int i = 0; i < 5; i++) {
|
||||
final DistributionSetRequestBodyPost bodyPost = (DistributionSetRequestBodyPost) new DistributionSetRequestBodyPost()
|
||||
.setName("Ds" + i).setDescription("Ds" + i).setVersion("" + i);
|
||||
sets.add(bodyPost);
|
||||
}
|
||||
|
||||
final DistributionSetsRest result = createDistributionSetResource().createDistributionSets(sets);
|
||||
for (final DistributionSetRest rest : result) {
|
||||
assignedTargetRequestBodies.add(new AssignedDistributionSetRequestBody().setDistributionSetId(rest
|
||||
.getDsId()));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static DistributionSetResource createDistributionSetResource() {
|
||||
final DistributionSetResource distributionSetResource = Feign.builder().logger(new Logger.ErrorLogger())
|
||||
.logLevel(Logger.Level.BASIC).decoder(new JacksonDecoder()).encoder(new JacksonEncoder())
|
||||
.requestInterceptor(new BasicAuthRequestInterceptor("admin", "admin"))
|
||||
.target(DistributionSetResource.class, "http://localhost:8080");
|
||||
return distributionSetResource;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,182 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.app.Start;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedTargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TargetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
import org.junit.Before;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Ignore;
|
||||
import org.junit.Test;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.context.annotation.Description;
|
||||
|
||||
import ru.yandex.qatools.allure.annotations.Features;
|
||||
import ru.yandex.qatools.allure.annotations.Stories;
|
||||
import feign.Feign;
|
||||
import feign.Logger;
|
||||
import feign.auth.BasicAuthRequestInterceptor;
|
||||
import feign.jackson.JacksonDecoder;
|
||||
import feign.jackson.JacksonEncoder;
|
||||
|
||||
@Features("Example Tests - Management RESTful API Client")
|
||||
@Stories("Target Tag Resource")
|
||||
public class TargetTagTest {
|
||||
|
||||
private TargetTagResource targetTagResource;
|
||||
|
||||
private static List<AssignedTargetRequestBody> assignedTargetRequestBodies;
|
||||
|
||||
@BeforeClass
|
||||
public static void startupServer() {
|
||||
SpringApplication.run(Start.class, new String[0]);
|
||||
createTargetsAssignment();
|
||||
assignedTargetRequestBodies.add(new AssignedTargetRequestBody().setControllerId("NotExist"));
|
||||
}
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
this.targetTagResource = createTargetTagResource();
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of target tag by ID")
|
||||
@Ignore
|
||||
public void getTargetTag() {
|
||||
final TagsRest result = createTargetTags(2);
|
||||
|
||||
assertThat(targetTagResource.getTargetTag(result.get(0).getTagId()).getName()).isEqualTo("Tag0");
|
||||
|
||||
deleteTargets(result);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple update of a target tag")
|
||||
@Ignore
|
||||
public void updateTargetTag() {
|
||||
final TagsRest created = createTargetTags(10);
|
||||
|
||||
targetTagResource.updateTagretTag(created.get(0).getTagId(), new TagRequestBodyPut().setDescription("Test")
|
||||
.setName("Test").setColour("Green"));
|
||||
|
||||
final TagRest targetTag = targetTagResource.getTargetTag(created.get(0).getTagId());
|
||||
assertThat(targetTag.getName()).isEqualTo("Test");
|
||||
assertThat(targetTag.getDescription()).isEqualTo("Test");
|
||||
assertThat(targetTag.getColour()).isEqualTo("Green");
|
||||
|
||||
deleteTargets(created);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of all assigned targets by a target tag.")
|
||||
@Ignore
|
||||
public void getTargetsByTargetTagId() {
|
||||
final TagsRest created = createTargetTags(10);
|
||||
final Long tagId = created.get(2).getTagId();
|
||||
targetTagResource.assignTargets(tagId, assignedTargetRequestBodies);
|
||||
|
||||
final TagRest targetTag = targetTagResource.getTargetTag(tagId);
|
||||
assertThat(targetTagResource.getAssignedTargets(tagId)).hasSize(5);
|
||||
|
||||
targetTagResource.unassignTargets(targetTag.getTagId());
|
||||
deleteTargets(created);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Toggle request to unassigned all assigned targets and assign all unassigned targets.")
|
||||
@Ignore
|
||||
public void toggleTagAssignment() {
|
||||
final TagsRest created = createTargetTags(10);
|
||||
final Long id = created.get(2).getTagId();
|
||||
|
||||
targetTagResource.assignTargets(id, assignedTargetRequestBodies);
|
||||
targetTagResource.unassignTarget(id, assignedTargetRequestBodies.get(0).getControllerId());
|
||||
|
||||
TargetTagAssigmentResultRest assigmentResultRest = targetTagResource.toggleTagAssignment(id,
|
||||
assignedTargetRequestBodies);
|
||||
|
||||
final TagRest targetTag = targetTagResource.getTargetTag(created.get(2).getTagId());
|
||||
assertThat(assigmentResultRest.getAssignedTargets()).hasSize(1);
|
||||
assertThat(assigmentResultRest.getUnassignedTargets()).hasSize(0);
|
||||
|
||||
assigmentResultRest = targetTagResource.toggleTagAssignment(id, assignedTargetRequestBodies);
|
||||
assertThat(assigmentResultRest.getAssignedTargets()).hasSize(0);
|
||||
assertThat(assigmentResultRest.getUnassignedTargets()).hasSize(5);
|
||||
|
||||
targetTagResource.unassignTargets(targetTag.getTagId());
|
||||
deleteTargets(created);
|
||||
}
|
||||
|
||||
private void deleteTargets(final List<TagRest> tags) {
|
||||
for (final TagRest tag : tags) {
|
||||
targetTagResource.deleteTargetTag(tag.getTagId());
|
||||
}
|
||||
}
|
||||
|
||||
private TagsRest createTargetTags(final int number) {
|
||||
|
||||
final List<TagRequestBodyPut> tags = new ArrayList<>();
|
||||
for (int i = 0; i < number; i++) {
|
||||
tags.add(new TagRequestBodyPut().setDescription("Tag " + i).setName("Tag" + i).setColour("Red"));
|
||||
}
|
||||
|
||||
final TagsRest result = targetTagResource.createTargetTag(tags);
|
||||
|
||||
assertThat(result).hasSize(number);
|
||||
return result;
|
||||
}
|
||||
|
||||
private TargetTagResource createTargetTagResource() {
|
||||
final TargetTagResource targetResource = Feign.builder().logger(new Logger.ErrorLogger())
|
||||
.logLevel(Logger.Level.BASIC).decoder(new JacksonDecoder()).encoder(new JacksonEncoder())
|
||||
.requestInterceptor(new BasicAuthRequestInterceptor("admin", "admin"))
|
||||
.target(TargetTagResource.class, "http://localhost:8080");
|
||||
return targetResource;
|
||||
}
|
||||
|
||||
private static void createTargetsAssignment() {
|
||||
|
||||
final List<TargetRequestBody> targets = new ArrayList<>();
|
||||
assignedTargetRequestBodies = new ArrayList<>();
|
||||
for (int i = 0; i < 5; i++) {
|
||||
|
||||
targets.add(new TargetRequestBody().setControllerId("test" + i).setName("testDevice"));
|
||||
}
|
||||
|
||||
final TargetsRest result = createTargetResource().createTargets(targets);
|
||||
for (final TargetRest rest : result) {
|
||||
assignedTargetRequestBodies.add(new AssignedTargetRequestBody().setControllerId(rest.getControllerId()));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static TargetResource createTargetResource() {
|
||||
final TargetResource targetResource = Feign.builder().logger(new Logger.ErrorLogger())
|
||||
.logLevel(Logger.Level.BASIC).decoder(new JacksonDecoder()).encoder(new JacksonEncoder())
|
||||
.requestInterceptor(new BasicAuthRequestInterceptor("admin", "admin"))
|
||||
.target(TargetResource.class, "http://localhost:8080");
|
||||
return targetResource;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,119 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.mgmt.api.client;
|
||||
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.app.Start;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Ignore;
|
||||
import org.junit.Test;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.context.annotation.Description;
|
||||
|
||||
import feign.Feign;
|
||||
import feign.Logger;
|
||||
import feign.auth.BasicAuthRequestInterceptor;
|
||||
import feign.jackson.JacksonDecoder;
|
||||
import feign.jackson.JacksonEncoder;
|
||||
import ru.yandex.qatools.allure.annotations.Features;
|
||||
import ru.yandex.qatools.allure.annotations.Stories;
|
||||
|
||||
@Features("Example Tests - Management RESTful API Client")
|
||||
@Stories("Target Resource")
|
||||
public class TargetTest {
|
||||
|
||||
@BeforeClass
|
||||
public static void startupServer() {
|
||||
SpringApplication.run(Start.class, new String[0]);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of target by ID")
|
||||
@Ignore
|
||||
public void getTarget() {
|
||||
final TargetResource targetResource = createTargetResource();
|
||||
final TargetsRest result = createTargets(targetResource, 1);
|
||||
|
||||
assertThat(targetResource.getTarget("test0").getName()).isEqualTo("testDevice");
|
||||
|
||||
deleteTargets(targetResource, result);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of all targets with defined page sizing information (i.e. offset and limit).")
|
||||
@Ignore
|
||||
public void getTargetsAsPagedListWithDefinedPageSizing() {
|
||||
final TargetResource targetResource = createTargetResource();
|
||||
final TargetsRest created = createTargets(targetResource, 20);
|
||||
|
||||
final TargetPagedList queryResult = targetResource.getTargets(0, 10);
|
||||
|
||||
assertThat(queryResult.getContent()).hasSize(10);
|
||||
assertThat(queryResult.getTotal()).isEqualTo(20);
|
||||
assertThat(queryResult.getSize()).isEqualTo(10);
|
||||
|
||||
deleteTargets(targetResource, created);
|
||||
}
|
||||
|
||||
// disabled as this runs not on CI environments.
|
||||
@Test
|
||||
@Description("Simple request of all targets with defualt paging parameters.")
|
||||
@Ignore
|
||||
public void getTargetsAsPagedListWithDefaultPageSizing() {
|
||||
final TargetResource targetResource = createTargetResource();
|
||||
final TargetsRest created = createTargets(targetResource, 20);
|
||||
|
||||
final TargetPagedList queryResult = targetResource.getTargets();
|
||||
|
||||
assertThat(queryResult.getContent()).hasSize(20);
|
||||
assertThat(queryResult.getTotal()).isEqualTo(20);
|
||||
assertThat(queryResult.getSize()).isEqualTo(20);
|
||||
|
||||
deleteTargets(targetResource, created);
|
||||
}
|
||||
|
||||
private void deleteTargets(final TargetResource targetResource, final List<TargetRest> targets) {
|
||||
for (final TargetRest targetRest : targets) {
|
||||
targetResource.deleteTarget(targetRest.getControllerId());
|
||||
}
|
||||
}
|
||||
|
||||
private TargetsRest createTargets(final TargetResource targetResource, final int number) {
|
||||
|
||||
final List<TargetRequestBody> targets = new ArrayList<>();
|
||||
for (int i = 0; i < number; i++) {
|
||||
|
||||
targets.add(new TargetRequestBody().setControllerId("test" + i).setName("testDevice"));
|
||||
}
|
||||
|
||||
final TargetsRest result = targetResource.createTargets(targets);
|
||||
|
||||
assertThat(result).hasSize(number);
|
||||
return result;
|
||||
}
|
||||
|
||||
private TargetResource createTargetResource() {
|
||||
final TargetResource targetResource = Feign.builder().logger(new Logger.ErrorLogger())
|
||||
.logLevel(Logger.Level.BASIC).decoder(new JacksonDecoder()).encoder(new JacksonEncoder())
|
||||
.requestInterceptor(new BasicAuthRequestInterceptor("admin", "admin"))
|
||||
.target(TargetResource.class, "http://localhost:8080");
|
||||
return targetResource;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -51,7 +51,16 @@ public enum TargetFields implements FieldNameProvider {
|
||||
*/
|
||||
ATTRIBUTE("targetInfo.controllerAttributes", true),
|
||||
|
||||
/**
|
||||
* distribution sets which is assigned to the target.
|
||||
*/
|
||||
ASSIGNEDDS("assignedDistributionSet", "name", "version"),
|
||||
|
||||
/**
|
||||
* distribution sets which is installed on the target.
|
||||
*/
|
||||
INSTALLEDDS("targetInfo.installedDistributionSet", "name", "version"),
|
||||
|
||||
/**
|
||||
* The tags field.
|
||||
*/
|
||||
|
||||
@@ -298,20 +298,7 @@ public class AmqpMessageHandlerService {
|
||||
*/
|
||||
private void updateActionStatus(final Message message) {
|
||||
final ActionUpdateStatus actionUpdateStatus = convertMessage(message, ActionUpdateStatus.class);
|
||||
final Long actionId = actionUpdateStatus.getActionId();
|
||||
LOG.debug("Target notifies intermediate about action {} with status {}.", actionId, actionUpdateStatus
|
||||
.getActionStatus().name());
|
||||
|
||||
if (actionId == null) {
|
||||
logAndThrowMessageError(message, "Invalid message no action id");
|
||||
}
|
||||
|
||||
final Action action = controllerManagement.findActionWithDetails(actionId);
|
||||
|
||||
if (action == null) {
|
||||
logAndThrowMessageError(message, "Got intermediate notification about action " + actionId
|
||||
+ " but action does not exist");
|
||||
}
|
||||
final Action action = checkActionExist(message, actionUpdateStatus);
|
||||
|
||||
final ActionStatus actionStatus = new ActionStatus();
|
||||
final List<String> messageText = actionUpdateStatus.getMessage();
|
||||
@@ -362,6 +349,29 @@ public class AmqpMessageHandlerService {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param message
|
||||
* @param actionUpdateStatus
|
||||
* @return
|
||||
*/
|
||||
private Action checkActionExist(final Message message, final ActionUpdateStatus actionUpdateStatus) {
|
||||
final Long actionId = actionUpdateStatus.getActionId();
|
||||
LOG.debug("Target notifies intermediate about action {} with status {}.", actionId, actionUpdateStatus
|
||||
.getActionStatus().name());
|
||||
|
||||
if (actionId == null) {
|
||||
logAndThrowMessageError(message, "Invalid message no action id");
|
||||
}
|
||||
|
||||
final Action action = controllerManagement.findActionWithDetails(actionId);
|
||||
|
||||
if (action == null) {
|
||||
logAndThrowMessageError(message, "Got intermediate notification about action " + actionId
|
||||
+ " but action does not exist");
|
||||
}
|
||||
return action;
|
||||
}
|
||||
|
||||
private void handleCancelRejected(final Message message, final Action action, final ActionStatus actionStatus) {
|
||||
if (action.isCancelingOrCanceled()) {
|
||||
|
||||
|
||||
@@ -45,7 +45,7 @@ import ru.yandex.qatools.allure.annotations.Stories;
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* Test Amqp controller authentfication.
|
||||
*/
|
||||
@Features("AMQP Authenfication Test")
|
||||
@Stories("Tests the authenfication")
|
||||
@@ -86,24 +86,34 @@ public class AmqpControllerAuthentficationTest {
|
||||
amqpMessageHandlerService.setAuthenticationManager(authenticationManager);
|
||||
}
|
||||
|
||||
@Test(expected = BadCredentialsException.class)
|
||||
@Test
|
||||
@Description("Tests authentication manager without principal")
|
||||
public void testAuthenticationeBadCredantialsWithoutPricipal() {
|
||||
final TenantSecruityToken securityToken = new TenantSecruityToken(TENANT, CONTROLLLER_ID, "12345");
|
||||
authenticationManager.doAuthenticate(securityToken);
|
||||
fail();
|
||||
try {
|
||||
authenticationManager.doAuthenticate(securityToken);
|
||||
fail("BadCredentialsException was excepeted since principal was missing");
|
||||
} catch (final BadCredentialsException exception) {
|
||||
// test ok - exception was excepted
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BadCredentialsException.class)
|
||||
@Description("Tests authentication manager without wrong credential")
|
||||
@Test
|
||||
@Description("Tests authentication manager without wrong credential")
|
||||
public void testAuthenticationBadCredantialsWithWrongCredential() {
|
||||
final TenantSecruityToken securityToken = new TenantSecruityToken(TENANT, CONTROLLLER_ID, "12345");
|
||||
when(systemManagement.getConfigurationValue(
|
||||
eq(TenantConfigurationKey.AUTHENTICATION_MODE_TARGET_SECURITY_TOKEN_ENABLED), any()))
|
||||
.thenReturn(Boolean.TRUE);
|
||||
securityToken.getHeaders().put(TenantSecruityToken.AUTHORIZATION_HEADER, "TargetToken 12" + CONTROLLLER_ID);
|
||||
authenticationManager.doAuthenticate(securityToken);
|
||||
fail();
|
||||
try {
|
||||
authenticationManager.doAuthenticate(securityToken);
|
||||
fail("BadCredentialsException was excepeted due to wrong credential");
|
||||
} catch (final BadCredentialsException exception) {
|
||||
// test ok - exception was excepted
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
@@ -161,7 +161,7 @@ public class RepositoryApplicationConfiguration extends JpaBaseConfiguration {
|
||||
@Override
|
||||
protected Map<String, Object> getVendorProperties() {
|
||||
|
||||
final Map<String, Object> properties = new HashMap<String, Object>();
|
||||
final Map<String, Object> properties = new HashMap<>();
|
||||
// Turn off dynamic weaving to disable LTW lookup in static weaving mode
|
||||
properties.put("eclipselink.weaving", "false");
|
||||
// needed for reports
|
||||
|
||||
@@ -8,19 +8,22 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.report.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
/**
|
||||
* A data report series which contains a list of {@link DataReportSeriesItem}.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
* @param <T>
|
||||
* the type of the report series item
|
||||
*/
|
||||
public class DataReportSeries<T extends Object> extends AbstractReportSeries {
|
||||
public class DataReportSeries<T extends Serializable> extends AbstractReportSeries {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private final List<DataReportSeriesItem<T>> data = new ArrayList<>();
|
||||
|
||||
@@ -46,7 +49,7 @@ public class DataReportSeries<T extends Object> extends AbstractReportSeries {
|
||||
}
|
||||
|
||||
private void setData(final List<DataReportSeriesItem<T>> values) {
|
||||
this.data.clear();
|
||||
data.clear();
|
||||
data.addAll(values);
|
||||
}
|
||||
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.report.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* An data report series item which contains a type and a value.
|
||||
*
|
||||
@@ -16,8 +18,9 @@ package org.eclipse.hawkbit.report.model;
|
||||
* @param <T>
|
||||
* the type of the report series item
|
||||
*/
|
||||
public class DataReportSeriesItem<T extends Object> {
|
||||
public class DataReportSeriesItem<T extends Serializable> implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
private final T type;
|
||||
private final Number data;
|
||||
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.report.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* A double data series which contains an inner and an outer series ideal for
|
||||
* showing donut charts.
|
||||
@@ -17,7 +19,7 @@ package org.eclipse.hawkbit.report.model;
|
||||
* @param <T>
|
||||
* The type parameter for the report series data
|
||||
*/
|
||||
public class InnerOuterDataReportSeries<T> {
|
||||
public class InnerOuterDataReportSeries<T extends Serializable> {
|
||||
|
||||
private final DataReportSeries<T> innerSeries;
|
||||
private final DataReportSeries<T> outerSeries;
|
||||
|
||||
@@ -15,7 +15,6 @@ import java.util.Map;
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Predicate;
|
||||
import javax.persistence.criteria.Root;
|
||||
import javax.validation.constraints.NotNull;
|
||||
|
||||
@@ -212,14 +211,9 @@ public class ControllerManagement implements EnvironmentAware {
|
||||
@Modifying
|
||||
@Transactional
|
||||
@PreAuthorize(SpringEvalExpressions.IS_CONTROLLER)
|
||||
public Target findOrRegisterTargetIfItDoesNotexist(@NotNull final String targetid, final URI address) {
|
||||
final Specification<Target> spec = new Specification<Target>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<Target> targetRoot, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
return cb.equal(targetRoot.get(Target_.controllerId), targetid);
|
||||
}
|
||||
};
|
||||
public Target findOrRegisterTargetIfItDoesNotexist(@NotEmpty final String targetid, final URI address) {
|
||||
final Specification<Target> spec = (targetRoot, query, cb) -> cb.equal(targetRoot.get(Target_.controllerId),
|
||||
targetid);
|
||||
|
||||
Target target = targetRepository.findOne(spec);
|
||||
|
||||
@@ -229,9 +223,9 @@ public class ControllerManagement implements EnvironmentAware {
|
||||
target.setName(targetid);
|
||||
return targetManagement.createTarget(target, TargetUpdateStatus.REGISTERED, System.currentTimeMillis(),
|
||||
address);
|
||||
} else {
|
||||
return updateLastTargetQuery(target.getTargetInfo(), address).getTarget();
|
||||
}
|
||||
|
||||
return updateLastTargetQuery(target.getTargetInfo(), address).getTarget();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -22,10 +22,6 @@ import java.util.stream.Collectors;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Predicate;
|
||||
import javax.persistence.criteria.Root;
|
||||
import javax.validation.constraints.NotNull;
|
||||
|
||||
import org.eclipse.hawkbit.eventbus.event.DistributionSetTagAssigmentResultEvent;
|
||||
@@ -53,13 +49,13 @@ import org.eclipse.hawkbit.repository.model.Tag;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.specifications.DistributionSetSpecification;
|
||||
import org.eclipse.hawkbit.repository.specifications.DistributionSetTypeSpecification;
|
||||
import org.eclipse.hawkbit.repository.specifications.SpecificationsBuilder;
|
||||
import org.hibernate.validator.constraints.NotEmpty;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.Page;
|
||||
import org.springframework.data.domain.PageImpl;
|
||||
import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.data.jpa.domain.Specifications;
|
||||
import org.springframework.data.jpa.repository.Modifying;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.stereotype.Service;
|
||||
@@ -203,7 +199,8 @@ public class DistributionSetManagement {
|
||||
}
|
||||
|
||||
final DistributionSetTagAssigmentResult resultAssignment = result;
|
||||
afterCommit.afterCommit(() -> eventBus.post(new DistributionSetTagAssigmentResultEvent(resultAssignment)));
|
||||
afterCommit
|
||||
.afterCommit(() -> eventBus.post(new DistributionSetTagAssigmentResultEvent(resultAssignment)));
|
||||
|
||||
// no reason to persist the tag
|
||||
entityManager.detach(myTag);
|
||||
@@ -263,7 +260,7 @@ public class DistributionSetManagement {
|
||||
@Transactional
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_DELETE_REPOSITORY)
|
||||
public void deleteDistributionSet(@NotNull final DistributionSet set) {
|
||||
this.deleteDistributionSet(set.getId());
|
||||
deleteDistributionSet(set.getId());
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -321,14 +318,10 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_CREATE_REPOSITORY)
|
||||
public DistributionSet createDistributionSet(@NotNull final DistributionSet dSet) {
|
||||
prepareDsSave(dSet);
|
||||
|
||||
if (dSet.getType() == null) {
|
||||
dSet.setType(systemManagement.getTenantMetadata().getDefaultDsType());
|
||||
}
|
||||
|
||||
final DistributionSet result = distributionSetRepository.save(dSet);
|
||||
|
||||
return result;
|
||||
return distributionSetRepository.save(dSet);
|
||||
}
|
||||
|
||||
private void prepareDsSave(final DistributionSet dSet) {
|
||||
@@ -400,7 +393,7 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_UPDATE_REPOSITORY)
|
||||
public DistributionSet unassignSoftwareModule(@NotNull final DistributionSet ds,
|
||||
final SoftwareModule softwareModule) {
|
||||
final Set<SoftwareModule> softwareModules = new HashSet<SoftwareModule>();
|
||||
final Set<SoftwareModule> softwareModules = new HashSet<>();
|
||||
softwareModules.add(softwareModule);
|
||||
ds.removeModule(softwareModule);
|
||||
checkDistributionSetSoftwareModulesIsAllowedToModify(ds, softwareModules);
|
||||
@@ -491,20 +484,11 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
private DistributionSet findDistributionSetsByFiltersAndInstalledOrAssignedTarget(
|
||||
final DistributionSetFilter distributionSetFilter) {
|
||||
|
||||
final List<Specification<DistributionSet>> specList = buildDistributionSetSpecifications(distributionSetFilter);
|
||||
|
||||
Specifications<DistributionSet> specs = null;
|
||||
if (!specList.isEmpty()) {
|
||||
specs = Specifications.where(specList.get(0));
|
||||
if (specList == null || specList.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
if (specList.size() > 1) {
|
||||
specList.remove(0);
|
||||
for (final Specification<DistributionSet> s : specList) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
return distributionSetRepository.findOne(specs);
|
||||
return distributionSetRepository.findOne(SpecificationsBuilder.combineWithAnd(specList));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -531,7 +515,7 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Page<DistributionSet> findDistributionSetsAll(@NotNull final Pageable pageReq, final Boolean deleted,
|
||||
final Boolean complete) {
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<Specification<DistributionSet>>();
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<>();
|
||||
|
||||
if (deleted != null) {
|
||||
final Specification<DistributionSet> spec = DistributionSetSpecification.isDeleted(deleted);
|
||||
@@ -563,7 +547,7 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Page<DistributionSet> findDistributionSetsAll(@NotNull final Specification<DistributionSet> spec,
|
||||
@NotNull final Pageable pageReq, final Boolean deleted) {
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<Specification<DistributionSet>>();
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<>();
|
||||
if (deleted != null) {
|
||||
specList.add(DistributionSetSpecification.isDeleted(deleted));
|
||||
}
|
||||
@@ -635,17 +619,6 @@ public class DistributionSetManagement {
|
||||
return new PageImpl<>(resultSet, pageable, findDistributionSetsByFilters.getTotalElements());
|
||||
}
|
||||
|
||||
private Long countDistributionSetByCriteriaAPI(@NotEmpty final List<Specification<DistributionSet>> specList) {
|
||||
Specifications<DistributionSet> specs = Specifications.where(specList.get(0));
|
||||
if (specList.size() > 1) {
|
||||
for (final Specification<DistributionSet> s : specList.subList(1, specList.size())) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
|
||||
return distributionSetRepository.count(specs);
|
||||
}
|
||||
|
||||
/**
|
||||
* Find distribution set by name and version.
|
||||
*
|
||||
@@ -689,12 +662,12 @@ public class DistributionSetManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Long countDistributionSetsAll() {
|
||||
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<Specification<DistributionSet>>();
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<>();
|
||||
|
||||
final Specification<DistributionSet> spec = DistributionSetSpecification.isDeleted(Boolean.FALSE);
|
||||
specList.add(spec);
|
||||
|
||||
return countDistributionSetByCriteriaAPI(specList);
|
||||
return distributionSetRepository.count(SpecificationsBuilder.combineWithAnd(specList));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -869,17 +842,10 @@ public class DistributionSetManagement {
|
||||
public Page<DistributionSetMetadata> findDistributionSetMetadataByDistributionSetId(
|
||||
@NotNull final Long distributionSetId, @NotNull final Pageable pageable) {
|
||||
|
||||
return distributionSetMetadataRepository.findAll(new Specification<DistributionSetMetadata>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<DistributionSetMetadata> root, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
|
||||
final Predicate predicate = cb.equal(
|
||||
root.get(DistributionSetMetadata_.distributionSet).get(DistributionSet_.id), distributionSetId);
|
||||
|
||||
return predicate;
|
||||
}
|
||||
}, pageable);
|
||||
return distributionSetMetadataRepository.findAll(
|
||||
(Specification<DistributionSetMetadata>) (root, query, cb) -> cb.equal(
|
||||
root.get(DistributionSetMetadata_.distributionSet).get(DistributionSet_.id), distributionSetId),
|
||||
pageable);
|
||||
|
||||
}
|
||||
|
||||
@@ -899,14 +865,14 @@ public class DistributionSetManagement {
|
||||
public Page<DistributionSetMetadata> findDistributionSetMetadataByDistributionSetId(
|
||||
@NotNull final Long distributionSetId, @NotNull final Specification<DistributionSetMetadata> spec,
|
||||
@NotNull final Pageable pageable) {
|
||||
return distributionSetMetadataRepository.findAll(new Specification<DistributionSetMetadata>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<DistributionSetMetadata> root, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
return cb.and(cb.equal(root.get(DistributionSetMetadata_.distributionSet).get(DistributionSet_.id),
|
||||
distributionSetId), spec.toPredicate(root, query, cb));
|
||||
}
|
||||
}, pageable);
|
||||
return distributionSetMetadataRepository
|
||||
.findAll(
|
||||
(Specification<DistributionSetMetadata>) (root, query,
|
||||
cb) -> cb.and(
|
||||
cb.equal(root.get(DistributionSetMetadata_.distributionSet)
|
||||
.get(DistributionSet_.id), distributionSetId),
|
||||
spec.toPredicate(root, query, cb)),
|
||||
pageable);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -956,7 +922,7 @@ public class DistributionSetManagement {
|
||||
|
||||
/**
|
||||
* Checking Distribution Set is already using while assign Software module.
|
||||
*
|
||||
*
|
||||
* @param distributionSet
|
||||
* @param softwareModules
|
||||
*/
|
||||
@@ -969,9 +935,9 @@ public class DistributionSetManagement {
|
||||
|
||||
private List<Specification<DistributionSet>> buildDistributionSetSpecifications(
|
||||
final DistributionSetFilter distributionSetFilter) {
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<Specification<DistributionSet>>();
|
||||
final List<Specification<DistributionSet>> specList = new ArrayList<>();
|
||||
|
||||
Specification<DistributionSet> spec = null;
|
||||
Specification<DistributionSet> spec;
|
||||
|
||||
if (null != distributionSetFilter.getIsComplete()) {
|
||||
spec = DistributionSetSpecification.isCompleted(distributionSetFilter.getIsComplete());
|
||||
@@ -1053,21 +1019,12 @@ public class DistributionSetManagement {
|
||||
*/
|
||||
private Page<DistributionSet> findByCriteriaAPI(@NotNull final Pageable pageable,
|
||||
final List<Specification<DistributionSet>> specList) {
|
||||
Specifications<DistributionSet> specs = null;
|
||||
if (!specList.isEmpty()) {
|
||||
specs = Specifications.where(specList.get(0));
|
||||
}
|
||||
if (specList.size() > 1) {
|
||||
for (final Specification<DistributionSet> s : specList.subList(1, specList.size())) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
|
||||
if (specList == null || specList.isEmpty()) {
|
||||
return distributionSetRepository.findAll(pageable);
|
||||
}
|
||||
|
||||
if (specs == null) {
|
||||
return distributionSetRepository.findAll(pageable);
|
||||
} else {
|
||||
return distributionSetRepository.findAll(specs, pageable);
|
||||
}
|
||||
return distributionSetRepository.findAll(SpecificationsBuilder.combineWithAnd(specList), pageable);
|
||||
}
|
||||
|
||||
private void checkAndThrowAlreadyIfDistributionSetMetadataExists(final DsMetadataCompositeKey metadataId) {
|
||||
|
||||
@@ -213,8 +213,8 @@ public class ReportManagement {
|
||||
* count
|
||||
*/
|
||||
@Cacheable("targetsCreatedOverPeriod")
|
||||
public <T> DataReportSeries<T> targetsCreatedOverPeriod(final DateType<T> dateType, final LocalDateTime from,
|
||||
final LocalDateTime to) {
|
||||
public <T extends Serializable> DataReportSeries<T> targetsCreatedOverPeriod(final DateType<T> dateType,
|
||||
final LocalDateTime from, final LocalDateTime to) {
|
||||
final Query createNativeQuery = entityManager
|
||||
.createNativeQuery(getTargetsCreatedQueryTemplate(dateType, from, to));
|
||||
final List<Object[]> resultList = createNativeQuery.getResultList();
|
||||
@@ -223,8 +223,7 @@ public class ReportManagement {
|
||||
.map(r -> new DataReportSeriesItem<>(dateType.format((String) r[0]), ((Number) r[1]).longValue()))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
final DataReportSeries<T> report = new DataReportSeries<>("CreatedTargets", reportItems);
|
||||
return report;
|
||||
return new DataReportSeries<>("CreatedTargets", reportItems);
|
||||
}
|
||||
|
||||
private String getTargetsCreatedQueryTemplate(final DateType<?> dateType, final LocalDateTime from,
|
||||
@@ -276,8 +275,8 @@ public class ReportManagement {
|
||||
* count
|
||||
*/
|
||||
@Cacheable("feedbackReceivedOverTime")
|
||||
public <T> DataReportSeries<T> feedbackReceivedOverTime(final DateType<T> dateType, final LocalDateTime from,
|
||||
final LocalDateTime to) {
|
||||
public <T extends Serializable> DataReportSeries<T> feedbackReceivedOverTime(final DateType<T> dateType,
|
||||
final LocalDateTime from, final LocalDateTime to) {
|
||||
final Query createNativeQuery = entityManager
|
||||
.createNativeQuery(getFeedbackReceivedQueryTemplate(dateType, from, to));
|
||||
final List<Object[]> resultList = createNativeQuery.getResultList();
|
||||
@@ -286,8 +285,7 @@ public class ReportManagement {
|
||||
.map(r -> new DataReportSeriesItem<>(dateType.format((String) r[0]), ((Number) r[1]).longValue()))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
final DataReportSeries<T> report = new DataReportSeries<>("FeedbackRecieved", reportItems);
|
||||
return report;
|
||||
return new DataReportSeries<>("FeedbackRecieved", reportItems);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -433,7 +431,7 @@ public class ReportManagement {
|
||||
}
|
||||
|
||||
private DataReportSeriesItem<String> toItem() {
|
||||
return new DataReportSeriesItem<String>(name.getName() != null ? name.getName() : "misc", count);
|
||||
return new DataReportSeriesItem<>(name.getName() != null ? name.getName() : "misc", count);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -245,8 +245,9 @@ public class RolloutGroupManagement {
|
||||
JoinType.LEFT);
|
||||
|
||||
final Root<RolloutTargetGroup> countQueryFrom = countQuery.distinct(true).from(RolloutTargetGroup.class);
|
||||
countQuery
|
||||
.select(cb.count(countQueryFrom.join(RolloutTargetGroup_.target).join(Target_.actions, JoinType.LEFT)))
|
||||
countQueryFrom.join(RolloutTargetGroup_.target);
|
||||
countQueryFrom.join(RolloutTargetGroup_.actions, JoinType.LEFT);
|
||||
countQuery.select(cb.count(countQueryFrom))
|
||||
.where(cb.equal(countQueryFrom.get(RolloutTargetGroup_.rolloutGroup), rolloutGroup));
|
||||
final Long totalCount = entityManager.createQuery(countQuery).getSingleResult();
|
||||
|
||||
|
||||
@@ -552,7 +552,7 @@ public class RolloutManagement {
|
||||
if (updated == 0) {
|
||||
// nothing to check, maybe another instance already checked in
|
||||
// between
|
||||
LOGGER.info("No rolloutcheck necessary for current scheduled check {}, next check at {}", lastCheck,
|
||||
LOGGER.debug("No rolloutcheck necessary for current scheduled check {}, next check at {}", lastCheck,
|
||||
lastCheck + delayBetweenChecks);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -40,6 +40,7 @@ import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule_;
|
||||
import org.eclipse.hawkbit.repository.model.SwMetadataCompositeKey;
|
||||
import org.eclipse.hawkbit.repository.specifications.SoftwareModuleSpecification;
|
||||
import org.eclipse.hawkbit.repository.specifications.SpecificationsBuilder;
|
||||
import org.hibernate.validator.constraints.NotEmpty;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.AuditorAware;
|
||||
@@ -48,7 +49,6 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.SliceImpl;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.data.jpa.domain.Specifications;
|
||||
import org.springframework.data.jpa.repository.Modifying;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.stereotype.Service;
|
||||
@@ -198,7 +198,7 @@ public class SoftwareManagement {
|
||||
/**
|
||||
* retrieves the {@link SoftwareModule}s by their {@link SoftwareModuleType}
|
||||
* .
|
||||
*
|
||||
*
|
||||
* @param pageable
|
||||
* page parameters
|
||||
* @param type
|
||||
@@ -209,7 +209,7 @@ public class SoftwareManagement {
|
||||
public Slice<SoftwareModule> findSoftwareModulesByType(@NotNull final Pageable pageable,
|
||||
@NotNull final SoftwareModuleType type) {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
Specification<SoftwareModule> spec = SoftwareModuleSpecification.equalType(type);
|
||||
specList.add(spec);
|
||||
@@ -230,7 +230,7 @@ public class SoftwareManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Long countSoftwareModulesByType(@NotNull final SoftwareModuleType type) {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
Specification<SoftwareModule> spec = SoftwareModuleSpecification.equalType(type);
|
||||
specList.add(spec);
|
||||
@@ -257,7 +257,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* retrieves {@link SoftwareModule}s by their name AND version.
|
||||
*
|
||||
*
|
||||
* @param name
|
||||
* of the {@link SoftwareModule}
|
||||
* @param version
|
||||
@@ -273,7 +273,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* Deletes the given {@link SoftwareModule} {@link Entity}.
|
||||
*
|
||||
*
|
||||
* @param bsm
|
||||
* is the {@link SoftwareModule} to be deleted
|
||||
*/
|
||||
@@ -291,26 +291,12 @@ public class SoftwareManagement {
|
||||
|
||||
private Slice<SoftwareModule> findSwModuleByCriteriaAPI(@NotNull final Pageable pageable,
|
||||
@NotEmpty final List<Specification<SoftwareModule>> specList) {
|
||||
|
||||
Specifications<SoftwareModule> specs = Specifications.where(specList.get(0));
|
||||
if (specList.size() > 1) {
|
||||
for (final Specification<SoftwareModule> s : specList.subList(1, specList.size())) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
|
||||
return criteriaNoCountDao.findAll(specs, pageable, SoftwareModule.class);
|
||||
return criteriaNoCountDao.findAll(SpecificationsBuilder.combineWithAnd(specList), pageable,
|
||||
SoftwareModule.class);
|
||||
}
|
||||
|
||||
private Long countSwModuleByCriteriaAPI(@NotEmpty final List<Specification<SoftwareModule>> specList) {
|
||||
Specifications<SoftwareModule> specs = Specifications.where(specList.get(0));
|
||||
if (specList.size() > 1) {
|
||||
for (final Specification<SoftwareModule> s : specList.subList(1, specList.size())) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
|
||||
return softwareModuleRepository.count(specs);
|
||||
return softwareModuleRepository.count(SpecificationsBuilder.combineWithAnd(specList));
|
||||
}
|
||||
|
||||
private void deleteGridFsArtifacts(final SoftwareModule swModule) {
|
||||
@@ -321,7 +307,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* Deletes {@link SoftwareModule}s which is any if the given ids.
|
||||
*
|
||||
*
|
||||
* @param ids
|
||||
* of the Software Moduels to be deleted
|
||||
*/
|
||||
@@ -366,20 +352,16 @@ public class SoftwareManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Slice<SoftwareModule> findSoftwareModulesAll(@NotNull final Pageable pageable) {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
Specification<SoftwareModule> spec = SoftwareModuleSpecification.isDeletedFalse();
|
||||
specList.add(spec);
|
||||
|
||||
spec = new Specification<SoftwareModule>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<SoftwareModule> root, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
if (!query.getResultType().isAssignableFrom(Long.class)) {
|
||||
root.fetch(SoftwareModule_.type);
|
||||
}
|
||||
return cb.conjunction();
|
||||
spec = (root, query, cb) -> {
|
||||
if (!query.getResultType().isAssignableFrom(Long.class)) {
|
||||
root.fetch(SoftwareModule_.type);
|
||||
}
|
||||
return cb.conjunction();
|
||||
};
|
||||
|
||||
specList.add(spec);
|
||||
@@ -396,7 +378,7 @@ public class SoftwareManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Long countSoftwareModulesAll() {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
final Specification<SoftwareModule> spec = SoftwareModuleSpecification.isDeletedFalse();
|
||||
specList.add(spec);
|
||||
@@ -479,7 +461,7 @@ public class SoftwareManagement {
|
||||
public Slice<SoftwareModule> findSoftwareModuleByFilters(@NotNull final Pageable pageable, final String searchText,
|
||||
final SoftwareModuleType type) {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
Specification<SoftwareModule> spec = SoftwareModuleSpecification.isDeletedFalse();
|
||||
specList.add(spec);
|
||||
@@ -494,15 +476,11 @@ public class SoftwareManagement {
|
||||
specList.add(spec);
|
||||
}
|
||||
|
||||
spec = new Specification<SoftwareModule>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<SoftwareModule> root, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
if (!query.getResultType().isAssignableFrom(Long.class)) {
|
||||
root.fetch(SoftwareModule_.type);
|
||||
}
|
||||
return cb.conjunction();
|
||||
spec = (root, query, cb) -> {
|
||||
if (!query.getResultType().isAssignableFrom(Long.class)) {
|
||||
root.fetch(SoftwareModule_.type);
|
||||
}
|
||||
return cb.conjunction();
|
||||
};
|
||||
|
||||
specList.add(spec);
|
||||
@@ -592,7 +570,7 @@ public class SoftwareManagement {
|
||||
|
||||
private List<Specification<SoftwareModule>> buildSpecificationList(final String searchText,
|
||||
final SoftwareModuleType type) {
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
if (!Strings.isNullOrEmpty(searchText)) {
|
||||
specList.add(SoftwareModuleSpecification.likeNameOrVersion(searchText));
|
||||
}
|
||||
@@ -631,7 +609,7 @@ public class SoftwareManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Long countSoftwareModuleByFilters(final String searchText, final SoftwareModuleType type) {
|
||||
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<Specification<SoftwareModule>>();
|
||||
final List<Specification<SoftwareModule>> specList = new ArrayList<>();
|
||||
|
||||
Specification<SoftwareModule> spec = SoftwareModuleSpecification.isDeletedFalse();
|
||||
specList.add(spec);
|
||||
@@ -788,7 +766,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* creates or updates a single software module meta data entry.
|
||||
*
|
||||
*
|
||||
* @param metadata
|
||||
* the meta data entry to create or update
|
||||
* @return the updated or created software module meta data entry
|
||||
@@ -813,7 +791,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* creates a list of software module meta data entries.
|
||||
*
|
||||
*
|
||||
* @param metadata
|
||||
* the meta data entries to create or update
|
||||
* @return the updated or created software module meta data entries
|
||||
@@ -835,7 +813,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* updates a distribution set meta data value if corresponding entry exists.
|
||||
*
|
||||
*
|
||||
* @param metadata
|
||||
* the meta data entry to be updated
|
||||
* @return the updated meta data entry
|
||||
@@ -858,7 +836,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* deletes a software module meta data entry.
|
||||
*
|
||||
*
|
||||
* @param id
|
||||
* the ID of the software module meta data to delete
|
||||
*/
|
||||
@@ -871,7 +849,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* finds all meta data by the given software module id.
|
||||
*
|
||||
*
|
||||
* @param swId
|
||||
* the software module id to retrieve the meta data from
|
||||
* @param pageable
|
||||
@@ -887,7 +865,7 @@ public class SoftwareManagement {
|
||||
|
||||
/**
|
||||
* finds all meta data by the given software module id.
|
||||
*
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the software module id to retrieve the meta data from
|
||||
* @param spec
|
||||
@@ -900,20 +878,19 @@ public class SoftwareManagement {
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_REPOSITORY)
|
||||
public Page<SoftwareModuleMetadata> findSoftwareModuleMetadataBySoftwareModuleId(final Long softwareModuleId,
|
||||
@NotNull final Specification<SoftwareModuleMetadata> spec, @NotNull final Pageable pageable) {
|
||||
return softwareModuleMetadataRepository.findAll(new Specification<SoftwareModuleMetadata>() {
|
||||
@Override
|
||||
public Predicate toPredicate(final Root<SoftwareModuleMetadata> root, final CriteriaQuery<?> query,
|
||||
final CriteriaBuilder cb) {
|
||||
|
||||
return cb.and(cb.equal(root.get(SoftwareModuleMetadata_.softwareModule).get(SoftwareModule_.id),
|
||||
softwareModuleId), spec.toPredicate(root, query, cb));
|
||||
}
|
||||
}, pageable);
|
||||
return softwareModuleMetadataRepository
|
||||
.findAll(
|
||||
(Specification<SoftwareModuleMetadata>) (root, query,
|
||||
cb) -> cb.and(
|
||||
cb.equal(root.get(SoftwareModuleMetadata_.softwareModule)
|
||||
.get(SoftwareModule_.id), softwareModuleId),
|
||||
spec.toPredicate(root, query, cb)),
|
||||
pageable);
|
||||
}
|
||||
|
||||
/**
|
||||
* finds a single software module meta data by its id.
|
||||
*
|
||||
*
|
||||
* @param id
|
||||
* the id of the software module meta data containing the meta
|
||||
* data key and the ID of the software module
|
||||
|
||||
@@ -16,6 +16,7 @@ import javax.validation.constraints.NotNull;
|
||||
import org.eclipse.hawkbit.im.authentication.SpPermission.SpringEvalExpressions;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityAlreadyExistsException;
|
||||
import org.eclipse.hawkbit.repository.model.TargetFilterQuery;
|
||||
import org.eclipse.hawkbit.repository.specifications.SpecificationsBuilder;
|
||||
import org.eclipse.hawkbit.repository.specifications.TargetFilterQuerySpecification;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.Page;
|
||||
@@ -33,7 +34,7 @@ import com.google.common.base.Strings;
|
||||
|
||||
/**
|
||||
* Business service facade for managing {@link TargetFilterQuery}s.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@@ -47,7 +48,7 @@ public class TargetFilterQueryManagement {
|
||||
|
||||
/**
|
||||
* creating new {@link TargetFilterQuery}.
|
||||
*
|
||||
*
|
||||
* @param customTargetFilter
|
||||
* @return the created {@link TargetFilterQuery}
|
||||
*/
|
||||
@@ -60,13 +61,12 @@ public class TargetFilterQueryManagement {
|
||||
if (targetFilterQueryRepository.findByName(customTargetFilter.getName()) != null) {
|
||||
throw new EntityAlreadyExistsException(customTargetFilter.getName());
|
||||
}
|
||||
final TargetFilterQuery filter = targetFilterQueryRepository.save(customTargetFilter);
|
||||
return filter;
|
||||
return targetFilterQueryRepository.save(customTargetFilter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete target filter query.
|
||||
*
|
||||
*
|
||||
* @param targetFilterQueryId
|
||||
* IDs of target filter query to be deleted
|
||||
*/
|
||||
@@ -78,9 +78,9 @@ public class TargetFilterQueryManagement {
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* Retrieves all target filter query{@link TargetFilterQuery}.
|
||||
*
|
||||
*
|
||||
* @param pageable
|
||||
* pagination parameter
|
||||
* @return the found {@link TargetFilterQuery}s
|
||||
@@ -92,8 +92,8 @@ public class TargetFilterQueryManagement {
|
||||
|
||||
/**
|
||||
* Retrieves all target filter query which {@link TargetFilterQuery}.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
* @param pageable
|
||||
* pagination parameter
|
||||
* @param name
|
||||
@@ -102,7 +102,7 @@ public class TargetFilterQueryManagement {
|
||||
*/
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_TARGET)
|
||||
public Page<TargetFilterQuery> findTargetFilterQueryByFilters(@NotNull final Pageable pageable, final String name) {
|
||||
final List<Specification<TargetFilterQuery>> specList = new ArrayList<Specification<TargetFilterQuery>>();
|
||||
final List<Specification<TargetFilterQuery>> specList = new ArrayList<>();
|
||||
if (!Strings.isNullOrEmpty(name)) {
|
||||
specList.add(TargetFilterQuerySpecification.likeName(name));
|
||||
}
|
||||
@@ -110,7 +110,7 @@ public class TargetFilterQueryManagement {
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* @param pageable
|
||||
* pagination parameter
|
||||
* @param specList
|
||||
@@ -119,29 +119,21 @@ public class TargetFilterQueryManagement {
|
||||
*/
|
||||
private Page<TargetFilterQuery> findTargetFilterQueryByCriteriaAPI(@NotNull final Pageable pageable,
|
||||
final List<Specification<TargetFilterQuery>> specList) {
|
||||
Specifications<TargetFilterQuery> specs = null;
|
||||
if (!specList.isEmpty()) {
|
||||
specs = Specifications.where(specList.get(0));
|
||||
}
|
||||
if (specList.size() > 1) {
|
||||
for (final Specification<TargetFilterQuery> s : specList.subList(1, specList.size())) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
if (specs == null) {
|
||||
if (specList == null || specList.isEmpty()) {
|
||||
return targetFilterQueryRepository.findAll(pageable);
|
||||
} else {
|
||||
return targetFilterQueryRepository.findAll(specs, pageable);
|
||||
}
|
||||
|
||||
final Specifications<TargetFilterQuery> specs = SpecificationsBuilder.combineWithAnd(specList);
|
||||
return targetFilterQueryRepository.findAll(specs, pageable);
|
||||
}
|
||||
|
||||
/**
|
||||
* Find target filter query by name.
|
||||
*
|
||||
*
|
||||
* @param targetFilterQueryName
|
||||
* Target filter query name
|
||||
* @return the found {@link TargetFilterQuery}
|
||||
*
|
||||
*
|
||||
*/
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_TARGET)
|
||||
public TargetFilterQuery findTargetFilterQueryByName(@NotNull final String targetFilterQueryName) {
|
||||
@@ -150,11 +142,11 @@ public class TargetFilterQueryManagement {
|
||||
|
||||
/**
|
||||
* Find target filter query by id.
|
||||
*
|
||||
*
|
||||
* @param targetFilterQueryId
|
||||
* Target filter query id
|
||||
* @return the found {@link TargetFilterQuery}
|
||||
*
|
||||
*
|
||||
*/
|
||||
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_READ_TARGET)
|
||||
public TargetFilterQuery findTargetFilterQueryById(@NotNull final Long targetFilterQueryId) {
|
||||
@@ -163,7 +155,7 @@ public class TargetFilterQueryManagement {
|
||||
|
||||
/**
|
||||
* updates the {@link TargetFilterQuery}.
|
||||
*
|
||||
*
|
||||
* @param targetFilterQuery
|
||||
* to be updated
|
||||
* @return the updated {@link TargetFilterQuery}
|
||||
|
||||
@@ -47,6 +47,7 @@ import org.eclipse.hawkbit.repository.model.TargetTagAssigmentResult;
|
||||
import org.eclipse.hawkbit.repository.model.TargetUpdateStatus;
|
||||
import org.eclipse.hawkbit.repository.model.Target_;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.repository.specifications.SpecificationsBuilder;
|
||||
import org.eclipse.hawkbit.repository.specifications.TargetSpecifications;
|
||||
import org.hibernate.validator.constraints.NotEmpty;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
@@ -59,7 +60,6 @@ import org.springframework.data.domain.SliceImpl;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.domain.Sort.Direction;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.data.jpa.domain.Specifications;
|
||||
import org.springframework.data.jpa.repository.Modifying;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
import org.springframework.stereotype.Service;
|
||||
@@ -508,39 +508,18 @@ public class TargetManagement {
|
||||
* @return the page with the found {@link Target}
|
||||
*/
|
||||
private Slice<Target> findByCriteriaAPI(final Pageable pageable, final List<Specification<Target>> specList) {
|
||||
final Specifications<Target> specs = creatingTargetSpecifications(specList);
|
||||
|
||||
if (specs == null) {
|
||||
if (specList == null || specList.isEmpty()) {
|
||||
return criteriaNoCountDao.findAll(pageable, Target.class);
|
||||
} else {
|
||||
return criteriaNoCountDao.findAll(specs, pageable, Target.class);
|
||||
}
|
||||
|
||||
return criteriaNoCountDao.findAll(SpecificationsBuilder.combineWithAnd(specList), pageable, Target.class);
|
||||
}
|
||||
|
||||
private Long countByCriteriaAPI(final List<Specification<Target>> specList) {
|
||||
final Specifications<Target> specs = creatingTargetSpecifications(specList);
|
||||
|
||||
if (specs == null) {
|
||||
if (specList == null || specList.isEmpty()) {
|
||||
return targetRepository.count();
|
||||
} else {
|
||||
return targetRepository.count(specs);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static Specifications<Target> creatingTargetSpecifications(final List<Specification<Target>> specList) {
|
||||
Specifications<Target> specs = null;
|
||||
if (!specList.isEmpty()) {
|
||||
specs = Specifications.where(specList.get(0));
|
||||
}
|
||||
if (specList.size() > 1) {
|
||||
specList.remove(0);
|
||||
for (final Specification<Target> s : specList) {
|
||||
specs = specs.and(s);
|
||||
}
|
||||
}
|
||||
return specs;
|
||||
return targetRepository.count(SpecificationsBuilder.combineWithAnd(specList));
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -77,7 +77,7 @@ public class Rollout extends NamedEntity {
|
||||
private int rolloutGroupsCreated = 0;
|
||||
|
||||
@Transient
|
||||
private TotalTargetCountStatus totalTargetCountStatus;
|
||||
private transient TotalTargetCountStatus totalTargetCountStatus;
|
||||
|
||||
/**
|
||||
* @return the distributionSet
|
||||
@@ -234,7 +234,7 @@ public class Rollout extends NamedEntity {
|
||||
*/
|
||||
public TotalTargetCountStatus getTotalTargetCountStatus() {
|
||||
if (totalTargetCountStatus == null) {
|
||||
this.totalTargetCountStatus = new TotalTargetCountStatus(totalTargets);
|
||||
totalTargetCountStatus = new TotalTargetCountStatus(totalTargets);
|
||||
}
|
||||
return totalTargetCountStatus;
|
||||
}
|
||||
@@ -255,11 +255,11 @@ public class Rollout extends NamedEntity {
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* @author Michael Hirsch
|
||||
*
|
||||
*/
|
||||
public static enum RolloutStatus {
|
||||
public enum RolloutStatus {
|
||||
|
||||
/**
|
||||
* Rollouts is beeing created.
|
||||
|
||||
@@ -27,7 +27,7 @@ import javax.persistence.UniqueConstraint;
|
||||
|
||||
/**
|
||||
* JPA entity definition of persisting a group of an rollout.
|
||||
*
|
||||
*
|
||||
* @author Michael Hirsch
|
||||
*
|
||||
*/
|
||||
@@ -116,7 +116,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
public void setSuccessCondition(final RolloutGroupSuccessCondition finishCondition) {
|
||||
this.successCondition = finishCondition;
|
||||
successCondition = finishCondition;
|
||||
}
|
||||
|
||||
public String getSuccessConditionExp() {
|
||||
@@ -124,7 +124,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
public void setSuccessConditionExp(final String finishExp) {
|
||||
this.successConditionExp = finishExp;
|
||||
successConditionExp = finishExp;
|
||||
}
|
||||
|
||||
public RolloutGroupErrorCondition getErrorCondition() {
|
||||
@@ -140,7 +140,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
public void setErrorConditionExp(final String errorExp) {
|
||||
this.errorConditionExp = errorExp;
|
||||
errorConditionExp = errorExp;
|
||||
}
|
||||
|
||||
public RolloutGroupErrorAction getErrorAction() {
|
||||
@@ -188,7 +188,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
*/
|
||||
public TotalTargetCountStatus getTotalTargetCountStatus() {
|
||||
if (totalTargetCountStatus == null) {
|
||||
this.totalTargetCountStatus = new TotalTargetCountStatus(totalTargets);
|
||||
totalTargetCountStatus = new TotalTargetCountStatus(totalTargets);
|
||||
}
|
||||
return totalTargetCountStatus;
|
||||
}
|
||||
@@ -210,7 +210,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* @author Michael Hirsch
|
||||
*
|
||||
*/
|
||||
@@ -343,7 +343,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
public void setSuccessCondition(final RolloutGroupSuccessCondition finishCondition) {
|
||||
this.successCondition = finishCondition;
|
||||
successCondition = finishCondition;
|
||||
}
|
||||
|
||||
public String getSuccessConditionExp() {
|
||||
@@ -351,7 +351,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
}
|
||||
|
||||
public void setSuccessConditionExp(final String finishConditionExp) {
|
||||
this.successConditionExp = finishConditionExp;
|
||||
successConditionExp = finishConditionExp;
|
||||
}
|
||||
|
||||
public RolloutGroupSuccessAction getSuccessAction() {
|
||||
@@ -416,7 +416,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
|
||||
/**
|
||||
* Sets the finish condition and expression on the builder.
|
||||
*
|
||||
*
|
||||
* @param condition
|
||||
* the finish condition
|
||||
* @param expression
|
||||
@@ -432,7 +432,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
|
||||
/**
|
||||
* Sets the success action and expression on the builder.
|
||||
*
|
||||
*
|
||||
* @param action
|
||||
* the success action
|
||||
* @param expression
|
||||
@@ -448,7 +448,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
|
||||
/**
|
||||
* Sets the error condition and expression on the builder.
|
||||
*
|
||||
*
|
||||
* @param condition
|
||||
* the error condition
|
||||
* @param expression
|
||||
@@ -464,7 +464,7 @@ public class RolloutGroup extends NamedEntity {
|
||||
|
||||
/**
|
||||
* Sets the error action and expression on the builder.
|
||||
*
|
||||
*
|
||||
* @param action
|
||||
* the error action
|
||||
* @param expression
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.repository.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
|
||||
import javax.persistence.CascadeType;
|
||||
@@ -30,16 +31,18 @@ import javax.persistence.Table;
|
||||
@IdClass(RolloutTargetGroupId.class)
|
||||
@Entity
|
||||
@Table(name = "sp_rollouttargetgroup")
|
||||
public class RolloutTargetGroup {
|
||||
public class RolloutTargetGroup implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@Id
|
||||
@ManyToOne(targetEntity = RolloutGroup.class, fetch = FetchType.LAZY, cascade = { CascadeType.PERSIST })
|
||||
@JoinColumn(name = "rolloutGroup_Id", foreignKey = @ForeignKey(value = ConstraintMode.CONSTRAINT, name = "fk_rollouttargetgroup_group"))
|
||||
@JoinColumn(name = "rolloutGroup_Id", foreignKey = @ForeignKey(value = ConstraintMode.CONSTRAINT, name = "fk_rollouttargetgroup_group") )
|
||||
private RolloutGroup rolloutGroup;
|
||||
|
||||
@Id
|
||||
@ManyToOne(targetEntity = Target.class, fetch = FetchType.LAZY, cascade = { CascadeType.PERSIST })
|
||||
@JoinColumn(name = "target_id", foreignKey = @ForeignKey(value = ConstraintMode.CONSTRAINT, name = "fk_rollouttargetgroup_target"))
|
||||
@JoinColumn(name = "target_id", foreignKey = @ForeignKey(value = ConstraintMode.CONSTRAINT, name = "fk_rollouttargetgroup_target") )
|
||||
private Target target;
|
||||
|
||||
@OneToMany(targetEntity = Action.class, fetch = FetchType.LAZY, cascade = { CascadeType.PERSIST })
|
||||
|
||||
@@ -32,6 +32,8 @@ import javax.persistence.PrimaryKeyJoinColumn;
|
||||
import javax.persistence.Table;
|
||||
import javax.persistence.Transient;
|
||||
import javax.persistence.UniqueConstraint;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import javax.validation.constraints.Size;
|
||||
|
||||
import org.eclipse.hawkbit.im.authentication.SpPermission;
|
||||
import org.eclipse.hawkbit.repository.model.helper.SecurityChecker;
|
||||
@@ -74,6 +76,8 @@ public class Target extends NamedEntity implements Persistable<Long> {
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@Column(name = "controller_id", length = 64)
|
||||
@Size(min = 1)
|
||||
@NotNull
|
||||
private String controllerId;
|
||||
|
||||
@Transient
|
||||
|
||||
@@ -9,12 +9,12 @@
|
||||
package org.eclipse.hawkbit.repository.model;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.EnumMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
* Store all states with the target count of a rollout or rolloutgroup.
|
||||
*
|
||||
*/
|
||||
@@ -27,12 +27,12 @@ public class TotalTargetCountStatus {
|
||||
SCHEDULED, RUNNING, ERROR, FINISHED, CANCELLED, NOTSTARTED
|
||||
}
|
||||
|
||||
private final Map<Status, Long> statusTotalCountMap = new HashMap<>();
|
||||
private final Map<Status, Long> statusTotalCountMap = new EnumMap<>(Status.class);
|
||||
private final Long totalTargetCount;
|
||||
|
||||
/**
|
||||
* Create a new states map with the target count for each state.
|
||||
*
|
||||
*
|
||||
* @param targetCountActionStatus
|
||||
* the action state map
|
||||
* @param totalTargets
|
||||
@@ -46,7 +46,7 @@ public class TotalTargetCountStatus {
|
||||
|
||||
/**
|
||||
* Create a new states map with the target count for each state.
|
||||
*
|
||||
*
|
||||
* @param totalTargetCount
|
||||
* the total target count
|
||||
*/
|
||||
@@ -56,7 +56,7 @@ public class TotalTargetCountStatus {
|
||||
|
||||
/**
|
||||
* The current state mape which the total target count
|
||||
*
|
||||
*
|
||||
* @return the statusTotalCountMap the state map
|
||||
*/
|
||||
public Map<Status, Long> getStatusTotalCountMap() {
|
||||
@@ -65,7 +65,7 @@ public class TotalTargetCountStatus {
|
||||
|
||||
/**
|
||||
* Gets the total target count from a state.
|
||||
*
|
||||
*
|
||||
* @param status
|
||||
* the state key
|
||||
* @return the current target count cannot be <null>
|
||||
@@ -77,7 +77,7 @@ public class TotalTargetCountStatus {
|
||||
|
||||
/**
|
||||
* Populate all target status to a the given map
|
||||
*
|
||||
*
|
||||
* @param statusTotalCountMap
|
||||
* the map
|
||||
* @param rolloutStatusCountItems
|
||||
|
||||
@@ -18,6 +18,7 @@ import java.util.stream.Collectors;
|
||||
import javax.persistence.EntityManager;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Expression;
|
||||
import javax.persistence.criteria.MapJoin;
|
||||
import javax.persistence.criteria.Path;
|
||||
import javax.persistence.criteria.Predicate;
|
||||
@@ -101,7 +102,7 @@ public final class RSQLUtility {
|
||||
*/
|
||||
public static <A extends Enum<A> & FieldNameProvider, T> Specification<T> parse(final String rsql,
|
||||
final Class<A> fieldNameProvider) {
|
||||
return new RSQLSpecification<>(rsql, fieldNameProvider);
|
||||
return new RSQLSpecification<>(rsql.toLowerCase(), fieldNameProvider);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -460,16 +461,46 @@ public final class RSQLUtility {
|
||||
singleList.add(cb.lessThanOrEqualTo(pathOfString(fieldPath), value));
|
||||
break;
|
||||
case "=in=":
|
||||
singleList.add(fieldPath.in(transformedValues));
|
||||
singleList.add(getInPredicate(transformedValues, fieldPath));
|
||||
break;
|
||||
case "=out=":
|
||||
singleList.add(cb.not(fieldPath.in(transformedValues)));
|
||||
singleList.add(getOutPredicate(transformedValues, fieldPath));
|
||||
break;
|
||||
default:
|
||||
LOGGER.info("operator symbol {} is either not supported or not implemented");
|
||||
}
|
||||
}
|
||||
|
||||
private Predicate getInPredicate(final List<Object> transformedValues, final Path<Object> fieldPath) {
|
||||
final List<String> inParams = new ArrayList<>();
|
||||
for (final Object param : transformedValues) {
|
||||
if (param instanceof String) {
|
||||
inParams.add(((String) param).toUpperCase());
|
||||
}
|
||||
}
|
||||
if (!inParams.isEmpty()) {
|
||||
return cb.upper(pathOfString(fieldPath)).in(inParams);
|
||||
} else {
|
||||
return fieldPath.in(transformedValues);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
private Predicate getOutPredicate(final List<Object> transformedValues, final Path<Object> fieldPath) {
|
||||
final List<String> outParams = new ArrayList<>();
|
||||
for (final Object param : transformedValues) {
|
||||
if (param instanceof String) {
|
||||
outParams.add(((String) param).toUpperCase());
|
||||
}
|
||||
}
|
||||
if (!outParams.isEmpty()) {
|
||||
return cb.not(cb.upper(pathOfString(fieldPath)).in(outParams));
|
||||
} else {
|
||||
return cb.not(fieldPath.in(transformedValues));
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
private Path<Object> getMapValueFieldPath(final A enumField, final Path<Object> fieldPath) {
|
||||
if (!enumField.isMap() || enumField.getValueFieldName() == null) {
|
||||
return fieldPath;
|
||||
@@ -477,6 +508,7 @@ public final class RSQLUtility {
|
||||
return fieldPath.get(enumField.getValueFieldName());
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private Predicate mapToMapPredicate(final ComparisonNode node, final Path<Object> fieldPath,
|
||||
final A enumField) {
|
||||
if (!enumField.isMap()) {
|
||||
@@ -485,10 +517,12 @@ public final class RSQLUtility {
|
||||
final String[] graph = node.getSelector().split("\\" + FieldNameProvider.SUB_ATTRIBUTE_SEPERATOR);
|
||||
final String keyValue = graph[graph.length - 1];
|
||||
if (fieldPath instanceof MapJoin) {
|
||||
return cb.equal(((MapJoin<?, ?, ?>) fieldPath).key(), keyValue);
|
||||
// Currently we support only string key .So below cast is safe.
|
||||
return cb.equal(cb.upper((Expression<String>) (((MapJoin<?, ?, ?>) fieldPath).key())),
|
||||
keyValue.toUpperCase());
|
||||
}
|
||||
|
||||
return cb.equal(fieldPath.get(enumField.getKeyFieldName()), keyValue);
|
||||
return cb.equal(cb.upper(fieldPath.get(enumField.getKeyFieldName())), keyValue.toUpperCase());
|
||||
}
|
||||
|
||||
private Predicate getEqualToPredicate(final Object transformedValue, final Path<Object> fieldPath) {
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.repository.specifications;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.data.jpa.domain.Specifications;
|
||||
|
||||
/**
|
||||
* Helper class to easily combine {@link Specification} instances.
|
||||
*
|
||||
*/
|
||||
public final class SpecificationsBuilder {
|
||||
|
||||
private SpecificationsBuilder() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Combine all given specification with and. The first specification is the
|
||||
* where clause.
|
||||
*
|
||||
* @param specList
|
||||
* all specification wich will combine
|
||||
* @return <null> if the given specification list is empty
|
||||
*/
|
||||
public static <T> Specifications<T> combineWithAnd(final List<Specification<T>> specList) {
|
||||
if (specList.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
Specifications<T> specs = Specifications.where(specList.get(0));
|
||||
specList.remove(0);
|
||||
for (final Specification<T> specification : specList) {
|
||||
specs = specs.and(specification);
|
||||
}
|
||||
return specs;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -16,7 +16,19 @@ import org.eclipse.hawkbit.repository.model.RolloutGroup;
|
||||
*/
|
||||
public interface RolloutGroupConditionEvaluator {
|
||||
|
||||
boolean verifyExpression(final String expression);
|
||||
default boolean verifyExpression(final String expression) {
|
||||
// percentage value between 0 and 100
|
||||
try {
|
||||
final Integer value = Integer.valueOf(expression);
|
||||
if (value >= 0 || value <= 100) {
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
} catch (final NumberFormatException e) {
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
boolean eval(Rollout rollout, RolloutGroup rolloutGroup, final String expression);
|
||||
}
|
||||
|
||||
@@ -18,31 +18,16 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
*/
|
||||
@Component("thresholdRolloutGroupErrorCondition")
|
||||
public class ThresholdRolloutGroupErrorCondition implements RolloutGroupConditionEvaluator {
|
||||
|
||||
private static Logger logger = LoggerFactory.getLogger(ThresholdRolloutGroupErrorCondition.class);
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(ThresholdRolloutGroupErrorCondition.class);
|
||||
|
||||
@Autowired
|
||||
private ActionRepository actionRepository;
|
||||
|
||||
@Override
|
||||
public boolean verifyExpression(final String expression) {
|
||||
// percentage value between 0 and 100
|
||||
try {
|
||||
final Integer value = Integer.valueOf(expression);
|
||||
if (value >= 0 || value <= 100) {
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
} catch (final RuntimeException e) {
|
||||
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean eval(final Rollout rollout, final RolloutGroup rolloutGroup, final String expression) {
|
||||
final Long totalGroup = actionRepository.countByRolloutAndRolloutGroup(rollout, rolloutGroup);
|
||||
@@ -60,7 +45,7 @@ public class ThresholdRolloutGroupErrorCondition implements RolloutGroupConditio
|
||||
// calculate threshold
|
||||
return ((float) error / (float) totalGroup) > ((float) threshold / 100F);
|
||||
} catch (final NumberFormatException e) {
|
||||
logger.error("Cannot evaluate condition expression " + expression, e);
|
||||
LOGGER.error("Cannot evaluate condition expression " + expression, e);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,47 +12,41 @@ import org.eclipse.hawkbit.repository.ActionRepository;
|
||||
import org.eclipse.hawkbit.repository.model.Action;
|
||||
import org.eclipse.hawkbit.repository.model.Rollout;
|
||||
import org.eclipse.hawkbit.repository.model.RolloutGroup;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
*
|
||||
*
|
||||
*/
|
||||
@Component("thresholdRolloutGroupSuccessCondition")
|
||||
public class ThresholdRolloutGroupSuccessCondition implements RolloutGroupConditionEvaluator {
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(ThresholdRolloutGroupSuccessCondition.class);
|
||||
|
||||
@Autowired
|
||||
private ActionRepository actionRepository;
|
||||
|
||||
@Override
|
||||
public boolean verifyExpression(final String expression) {
|
||||
// percentage value between 0 and 100
|
||||
try {
|
||||
final Integer value = Integer.valueOf(expression);
|
||||
if (value >= 0 || value <= 100) {
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
} catch (final RuntimeException e) {
|
||||
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean eval(final Rollout rollout, final RolloutGroup rolloutGroup, final String expression) {
|
||||
final Long totalGroup = rolloutGroup.getTotalTargets();
|
||||
final Long finished = actionRepository.countByRolloutIdAndRolloutGroupIdAndStatus(rollout.getId(),
|
||||
final Long finished = this.actionRepository.countByRolloutIdAndRolloutGroupIdAndStatus(rollout.getId(),
|
||||
rolloutGroup.getId(), Action.Status.FINISHED);
|
||||
final Integer threshold = Integer.valueOf(expression);
|
||||
try {
|
||||
final Integer threshold = Integer.valueOf(expression);
|
||||
|
||||
if (totalGroup == 0) {
|
||||
// in case e.g. targets has been deleted we don't have any actions
|
||||
// left for this group, so the group is finished
|
||||
return true;
|
||||
if (totalGroup == 0) {
|
||||
// in case e.g. targets has been deleted we don't have any
|
||||
// actions
|
||||
// left for this group, so the group is finished
|
||||
return true;
|
||||
}
|
||||
// calculate threshold
|
||||
return ((float) finished / (float) totalGroup) >= ((float) threshold / 100F);
|
||||
} catch (final NumberFormatException e) {
|
||||
LOGGER.error("Cannot evaluate condition expression " + expression, e);
|
||||
return false;
|
||||
}
|
||||
// calculate threshold
|
||||
return ((float) finished / (float) totalGroup) >= ((float) threshold / 100F);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -9,10 +9,13 @@
|
||||
package org.eclipse.hawkbit.repository;
|
||||
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.fail;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import javax.validation.ConstraintViolationException;
|
||||
|
||||
import org.apache.commons.lang3.RandomStringUtils;
|
||||
import org.eclipse.hawkbit.AbstractIntegrationTest;
|
||||
import org.eclipse.hawkbit.TestDataUtil;
|
||||
@@ -71,6 +74,24 @@ public class ControllerManagementTest extends AbstractIntegrationTest {
|
||||
.getNumberOfElements()).isEqualTo(3);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Register a controller which not exist")
|
||||
public void testfindOrRegisterTargetIfItDoesNotexist() {
|
||||
final Target target = controllerManagament.findOrRegisterTargetIfItDoesNotexist("AA", null);
|
||||
assertThat(target).as("target should not be null").isNotNull();
|
||||
|
||||
final Target sameTarget = controllerManagament.findOrRegisterTargetIfItDoesNotexist("AA", null);
|
||||
assertThat(target).as("Target should be the equals").isEqualTo(sameTarget);
|
||||
assertThat(targetRepository.count()).as("Only 1 target should be registred").isEqualTo(1L);
|
||||
|
||||
try {
|
||||
controllerManagament.findOrRegisterTargetIfItDoesNotexist("", null);
|
||||
fail("target with empty controller id should not be registred");
|
||||
} catch (final ConstraintViolationException e) {
|
||||
// ok
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Controller trys to finish an update process after it has been finished by an error action status.")
|
||||
public void tryToFinishUpdateProcessMoreThenOnce() {
|
||||
|
||||
@@ -99,7 +99,7 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
assertThat(targetsCreatedOverPeriod.getData()).hasSize(maxMonthBackAmountReportTargets + 1);
|
||||
for (final DataReportSeriesItem<LocalDate> reportItem : targetsCreatedOverPeriod.getData()) {
|
||||
// only one target is created for each month
|
||||
assertThat(reportItem.getData().intValue()).isEqualTo(1);
|
||||
assertThat(reportItem.getData().intValue()).as("Target for each month").isEqualTo(1);
|
||||
}
|
||||
|
||||
// check cache evict
|
||||
@@ -109,7 +109,7 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
}
|
||||
targetsCreatedOverPeriod = reportManagement.targetsCreatedOverPeriod(DateTypes.perMonth(), from, to);
|
||||
for (final DataReportSeriesItem<LocalDate> reportItem : targetsCreatedOverPeriod.getData()) {
|
||||
assertThat(reportItem.getData().intValue()).isEqualTo(2);
|
||||
assertThat(reportItem.getData().intValue()).as("Target for each month").isEqualTo(2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -221,21 +221,26 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
.getData()[0];
|
||||
if (dataReportSeriesItem.getType().equals("ds1")) {
|
||||
// total count of three because ds1 has two different versions
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(3L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Version/Item type of DistributionSet 1 in statistics")
|
||||
.isEqualTo(3L);
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(Arrays.stream(outerData).map(DataReportSeriesItem::getType).collect(Collectors.toList()))
|
||||
.contains("0.0.0", "0.0.1");
|
||||
} else if (dataReportSeriesItem.getType().equals("ds2")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(1L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Version/Item type of DistributionSet 2 in statistics")
|
||||
.isEqualTo(1L);
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(outerData).hasSize(1);
|
||||
assertThat(outerData[0].getType()).isEqualTo("0.0.2");
|
||||
|
||||
assertThat(outerData[0].getType()).as("Version/Item type of DistributionSet 2 in statistics")
|
||||
.isEqualTo("0.0.2");
|
||||
} else if (dataReportSeriesItem.getType().equals("ds3")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(0L);
|
||||
|
||||
assertThat(dataReportSeriesItem.getData()).as("Version/Item type of DistributionSet 3 in statistics")
|
||||
.isEqualTo(0L);
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(outerData).hasSize(1);
|
||||
assertThat(outerData[0].getType()).isEqualTo("0.0.3");
|
||||
assertThat(outerData[0].getType()).as("Version/Item type of DistributionSet 3 in statistics")
|
||||
.isEqualTo("0.0.3");
|
||||
} else {
|
||||
fail("no assertion count for distribution set " + dataReportSeriesItem.getType());
|
||||
}
|
||||
@@ -251,8 +256,7 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
final DataReportSeriesItem<String> dataReportSeriesItem = innerOuterDataReportSeries.getInnerSeries()
|
||||
.getData()[0];
|
||||
if (dataReportSeriesItem.getType().equals("ds1")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(4L);
|
||||
|
||||
assertThat(dataReportSeriesItem.getData()).as("Data report item number").isEqualTo(4L);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -278,19 +282,23 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
|
||||
switch (reportItem.getType()) {
|
||||
case ERROR:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownErrorCount);
|
||||
assertThat(reportItem.getData()).as("ERROR count for targets in statistics").isEqualTo(knownErrorCount);
|
||||
break;
|
||||
case IN_SYNC:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownSyncCount);
|
||||
assertThat(reportItem.getData()).as("IN_SYNC count for targets in statistics")
|
||||
.isEqualTo(knownSyncCount);
|
||||
break;
|
||||
case PENDING:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownPendingCount);
|
||||
assertThat(reportItem.getData()).as("PENDING count for targets in statistics")
|
||||
.isEqualTo(knownPendingCount);
|
||||
break;
|
||||
case REGISTERED:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownRegCount);
|
||||
assertThat(reportItem.getData()).as("REGISTERED count for targets in statistics")
|
||||
.isEqualTo(knownRegCount);
|
||||
break;
|
||||
case UNKNOWN:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownUnknownCount);
|
||||
assertThat(reportItem.getData()).as("UNKNOWN count for targets in statistics")
|
||||
.isEqualTo(knownUnknownCount);
|
||||
break;
|
||||
default:
|
||||
fail("missing case for unknown target update status " + reportItem.getType());
|
||||
@@ -309,19 +317,24 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
|
||||
switch (reportItem.getType()) {
|
||||
case ERROR:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownErrorCount * 2);
|
||||
assertThat(reportItem.getData()).as("ERROR count for targets in statistics")
|
||||
.isEqualTo(knownErrorCount * 2);
|
||||
break;
|
||||
case IN_SYNC:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownSyncCount * 2);
|
||||
assertThat(reportItem.getData()).as("IN_SYNC count for targets in statistics")
|
||||
.isEqualTo(knownSyncCount * 2);
|
||||
break;
|
||||
case PENDING:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownPendingCount * 2);
|
||||
assertThat(reportItem.getData()).as("PENDING count for targets in statistics")
|
||||
.isEqualTo(knownPendingCount * 2);
|
||||
break;
|
||||
case REGISTERED:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownRegCount * 2);
|
||||
assertThat(reportItem.getData()).as("REGISTERED count for targets in statistics")
|
||||
.isEqualTo(knownRegCount * 2);
|
||||
break;
|
||||
case UNKNOWN:
|
||||
assertThat(reportItem.getData()).isEqualTo(knownUnknownCount * 2);
|
||||
assertThat(reportItem.getData()).as("UNKNOWN count for targets in statistics")
|
||||
.isEqualTo(knownUnknownCount * 2);
|
||||
break;
|
||||
default:
|
||||
fail("missing case for unknown target update status " + reportItem.getType());
|
||||
@@ -373,22 +386,30 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
final DataReportSeriesItem<String> dataReportSeriesItem = innerOuterDataReportSeries.getInnerSeries()
|
||||
.getData()[0];
|
||||
if (dataReportSeriesItem.getType().equals("ds1")) {
|
||||
|
||||
// total count of three because ds1 has two different versions
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(3L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Total count of DistributionSet 1 in statistics")
|
||||
.isEqualTo(3L);
|
||||
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(Arrays.stream(outerData).map(DataReportSeriesItem::getType).collect(Collectors.toList()))
|
||||
.contains("0.0.0", "0.0.1");
|
||||
|
||||
} else if (dataReportSeriesItem.getType().equals("ds2")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(1L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Total count of DistributionSet 2 in statistics")
|
||||
.isEqualTo(1L);
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(outerData).hasSize(1);
|
||||
assertThat(outerData[0].getType()).isEqualTo("0.0.2");
|
||||
assertThat(outerData[0].getType()).as("Version/Item type of DistributionSet 2 in statistics")
|
||||
.isEqualTo("0.0.2");
|
||||
|
||||
} else if (dataReportSeriesItem.getType().equals("ds3")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(0L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Total count of DistributionSet 3 in statistics")
|
||||
.isEqualTo(0L);
|
||||
final DataReportSeriesItem<String>[] outerData = innerOuterDataReportSeries.getOuterSeries().getData();
|
||||
assertThat(outerData).hasSize(1);
|
||||
assertThat(outerData[0].getType()).isEqualTo("0.0.3");
|
||||
assertThat(outerData[0].getType()).as("Version/Item type of DistributionSet 3 in statistics")
|
||||
.isEqualTo("0.0.3");
|
||||
} else {
|
||||
fail("no assertion count for distribution set " + dataReportSeriesItem.getType());
|
||||
}
|
||||
@@ -402,7 +423,8 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
final DataReportSeriesItem<String> dataReportSeriesItem = innerOuterDataReportSeries.getInnerSeries()
|
||||
.getData()[0];
|
||||
if (dataReportSeriesItem.getType().equals("ds1")) {
|
||||
assertThat(dataReportSeriesItem.getData()).isEqualTo(4L);
|
||||
assertThat(dataReportSeriesItem.getData()).as("Total count of DistributionSet 1 in statistics")
|
||||
.isEqualTo(4L);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -435,29 +457,24 @@ public class ReportManagementTest extends AbstractIntegrationTest {
|
||||
DataReportSeries<SeriesTime> targetsNotLastPoll = reportManagement.targetsLastPoll();
|
||||
DataReportSeriesItem<SeriesTime>[] data = targetsNotLastPoll.getData();
|
||||
|
||||
// for( final DataReportSeriesItem<SeriesTime> dataReportSeriesItem :
|
||||
// data ) {
|
||||
// System.out.println( dataReportSeriesItem.getData() );
|
||||
// }
|
||||
|
||||
// --- Verfiy ---
|
||||
|
||||
// verify hour
|
||||
assertThat(data[0].getType()).isEqualTo(SeriesTime.HOUR);
|
||||
assertThat(data[0].getData()).isEqualTo((long) knownTargetsPollLastHour);
|
||||
assertThat(data[0].getType()).as("Series time").isEqualTo(SeriesTime.HOUR);
|
||||
assertThat(data[0].getData()).as("Targets poll last hour").isEqualTo((long) knownTargetsPollLastHour);
|
||||
// verify day
|
||||
assertThat(data[1].getType()).isEqualTo(SeriesTime.DAY);
|
||||
assertThat(data[1].getData()).isEqualTo((long) knownTargetsPollLastDay);
|
||||
assertThat(data[1].getType()).as("Series time").isEqualTo(SeriesTime.DAY);
|
||||
assertThat(data[1].getData()).as("Targets poll last day").isEqualTo((long) knownTargetsPollLastDay);
|
||||
// verify week
|
||||
assertThat(data[2].getType()).isEqualTo(SeriesTime.WEEK);
|
||||
assertThat(data[2].getData()).isEqualTo((long) knownTargetsPollLastWeek);
|
||||
assertThat(data[2].getType()).as("Series time").isEqualTo(SeriesTime.WEEK);
|
||||
assertThat(data[2].getData()).as("Targets poll last week").isEqualTo((long) knownTargetsPollLastWeek);
|
||||
|
||||
// test cache evict
|
||||
createTargets("hourPoll2", knownTargetsPollLastHour, now.minusMinutes(59));
|
||||
targetsNotLastPoll = reportManagement.targetsLastPoll();
|
||||
data = targetsNotLastPoll.getData();
|
||||
assertThat(data[0].getType()).isEqualTo(SeriesTime.HOUR);
|
||||
assertThat(data[0].getData()).isEqualTo((long) knownTargetsPollLastHour * 2);
|
||||
assertThat(data[0].getType()).as("Series time").isEqualTo(SeriesTime.HOUR);
|
||||
assertThat(data[0].getData()).as("Targets poll last hour").isEqualTo((long) knownTargetsPollLastHour * 2);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -10,7 +10,6 @@ package org.eclipse.hawkbit.repository;
|
||||
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.junit.Assert.fail;
|
||||
@@ -26,6 +25,7 @@ import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import javax.persistence.Query;
|
||||
import javax.validation.ConstraintViolationException;
|
||||
|
||||
import org.eclipse.hawkbit.AbstractIntegrationTest;
|
||||
import org.eclipse.hawkbit.TestDataUtil;
|
||||
@@ -65,6 +65,24 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Verify that a target with empty controller id cannot be created")
|
||||
public void createTargetWithNoControllerId() {
|
||||
try {
|
||||
targetManagement.createTarget(new Target(""));
|
||||
fail("target with empty controller id should not be created");
|
||||
} catch (final ConstraintViolationException e) {
|
||||
// ok
|
||||
}
|
||||
|
||||
try {
|
||||
targetManagement.createTarget(new Target(null));
|
||||
fail("target with empty controller id should not be created");
|
||||
} catch (final ConstraintViolationException e) {
|
||||
// ok
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Ensures that targets can assigned and unassigned to a target tag. Not exists target will be ignored for the assignment.")
|
||||
public void assignAndUnassignTargetsToTag() {
|
||||
@@ -226,10 +244,10 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
}
|
||||
}
|
||||
if (strict) {
|
||||
fail();
|
||||
fail("Target does not contain all tags");
|
||||
}
|
||||
}
|
||||
fail();
|
||||
fail("Target does not contain any tags or the expected tag was not found");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -240,7 +258,7 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
for (final Tag tag : tags) {
|
||||
for (final Tag tt : t.getTags()) {
|
||||
if (tag.getName().equals(tt.getName())) {
|
||||
fail();
|
||||
fail("Target should have no tags");
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -256,30 +274,33 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
final Target target = TestDataUtil.buildTargetFixture(myCtrlID, "the description!");
|
||||
|
||||
Target savedTarget = targetManagement.createTarget(target);
|
||||
assertNotNull(savedTarget);
|
||||
assertNotNull("The target should not be null", savedTarget);
|
||||
final Long createdAt = savedTarget.getCreatedAt();
|
||||
Long modifiedAt = savedTarget.getLastModifiedAt();
|
||||
assertEquals(createdAt, modifiedAt);
|
||||
assertNotNull(savedTarget.getCreatedAt());
|
||||
assertNotNull(savedTarget.getLastModifiedAt());
|
||||
assertEquals(target, savedTarget);
|
||||
|
||||
assertThat(createdAt).as("CreatedAt compared with modifiedAt").isEqualTo(modifiedAt);
|
||||
assertNotNull("The createdAt attribut of the target should no be null", savedTarget.getCreatedAt());
|
||||
assertNotNull("The lastModifiedAt attribut of the target should no be null", savedTarget.getLastModifiedAt());
|
||||
assertThat(target).as("Target compared with saved target").isEqualTo(savedTarget);
|
||||
|
||||
savedTarget.setDescription("changed description");
|
||||
Thread.sleep(1);
|
||||
savedTarget = targetManagement.updateTarget(savedTarget);
|
||||
|
||||
assertNotNull(savedTarget.getLastModifiedAt());
|
||||
assertNotEquals(createdAt, savedTarget.getLastModifiedAt());
|
||||
assertNotEquals(modifiedAt, savedTarget.getLastModifiedAt());
|
||||
assertNotNull("The lastModifiedAt attribute of the target should not be null", savedTarget.getLastModifiedAt());
|
||||
assertThat(createdAt).as("CreatedAt compared with saved modifiedAt")
|
||||
.isNotEqualTo(savedTarget.getLastModifiedAt());
|
||||
assertThat(modifiedAt).as("ModifiedAt compared with saved modifiedAt")
|
||||
.isNotEqualTo(savedTarget.getLastModifiedAt());
|
||||
modifiedAt = savedTarget.getLastModifiedAt();
|
||||
|
||||
final Target foundTarget = targetManagement.findTargetByControllerID(savedTarget.getControllerId());
|
||||
|
||||
assertNotNull(foundTarget);
|
||||
assertEquals(myCtrlID, foundTarget.getControllerId());
|
||||
assertEquals(savedTarget, foundTarget);
|
||||
assertEquals(createdAt, foundTarget.getCreatedAt());
|
||||
assertEquals(modifiedAt, foundTarget.getLastModifiedAt());
|
||||
assertNotNull("The target should not be null", foundTarget);
|
||||
assertThat(myCtrlID).as("ControllerId compared with saved controllerId")
|
||||
.isEqualTo(foundTarget.getControllerId());
|
||||
assertThat(savedTarget).as("Target compared with saved target").isEqualTo(foundTarget);
|
||||
assertThat(createdAt).as("CreatedAt compared with saved createdAt").isEqualTo(foundTarget.getCreatedAt());
|
||||
assertThat(modifiedAt).as("LastModifiedAt compared with saved lastModifiedAt")
|
||||
.isEqualTo(foundTarget.getLastModifiedAt());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -296,8 +317,11 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
final Target savedExtra = targetManagement.createTarget(extra);
|
||||
|
||||
Iterable<Target> allFound = targetRepository.findAll();
|
||||
assertEquals(firstList.size(), firstSaved.spliterator().getExactSizeIfKnown());
|
||||
assertEquals(firstList.size() + 1, allFound.spliterator().getExactSizeIfKnown());
|
||||
|
||||
assertThat(Long.valueOf(firstList.size())).as("List size of targets")
|
||||
.isEqualTo(firstSaved.spliterator().getExactSizeIfKnown());
|
||||
assertThat(Long.valueOf(firstList.size() + 1)).as("LastModifiedAt compared with saved lastModifiedAt")
|
||||
.isEqualTo(allFound.spliterator().getExactSizeIfKnown());
|
||||
|
||||
// change the objects and save to again to trigger a change on
|
||||
// lastModifiedAt
|
||||
@@ -308,18 +332,23 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
_founds: for (final Target foundTarget : allFound) {
|
||||
for (final Target changedTarget : firstSaved) {
|
||||
if (changedTarget.getControllerId().equals(foundTarget.getControllerId())) {
|
||||
assertEquals(changedTarget.getDescription(), foundTarget.getDescription());
|
||||
assertTrue(changedTarget.getName().startsWith(foundTarget.getName()));
|
||||
assertTrue(changedTarget.getName().endsWith("changed"));
|
||||
assertEquals(changedTarget.getCreatedAt(), foundTarget.getCreatedAt());
|
||||
assertThat(changedTarget.getLastModifiedAt()).isNotEqualTo(changedTarget.getCreatedAt());
|
||||
|
||||
assertThat(changedTarget.getDescription())
|
||||
.as("Description of changed target compared with description saved target")
|
||||
.isEqualTo(foundTarget.getDescription());
|
||||
assertThat(changedTarget.getName()).as("Name of changed target starts with name of saved target")
|
||||
.startsWith(foundTarget.getName());
|
||||
assertThat(changedTarget.getName()).as("Name of changed target ends with 'changed'")
|
||||
.endsWith("changed");
|
||||
assertThat(changedTarget.getCreatedAt()).as("CreatedAt compared with saved createdAt")
|
||||
.isEqualTo(foundTarget.getCreatedAt());
|
||||
assertThat(changedTarget.getLastModifiedAt()).as("LastModifiedAt compared with saved createdAt")
|
||||
.isNotEqualTo(changedTarget.getCreatedAt());
|
||||
continue _founds;
|
||||
}
|
||||
}
|
||||
|
||||
if (!foundTarget.getControllerId().equals(savedExtra.getControllerId())) {
|
||||
fail();
|
||||
fail("The controllerId of the found target is not equal to the controllerId of the saved target");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -341,8 +370,8 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
targetManagement.deleteTargets(deletedTargetIDs);
|
||||
|
||||
allFound = targetManagement.findTargetsAll(new PageRequest(0, 200)).getContent();
|
||||
assertEquals(firstSaved.spliterator().getExactSizeIfKnown() - nr2Del,
|
||||
allFound.spliterator().getExactSizeIfKnown());
|
||||
assertThat(firstSaved.spliterator().getExactSizeIfKnown() - nr2Del).as("Size of splited list")
|
||||
.isEqualTo(allFound.spliterator().getExactSizeIfKnown());
|
||||
|
||||
// verify that all undeleted are still found
|
||||
assertThat(allFound).doesNotContain(deletedTargets);
|
||||
@@ -376,15 +405,26 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
}
|
||||
final Query qry = entityManager.createNativeQuery("select * from sp_target_attributes ta");
|
||||
final List result = qry.getResultList();
|
||||
assertEquals(attribs.size() * ts.spliterator().getExactSizeIfKnown(), result.size());
|
||||
|
||||
assertThat(attribs.size() * ts.spliterator().getExactSizeIfKnown()).as("Amount of all target attributes")
|
||||
.isEqualTo(result.size());
|
||||
|
||||
for (final Target myT : ts) {
|
||||
final Target t = targetManagement.findTargetByControllerIDWithDetails(myT.getControllerId());
|
||||
assertEquals(attribs.size(), t.getTargetInfo().getControllerAttributes().size());
|
||||
assertThat(attribs.size()).as("Amount of target attributes per target")
|
||||
.isEqualTo(t.getTargetInfo().getControllerAttributes().size());
|
||||
|
||||
for (final Entry<String, String> ca : t.getTargetInfo().getControllerAttributes().entrySet()) {
|
||||
assertTrue(attribs.containsKey(ca.getKey()));
|
||||
assertTrue("Attributes list does not contain target attribute key", attribs.containsKey(ca.getKey()));
|
||||
// has the same value: see string concatenation above
|
||||
assertEquals(String.format("%s-%s", attribs.get(ca.getKey()), t.getControllerId()), ca.getValue());
|
||||
// assertThat(String.format("%s-%s",
|
||||
// attribs.get(ca.getKey()))).as("Value of string
|
||||
// concatenation")
|
||||
// .isEqualTo(ca.getValue());
|
||||
|
||||
assertEquals("The value of the string concatenation is not equal to the value of the target attributes",
|
||||
String.format("%s-%s", attribs.get(ca.getKey()), t.getControllerId()), ca.getValue());
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -656,9 +696,8 @@ public class TargetManagementTest extends AbstractIntegrationTest {
|
||||
final List<Target> targetsListWithNoTag = targetManagement
|
||||
.findTargetByFilters(new PageRequest(0, 500), null, null, null, Boolean.TRUE, tagNames).getContent();
|
||||
|
||||
// Total targets
|
||||
assertEquals(50, targetManagement.findAllTargetIds().size());
|
||||
// Targets with no tag
|
||||
assertEquals(25, targetsListWithNoTag.size());
|
||||
assertThat(50).as("Total targets").isEqualTo(targetManagement.findAllTargetIds().size());
|
||||
assertThat(25).as("Targets with no tag").isEqualTo(targetsListWithNoTag.size());
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -114,8 +114,9 @@ public class RSQLTargetFieldTest extends AbstractIntegrationTest {
|
||||
assertRSQLQuery(TargetFields.UPDATESTATUS.name() + "!=pending", 3);
|
||||
try {
|
||||
assertRSQLQuery(TargetFields.UPDATESTATUS.name() + "==noExist*", 0);
|
||||
fail();
|
||||
fail("RSQLParameterUnsupportedFieldException was expected since update status unknown");
|
||||
} catch (final RSQLParameterUnsupportedFieldException e) {
|
||||
// test ok - exception was excepted
|
||||
}
|
||||
assertRSQLQuery(TargetFields.UPDATESTATUS.name() + "=in=(pending,error)", 1);
|
||||
assertRSQLQuery(TargetFields.UPDATESTATUS.name() + "=out=(pending,error)", 3);
|
||||
|
||||
@@ -0,0 +1,365 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRestPageList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.TargetAssignmentRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.TargetAssignmentResponseBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleAssigmentRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModulePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetPagedList;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling for DistributionSet CRUD operations.
|
||||
*/
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSET_V1_REQUEST_MAPPING)
|
||||
public interface DistributionSetRestApi {
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all DistributionSets .
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of sets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all set for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetPagedList> getDistributionSets(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single DistributionSet .
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the set to retrieve
|
||||
*
|
||||
* @return a single DistributionSet with status OK.
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no DistributionSet with the given ID exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getDistributionSet(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new distribution sets . The request
|
||||
* body must always be a list of sets.
|
||||
*
|
||||
* @param sets
|
||||
* the DistributionSets to be created.
|
||||
* @return In case all sets could successful created the ResponseEntity with
|
||||
* status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetsRest> createDistributionSets(
|
||||
@RequestBody final List<DistributionSetRequestBodyPost> sets);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single DistributionSet .
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the DistributionSet to delete
|
||||
* @return status OK if delete as successful.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}")
|
||||
public ResponseEntity<Void> deleteDistributionSet(@PathVariable("distributionSetId") final Long distributionSetId);
|
||||
|
||||
/**
|
||||
* Handles the UPDATE request for a single DistributionSet .
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the DistributionSet to delete
|
||||
* @param toUpdate
|
||||
* with the data that needs updating
|
||||
*
|
||||
* @return status OK if update as successful with updated content.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<DistributionSetRest> updateDistributionSet(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestBody final DistributionSetRequestBodyPut toUpdate);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving assigned targets to a specific
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to retrieve the assigned
|
||||
* targets
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* targets
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/assignedTargets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getAssignedTargets(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving installed targets to a specific
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to retrieve the assigned
|
||||
* targets
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* targets
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/installedTargets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getInstalledTargets(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the POST request of assigning multiple targets to a single
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set within the URL path parameter
|
||||
* @param targetIds
|
||||
* the IDs of the target which should get assigned to the
|
||||
* distribution set given in the response body
|
||||
* @return status OK if the assignment of the targets was successful and a
|
||||
* complex return body which contains information about the assigned
|
||||
* targets and the already assigned targets counters
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/assignedTargets", consumes = {
|
||||
"application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetAssignmentResponseBody> createAssignedTarget(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestBody final List<TargetAssignmentRequestBody> targetIds);
|
||||
|
||||
/**
|
||||
* Gets a paged list of meta data for a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set for the meta data
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=key==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/metadata", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRestPageList> getMetadata(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Gets a single meta data value for a specific key of a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to get the meta data from
|
||||
* @param metadataKey
|
||||
* the key of the meta data entry to retrieve the value from
|
||||
* @return status OK if get request is successful with the value of the meta
|
||||
* data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<MetadataRest> getMetadataValue(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@PathVariable("metadataKey") final String metadataKey);
|
||||
|
||||
/**
|
||||
* Updates a single meta data value of a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to update the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to update the value
|
||||
* @return status OK if the update request is successful and the updated
|
||||
* meta data result
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRest> updateMetadata(@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@PathVariable("metadataKey") final String metadataKey, @RequestBody final MetadataRest metadata);
|
||||
|
||||
/**
|
||||
* Deletes a single meta data entry from the distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to delete the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to delete
|
||||
* @return status OK if the delete request is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}/metadata/{metadataKey}")
|
||||
public ResponseEntity<Void> deleteMetadata(@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@PathVariable("metadataKey") final String metadataKey);
|
||||
|
||||
/**
|
||||
* Creates a list of meta data for a specific distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to create meta data for
|
||||
* @param metadataRest
|
||||
* the list of meta data entries to create
|
||||
* @return status created if post request is successful with the value of
|
||||
* the created meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/metadata", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<List<MetadataRest>> createMetadata(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestBody final List<MetadataRest> metadataRest);
|
||||
|
||||
/**
|
||||
* Assigns a list of software modules to a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to assign software modules for
|
||||
* @param softwareModuleIDs
|
||||
* the list of software modules ids to assign
|
||||
* @return http status
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/assignedSM", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> assignSoftwareModules(@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestBody final List<SoftwareModuleAssigmentRest> softwareModuleIDs);
|
||||
|
||||
/**
|
||||
* Deletes the assignment of the software module form the distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to reject the software module
|
||||
* for
|
||||
* @param softwareModuleId
|
||||
* the software module id to get rejected form the distribution
|
||||
* set
|
||||
* @return status OK if rejection was successful.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}/assignedSM/{softwareModuleId}")
|
||||
public ResponseEntity<Void> deleteAssignSoftwareModules(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@PathVariable("softwareModuleId") final Long softwareModuleId);
|
||||
|
||||
/**
|
||||
* Handles the GET request for retrieving the assigned software modules of a
|
||||
* specific distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution to retrieve
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of sets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @return a list of the assigned software modules of a distribution set
|
||||
* with status OK, if none is assigned than {@code null}
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/assignedSM", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModulePagedList> getAssignedSoftwareModules(
|
||||
@PathVariable("distributionSetId") final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam);
|
||||
}
|
||||
@@ -0,0 +1,215 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedDistributionSetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.DistributionSetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling for DistributionSetTag CRUD operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING)
|
||||
public interface DistributionSetTagRestApi {
|
||||
/**
|
||||
* Handles the GET request of retrieving all DistributionSet tags.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of DistributionSet tags for pagination,
|
||||
* might not be present in the rest request then default value
|
||||
* will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all target tags for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagPagedList> getDistributionSetTags(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
*
|
||||
* @return a single distribution set tag with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionsetTagId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> getDistributionSetTag(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new distribution set tag. The
|
||||
* request body must always be a list of tags.
|
||||
*
|
||||
* @param tags
|
||||
* the distribution set tags to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created. The Response Body are the created
|
||||
* distribution set tags but without ResponseBody.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagsRest> createDistributionSetTags(@RequestBody final List<TagRequestBodyPut> tags);
|
||||
|
||||
/**
|
||||
*
|
||||
* Handles the PUT request of updating a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @param restDSTagRest
|
||||
* the the request body to be updated
|
||||
* @return status OK if update is successful and the updated distribution
|
||||
* set tag.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionsetTagId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> updateDistributionSetTag(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId,
|
||||
@RequestBody final TagRequestBodyPut restDSTagRest);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @return status OK if delete as successfully.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionsetTagId}")
|
||||
public ResponseEntity<Void> deleteDistributionSetTag(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all assigned distribution sets by
|
||||
* the given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
*
|
||||
* @return the list of assigned distribution sets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<DistributionSetsRest> getAssignedDistributionSets(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId);
|
||||
|
||||
/**
|
||||
* Handles the POST request to toggle the assignment of distribution sets by
|
||||
* the given tag id.
|
||||
*
|
||||
* @param distributionsetTagIds
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @param assignedDSRequestBodies
|
||||
* list of distribution set ids to be toggled
|
||||
*
|
||||
* @return the list of assigned distribution sets and unassigned
|
||||
* distribution sets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING
|
||||
+ "/toggleTagAssignment")
|
||||
public ResponseEntity<DistributionSetTagAssigmentResultRest> toggleTagAssignment(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId,
|
||||
@RequestBody final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies);
|
||||
|
||||
/**
|
||||
* Handles the POST request to assign distribution sets to the given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @param assignedDSRequestBodies
|
||||
* list of distribution sets ids to be assigned
|
||||
*
|
||||
* @return the list of assigned distribution set.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<DistributionSetsRest> assignDistributionSets(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId,
|
||||
@RequestBody final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign all distribution set from the
|
||||
* given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<Void> unassignDistributionSets(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign one distribution set from the
|
||||
* given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @param distributionsetId
|
||||
* the ID of the distribution set to unassign
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING
|
||||
+ "/{distributionsetId}")
|
||||
public ResponseEntity<Void> unassignDistributionSet(
|
||||
@PathVariable("distributionsetTagId") final Long distributionsetTagId,
|
||||
@PathVariable("distributionsetId") final Long distributionsetId);
|
||||
}
|
||||
@@ -0,0 +1,259 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.IdRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypesRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypesRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling for SoftwareModule and related Artifact CRUD
|
||||
* operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSETTYPE_V1_REQUEST_MAPPING)
|
||||
public interface DistributionSetTypeRestApi {
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all DistributionSetTypes.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all DistributionSetType for a defined or default page
|
||||
* request with status OK. The response is always paged. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetTypePagedList> getDistributionSetTypes(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single DistributionSetType
|
||||
* within.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the module type to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetTypeRest> getDistributionSetType(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single Distribution Set Type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as sucessfull.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}")
|
||||
public ResponseEntity<Void> deleteDistributionSetType(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId);
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a Distribution Set Type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the software module in the URL
|
||||
* @param restDistributionSetType
|
||||
* the module type to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetTypeId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetTypeRest> updateDistributionSetType(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId,
|
||||
@RequestBody final DistributionSetTypeRequestBodyPut restDistributionSetType);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new DistributionSetTypes. The
|
||||
* request body must always be a list of types.
|
||||
*
|
||||
* @param distributionSetTypes
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetTypesRest> createDistributionSetTypes(
|
||||
@RequestBody final List<DistributionSetTypeRequestBodyPost> distributionSetTypes);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the list of mandatory software
|
||||
* module types in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypesRest> getMandatoryModules(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the single mandatory software
|
||||
* module type in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param softwareModuleTypeId
|
||||
* of SoftwareModuleType.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getMandatoryModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId,
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the single optional software module
|
||||
* type in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param softwareModuleTypeId
|
||||
* of SoftwareModuleType.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getOptionalModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId,
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the list of optional software
|
||||
* module types in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypesRest> getOptionalModules(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId);
|
||||
|
||||
/**
|
||||
* Handles DELETE request for removing a mandatory module from the
|
||||
* DistributionSetType.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param softwareModuleTypeId
|
||||
* of the SoftwareModuleType to remove
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> removeMandatoryModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId,
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles DELETE request for removing an optional module from the
|
||||
* DistributionSetType.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param softwareModuleTypeId
|
||||
* of the SoftwareModuleType to remove
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> removeOptionalModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId,
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles the POST request for adding a mandatory software module type to a
|
||||
* distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param smtId
|
||||
* of the SoftwareModuleType to add
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> addMandatoryModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId, @RequestBody final IdRest smtId);
|
||||
|
||||
/**
|
||||
* Handles the POST request for adding an optional software module type to a
|
||||
* distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the DistributionSetType.
|
||||
* @param smtId
|
||||
* of the SoftwareModuleType to add
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> addOptionalModule(
|
||||
@PathVariable("distributionSetTypeId") final Long distributionSetTypeId, @RequestBody final IdRest smtId);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,209 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutResponseBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutRestRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rolloutgroup.RolloutGroupPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rolloutgroup.RolloutGroupResponseBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetPagedList;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling rollout CRUD operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.ROLLOUT_V1_REQUEST_MAPPING)
|
||||
public interface RolloutRestApi {
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all rollouts.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollouts for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all rollouts for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutPagedList> getRollouts(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to retrieve
|
||||
* @return a single rollout with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no rollout with the given {@code rolloutId} exists.
|
||||
*/
|
||||
@RequestMapping(value = "/{rolloutId}", method = RequestMethod.GET, produces = { MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" })
|
||||
public ResponseEntity<RolloutResponseBody> getRollout(@PathVariable("rolloutId") final Long rolloutId);
|
||||
|
||||
/**
|
||||
* Handles the POST request for creating rollout.
|
||||
*
|
||||
* @param rollout
|
||||
* the rollout body to be created.
|
||||
* @return In case rollout could successful created the ResponseEntity with
|
||||
* status code 201 with the successfully created rollout. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
* @throws EntityNotFoundException
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<RolloutResponseBody> create(@RequestBody final RolloutRestRequestBody rolloutRequestBody);
|
||||
|
||||
/**
|
||||
* Handles the POST request for starting a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be started.
|
||||
* @return OK response (200) if rollout could be started. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#startRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/start", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> start(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_ASYNC, defaultValue = "false") final boolean startAsync);
|
||||
|
||||
/**
|
||||
* Handles the POST request for pausing a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be paused.
|
||||
* @return OK response (200) if rollout could be paused. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#pauseRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/pause", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> pause(@PathVariable("rolloutId") final Long rolloutId);
|
||||
|
||||
/**
|
||||
* Handles the POST request for resuming a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be resumed.
|
||||
* @return OK response (200) if rollout could be resumed. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#resumeRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/resume", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> resume(@PathVariable("rolloutId") final Long rolloutId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all rollout groups referred to a
|
||||
* rollout.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollout groups for pagination, might not
|
||||
* be present in the rest request then default value will be
|
||||
* applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all rollout groups referred to a rollout for a defined
|
||||
* or default page request with status OK. The response is always
|
||||
* paged. In any failure the JsonResponseExceptionHandler is
|
||||
* handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutGroupPagedList> getRolloutGroups(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request for retrieving a single rollout group.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the rolloutId to retrieve the group from
|
||||
* @param groupId
|
||||
* the groupId to retrieve the rollout group
|
||||
* @return the OK response containing the RolloutGroupResponseBody
|
||||
* @throws EntityNotFoundException
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups/{groupId}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutGroupResponseBody> getRolloutGroup(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@PathVariable("groupId") final Long groupId);
|
||||
|
||||
/**
|
||||
* Retrieves all targets related to a specific rollout group.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout
|
||||
* @param groupId
|
||||
* the ID of the rollout group
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollout groups for pagination, might not
|
||||
* be present in the rest request then default value will be
|
||||
* applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a paged list of targets related to a specific rollout and rollout
|
||||
* group.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups/{groupId}/targets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getRolloutGroupTargets(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@PathVariable("groupId") final Long groupId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
}
|
||||
@@ -0,0 +1,289 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRestPageList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.artifact.ArtifactRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.artifact.ArtifactsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModulePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModuleRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremodule.SoftwareModulesRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.ResponseBody;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
/**
|
||||
* REST Resource handling for SoftwareModule and related Artifact CRUD
|
||||
* operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.SOFTWAREMODULE_V1_REQUEST_MAPPING)
|
||||
public interface SoftwareModuleRestAPI {
|
||||
|
||||
/**
|
||||
* Handles POST request for artifact upload.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent SoftwareModule
|
||||
* @param file
|
||||
* that has to be uploaded
|
||||
* @param optionalFileName
|
||||
* to override {@link MultipartFile#getOriginalFilename()}
|
||||
* @param md5Sum
|
||||
* checksum for uploaded content check
|
||||
* @param sha1Sum
|
||||
* checksum for uploaded content check
|
||||
*
|
||||
* @return In case all sets could successful be created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{softwareModuleId}/artifacts", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ArtifactRest> uploadArtifact(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@RequestParam("file") final MultipartFile file,
|
||||
@RequestParam(value = "filename", required = false) final String optionalFileName,
|
||||
@RequestParam(value = "md5sum", required = false) final String md5Sum,
|
||||
@RequestParam(value = "sha1sum", required = false) final String sha1Sum);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all meta data of artifacts assigned
|
||||
* to a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent SoftwareModule
|
||||
*
|
||||
* @return a list of all artifacts for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@ResponseBody
|
||||
public ResponseEntity<ArtifactsRest> getArtifacts(@PathVariable("softwareModuleId") final Long softwareModuleId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single Artifact meta data
|
||||
* request.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent SoftwareModule
|
||||
* @param artifactId
|
||||
* of the related LocalArtifact
|
||||
*
|
||||
* @return responseEntity with status ok if successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts/{artifactId}", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@ResponseBody
|
||||
public ResponseEntity<ArtifactRest> getArtifact(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("artifactId") final Long artifactId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single SoftwareModule.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module that has the artifact
|
||||
* @param artifactId
|
||||
* of the artifact to be deleted
|
||||
*
|
||||
* @return status OK if delete as successful.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}/artifacts/{artifactId}")
|
||||
@ResponseBody
|
||||
public ResponseEntity<Void> deleteArtifact(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("artifactId") final Long artifactId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all softwaremodules.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all modules for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModulePagedList> getSoftwareModules(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleRest> getSoftwareModule(
|
||||
@PathVariable("softwareModuleId") final Long softwareModuleId);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new softwaremodules. The request
|
||||
* body must always be a list of modules.
|
||||
*
|
||||
* @param softwareModules
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModulesRest> createSoftwareModules(
|
||||
@RequestBody final List<SoftwareModuleRequestBodyPost> softwareModules);
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module in the URL
|
||||
* @param restSoftwareModule
|
||||
* the modules to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleRest> updateSoftwareModule(
|
||||
@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@RequestBody final SoftwareModuleRequestBodyPut restSoftwareModule);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single softwaremodule.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as sucessfull.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}")
|
||||
public ResponseEntity<Void> deleteSoftwareModule(@PathVariable("softwareModuleId") final Long softwareModuleId);
|
||||
|
||||
/**
|
||||
* Gets a paged list of meta data for a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module for the meta data
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of meta data for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=key==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/metadata", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRestPageList> getMetadata(
|
||||
@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Gets a single meta data value for a specific key of a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to get the meta data from
|
||||
* @param metadataKey
|
||||
* the key of the meta data entry to retrieve the value from
|
||||
* @return status OK if get request is successful with the value of the meta
|
||||
* data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<MetadataRest> getMetadataValue(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("metadataKey") final String metadataKey);
|
||||
|
||||
/**
|
||||
* Updates a single meta data value of a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to update the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to update the value
|
||||
* @return status OK if the update request is successful and the updated
|
||||
* meta data result
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRest> updateMetadata(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("metadataKey") final String metadataKey, @RequestBody final MetadataRest metadata);
|
||||
|
||||
/**
|
||||
* Deletes a single meta data entry from the software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to delete the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to delete
|
||||
* @return status OK if the delete request is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}/metadata/{metadataKey}")
|
||||
public ResponseEntity<Void> deleteMetadata(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("metadataKey") final String metadataKey);
|
||||
|
||||
/**
|
||||
* Creates a list of meta data for a specific software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the distribution set to create meta data for
|
||||
* @param metadataRest
|
||||
* the list of meta data entries to create
|
||||
* @return status created if post request is successful with the value of
|
||||
* the created meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{softwareModuleId}/metadata", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<List<MetadataRest>> createMetadata(
|
||||
@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@RequestBody final List<MetadataRest> metadataRest);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,119 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypesRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling for SoftwareModule and related Artifact CRUD
|
||||
* operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.SOFTWAREMODULETYPE_V1_REQUEST_MAPPING)
|
||||
public interface SoftwareModuleTypeRestApi {
|
||||
/**
|
||||
* Handles the GET request of retrieving all SoftwareModuleTypes .
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all module type for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypePagedList> getTypes(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single software module type .
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the module type to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleTypeId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getSoftwareModuleType(
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single software module type .
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as successfully.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleTypeId}")
|
||||
public ResponseEntity<Void> deleteSoftwareModuleType(
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId);
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a software module type .
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the software module in the URL
|
||||
* @param restSoftwareModuleType
|
||||
* the module type to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleTypeId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> updateSoftwareModuleType(
|
||||
@PathVariable("softwareModuleTypeId") final Long softwareModuleTypeId,
|
||||
@RequestBody final SoftwareModuleTypeRequestBodyPut restSoftwareModuleType);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new SoftwareModuleTypes. The request
|
||||
* body must always be a list of types.
|
||||
*
|
||||
* @param softwareModuleTypes
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypesRest> createSoftwareModuleTypes(
|
||||
@RequestBody final List<SoftwareModuleTypeRequestBodyPost> softwareModuleTypes);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,284 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionStatusPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.DistributionSetAssigmentRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetAttributes;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* Api for handling target operations.
|
||||
*/
|
||||
@RequestMapping(RestConstants.TARGET_V1_REQUEST_MAPPING)
|
||||
public interface TargetRestApi {
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve
|
||||
* @return a single target with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetRest> getTarget(@PathVariable("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all targets.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all targets for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetPagedList> getTargets(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new targets. The request body must
|
||||
* always be a list of targets.
|
||||
*
|
||||
* @param targets
|
||||
* the targets to be created.
|
||||
* @return In case all targets could successful created the ResponseEntity
|
||||
* with status code 201 with a list of successfully created
|
||||
* entities. In any failure the JsonResponseExceptionHandler is
|
||||
* handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetsRest> createTargets(@RequestBody final List<TargetRequestBody> targets);
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a target. The ID is within the URL
|
||||
* path of the request. A given ID in the request body is ignored. It's not
|
||||
* possible to set fields to {@code null} values.
|
||||
*
|
||||
* @param targetId
|
||||
* the path parameter which contains the ID of the target
|
||||
* @param targetRest
|
||||
* the request body which contains the fields which should be
|
||||
* updated, fields which are not given are ignored for the
|
||||
* udpate.
|
||||
* @return the updated target response which contains all fields also fields
|
||||
* which have not updated
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{targetId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetRest> updateTarget(@PathVariable("targetId") final String targetId,
|
||||
@RequestBody final TargetRequestBody targetRest);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request of deleting a target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to be deleted
|
||||
* @return If the given targetId could exists and could be deleted Http OK.
|
||||
* In any failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> deleteTarget(@PathVariable("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the attributes of a specific
|
||||
* target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve the attributes.
|
||||
* @return the target attributes as map response with status OK
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/attributes", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetAttributes> getAttributes(@PathVariable("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the Actions of a specific target.
|
||||
*
|
||||
* @param targetId
|
||||
* to load actions for
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=status==pending}
|
||||
* @return a list of all Actions for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionPagedList> getActionHistory(@PathVariable("targetId") final String targetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a specific Actions of a specific
|
||||
* Target.
|
||||
*
|
||||
* @param targetId
|
||||
* to load the action for
|
||||
* @param actionId
|
||||
* to load
|
||||
* @return the action
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions/{actionId}", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionRest> getAction(@PathVariable("targetId") final String targetId,
|
||||
@PathVariable("actionId") final Long actionId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request of canceling an specific Actions of a specific
|
||||
* Target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target in the URL path parameter
|
||||
* @param actionId
|
||||
* the ID of the action in the URL path parameter
|
||||
* @param force
|
||||
* optional parameter, which indicates a force cancel
|
||||
* @return status no content in case cancellation was successful
|
||||
* @throws CancelActionNotAllowedException
|
||||
* if the given action is not active and cannot be canceled.
|
||||
* @throws EntityNotFoundException
|
||||
* if the target or the action is not found
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetId}/actions/{actionId}")
|
||||
public ResponseEntity<Void> cancelAction(@PathVariable("targetId") final String targetId,
|
||||
@PathVariable("actionId") final Long actionId,
|
||||
@RequestParam(value = "force", required = false, defaultValue = "false") final boolean force);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the ActionStatus of a specific
|
||||
* target and action.
|
||||
*
|
||||
* @param targetId
|
||||
* of the the action
|
||||
* @param actionId
|
||||
* of the status we are intend to load
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @return a list of all ActionStatus for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions/{actionId}/status", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionStatusPagedList> getActionStatusList(@PathVariable("targetId") final String targetId,
|
||||
@PathVariable("actionId") final Long actionId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the assigned distribution set of an
|
||||
* specific target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve the assigned distribution
|
||||
* @return the assigned distribution set with status OK, if none is assigned
|
||||
* than {@code null} content (e.g. "{}")
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/assignedDS", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getAssignedDistributionSet(
|
||||
@PathVariable("targetId") final String targetId);
|
||||
|
||||
/**
|
||||
* Changes the assigned distribution set of a target.
|
||||
*
|
||||
* @param targetId
|
||||
* of the target to change
|
||||
* @param dsId
|
||||
* of the distributionset that is to be assigned
|
||||
* @return http status
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{targetId}/assignedDS", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> postAssignedDistributionSet(@PathVariable("targetId") final String targetId,
|
||||
@RequestBody final DistributionSetAssigmentRest dsId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the installed distribution set of
|
||||
* an specific target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve
|
||||
* @return the assigned installed set with status OK, if none is installed
|
||||
* than {@code null} content (e.g. "{}")
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/installedDS", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getInstalledDistributionSet(
|
||||
@PathVariable("targetId") final String targetId);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,196 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource.api;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.rest.resource.RestConstants;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedTargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TargetTagAssigmentResultRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.target.TargetsRest;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
|
||||
/**
|
||||
* REST Resource handling for TargetTag CRUD operations.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(RestConstants.TARGET_TAG_V1_REQUEST_MAPPING)
|
||||
public interface TargetTagRestApi {
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all target tags.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of target tags for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all target tags for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagPagedList> getTargetTags(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single target tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
*
|
||||
* @return a single target tag with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetTagId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> getTargetTag(@PathVariable("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new target tag. The request body
|
||||
* must always be a list of tags.
|
||||
*
|
||||
* @param tags
|
||||
* the target tags to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created. The Response Body are the created
|
||||
* target tags but without ResponseBody.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagsRest> createTargetTags(@RequestBody final List<TagRequestBodyPut> tags);
|
||||
|
||||
/**
|
||||
*
|
||||
* Handles the PUT request of updating a single targetr tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @param restTargetTagRest
|
||||
* the the request body to be updated
|
||||
* @return status OK if update is successful and the updated target tag.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{targetTagId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> updateTagretTag(@PathVariable("targetTagId") final Long targetTagId,
|
||||
@RequestBody final TagRequestBodyPut restTargetTagRest);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single target tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @return status OK if delete as successfully.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetTagId}")
|
||||
public ResponseEntity<Void> deleteTargetTag(@PathVariable("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all assigned targets by the given
|
||||
* tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
*
|
||||
* @return the list of assigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<TargetsRest> getAssignedTargets(@PathVariable("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Handles the POST request to toggle the assignment of targets by the given
|
||||
* tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @param assignedTargetRequestBodies
|
||||
* list of target ids to be toggled
|
||||
*
|
||||
* @return the list of assigned targets and unassigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING
|
||||
+ "/toggleTagAssignment")
|
||||
public ResponseEntity<TargetTagAssigmentResultRest> toggleTagAssignment(
|
||||
@PathVariable("targetTagId") final Long targetTagId,
|
||||
@RequestBody final List<AssignedTargetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Handles the POST request to assign targets to the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @param assignedTargetRequestBodies
|
||||
* list of target ids to be assigned
|
||||
*
|
||||
* @return the list of assigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<TargetsRest> assignTargets(@PathVariable("targetTagId") final Long targetTagId,
|
||||
@RequestBody final List<AssignedTargetRequestBody> assignedTargetRequestBodies);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign all targets from the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<Void> unassignTargets(@PathVariable("targetTagId") final Long targetTagId);
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign one target from the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @param controllerId
|
||||
* the ID of the target to unassign
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING
|
||||
+ "/{controllerId}")
|
||||
public ResponseEntity<Void> unassignTarget(@PathVariable("targetTagId") final Long targetTagId,
|
||||
@PathVariable("controllerId") final String controllerId);
|
||||
}
|
||||
@@ -22,6 +22,8 @@ import org.eclipse.hawkbit.repository.model.DistributionSet;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetMetadata;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetType;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetRest;
|
||||
@@ -169,13 +171,13 @@ public final class DistributionSetMapper {
|
||||
response.setRequiredMigrationStep(distributionSet.isRequiredMigrationStep());
|
||||
|
||||
response.add(
|
||||
linkTo(methodOn(DistributionSetResource.class).getDistributionSet(response.getDsId())).withRel("self"));
|
||||
linkTo(methodOn(DistributionSetRestApi.class).getDistributionSet(response.getDsId())).withRel("self"));
|
||||
|
||||
response.add(linkTo(
|
||||
methodOn(DistributionSetTypeResource.class).getDistributionSetType(distributionSet.getType().getId()))
|
||||
methodOn(DistributionSetTypeRestApi.class).getDistributionSetType(distributionSet.getType().getId()))
|
||||
.withRel("type"));
|
||||
|
||||
response.add(linkTo(methodOn(DistributionSetResource.class).getMetadata(response.getDsId(),
|
||||
response.add(linkTo(methodOn(DistributionSetRestApi.class).getMetadata(response.getDsId(),
|
||||
Integer.parseInt(RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET),
|
||||
Integer.parseInt(RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT), null, null))
|
||||
.withRel("metadata"));
|
||||
|
||||
@@ -30,6 +30,7 @@ import org.eclipse.hawkbit.repository.model.DsMetadataCompositeKey;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.helper.RestResourceConversionHelper;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRestPageList;
|
||||
@@ -51,25 +52,14 @@ import org.springframework.data.domain.Page;
|
||||
import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* REST Resource handling for {@link DistributionSet} CRUD operations.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSET_V1_REQUEST_MAPPING)
|
||||
public class DistributionSetResource {
|
||||
public class DistributionSetResource implements DistributionSetRestApi {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(DistributionSetResource.class);
|
||||
|
||||
@Autowired
|
||||
@@ -90,32 +80,9 @@ public class DistributionSetResource {
|
||||
@Autowired
|
||||
private DistributionSetManagement distributionSetManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all {@link DistributionSet}s within
|
||||
* SP.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of sets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all set for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetPagedList> getDistributionSets(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetPagedList> getDistributionSets(final int pagingOffsetParam,
|
||||
final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -124,99 +91,51 @@ public class DistributionSetResource {
|
||||
final Pageable pageable = new OffsetBasedPageRequest(sanitizedOffsetParam, sanitizedLimitParam, sorting);
|
||||
final Page<DistributionSet> findDsPage;
|
||||
if (rsqlParam != null) {
|
||||
findDsPage = distributionSetManagement.findDistributionSetsAll(
|
||||
findDsPage = this.distributionSetManagement.findDistributionSetsAll(
|
||||
RSQLUtility.parse(rsqlParam, DistributionSetFields.class), pageable, false);
|
||||
} else {
|
||||
findDsPage = distributionSetManagement.findDistributionSetsAll(pageable, false, null);
|
||||
findDsPage = this.distributionSetManagement.findDistributionSetsAll(pageable, false, null);
|
||||
}
|
||||
|
||||
final List<DistributionSetRest> rest = DistributionSetMapper.toResponseFromDsList(findDsPage.getContent());
|
||||
return new ResponseEntity<>(new DistributionSetPagedList(rest, findDsPage.getTotalElements()), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single {@link DistributionSet}
|
||||
* within SP.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the set to retrieve
|
||||
*
|
||||
* @return a single {@link DistributionSet} with status OK.
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no {@link DistributionSet} with the given ID exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getDistributionSet(@PathVariable final Long distributionSetId) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetRest> getDistributionSet(final Long distributionSetId) {
|
||||
final DistributionSet foundDs = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
|
||||
return new ResponseEntity<>(DistributionSetMapper.toResponse(foundDs), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new distribution sets within SP. The
|
||||
* request body must always be a list of sets. The requests is delegating to
|
||||
* the {@link SoftwareManagement#createDistributionSet(DistributionSet))}.
|
||||
*
|
||||
* @param sets
|
||||
* the {@link DistributionSet}s to be created.
|
||||
* @return In case all sets could successful created the ResponseEntity with
|
||||
* status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetsRest> createDistributionSets(
|
||||
@RequestBody final List<DistributionSetRequestBodyPost> sets) {
|
||||
final List<DistributionSetRequestBodyPost> sets) {
|
||||
|
||||
LOG.debug("creating {} distribution sets", sets.size());
|
||||
// set default Ds type if ds type is null
|
||||
sets.stream().filter(ds -> ds.getType() == null).forEach(ds -> ds.setType(
|
||||
systemManagement.getTenantMetadata(currentTenant.getCurrentTenant()).getDefaultDsType().getKey()));
|
||||
sets.stream().filter(ds -> ds.getType() == null).forEach(ds -> ds.setType(this.systemManagement
|
||||
.getTenantMetadata(this.currentTenant.getCurrentTenant()).getDefaultDsType().getKey()));
|
||||
|
||||
final Iterable<DistributionSet> createdDSets = distributionSetManagement.createDistributionSets(
|
||||
DistributionSetMapper.dsFromRequest(sets, softwareManagement, distributionSetManagement));
|
||||
final Iterable<DistributionSet> createdDSets = this.distributionSetManagement.createDistributionSets(
|
||||
DistributionSetMapper.dsFromRequest(sets, this.softwareManagement, this.distributionSetManagement));
|
||||
|
||||
LOG.debug("{} distribution sets created, return status {}", sets.size(), HttpStatus.CREATED);
|
||||
return new ResponseEntity<>(DistributionSetMapper.toResponseDistributionSets(createdDSets), HttpStatus.CREATED);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single {@link DistributionSet} within
|
||||
* SP.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the {@link DistributionSet} to delete
|
||||
* @return status OK if delete as successful.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}")
|
||||
public ResponseEntity<Void> deleteDistributionSet(@PathVariable final Long distributionSetId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteDistributionSet(final Long distributionSetId) {
|
||||
final DistributionSet set = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
|
||||
distributionSetManagement.deleteDistributionSet(set);
|
||||
this.distributionSetManagement.deleteDistributionSet(set);
|
||||
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the UPDATE request for a single {@link DistributionSet} within
|
||||
* SP.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the {@link DistributionSet} to delete
|
||||
* @param toUpdate
|
||||
* with the data that needs updating
|
||||
*
|
||||
* @return status OK if update as successful with updated content.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<DistributionSetRest> updateDistributionSet(@PathVariable final Long distributionSetId,
|
||||
@RequestBody final DistributionSetRequestBodyPut toUpdate) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetRest> updateDistributionSet(final Long distributionSetId,
|
||||
final DistributionSetRequestBodyPut toUpdate) {
|
||||
final DistributionSet set = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
|
||||
if (toUpdate.getDescription() != null) {
|
||||
@@ -231,38 +150,13 @@ public class DistributionSetResource {
|
||||
set.setVersion(toUpdate.getVersion());
|
||||
}
|
||||
return new ResponseEntity<>(
|
||||
DistributionSetMapper.toResponse(distributionSetManagement.updateDistributionSet(set)), HttpStatus.OK);
|
||||
DistributionSetMapper.toResponse(this.distributionSetManagement.updateDistributionSet(set)),
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving assigned targets to a specific
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to retrieve the assigned
|
||||
* targets
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* targets
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/assignedTargets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getAssignedTargets(@PathVariable final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TargetPagedList> getAssignedTargets(final Long distributionSetId, final int pagingOffsetParam,
|
||||
final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
@@ -275,45 +169,19 @@ public class DistributionSetResource {
|
||||
final Pageable pageable = new OffsetBasedPageRequest(sanitizedOffsetParam, sanitizedLimitParam, sorting);
|
||||
final Page<Target> targetsAssignedDS;
|
||||
if (rsqlParam != null) {
|
||||
targetsAssignedDS = targetManagement.findTargetByAssignedDistributionSet(distributionSetId,
|
||||
targetsAssignedDS = this.targetManagement.findTargetByAssignedDistributionSet(distributionSetId,
|
||||
RSQLUtility.parse(rsqlParam, TargetFields.class), pageable);
|
||||
} else {
|
||||
targetsAssignedDS = targetManagement.findTargetByAssignedDistributionSet(distributionSetId, pageable);
|
||||
targetsAssignedDS = this.targetManagement.findTargetByAssignedDistributionSet(distributionSetId, pageable);
|
||||
}
|
||||
|
||||
return new ResponseEntity<>(new TargetPagedList(TargetMapper.toResponse(targetsAssignedDS.getContent()),
|
||||
targetsAssignedDS.getTotalElements()), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving installed targets to a specific
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to retrieve the assigned
|
||||
* targets
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* targets
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/installedTargets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getInstalledTargets(@PathVariable final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TargetPagedList> getInstalledTargets(final Long distributionSetId,
|
||||
final int pagingOffsetParam, final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
@@ -325,36 +193,22 @@ public class DistributionSetResource {
|
||||
final Pageable pageable = new OffsetBasedPageRequest(sanitizedOffsetParam, sanitizedLimitParam, sorting);
|
||||
final Page<Target> targetsInstalledDS;
|
||||
if (rsqlParam != null) {
|
||||
targetsInstalledDS = targetManagement.findTargetByInstalledDistributionSet(distributionSetId,
|
||||
targetsInstalledDS = this.targetManagement.findTargetByInstalledDistributionSet(distributionSetId,
|
||||
RSQLUtility.parse(rsqlParam, TargetFields.class), pageable);
|
||||
} else {
|
||||
targetsInstalledDS = targetManagement.findTargetByInstalledDistributionSet(distributionSetId, pageable);
|
||||
targetsInstalledDS = this.targetManagement.findTargetByInstalledDistributionSet(distributionSetId,
|
||||
pageable);
|
||||
}
|
||||
|
||||
return new ResponseEntity<>(new TargetPagedList(TargetMapper.toResponse(targetsInstalledDS.getContent()),
|
||||
targetsInstalledDS.getTotalElements()), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of assigning multiple targets to a single
|
||||
* distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set within the URL path parameter
|
||||
* @param targetIds
|
||||
* the IDs of the target which should get assigned to the
|
||||
* distribution set given in the response body
|
||||
* @return status OK if the assignment of the targets was successful and a
|
||||
* complex return body which contains information about the assigned
|
||||
* targets and the already assigned targets counters
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/assignedTargets", consumes = {
|
||||
"application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetAssignmentResponseBody> createAssignedTarget(@PathVariable final Long distributionSetId,
|
||||
@RequestBody final List<TargetAssignmentRequestBody> targetIds) {
|
||||
@Override
|
||||
public ResponseEntity<TargetAssignmentResponseBody> createAssignedTarget(final Long distributionSetId,
|
||||
final List<TargetAssignmentRequestBody> targetIds) {
|
||||
|
||||
final DistributionSetAssignmentResult assignDistributionSet = deployManagament.assignDistributionSet(
|
||||
final DistributionSetAssignmentResult assignDistributionSet = this.deployManagament.assignDistributionSet(
|
||||
distributionSetId,
|
||||
targetIds.stream()
|
||||
.map(t -> new TargetWithActionType(t.getId(),
|
||||
@@ -364,33 +218,9 @@ public class DistributionSetResource {
|
||||
return new ResponseEntity<>(DistributionSetMapper.toResponse(assignDistributionSet), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a paged list of meta data for a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set for the meta data
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=key==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/metadata", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRestPageList> getMetadata(@PathVariable final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<MetadataRestPageList> getMetadata(final Long distributionSetId, final int pagingOffsetParam,
|
||||
final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
@@ -404,11 +234,11 @@ public class DistributionSetResource {
|
||||
final Page<DistributionSetMetadata> metaDataPage;
|
||||
|
||||
if (rsqlParam != null) {
|
||||
metaDataPage = distributionSetManagement.findDistributionSetMetadataByDistributionSetId(distributionSetId,
|
||||
RSQLUtility.parse(rsqlParam, DistributionSetMetadataFields.class), pageable);
|
||||
metaDataPage = this.distributionSetManagement.findDistributionSetMetadataByDistributionSetId(
|
||||
distributionSetId, RSQLUtility.parse(rsqlParam, DistributionSetMetadataFields.class), pageable);
|
||||
} else {
|
||||
metaDataPage = distributionSetManagement.findDistributionSetMetadataByDistributionSetId(distributionSetId,
|
||||
pageable);
|
||||
metaDataPage = this.distributionSetManagement
|
||||
.findDistributionSetMetadataByDistributionSetId(distributionSetId, pageable);
|
||||
}
|
||||
|
||||
return new ResponseEntity<>(
|
||||
@@ -418,119 +248,59 @@ public class DistributionSetResource {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a single meta data value for a specific key of a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to get the meta data from
|
||||
* @param metadataKey
|
||||
* the key of the meta data entry to retrieve the value from
|
||||
* @return status OK if get request is successful with the value of the meta
|
||||
* data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<MetadataRest> getMetadataValue(@PathVariable final Long distributionSetId,
|
||||
@PathVariable final String metadataKey) {
|
||||
@Override
|
||||
public ResponseEntity<MetadataRest> getMetadataValue(final Long distributionSetId, final String metadataKey) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
final DistributionSetMetadata findOne = distributionSetManagement
|
||||
final DistributionSetMetadata findOne = this.distributionSetManagement
|
||||
.findOne(new DsMetadataCompositeKey(ds, metadataKey));
|
||||
return ResponseEntity.<MetadataRest> ok(DistributionSetMapper.toResponseDsMetadata(findOne));
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates a single meta data value of a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to update the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to update the value
|
||||
* @return status OK if the update request is successful and the updated
|
||||
* meta data result
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<MetadataRest> updateMetadata(@PathVariable final Long distributionSetId,
|
||||
@PathVariable final String metadataKey, @RequestBody final MetadataRest metadata) {
|
||||
@Override
|
||||
public ResponseEntity<MetadataRest> updateMetadata(final Long distributionSetId, final String metadataKey,
|
||||
final MetadataRest metadata) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
final DistributionSetMetadata updated = distributionSetManagement
|
||||
final DistributionSetMetadata updated = this.distributionSetManagement
|
||||
.updateDistributionSetMetadata(new DistributionSetMetadata(metadataKey, ds, metadata.getValue()));
|
||||
return ResponseEntity.ok(DistributionSetMapper.toResponseDsMetadata(updated));
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes a single meta data entry from the distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to delete the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to delete
|
||||
* @return status OK if the delete request is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}/metadata/{metadataKey}")
|
||||
public ResponseEntity<Void> deleteMetadata(@PathVariable final Long distributionSetId,
|
||||
@PathVariable final String metadataKey) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteMetadata(final Long distributionSetId, final String metadataKey) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
distributionSetManagement.deleteDistributionSetMetadata(new DsMetadataCompositeKey(ds, metadataKey));
|
||||
this.distributionSetManagement.deleteDistributionSetMetadata(new DsMetadataCompositeKey(ds, metadataKey));
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a list of meta data for a specific distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to create meta data for
|
||||
* @param metadataRest
|
||||
* the list of meta data entries to create
|
||||
* @return status created if post request is successful with the value of
|
||||
* the created meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/metadata", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<List<MetadataRest>> createMetadata(@PathVariable final Long distributionSetId,
|
||||
@RequestBody final List<MetadataRest> metadataRest) {
|
||||
@Override
|
||||
public ResponseEntity<List<MetadataRest>> createMetadata(final Long distributionSetId,
|
||||
final List<MetadataRest> metadataRest) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
|
||||
final List<DistributionSetMetadata> created = distributionSetManagement
|
||||
final List<DistributionSetMetadata> created = this.distributionSetManagement
|
||||
.createDistributionSetMetadata(DistributionSetMapper.fromRequestDsMetadata(ds, metadataRest));
|
||||
return new ResponseEntity<>(DistributionSetMapper.toResponseDsMetadata(created), HttpStatus.CREATED);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Assigns a list of software modules to a distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to assign software modules for
|
||||
* @param softwareModuleIDs
|
||||
* the list of software modules ids to assign
|
||||
* @return {@link HttpStatus#OK}
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetId}/assignedSM", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> assignSoftwareModules(@PathVariable final Long distributionSetId,
|
||||
@RequestBody final List<SoftwareModuleAssigmentRest> softwareModuleIDs) {
|
||||
@Override
|
||||
public ResponseEntity<Void> assignSoftwareModules(final Long distributionSetId,
|
||||
final List<SoftwareModuleAssigmentRest> softwareModuleIDs) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
|
||||
final Set<SoftwareModule> softwareModuleToBeAssigned = new HashSet<>();
|
||||
for (final SoftwareModuleAssigmentRest sm : softwareModuleIDs) {
|
||||
final SoftwareModule softwareModule = softwareManagement.findSoftwareModuleById(sm.getId());
|
||||
final SoftwareModule softwareModule = this.softwareManagement.findSoftwareModuleById(sm.getId());
|
||||
if (softwareModule != null) {
|
||||
softwareModuleToBeAssigned.add(softwareModule);
|
||||
} else {
|
||||
@@ -538,63 +308,23 @@ public class DistributionSetResource {
|
||||
}
|
||||
}
|
||||
// Add Softwaremodules to DisSet only if all of them were found
|
||||
distributionSetManagement.assignSoftwareModules(ds, softwareModuleToBeAssigned);
|
||||
this.distributionSetManagement.assignSoftwareModules(ds, softwareModuleToBeAssigned);
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes the assignment of the software module form the distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution set to reject the software module
|
||||
* for
|
||||
* @param softwareModuleId
|
||||
* the software module id to get rejected form the distribution
|
||||
* set
|
||||
* @return status OK if rejection was successful.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetId}/assignedSM/{softwareModuleId}")
|
||||
public ResponseEntity<Void> deleteAssignSoftwareModules(@PathVariable final Long distributionSetId,
|
||||
@PathVariable final Long softwareModuleId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteAssignSoftwareModules(final Long distributionSetId, final Long softwareModuleId) {
|
||||
// check if distribution set and software module exist otherwise throw
|
||||
// exception immediately
|
||||
final DistributionSet ds = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
final SoftwareModule sm = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId);
|
||||
distributionSetManagement.unassignSoftwareModule(ds, sm);
|
||||
this.distributionSetManagement.unassignSoftwareModule(ds, sm);
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request for retrieving the assigned software modules of a
|
||||
* specific distribution set.
|
||||
*
|
||||
* @param distributionSetId
|
||||
* the ID of the distribution to retrieve
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of sets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @return a list of the assigned software modules of a distribution set
|
||||
* with status OK, if none is assigned than {@code null}
|
||||
* @throws EntityNotFoundException
|
||||
* in case no distribution set with the given
|
||||
* {@code distributionSetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetId}/assignedSM", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModulePagedList> getAssignedSoftwareModules(
|
||||
@PathVariable final Long distributionSetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam) {
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModulePagedList> getAssignedSoftwareModules(final Long distributionSetId,
|
||||
final int pagingOffsetParam, final int pagingLimitParam, final String sortParam) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
// immediately
|
||||
final DistributionSet foundDs = findDistributionSetWithExceptionIfNotFound(distributionSetId);
|
||||
@@ -602,7 +332,7 @@ public class DistributionSetResource {
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
final Sort sorting = PagingUtility.sanitizeSoftwareModuleSortParam(sortParam);
|
||||
final Pageable pageable = new OffsetBasedPageRequest(sanitizedOffsetParam, sanitizedLimitParam, sorting);
|
||||
final Page<SoftwareModule> softwaremodules = softwareManagement.findSoftwareModuleByAssignedTo(pageable,
|
||||
final Page<SoftwareModule> softwaremodules = this.softwareManagement.findSoftwareModuleByAssignedTo(pageable,
|
||||
foundDs);
|
||||
return new ResponseEntity<>(
|
||||
new SoftwareModulePagedList(SoftwareModuleMapper.toResponse(softwaremodules.getContent()),
|
||||
@@ -611,7 +341,7 @@ public class DistributionSetResource {
|
||||
}
|
||||
|
||||
private DistributionSet findDistributionSetWithExceptionIfNotFound(final Long distributionSetId) {
|
||||
final DistributionSet set = distributionSetManagement.findDistributionSetById(distributionSetId);
|
||||
final DistributionSet set = this.distributionSetManagement.findDistributionSetById(distributionSetId);
|
||||
if (set == null) {
|
||||
throw new EntityNotFoundException("DistributionSet with Id {" + distributionSetId + "} does not exist");
|
||||
}
|
||||
@@ -620,7 +350,7 @@ public class DistributionSetResource {
|
||||
}
|
||||
|
||||
private SoftwareModule findSoftwareModuleWithExceptionIfNotFound(final Long softwareModuleId) {
|
||||
final SoftwareModule sm = softwareManagement.findSoftwareModuleById(softwareModuleId);
|
||||
final SoftwareModule sm = this.softwareManagement.findSoftwareModuleById(softwareModuleId);
|
||||
if (sm == null) {
|
||||
throw new EntityNotFoundException("SoftwareModule with Id {" + softwareModuleId + "} does not exist");
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import org.eclipse.hawkbit.repository.model.DistributionSet;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetTag;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetTagAssigmentResult;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTagRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionset.DistributionSetsRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedDistributionSetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.DistributionSetTagAssigmentResultRest;
|
||||
@@ -34,13 +35,7 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
@@ -48,8 +43,7 @@ import org.springframework.web.bind.annotation.RestController;
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSET_TAG_V1_REQUEST_MAPPING)
|
||||
public class DistributionSetTagResource {
|
||||
public class DistributionSetTagResource implements DistributionSetTagRestApi {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(DistributionSetTagResource.class);
|
||||
|
||||
@Autowired
|
||||
@@ -58,32 +52,9 @@ public class DistributionSetTagResource {
|
||||
@Autowired
|
||||
private DistributionSetManagement distributionSetManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all DistributionSet tags.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of DistributionSet tags for pagination,
|
||||
* might not be present in the rest request then default value
|
||||
* will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all target tags for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagPagedList> getDistributionSetTags(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TagPagedList> getDistributionSetTags(final int pagingOffsetParam, final int pagingLimitParam,
|
||||
final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -93,11 +64,11 @@ public class DistributionSetTagResource {
|
||||
final Slice<DistributionSetTag> findTargetsAll;
|
||||
final Long countTargetsAll;
|
||||
if (rsqlParam == null) {
|
||||
findTargetsAll = tagManagement.findAllDistributionSetTags(pageable);
|
||||
countTargetsAll = tagManagement.countTargetTags();
|
||||
findTargetsAll = this.tagManagement.findAllDistributionSetTags(pageable);
|
||||
countTargetsAll = this.tagManagement.countTargetTags();
|
||||
|
||||
} else {
|
||||
final Page<DistributionSetTag> findTargetPage = tagManagement
|
||||
final Page<DistributionSetTag> findTargetPage = this.tagManagement
|
||||
.findAllDistributionSetTags(RSQLUtility.parse(rsqlParam, TagFields.class), pageable);
|
||||
countTargetsAll = findTargetPage.getTotalElements();
|
||||
findTargetsAll = findTargetPage;
|
||||
@@ -108,141 +79,63 @@ public class DistributionSetTagResource {
|
||||
return new ResponseEntity<>(new TagPagedList(rest, countTargetsAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
*
|
||||
* @return a single distribution set tag with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionsetTagId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> getDistributionSetTag(@PathVariable final Long distributionsetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<TagRest> getDistributionSetTag(final Long distributionsetTagId) {
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
return new ResponseEntity<>(TagMapper.toResponse(tag), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new distribution set tag. The
|
||||
* request body must always be a list of tags.
|
||||
*
|
||||
* @param tags
|
||||
* the distribution set tags to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created. The Response Body are the created
|
||||
* distribution set tags but without ResponseBody.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagsRest> createDistributionSetTags(@RequestBody final List<TagRequestBodyPut> tags) {
|
||||
@Override
|
||||
public ResponseEntity<TagsRest> createDistributionSetTags(final List<TagRequestBodyPut> tags) {
|
||||
LOG.debug("creating {} ds tags", tags.size());
|
||||
|
||||
final List<DistributionSetTag> createdTags = tagManagement
|
||||
final List<DistributionSetTag> createdTags = this.tagManagement
|
||||
.createDistributionSetTags(TagMapper.mapDistributionSetTagFromRequest(tags));
|
||||
|
||||
return new ResponseEntity<>(TagMapper.toResponseDistributionSetTag(createdTags), HttpStatus.CREATED);
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Handles the PUT request of updating a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @param restDSTagRest
|
||||
* the the request body to be updated
|
||||
* @return status OK if update is successful and the updated distribution
|
||||
* set tag.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionsetTagId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> updateDistributionSetTag(@PathVariable final Long distributionsetTagId,
|
||||
@RequestBody final TagRequestBodyPut restDSTagRest) {
|
||||
@Override
|
||||
public ResponseEntity<TagRest> updateDistributionSetTag(final Long distributionsetTagId,
|
||||
final TagRequestBodyPut restDSTagRest) {
|
||||
LOG.debug("update {} ds tag", restDSTagRest);
|
||||
|
||||
final DistributionSetTag distributionSetTag = findDistributionTagById(distributionsetTagId);
|
||||
TagMapper.updateTag(restDSTagRest, distributionSetTag);
|
||||
final DistributionSetTag updateDistributionSetTag = tagManagement.updateDistributionSetTag(distributionSetTag);
|
||||
final DistributionSetTag updateDistributionSetTag = this.tagManagement
|
||||
.updateDistributionSetTag(distributionSetTag);
|
||||
|
||||
LOG.debug("ds tag updated");
|
||||
|
||||
return new ResponseEntity<>(TagMapper.toResponse(updateDistributionSetTag), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single distribution set tag.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @return status OK if delete as successfully.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionsetTagId}")
|
||||
public ResponseEntity<Void> deleteDistributionSetTag(@PathVariable final Long distributionsetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteDistributionSetTag(final Long distributionsetTagId) {
|
||||
LOG.debug("Delete {} distribution set tag", distributionsetTagId);
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
|
||||
tagManagement.deleteDistributionSetTag(tag.getName());
|
||||
this.tagManagement.deleteDistributionSetTag(tag.getName());
|
||||
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all assigned distribution sets by
|
||||
* the given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
*
|
||||
* @return the list of assigned distribution sets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<DistributionSetsRest> getAssignedDistributionSets(
|
||||
@PathVariable final Long distributionsetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetsRest> getAssignedDistributionSets(final Long distributionsetTagId) {
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
return new ResponseEntity<>(
|
||||
DistributionSetMapper.toResponseDistributionSets(tag.getAssignedToDistributionSet()), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request to toggle the assignment of distribution sets by
|
||||
* the given tag id.
|
||||
*
|
||||
* @param distributionsetTagIds
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @param assignedDSRequestBodies
|
||||
* list of distribution set ids to be toggled
|
||||
*
|
||||
* @return the list of assigned distribution sets and unassigned
|
||||
* distribution sets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING
|
||||
+ "/toggleTagAssignment")
|
||||
public ResponseEntity<DistributionSetTagAssigmentResultRest> toggleTagAssignment(
|
||||
@PathVariable final Long distributionsetTagId,
|
||||
@RequestBody final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetTagAssigmentResultRest> toggleTagAssignment(final Long distributionsetTagId,
|
||||
final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies) {
|
||||
LOG.debug("Toggle distribution set assignment {} for ds tag {}", assignedDSRequestBodies.size(),
|
||||
distributionsetTagId);
|
||||
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
|
||||
final DistributionSetTagAssigmentResult assigmentResult = distributionSetManagement
|
||||
final DistributionSetTagAssigmentResult assigmentResult = this.distributionSetManagement
|
||||
.toggleTagAssignment(findDistributionSetIds(assignedDSRequestBodies), tag.getName());
|
||||
|
||||
final DistributionSetTagAssigmentResultRest tagAssigmentResultRest = new DistributionSetTagAssigmentResultRest();
|
||||
@@ -257,44 +150,20 @@ public class DistributionSetTagResource {
|
||||
return new ResponseEntity<>(tagAssigmentResultRest, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request to assign distribution sets to the given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @param assignedDSRequestBodies
|
||||
* list of distribution sets ids to be assigned
|
||||
*
|
||||
* @return the list of assigned distribution set.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<DistributionSetsRest> assignDistributionSets(@PathVariable final Long distributionsetTagId,
|
||||
@RequestBody final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetsRest> assignDistributionSets(final Long distributionsetTagId,
|
||||
final List<AssignedDistributionSetRequestBody> assignedDSRequestBodies) {
|
||||
LOG.debug("Assign DistributionSet {} for ds tag {}", assignedDSRequestBodies.size(), distributionsetTagId);
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
|
||||
final List<DistributionSet> assignedDs = distributionSetManagement
|
||||
final List<DistributionSet> assignedDs = this.distributionSetManagement
|
||||
.assignTag(findDistributionSetIds(assignedDSRequestBodies), tag);
|
||||
LOG.debug("Assignd DistributionSet {}", assignedDs.size());
|
||||
return new ResponseEntity<>(DistributionSetMapper.toResponseDistributionSets(assignedDs), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign all distribution set from the
|
||||
* given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag to retrieve
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING)
|
||||
public ResponseEntity<Void> unassignDistributionSets(@PathVariable final Long distributionsetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> unassignDistributionSets(final Long distributionsetTagId) {
|
||||
LOG.debug("Unassign all DS for ds tag {}", distributionsetTagId);
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
if (tag.getAssignedToDistributionSet() == null) {
|
||||
@@ -302,36 +171,22 @@ public class DistributionSetTagResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
final List<DistributionSet> distributionSets = distributionSetManagement.unAssignAllDistributionSetsByTag(tag);
|
||||
final List<DistributionSet> distributionSets = this.distributionSetManagement
|
||||
.unAssignAllDistributionSetsByTag(tag);
|
||||
LOG.debug("Unassigned ds {}", distributionSets.size());
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign one distribution set from the
|
||||
* given tag id.
|
||||
*
|
||||
* @param distributionsetTagId
|
||||
* the ID of the distribution set tag
|
||||
* @param distributionsetId
|
||||
* the ID of the distribution set to unassign
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code distributionsetTagId} doesn't
|
||||
* exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = RestConstants.DISTRIBUTIONSET_REQUEST_MAPPING
|
||||
+ "/{distributionsetId}")
|
||||
public ResponseEntity<Void> unassignDistributionSet(@PathVariable final Long distributionsetTagId,
|
||||
@PathVariable final Long distributionsetId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> unassignDistributionSet(final Long distributionsetTagId, final Long distributionsetId) {
|
||||
LOG.debug("Unassign ds {} for ds tag {}", distributionsetId, distributionsetTagId);
|
||||
final DistributionSetTag tag = findDistributionTagById(distributionsetTagId);
|
||||
distributionSetManagement.unAssignTag(distributionsetId, tag);
|
||||
this.distributionSetManagement.unAssignTag(distributionsetId, tag);
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
private DistributionSetTag findDistributionTagById(final Long distributionsetTagId) {
|
||||
final DistributionSetTag tag = tagManagement.findDistributionSetTagById(distributionsetTagId);
|
||||
final DistributionSetTag tag = this.tagManagement.findDistributionSetTagById(distributionsetTagId);
|
||||
if (tag == null) {
|
||||
throw new EntityNotFoundException("Distribution Tag with Id {" + distributionsetTagId + "} does not exist");
|
||||
}
|
||||
|
||||
@@ -18,6 +18,7 @@ import org.eclipse.hawkbit.repository.SoftwareManagement;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetType;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypesRest;
|
||||
@@ -101,13 +102,13 @@ final class DistributionSetTypeMapper {
|
||||
result.setKey(type.getKey());
|
||||
result.setModuleId(type.getId());
|
||||
|
||||
result.add(linkTo(methodOn(DistributionSetTypeResource.class).getDistributionSetType(result.getModuleId()))
|
||||
result.add(linkTo(methodOn(DistributionSetTypeRestApi.class).getDistributionSetType(result.getModuleId()))
|
||||
.withRel("self"));
|
||||
|
||||
result.add(linkTo(methodOn(DistributionSetTypeResource.class).getMandatoryModules(result.getModuleId()))
|
||||
result.add(linkTo(methodOn(DistributionSetTypeRestApi.class).getMandatoryModules(result.getModuleId()))
|
||||
.withRel(RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULES));
|
||||
|
||||
result.add(linkTo(methodOn(DistributionSetTypeResource.class).getOptionalModules(result.getModuleId()))
|
||||
result.add(linkTo(methodOn(DistributionSetTypeRestApi.class).getOptionalModules(result.getModuleId()))
|
||||
.withRel(RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULES));
|
||||
|
||||
return result;
|
||||
|
||||
@@ -19,6 +19,7 @@ import org.eclipse.hawkbit.repository.model.DistributionSetType;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.IdRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.distributionsettype.DistributionSetTypeRequestBodyPost;
|
||||
@@ -33,12 +34,9 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
@@ -47,12 +45,9 @@ import org.springframework.web.bind.annotation.RestController;
|
||||
* {@link Artifact} CRUD operations.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.DISTRIBUTIONSETTYPE_V1_REQUEST_MAPPING)
|
||||
public class DistributionSetTypeResource {
|
||||
public class DistributionSetTypeResource implements DistributionSetTypeRestApi {
|
||||
|
||||
@Autowired
|
||||
private SoftwareManagement softwareManagement;
|
||||
@@ -60,30 +55,7 @@ public class DistributionSetTypeResource {
|
||||
@Autowired
|
||||
private DistributionSetManagement distributionSetManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all {@link DistributionSetType}s
|
||||
* within SP.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all {@link DistributionSetType} for a defined or
|
||||
* default page request with status OK. The response is always
|
||||
* paged. In any failure the JsonResponseExceptionHandler is
|
||||
* handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetTypePagedList> getDistributionSetTypes(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@@ -112,19 +84,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(new DistributionSetTypePagedList(rest, countModulesAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single
|
||||
* {@link DistributionSetType} within SP.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the module type to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetTypeRest> getDistributionSetType(
|
||||
@PathVariable final Long distributionSetTypeId) {
|
||||
final DistributionSetType foundType = findDistributionSetTypeWithExceptionIfNotFound(distributionSetTypeId);
|
||||
@@ -132,15 +92,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(DistributionSetTypeMapper.toResponse(foundType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single Distribution Set Type within SP.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as sucessfull.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}")
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteDistributionSetType(@PathVariable final Long distributionSetTypeId) {
|
||||
final DistributionSetType module = findDistributionSetTypeWithExceptionIfNotFound(distributionSetTypeId);
|
||||
|
||||
@@ -149,17 +101,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a Distribution Set Type within SP.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* the ID of the software module in the URL
|
||||
* @param restDistributionSetType
|
||||
* the module type to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{distributionSetTypeId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetTypeRest> updateDistributionSetType(
|
||||
@PathVariable final Long distributionSetTypeId,
|
||||
@RequestBody final DistributionSetTypeRequestBodyPut restDistributionSetType) {
|
||||
@@ -176,19 +118,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(DistributionSetTypeMapper.toResponse(updatedDistributionSetType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new {@link DistributionSetType}s
|
||||
* within SP. The request body must always be a list of types.
|
||||
*
|
||||
* @param distributionSetTypes
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetTypesRest> createDistributionSetTypes(
|
||||
@RequestBody final List<DistributionSetTypeRequestBodyPost> distributionSetTypes) {
|
||||
|
||||
@@ -208,17 +138,7 @@ public class DistributionSetTypeResource {
|
||||
return module;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the list of mandatory software
|
||||
* module types in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypesRest> getMandatoryModules(@PathVariable final Long distributionSetTypeId) {
|
||||
|
||||
final DistributionSetType foundType = findDistributionSetTypeWithExceptionIfNotFound(distributionSetTypeId);
|
||||
@@ -229,19 +149,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(rest, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the single mandatory software
|
||||
* module type in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param softwareModuleTypeId
|
||||
* of {@link SoftwareModuleType}.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getMandatoryModule(@PathVariable final Long distributionSetTypeId,
|
||||
@PathVariable final Long softwareModuleTypeId) {
|
||||
|
||||
@@ -257,19 +165,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(SoftwareModuleTypeMapper.toResponse(foundSmType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the single optional software module
|
||||
* type in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param softwareModuleTypeId
|
||||
* of {@link SoftwareModuleType}.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getOptionalModule(@PathVariable final Long distributionSetTypeId,
|
||||
@PathVariable final Long softwareModuleTypeId) {
|
||||
|
||||
@@ -285,17 +181,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(SoftwareModuleTypeMapper.toResponse(foundSmType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the list of optional software
|
||||
* module types in that distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @return Unpaged list of module types and OK in case of success.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypesRest> getOptionalModules(@PathVariable final Long distributionSetTypeId) {
|
||||
|
||||
final DistributionSetType foundType = findDistributionSetTypeWithExceptionIfNotFound(distributionSetTypeId);
|
||||
@@ -306,20 +192,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(rest, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles DELETE request for removing a mandatory module from the
|
||||
* {@link DistributionSetType}.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param softwareModuleTypeId
|
||||
* of the {@link SoftwareModuleType} to remove
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<Void> removeMandatoryModule(@PathVariable final Long distributionSetTypeId,
|
||||
@PathVariable final Long softwareModuleTypeId) {
|
||||
|
||||
@@ -339,20 +212,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles DELETE request for removing an optional module from the
|
||||
* {@link DistributionSetType}.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param softwareModuleTypeId
|
||||
* of the {@link SoftwareModuleType} to remove
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES
|
||||
+ "/{softwareModuleTypeId}", produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<Void> removeOptionalModule(@PathVariable final Long distributionSetTypeId,
|
||||
@PathVariable final Long softwareModuleTypeId) {
|
||||
final DistributionSetType foundType = findDistributionSetTypeWithExceptionIfNotFound(distributionSetTypeId);
|
||||
@@ -371,21 +231,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for adding a mandatory software module type to a
|
||||
* distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param smtId
|
||||
* of the {@link SoftwareModuleType} to add
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_MANDATORY_MODULE_TYPES, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<Void> addMandatoryModule(@PathVariable final Long distributionSetTypeId,
|
||||
@RequestBody final IdRest smtId) {
|
||||
|
||||
@@ -400,21 +246,7 @@ public class DistributionSetTypeResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for adding an optional software module type to a
|
||||
* distribution set type.
|
||||
*
|
||||
* @param distributionSetTypeId
|
||||
* of the {@link DistributionSetType}.
|
||||
* @param smtId
|
||||
* of the {@link SoftwareModuleType} to add
|
||||
*
|
||||
* @return OK if the request was successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{distributionSetTypeId}/"
|
||||
+ RestConstants.DISTRIBUTIONSETTYPE_V1_OPTIONAL_MODULE_TYPES, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<Void> addOptionalModule(@PathVariable final Long distributionSetTypeId,
|
||||
@RequestBody final IdRest smtId) {
|
||||
|
||||
|
||||
@@ -0,0 +1,92 @@
|
||||
/**
|
||||
* Copyright (c) 2015 Bosch Software Innovations GmbH and others.
|
||||
*
|
||||
* All rights reserved. This program and the accompanying materials
|
||||
* are made available under the terms of the Eclipse Public License v1.0
|
||||
* which accompanies this distribution, and is available at
|
||||
* http://www.eclipse.org/legal/epl-v10.html
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
import org.eclipse.hawkbit.artifact.repository.model.DbArtifact;
|
||||
import org.eclipse.hawkbit.repository.ArtifactManagement;
|
||||
import org.eclipse.hawkbit.repository.SoftwareManagement;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
|
||||
import org.eclipse.hawkbit.repository.model.LocalArtifact;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.rest.resource.helper.RestResourceConversionHelper;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.ResponseBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* @author Jonathan Knoblauch
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.SOFTWAREMODULE_V1_REQUEST_MAPPING)
|
||||
public class DownloadArtifactResource {
|
||||
|
||||
@Autowired
|
||||
private SoftwareManagement softwareManagement;
|
||||
|
||||
@Autowired
|
||||
private ArtifactManagement artifactManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request for downloading an artifact.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent SoftwareModule
|
||||
* @param artifactId
|
||||
* of the related LocalArtifact
|
||||
* @param servletResponse
|
||||
* of the servlet
|
||||
* @param request
|
||||
* of the client
|
||||
*
|
||||
* @return responseEntity with status ok if successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts/{artifactId}/download")
|
||||
@ResponseBody
|
||||
public ResponseEntity<Void> downloadArtifact(@PathVariable("softwareModuleId") final Long softwareModuleId,
|
||||
@PathVariable("artifactId") final Long artifactId, final HttpServletResponse servletResponse,
|
||||
final HttpServletRequest request) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, artifactId);
|
||||
|
||||
if (null == module || !module.getLocalArtifact(artifactId).isPresent()) {
|
||||
return new ResponseEntity<>(HttpStatus.NOT_FOUND);
|
||||
}
|
||||
|
||||
final LocalArtifact artifact = module.getLocalArtifact(artifactId).get();
|
||||
final DbArtifact file = artifactManagement.loadLocalArtifactBinary(artifact);
|
||||
|
||||
final String ifMatch = request.getHeader("If-Match");
|
||||
if (ifMatch != null && !RestResourceConversionHelper.matchesHttpHeader(ifMatch, artifact.getSha1Hash())) {
|
||||
return new ResponseEntity<>(HttpStatus.PRECONDITION_FAILED);
|
||||
}
|
||||
|
||||
return RestResourceConversionHelper.writeFileResponse(artifact, servletResponse, request, file);
|
||||
|
||||
}
|
||||
|
||||
private SoftwareModule findSoftwareModuleWithExceptionIfNotFound(final Long softwareModuleId,
|
||||
final Long artifactId) {
|
||||
final SoftwareModule module = softwareManagement.findSoftwareModuleById(softwareModuleId);
|
||||
if (module == null) {
|
||||
throw new EntityNotFoundException("SoftwareModule with Id {" + softwareModuleId + "} does not exist");
|
||||
} else if (artifactId != null && !module.getLocalArtifact(artifactId).isPresent()) {
|
||||
throw new EntityNotFoundException("Artifact with Id {" + artifactId + "} does not exist");
|
||||
}
|
||||
return module;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -23,6 +23,7 @@ import org.eclipse.hawkbit.repository.model.RolloutGroup.RolloutGroupErrorCondit
|
||||
import org.eclipse.hawkbit.repository.model.RolloutGroup.RolloutGroupSuccessAction;
|
||||
import org.eclipse.hawkbit.repository.model.RolloutGroup.RolloutGroupSuccessCondition;
|
||||
import org.eclipse.hawkbit.repository.model.TotalTargetCountStatus;
|
||||
import org.eclipse.hawkbit.rest.resource.api.RolloutRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.helper.RestResourceConversionHelper;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutCondition.Condition;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutErrorAction.ErrorAction;
|
||||
@@ -70,12 +71,12 @@ final class RolloutMapper {
|
||||
rollout.getTotalTargetCountStatus().getTotalTargetCountByStatus(status));
|
||||
}
|
||||
|
||||
body.add(linkTo(methodOn(RolloutResource.class).getRollout(rollout.getId())).withRel("self"));
|
||||
body.add(linkTo(methodOn(RolloutResource.class).start(rollout.getId(), false)).withRel("start"));
|
||||
body.add(linkTo(methodOn(RolloutResource.class).start(rollout.getId(), true)).withRel("startAsync"));
|
||||
body.add(linkTo(methodOn(RolloutResource.class).pause(rollout.getId())).withRel("pause"));
|
||||
body.add(linkTo(methodOn(RolloutResource.class).resume(rollout.getId())).withRel("resume"));
|
||||
body.add(linkTo(methodOn(RolloutResource.class).getRolloutGroups(rollout.getId(),
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).getRollout(rollout.getId())).withRel("self"));
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).start(rollout.getId(), false)).withRel("start"));
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).start(rollout.getId(), true)).withRel("startAsync"));
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).pause(rollout.getId())).withRel("pause"));
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).resume(rollout.getId())).withRel("resume"));
|
||||
body.add(linkTo(methodOn(RolloutRestApi.class).getRolloutGroups(rollout.getId(),
|
||||
Integer.parseInt(RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET),
|
||||
Integer.parseInt(RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT), null, null)).withRel("groups"));
|
||||
return body;
|
||||
@@ -115,8 +116,9 @@ final class RolloutMapper {
|
||||
body.setName(rolloutGroup.getName());
|
||||
body.setRolloutGroupId(rolloutGroup.getId());
|
||||
body.setStatus(rolloutGroup.getStatus().toString().toLowerCase());
|
||||
body.add(linkTo(methodOn(RolloutResource.class).getRolloutGroup(rolloutGroup.getRollout().getId(),
|
||||
rolloutGroup.getId())).withRel("self"));
|
||||
body.add(linkTo(
|
||||
methodOn(RolloutRestApi.class).getRolloutGroup(rolloutGroup.getRollout().getId(), rolloutGroup.getId()))
|
||||
.withRel("self"));
|
||||
return body;
|
||||
}
|
||||
|
||||
|
||||
@@ -27,6 +27,7 @@ import org.eclipse.hawkbit.repository.model.RolloutGroup.RolloutGroupSuccessActi
|
||||
import org.eclipse.hawkbit.repository.model.RolloutGroup.RolloutGroupSuccessCondition;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.RolloutRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutResponseBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.rollout.RolloutRestRequestBody;
|
||||
@@ -40,13 +41,8 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
@@ -54,8 +50,9 @@ import org.springframework.web.bind.annotation.RestController;
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.ROLLOUT_V1_REQUEST_MAPPING)
|
||||
public class RolloutResource {
|
||||
public class RolloutResource implements RolloutRestApi {
|
||||
|
||||
private static final String DOES_NOT_EXIST = "} does not exist";
|
||||
|
||||
@Autowired
|
||||
private RolloutManagement rolloutManagement;
|
||||
@@ -66,31 +63,9 @@ public class RolloutResource {
|
||||
@Autowired
|
||||
private DistributionSetManagement distributionSetManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all rollouts.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollouts for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all rollouts for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutPagedList> getRollouts(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<RolloutPagedList> getRollouts(final int pagingOffsetParam, final int pagingLimitParam,
|
||||
final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -100,50 +75,28 @@ public class RolloutResource {
|
||||
|
||||
final Page<Rollout> findModulesAll;
|
||||
if (rsqlParam != null) {
|
||||
findModulesAll = rolloutManagement
|
||||
findModulesAll = this.rolloutManagement
|
||||
.findAllWithDetailedStatusByPredicate(RSQLUtility.parse(rsqlParam, RolloutFields.class), pageable);
|
||||
} else {
|
||||
findModulesAll = rolloutManagement.findAll(pageable);
|
||||
findModulesAll = this.rolloutManagement.findAll(pageable);
|
||||
}
|
||||
|
||||
final List<RolloutResponseBody> rest = RolloutMapper.toResponseRollout(findModulesAll.getContent());
|
||||
return new ResponseEntity<>(new RolloutPagedList(rest, findModulesAll.getTotalElements()), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to retrieve
|
||||
* @return a single rollout with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no rollout with the given {@code rolloutId} exists.
|
||||
*/
|
||||
@RequestMapping(value = "/{rolloutId}", method = RequestMethod.GET, produces = { MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" })
|
||||
public ResponseEntity<RolloutResponseBody> getRollout(@PathVariable("rolloutId") final Long rolloutId) {
|
||||
@Override
|
||||
public ResponseEntity<RolloutResponseBody> getRollout(final Long rolloutId) {
|
||||
final Rollout findRolloutById = findRolloutOrThrowException(rolloutId);
|
||||
return new ResponseEntity<>(RolloutMapper.toResponseRollout(findRolloutById), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for creating rollout.
|
||||
*
|
||||
* @param rollout
|
||||
* the rollout body to be created.
|
||||
* @return In case rollout could successful created the ResponseEntity with
|
||||
* status code 201 with the successfully created rollout. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
* @throws EntityNotFoundException
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<RolloutResponseBody> create(@RequestBody final RolloutRestRequestBody rolloutRequestBody) {
|
||||
|
||||
// first check the given RSQL query if it's well formed, otherwise and
|
||||
// exception is thrown
|
||||
RSQLUtility.isValid(rolloutRequestBody.getTargetFilterQuery());
|
||||
RSQLUtility.parse(rolloutRequestBody.getTargetFilterQuery(), TargetFields.class);
|
||||
|
||||
final DistributionSet distributionSet = findDistributionSetOrThrowException(rolloutRequestBody);
|
||||
|
||||
@@ -181,7 +134,7 @@ public class RolloutResource {
|
||||
.successCondition(successCondition, successConditionExpr)
|
||||
.successAction(successAction, successActionExpr).errorCondition(errorCondition, errorConditionExpr)
|
||||
.errorAction(errorAction, errorActionExpr).build();
|
||||
final Rollout rollout = rolloutManagement.createRollout(
|
||||
final Rollout rollout = this.rolloutManagement.createRollout(
|
||||
RolloutMapper.fromRequest(rolloutRequestBody, distributionSet,
|
||||
rolloutRequestBody.getTargetFilterQuery()),
|
||||
rolloutRequestBody.getAmountGroups(), rolloutGroupConditions);
|
||||
@@ -189,97 +142,34 @@ public class RolloutResource {
|
||||
return ResponseEntity.status(HttpStatus.CREATED).body(RolloutMapper.toResponseRollout(rollout));
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for starting a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be started.
|
||||
* @return OK response (200) if rollout could be started. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#startRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/start", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> start(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_ASYNC, defaultValue = "false") final boolean startAsync) {
|
||||
@Override
|
||||
public ResponseEntity<Void> start(final Long rolloutId, final boolean startAsync) {
|
||||
final Rollout rollout = findRolloutOrThrowException(rolloutId);
|
||||
if (startAsync) {
|
||||
rolloutManagement.startRolloutAsync(rollout);
|
||||
this.rolloutManagement.startRolloutAsync(rollout);
|
||||
} else {
|
||||
rolloutManagement.startRollout(rollout);
|
||||
this.rolloutManagement.startRollout(rollout);
|
||||
}
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for pausing a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be paused.
|
||||
* @return OK response (200) if rollout could be paused. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#pauseRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/pause", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> pause(@PathVariable("rolloutId") final Long rolloutId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> pause(final Long rolloutId) {
|
||||
final Rollout rollout = findRolloutOrThrowException(rolloutId);
|
||||
rolloutManagement.pauseRollout(rollout);
|
||||
this.rolloutManagement.pauseRollout(rollout);
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request for resuming a rollout.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout to be resumed.
|
||||
* @return OK response (200) if rollout could be resumed. In case of any
|
||||
* exception the corresponding errors occur.
|
||||
* @throws EntityNotFoundException
|
||||
* @see RolloutManagement#resumeRollout(Rollout)
|
||||
* @see ResponseExceptionHandler
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{rolloutId}/resume", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> resume(@PathVariable("rolloutId") final Long rolloutId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> resume(final Long rolloutId) {
|
||||
final Rollout rollout = findRolloutOrThrowException(rolloutId);
|
||||
rolloutManagement.resumeRollout(rollout);
|
||||
this.rolloutManagement.resumeRollout(rollout);
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all rollout groups referred to a
|
||||
* rollout.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollout groups for pagination, might not
|
||||
* be present in the rest request then default value will be
|
||||
* applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all rollout groups referred to a rollout for a defined
|
||||
* or default page request with status OK. The response is always
|
||||
* paged. In any failure the JsonResponseExceptionHandler is
|
||||
* handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutGroupPagedList> getRolloutGroups(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<RolloutGroupPagedList> getRolloutGroups(final Long rolloutId, final int pagingOffsetParam,
|
||||
final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
final Rollout rollout = findRolloutOrThrowException(rolloutId);
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
@@ -290,10 +180,10 @@ public class RolloutResource {
|
||||
|
||||
final Page<RolloutGroup> findRolloutGroupsAll;
|
||||
if (rsqlParam != null) {
|
||||
findRolloutGroupsAll = rolloutGroupManagement.findRolloutGroupsByPredicate(rollout,
|
||||
findRolloutGroupsAll = this.rolloutGroupManagement.findRolloutGroupsByPredicate(rollout,
|
||||
RSQLUtility.parse(rsqlParam, RolloutGroupFields.class), pageable);
|
||||
} else {
|
||||
findRolloutGroupsAll = rolloutGroupManagement.findRolloutGroupsByRolloutId(rolloutId, pageable);
|
||||
findRolloutGroupsAll = this.rolloutGroupManagement.findRolloutGroupsByRolloutId(rolloutId, pageable);
|
||||
}
|
||||
|
||||
final List<RolloutGroupResponseBody> rest = RolloutMapper
|
||||
@@ -302,56 +192,16 @@ public class RolloutResource {
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request for retrieving a single rollout group.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the rolloutId to retrieve the group from
|
||||
* @param groupId
|
||||
* the groupId to retrieve the rollout group
|
||||
* @return the OK response containing the {@link RolloutGroupResponseBody}
|
||||
* @throws EntityNotFoundException
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups/{groupId}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<RolloutGroupResponseBody> getRolloutGroup(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@PathVariable("groupId") final Long groupId) {
|
||||
@Override
|
||||
public ResponseEntity<RolloutGroupResponseBody> getRolloutGroup(final Long rolloutId, final Long groupId) {
|
||||
findRolloutOrThrowException(rolloutId);
|
||||
final RolloutGroup rolloutGroup = findRolloutGroupOrThrowException(groupId);
|
||||
return ResponseEntity.ok(RolloutMapper.toResponseRolloutGroup(rolloutGroup));
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves all targets related to a specific rollout group.
|
||||
*
|
||||
* @param rolloutId
|
||||
* the ID of the rollout
|
||||
* @param groupId
|
||||
* the ID of the rollout group
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of rollout groups for pagination, might not
|
||||
* be present in the rest request then default value will be
|
||||
* applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a paged list of targets related to a specific rollout and rollout
|
||||
* group.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{rolloutId}/deploygroups/{groupId}/targets", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
public ResponseEntity<TargetPagedList> getRolloutGroupTargets(@PathVariable("rolloutId") final Long rolloutId,
|
||||
@PathVariable("groupId") final Long groupId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TargetPagedList> getRolloutGroupTargets(final Long rolloutId, final Long groupId,
|
||||
final int pagingOffsetParam, final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
findRolloutOrThrowException(rolloutId);
|
||||
final RolloutGroup rolloutGroup = findRolloutGroupOrThrowException(groupId);
|
||||
|
||||
@@ -364,10 +214,11 @@ public class RolloutResource {
|
||||
final Page<Target> rolloutGroupTargets;
|
||||
if (rsqlParam != null) {
|
||||
final Specification<Target> rsqlSpecification = RSQLUtility.parse(rsqlParam, TargetFields.class);
|
||||
rolloutGroupTargets = rolloutGroupManagement.findRolloutGroupTargets(rolloutGroup, rsqlSpecification,
|
||||
rolloutGroupTargets = this.rolloutGroupManagement.findRolloutGroupTargets(rolloutGroup, rsqlSpecification,
|
||||
pageable);
|
||||
} else {
|
||||
final Page<Target> pageTargets = rolloutGroupManagement.findRolloutGroupTargets(rolloutGroup, pageable);
|
||||
final Page<Target> pageTargets = this.rolloutGroupManagement.findRolloutGroupTargets(rolloutGroup,
|
||||
pageable);
|
||||
rolloutGroupTargets = pageTargets;
|
||||
}
|
||||
final List<TargetRest> rest = TargetMapper.toResponse(rolloutGroupTargets.getContent());
|
||||
@@ -375,27 +226,27 @@ public class RolloutResource {
|
||||
}
|
||||
|
||||
private Rollout findRolloutOrThrowException(final Long rolloutId) {
|
||||
final Rollout rollout = rolloutManagement.findRolloutWithDetailedStatus(rolloutId);
|
||||
final Rollout rollout = this.rolloutManagement.findRolloutWithDetailedStatus(rolloutId);
|
||||
if (rollout == null) {
|
||||
throw new EntityNotFoundException("Rollout with Id {" + rolloutId + "} does not exist");
|
||||
throw new EntityNotFoundException("Rollout with Id {" + rolloutId + DOES_NOT_EXIST);
|
||||
}
|
||||
return rollout;
|
||||
}
|
||||
|
||||
private RolloutGroup findRolloutGroupOrThrowException(final Long rolloutGroupId) {
|
||||
final RolloutGroup rolloutGroup = rolloutGroupManagement.findRolloutGroupById(rolloutGroupId);
|
||||
final RolloutGroup rolloutGroup = this.rolloutGroupManagement.findRolloutGroupById(rolloutGroupId);
|
||||
if (rolloutGroup == null) {
|
||||
throw new EntityNotFoundException("Group with Id {" + rolloutGroupId + "} does not exist");
|
||||
throw new EntityNotFoundException("Group with Id {" + rolloutGroupId + DOES_NOT_EXIST);
|
||||
}
|
||||
return rolloutGroup;
|
||||
}
|
||||
|
||||
private DistributionSet findDistributionSetOrThrowException(final RolloutRestRequestBody rolloutRequestBody) {
|
||||
final DistributionSet ds = distributionSetManagement
|
||||
final DistributionSet ds = this.distributionSetManagement
|
||||
.findDistributionSetById(rolloutRequestBody.getDistributionSetId());
|
||||
if (ds == null) {
|
||||
throw new EntityNotFoundException(
|
||||
"DistributionSet with Id {" + rolloutRequestBody.getDistributionSetId() + "} does not exist");
|
||||
"DistributionSet with Id {" + rolloutRequestBody.getDistributionSetId() + DOES_NOT_EXIST);
|
||||
}
|
||||
return ds;
|
||||
}
|
||||
|
||||
@@ -21,6 +21,8 @@ import org.eclipse.hawkbit.repository.model.LocalArtifact;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleMetadata;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleRestAPI;
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.artifact.ArtifactHash;
|
||||
import org.eclipse.hawkbit.rest.resource.model.artifact.ArtifactRest;
|
||||
@@ -142,13 +144,13 @@ public final class SoftwareModuleMapper {
|
||||
response.setType(baseSofwareModule.getType().getKey());
|
||||
response.setVendor(baseSofwareModule.getVendor());
|
||||
|
||||
response.add(linkTo(methodOn(SoftwareModuleResource.class).getArtifacts(response.getModuleId()))
|
||||
response.add(linkTo(methodOn(SoftwareModuleRestAPI.class).getArtifacts(response.getModuleId()))
|
||||
.withRel(RestConstants.SOFTWAREMODULE_V1_ARTIFACT));
|
||||
response.add(linkTo(methodOn(SoftwareModuleResource.class).getSoftwareModule(response.getModuleId()))
|
||||
response.add(linkTo(methodOn(SoftwareModuleRestAPI.class).getSoftwareModule(response.getModuleId()))
|
||||
.withRel("self"));
|
||||
|
||||
response.add(linkTo(
|
||||
methodOn(SoftwareModuleTypeResource.class).getSoftwareModuleType(baseSofwareModule.getType().getId()))
|
||||
methodOn(SoftwareModuleTypeRestApi.class).getSoftwareModuleType(baseSofwareModule.getType().getId()))
|
||||
.withRel(RestConstants.SOFTWAREMODULE_V1_TYPE));
|
||||
|
||||
response.add(linkTo(methodOn(SoftwareModuleResource.class).getMetadata(response.getModuleId(),
|
||||
@@ -178,13 +180,13 @@ public final class SoftwareModuleMapper {
|
||||
|
||||
RestModelMapper.mapBaseToBase(artifactRest, artifact);
|
||||
|
||||
artifactRest.add(linkTo(methodOn(SoftwareModuleResource.class).getArtifact(artifact.getSoftwareModule().getId(),
|
||||
artifactRest.add(linkTo(methodOn(SoftwareModuleRestAPI.class).getArtifact(artifact.getSoftwareModule().getId(),
|
||||
artifact.getId())).withRel("self"));
|
||||
|
||||
if (artifact instanceof LocalArtifact) {
|
||||
artifactRest.add(
|
||||
linkTo(methodOn(SoftwareModuleResource.class).downloadArtifact(artifact.getSoftwareModule().getId(),
|
||||
artifact.getId(), null, null)).withRel("download"));
|
||||
artifactRest.add(linkTo(methodOn(DownloadArtifactResource.class)
|
||||
.downloadArtifact(artifact.getSoftwareModule().getId(), artifact.getId(), null, null))
|
||||
.withRel("download"));
|
||||
}
|
||||
|
||||
return artifactRest;
|
||||
|
||||
@@ -11,22 +11,17 @@ package org.eclipse.hawkbit.rest.resource;
|
||||
import java.io.IOException;
|
||||
import java.util.List;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
import org.eclipse.hawkbit.artifact.repository.model.DbArtifact;
|
||||
import org.eclipse.hawkbit.repository.ArtifactManagement;
|
||||
import org.eclipse.hawkbit.repository.SoftwareManagement;
|
||||
import org.eclipse.hawkbit.repository.SoftwareModuleFields;
|
||||
import org.eclipse.hawkbit.repository.SoftwareModuleMetadataFields;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
|
||||
import org.eclipse.hawkbit.repository.model.Artifact;
|
||||
import org.eclipse.hawkbit.repository.model.LocalArtifact;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleMetadata;
|
||||
import org.eclipse.hawkbit.repository.model.SwMetadataCompositeKey;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.helper.RestResourceConversionHelper;
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleRestAPI;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.MetadataRestPageList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.artifact.ArtifactRest;
|
||||
@@ -44,14 +39,10 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.ResponseBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
@@ -59,13 +50,9 @@ import org.springframework.web.multipart.MultipartFile;
|
||||
* REST Resource handling for {@link SoftwareModule} and related
|
||||
* {@link Artifact} CRUD operations.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.SOFTWAREMODULE_V1_REQUEST_MAPPING)
|
||||
public class SoftwareModuleResource {
|
||||
public class SoftwareModuleResource implements SoftwareModuleRestAPI {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(SoftwareModuleResource.class);
|
||||
|
||||
@Autowired
|
||||
@@ -74,25 +61,7 @@ public class SoftwareModuleResource {
|
||||
@Autowired
|
||||
private SoftwareManagement softwareManagement;
|
||||
|
||||
/**
|
||||
* Handles POST request for artifact upload.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent {@link SoftwareModule}
|
||||
* @param file
|
||||
* that has to be uploaded
|
||||
* @param optionalFileName
|
||||
* to override {@link MultipartFile#getOriginalFilename()}
|
||||
* @param md5Sum
|
||||
* checksum for uploaded content check
|
||||
* @param sha1Sum
|
||||
* checksum for uploaded content check
|
||||
*
|
||||
* @return {@link ResponseEntity} if status {@link HttpStatus#CREATED} if
|
||||
* successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{softwareModuleId}/artifacts", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<ArtifactRest> uploadArtifact(@PathVariable final Long softwareModuleId,
|
||||
@RequestParam("file") final MultipartFile file,
|
||||
@RequestParam(value = "filename", required = false) final String optionalFileName,
|
||||
@@ -123,19 +92,7 @@ public class SoftwareModuleResource {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all meta data of artifacts assigned
|
||||
* to a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent {@link SoftwareModule}
|
||||
*
|
||||
* @return {@link ResponseEntity} with status {@link HttpStatus#OK} if
|
||||
* successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@ResponseBody
|
||||
@Override
|
||||
public ResponseEntity<ArtifactsRest> getArtifacts(@PathVariable final Long softwareModuleId) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, null);
|
||||
|
||||
@@ -146,55 +103,49 @@ public class SoftwareModuleResource {
|
||||
* Handles the GET request for downloading an artifact.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent {@link SoftwareModule}
|
||||
* of the parent SoftwareModule
|
||||
* @param artifactId
|
||||
* of the related {@link LocalArtifact}
|
||||
* of the related LocalArtifact
|
||||
* @param servletResponse
|
||||
* of the servlet
|
||||
* @param request
|
||||
* of the client
|
||||
*
|
||||
* @return {@link ResponseEntity} with status {@link HttpStatus#OK} if
|
||||
* successful
|
||||
* @return responseEntity with status ok if successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts/{artifactId}/download")
|
||||
@ResponseBody
|
||||
public ResponseEntity<Void> downloadArtifact(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final Long artifactId, final HttpServletResponse servletResponse,
|
||||
final HttpServletRequest request) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, artifactId);
|
||||
// @RequestMapping(method = RequestMethod.GET, value =
|
||||
// RestConstants.SOFTWAREMODULE_V1_REQUEST_MAPPING
|
||||
// + "/{softwareModuleId}/artifacts/{artifactId}/download")
|
||||
// @ResponseBody
|
||||
// public ResponseEntity<Void> downloadArtifact(@PathVariable final Long
|
||||
// softwareModuleId,
|
||||
// @PathVariable final Long artifactId, final HttpServletResponse
|
||||
// servletResponse,
|
||||
// final HttpServletRequest request) {
|
||||
// final SoftwareModule module =
|
||||
// findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, artifactId);
|
||||
//
|
||||
// if (null == module || !module.getLocalArtifact(artifactId).isPresent()) {
|
||||
// return new ResponseEntity<>(HttpStatus.NOT_FOUND);
|
||||
// }
|
||||
//
|
||||
// final LocalArtifact artifact = module.getLocalArtifact(artifactId).get();
|
||||
// final DbArtifact file =
|
||||
// artifactManagement.loadLocalArtifactBinary(artifact);
|
||||
//
|
||||
// final String ifMatch = request.getHeader("If-Match");
|
||||
// if (ifMatch != null &&
|
||||
// !RestResourceConversionHelper.matchesHttpHeader(ifMatch,
|
||||
// artifact.getSha1Hash())) {
|
||||
// return new ResponseEntity<>(HttpStatus.PRECONDITION_FAILED);
|
||||
// }
|
||||
//
|
||||
// return RestResourceConversionHelper.writeFileResponse(artifact,
|
||||
// servletResponse, request, file);
|
||||
//
|
||||
// }
|
||||
|
||||
if (null == module || !module.getLocalArtifact(artifactId).isPresent()) {
|
||||
return new ResponseEntity<>(HttpStatus.NOT_FOUND);
|
||||
}
|
||||
|
||||
final LocalArtifact artifact = module.getLocalArtifact(artifactId).get();
|
||||
final DbArtifact file = artifactManagement.loadLocalArtifactBinary(artifact);
|
||||
|
||||
final String ifMatch = request.getHeader("If-Match");
|
||||
if (ifMatch != null && !RestResourceConversionHelper.matchesHttpHeader(ifMatch, artifact.getSha1Hash())) {
|
||||
return new ResponseEntity<>(HttpStatus.PRECONDITION_FAILED);
|
||||
}
|
||||
|
||||
return RestResourceConversionHelper.writeFileResponse(artifact, servletResponse, request, file);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single Artifact meta data
|
||||
* request.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* of the parent {@link SoftwareModule}
|
||||
* @param artifactId
|
||||
* of the related {@link LocalArtifact}
|
||||
*
|
||||
* @return {@link ResponseEntity} with status {@link HttpStatus#OK} if
|
||||
* successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/artifacts/{artifactId}", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@ResponseBody
|
||||
@Override
|
||||
public ResponseEntity<ArtifactRest> getArtifact(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final Long artifactId) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, artifactId);
|
||||
@@ -203,18 +154,7 @@ public class SoftwareModuleResource {
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single SoftwareModule within SP.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module that has the artifact
|
||||
* @param artifactId
|
||||
* of the artifact to be deleted
|
||||
*
|
||||
* @return status OK if delete as successful.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}/artifacts/{artifactId}")
|
||||
@ResponseBody
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteArtifact(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final Long artifactId) {
|
||||
findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, artifactId);
|
||||
@@ -225,27 +165,7 @@ public class SoftwareModuleResource {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all softwaremodules within SP.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all modules for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModulePagedList> getSoftwareModules(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@@ -273,38 +193,14 @@ public class SoftwareModuleResource {
|
||||
return new ResponseEntity<>(new SoftwareModulePagedList(rest, countModulesAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single software module within SP.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleRest> getSoftwareModule(@PathVariable final Long softwareModuleId) {
|
||||
final SoftwareModule findBaseSoftareModule = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, null);
|
||||
|
||||
return new ResponseEntity<>(SoftwareModuleMapper.toResponse(findBaseSoftareModule), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new softwaremodules within SP. The
|
||||
* request body must always be a list of modules. The requests is delgating
|
||||
* to the {@link SoftwareManagement#createSoftwareModule(Iterable)}.
|
||||
*
|
||||
* @param softwareModules
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModulesRest> createSoftwareModules(
|
||||
@RequestBody final List<SoftwareModuleRequestBodyPost> softwareModules) {
|
||||
LOG.debug("creating {} softwareModules", softwareModules.size());
|
||||
@@ -316,18 +212,7 @@ public class SoftwareModuleResource {
|
||||
HttpStatus.CREATED);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a software module within SP.
|
||||
* {@link SoftwareManagement#createSoftwareModule(Iterable)}.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module in the URL
|
||||
* @param restSoftwareModule
|
||||
* the modules to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleRest> updateSoftwareModule(@PathVariable final Long softwareModuleId,
|
||||
@RequestBody final SoftwareModuleRequestBodyPut restSoftwareModule) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, null);
|
||||
@@ -344,15 +229,7 @@ public class SoftwareModuleResource {
|
||||
return new ResponseEntity<>(SoftwareModuleMapper.toResponse(updateSoftwareModule), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single softwaremodule within SP.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as sucessfull.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}")
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteSoftwareModule(@PathVariable final Long softwareModuleId) {
|
||||
final SoftwareModule module = findSoftwareModuleWithExceptionIfNotFound(softwareModuleId, null);
|
||||
|
||||
@@ -361,28 +238,7 @@ public class SoftwareModuleResource {
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a paged list of meta data for a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module for the meta data
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of meta data for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=key==abc}
|
||||
* @return status OK if get request is successful with the paged list of
|
||||
* meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/metadata", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
@Override
|
||||
public ResponseEntity<MetadataRestPageList> getMetadata(@PathVariable final Long softwareModuleId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@@ -412,18 +268,7 @@ public class SoftwareModuleResource {
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a single meta data value for a specific key of a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to get the meta data from
|
||||
* @param metadataKey
|
||||
* the key of the meta data entry to retrieve the value from
|
||||
* @return status OK if get request is successful with the value of the meta
|
||||
* data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<MetadataRest> getMetadataValue(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final String metadataKey) {
|
||||
// check if distribution set exists otherwise throw exception
|
||||
@@ -433,18 +278,7 @@ public class SoftwareModuleResource {
|
||||
return ResponseEntity.<MetadataRest> ok(SoftwareModuleMapper.toResponseSwMetadata(findOne));
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates a single meta data value of a software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to update the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to update the value
|
||||
* @return status OK if the update request is successful and the updated
|
||||
* meta data result
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleId}/metadata/{metadataKey}", produces = {
|
||||
MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
@Override
|
||||
public ResponseEntity<MetadataRest> updateMetadata(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final String metadataKey, @RequestBody final MetadataRest metadata) {
|
||||
// check if software module exists otherwise throw exception immediately
|
||||
@@ -454,16 +288,7 @@ public class SoftwareModuleResource {
|
||||
return ResponseEntity.ok(SoftwareModuleMapper.toResponseSwMetadata(updated));
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes a single meta data entry from the software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the software module to delete the meta data entry
|
||||
* @param metadataKey
|
||||
* the key of the meta data to delete
|
||||
* @return status OK if the delete request is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleId}/metadata/{metadataKey}")
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteMetadata(@PathVariable final Long softwareModuleId,
|
||||
@PathVariable final String metadataKey) {
|
||||
// check if software module exists otherwise throw exception immediately
|
||||
@@ -472,19 +297,7 @@ public class SoftwareModuleResource {
|
||||
return ResponseEntity.ok().build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a list of meta data for a specific software module.
|
||||
*
|
||||
* @param softwareModuleId
|
||||
* the ID of the distribution set to create meta data for
|
||||
* @param metadataRest
|
||||
* the list of meta data entries to create
|
||||
* @return status created if post request is successful with the value of
|
||||
* the created meta data
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{softwareModuleId}/metadata", consumes = {
|
||||
MediaType.APPLICATION_JSON_VALUE,
|
||||
"application/hal+json" }, produces = { MediaType.APPLICATION_JSON_VALUE, "application/hal+json" })
|
||||
@Override
|
||||
public ResponseEntity<List<MetadataRest>> createMetadata(@PathVariable final Long softwareModuleId,
|
||||
@RequestBody final List<MetadataRest> metadataRest) {
|
||||
// check if software module exists otherwise throw exception immediately
|
||||
|
||||
@@ -16,6 +16,7 @@ import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypesRest;
|
||||
@@ -73,7 +74,7 @@ final class SoftwareModuleTypeMapper {
|
||||
result.setMaxAssignments(type.getMaxAssignments());
|
||||
result.setModuleId(type.getId());
|
||||
|
||||
result.add(linkTo(methodOn(SoftwareModuleTypeResource.class).getSoftwareModuleType(result.getModuleId()))
|
||||
result.add(linkTo(methodOn(SoftwareModuleTypeRestApi.class).getSoftwareModuleType(result.getModuleId()))
|
||||
.withRel("self"));
|
||||
|
||||
return result;
|
||||
|
||||
@@ -10,8 +10,6 @@ package org.eclipse.hawkbit.rest.resource;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
|
||||
import org.eclipse.hawkbit.repository.SoftwareManagement;
|
||||
import org.eclipse.hawkbit.repository.SoftwareModuleTypeFields;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
|
||||
@@ -19,6 +17,7 @@ import org.eclipse.hawkbit.repository.model.Artifact;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModuleType;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.SoftwareModuleTypeRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypePagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPost;
|
||||
import org.eclipse.hawkbit.rest.resource.model.softwaremoduletype.SoftwareModuleTypeRequestBodyPut;
|
||||
@@ -30,59 +29,22 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* REST Resource handling for {@link SoftwareModule} and related
|
||||
* {@link Artifact} CRUD operations.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.SOFTWAREMODULETYPE_V1_REQUEST_MAPPING)
|
||||
public class SoftwareModuleTypeResource {
|
||||
public class SoftwareModuleTypeResource implements SoftwareModuleTypeRestApi {
|
||||
@Autowired
|
||||
private SoftwareManagement softwareManagement;
|
||||
|
||||
@Autowired
|
||||
private EntityManager entityManager;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all {@link SoftwareModuleType}s
|
||||
* within SP.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of modules for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
*
|
||||
* @return a list of all module type for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypePagedList> getTypes(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypePagedList> getTypes(final int pagingOffsetParam, final int pagingLimitParam,
|
||||
final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -93,12 +55,12 @@ public class SoftwareModuleTypeResource {
|
||||
final Slice<SoftwareModuleType> findModuleTypessAll;
|
||||
Long countModulesAll;
|
||||
if (rsqlParam != null) {
|
||||
findModuleTypessAll = softwareManagement.findSoftwareModuleTypesByPredicate(
|
||||
findModuleTypessAll = this.softwareManagement.findSoftwareModuleTypesByPredicate(
|
||||
RSQLUtility.parse(rsqlParam, SoftwareModuleTypeFields.class), pageable);
|
||||
countModulesAll = ((Page<SoftwareModuleType>) findModuleTypessAll).getTotalElements();
|
||||
} else {
|
||||
findModuleTypessAll = softwareManagement.findSoftwareModuleTypesAll(pageable);
|
||||
countModulesAll = softwareManagement.countSoftwareModuleTypesAll();
|
||||
findModuleTypessAll = this.softwareManagement.findSoftwareModuleTypesAll(pageable);
|
||||
countModulesAll = this.softwareManagement.countSoftwareModuleTypesAll();
|
||||
}
|
||||
|
||||
final List<SoftwareModuleTypeRest> rest = SoftwareModuleTypeMapper
|
||||
@@ -106,56 +68,25 @@ public class SoftwareModuleTypeResource {
|
||||
return new ResponseEntity<>(new SoftwareModuleTypePagedList(rest, countModulesAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single software module type
|
||||
* within SP.
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the module type to retrieve
|
||||
*
|
||||
* @return a single softwareModule with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no with the given {@code softwareModuleId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{softwareModuleTypeId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getSoftwareModuleType(@PathVariable final Long softwareModuleTypeId) {
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypeRest> getSoftwareModuleType(final Long softwareModuleTypeId) {
|
||||
final SoftwareModuleType foundType = findSoftwareModuleTypeWithExceptionIfNotFound(softwareModuleTypeId);
|
||||
|
||||
return new ResponseEntity<>(SoftwareModuleTypeMapper.toResponse(foundType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single software module type within SP.
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the module to retrieve
|
||||
* @return status OK if delete as sucessfull.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{softwareModuleTypeId}")
|
||||
public ResponseEntity<Void> deleteSoftwareModuleType(@PathVariable final Long softwareModuleTypeId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteSoftwareModuleType(final Long softwareModuleTypeId) {
|
||||
final SoftwareModuleType module = findSoftwareModuleTypeWithExceptionIfNotFound(softwareModuleTypeId);
|
||||
|
||||
softwareManagement.deleteSoftwareModuleType(module);
|
||||
this.softwareManagement.deleteSoftwareModuleType(module);
|
||||
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a software module type within SP.
|
||||
*
|
||||
* @param softwareModuleTypeId
|
||||
* the ID of the software module in the URL
|
||||
* @param restSoftwareModuleType
|
||||
* the module type to be updated.
|
||||
* @return status OK if update is successful
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{softwareModuleTypeId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<SoftwareModuleTypeRest> updateSoftwareModuleType(
|
||||
@PathVariable final Long softwareModuleTypeId,
|
||||
@RequestBody final SoftwareModuleTypeRequestBodyPut restSoftwareModuleType) {
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypeRest> updateSoftwareModuleType(final Long softwareModuleTypeId,
|
||||
final SoftwareModuleTypeRequestBodyPut restSoftwareModuleType) {
|
||||
final SoftwareModuleType type = findSoftwareModuleTypeWithExceptionIfNotFound(softwareModuleTypeId);
|
||||
|
||||
// only description can be modified
|
||||
@@ -163,27 +94,15 @@ public class SoftwareModuleTypeResource {
|
||||
type.setDescription(restSoftwareModuleType.getDescription());
|
||||
}
|
||||
|
||||
final SoftwareModuleType updatedSoftwareModuleType = softwareManagement.updateSoftwareModuleType(type);
|
||||
final SoftwareModuleType updatedSoftwareModuleType = this.softwareManagement.updateSoftwareModuleType(type);
|
||||
return new ResponseEntity<>(SoftwareModuleTypeMapper.toResponse(updatedSoftwareModuleType), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new {@link SoftwareModuleType}s
|
||||
* within SP. The request body must always be a list of types.
|
||||
*
|
||||
* @param softwareModuleTypes
|
||||
* the modules to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created but without ResponseBody. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<SoftwareModuleTypesRest> createSoftwareModuleTypes(
|
||||
@RequestBody final List<SoftwareModuleTypeRequestBodyPost> softwareModuleTypes) {
|
||||
final List<SoftwareModuleTypeRequestBodyPost> softwareModuleTypes) {
|
||||
|
||||
final List<SoftwareModuleType> createdSoftwareModules = softwareManagement
|
||||
final List<SoftwareModuleType> createdSoftwareModules = this.softwareManagement
|
||||
.createSoftwareModuleTypes(SoftwareModuleTypeMapper.smFromRequest(softwareModuleTypes));
|
||||
|
||||
return new ResponseEntity<>(SoftwareModuleTypeMapper.toTypesResponse(createdSoftwareModules),
|
||||
@@ -191,7 +110,7 @@ public class SoftwareModuleTypeResource {
|
||||
}
|
||||
|
||||
private SoftwareModuleType findSoftwareModuleTypeWithExceptionIfNotFound(final Long softwareModuleTypeId) {
|
||||
final SoftwareModuleType module = softwareManagement.findSoftwareModuleTypeById(softwareModuleTypeId);
|
||||
final SoftwareModuleType module = this.softwareManagement.findSoftwareModuleTypeById(softwareModuleTypeId);
|
||||
if (module == null) {
|
||||
throw new EntityNotFoundException(
|
||||
"SoftwareModuleType with Id {" + softwareModuleTypeId + "} does not exist");
|
||||
|
||||
@@ -17,6 +17,8 @@ import java.util.List;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetTag;
|
||||
import org.eclipse.hawkbit.repository.model.Tag;
|
||||
import org.eclipse.hawkbit.repository.model.TargetTag;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetTagRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetTagRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagsRest;
|
||||
@@ -53,9 +55,9 @@ final class TagMapper {
|
||||
|
||||
mapTag(response, targetTag);
|
||||
|
||||
response.add(linkTo(methodOn(TargetTagResource.class).getTargetTag(targetTag.getId())).withRel("self"));
|
||||
response.add(linkTo(methodOn(TargetTagRestApi.class).getTargetTag(targetTag.getId())).withRel("self"));
|
||||
|
||||
response.add(linkTo(methodOn(TargetTagResource.class).getAssignedTargets(targetTag.getId()))
|
||||
response.add(linkTo(methodOn(TargetTagRestApi.class).getAssignedTargets(targetTag.getId()))
|
||||
.withRel("assignedTargets"));
|
||||
|
||||
return response;
|
||||
@@ -83,12 +85,11 @@ final class TagMapper {
|
||||
|
||||
mapTag(response, distributionSetTag);
|
||||
|
||||
response.add(
|
||||
linkTo(methodOn(DistributionSetTagResource.class).getDistributionSetTag(distributionSetTag.getId()))
|
||||
.withRel("self"));
|
||||
response.add(linkTo(methodOn(DistributionSetTagRestApi.class).getDistributionSetTag(distributionSetTag.getId()))
|
||||
.withRel("self"));
|
||||
|
||||
response.add(linkTo(
|
||||
methodOn(DistributionSetTagResource.class).getAssignedDistributionSets(distributionSetTag.getId()))
|
||||
methodOn(DistributionSetTagRestApi.class).getAssignedDistributionSets(distributionSetTag.getId()))
|
||||
.withRel("assignedDistributionSets"));
|
||||
|
||||
return response;
|
||||
|
||||
@@ -23,6 +23,7 @@ import org.eclipse.hawkbit.repository.model.ActionStatus;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.model.TargetInfo.PollStatus;
|
||||
import org.eclipse.hawkbit.repository.model.TargetUpdateStatus;
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.PollStatusRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionRest;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionStatusRest;
|
||||
@@ -45,18 +46,18 @@ final public class TargetMapper {
|
||||
|
||||
/**
|
||||
* Add links to a target response.
|
||||
*
|
||||
*
|
||||
* @param response
|
||||
* the target response
|
||||
*/
|
||||
public static void addTargetLinks(final TargetRest response) {
|
||||
response.add(linkTo(methodOn(TargetResource.class).getAssignedDistributionSet(response.getControllerId()))
|
||||
response.add(linkTo(methodOn(TargetRestApi.class).getAssignedDistributionSet(response.getControllerId()))
|
||||
.withRel(RestConstants.TARGET_V1_ASSIGNED_DISTRIBUTION_SET));
|
||||
response.add(linkTo(methodOn(TargetResource.class).getInstalledDistributionSet(response.getControllerId()))
|
||||
response.add(linkTo(methodOn(TargetRestApi.class).getInstalledDistributionSet(response.getControllerId()))
|
||||
.withRel(RestConstants.TARGET_V1_INSTALLED_DISTRIBUTION_SET));
|
||||
response.add(linkTo(methodOn(TargetResource.class).getAttributes(response.getControllerId()))
|
||||
response.add(linkTo(methodOn(TargetRestApi.class).getAttributes(response.getControllerId()))
|
||||
.withRel(RestConstants.TARGET_V1_ATTRIBUTES));
|
||||
response.add(linkTo(methodOn(TargetResource.class).getActionHistory(response.getControllerId(), 0,
|
||||
response.add(linkTo(methodOn(TargetRestApi.class).getActionHistory(response.getControllerId(), 0,
|
||||
RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT_VALUE,
|
||||
ActionFields.ID.getFieldName() + ":" + SortDirection.DESC, null))
|
||||
.withRel(RestConstants.TARGET_V1_ACTIONS));
|
||||
@@ -64,7 +65,7 @@ final public class TargetMapper {
|
||||
|
||||
/**
|
||||
* Add the pollstatus to a target response.
|
||||
*
|
||||
*
|
||||
* @param target
|
||||
* the target
|
||||
* @param targetRest
|
||||
@@ -85,7 +86,7 @@ final public class TargetMapper {
|
||||
|
||||
/**
|
||||
* Create a response which includes links and pollstatus for all targets.
|
||||
*
|
||||
*
|
||||
* @param targets
|
||||
* the targets
|
||||
* @return the response
|
||||
@@ -105,7 +106,7 @@ final public class TargetMapper {
|
||||
|
||||
/**
|
||||
* Create a response for targets.
|
||||
*
|
||||
*
|
||||
* @param targets
|
||||
* list of targets
|
||||
* @return the response
|
||||
@@ -123,7 +124,7 @@ final public class TargetMapper {
|
||||
|
||||
/**
|
||||
* Create a response for target.
|
||||
*
|
||||
*
|
||||
* @param target
|
||||
* the target
|
||||
* @return the response
|
||||
@@ -163,7 +164,7 @@ final public class TargetMapper {
|
||||
targetRest.setInstalledAt(installationDate);
|
||||
}
|
||||
|
||||
targetRest.add(linkTo(methodOn(TargetResource.class).getTarget(target.getControllerId())).withRel("self"));
|
||||
targetRest.add(linkTo(methodOn(TargetRestApi.class).getTarget(target.getControllerId())).withRel("self"));
|
||||
|
||||
return targetRest;
|
||||
}
|
||||
@@ -210,7 +211,7 @@ final public class TargetMapper {
|
||||
|
||||
RestModelMapper.mapBaseToBase(result, action);
|
||||
|
||||
result.add(linkTo(methodOn(TargetResource.class).getAction(targetId, action.getId())).withRel("self"));
|
||||
result.add(linkTo(methodOn(TargetRestApi.class).getAction(targetId, action.getId())).withRel("self"));
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -20,13 +20,14 @@ import org.eclipse.hawkbit.repository.ActionStatusFields;
|
||||
import org.eclipse.hawkbit.repository.DeploymentManagement;
|
||||
import org.eclipse.hawkbit.repository.TargetFields;
|
||||
import org.eclipse.hawkbit.repository.TargetManagement;
|
||||
import org.eclipse.hawkbit.repository.exception.CancelActionNotAllowedException;
|
||||
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
|
||||
import org.eclipse.hawkbit.repository.model.Action;
|
||||
import org.eclipse.hawkbit.repository.model.Action.ActionType;
|
||||
import org.eclipse.hawkbit.repository.model.ActionStatus;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.DistributionSetRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.helper.RestResourceConversionHelper;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.action.ActionRest;
|
||||
@@ -47,25 +48,15 @@ import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* REST Resource handling target CRUD operations.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.TARGET_V1_REQUEST_MAPPING)
|
||||
public class TargetResource {
|
||||
public class TargetResource implements TargetRestApi {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(TargetResource.class);
|
||||
|
||||
@Autowired
|
||||
@@ -74,18 +65,8 @@ public class TargetResource {
|
||||
@Autowired
|
||||
private DeploymentManagement deploymentManagement;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single target within SP.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve
|
||||
* @return a single target with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetRest> getTarget(@PathVariable final String targetId) {
|
||||
@Override
|
||||
public ResponseEntity<TargetRest> getTarget(final String targetId) {
|
||||
final Target findTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
// to single response include poll status
|
||||
final TargetRest response = TargetMapper.toResponse(findTarget);
|
||||
@@ -95,31 +76,9 @@ public class TargetResource {
|
||||
return new ResponseEntity<>(response, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all targets within SP.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all targets for a defined or default page request with
|
||||
* status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetPagedList> getTargets(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TargetPagedList> getTargets(final int pagingOffsetParam, final int pagingLimitParam,
|
||||
final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -129,58 +88,29 @@ public class TargetResource {
|
||||
final Slice<Target> findTargetsAll;
|
||||
final Long countTargetsAll;
|
||||
if (rsqlParam != null) {
|
||||
final Page<Target> findTargetPage = targetManagement
|
||||
final Page<Target> findTargetPage = this.targetManagement
|
||||
.findTargetsAll(RSQLUtility.parse(rsqlParam, TargetFields.class), pageable);
|
||||
countTargetsAll = findTargetPage.getTotalElements();
|
||||
findTargetsAll = findTargetPage;
|
||||
} else {
|
||||
findTargetsAll = targetManagement.findTargetsAll(pageable);
|
||||
countTargetsAll = targetManagement.countTargetsAll();
|
||||
findTargetsAll = this.targetManagement.findTargetsAll(pageable);
|
||||
countTargetsAll = this.targetManagement.countTargetsAll();
|
||||
}
|
||||
|
||||
final List<TargetRest> rest = TargetMapper.toResponse(findTargetsAll.getContent());
|
||||
return new ResponseEntity<>(new TargetPagedList(rest, countTargetsAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new targets within SP. The request
|
||||
* body must always be a list of targets. The requests is delegating to the
|
||||
* {@link TargetManagement#createTarget(Iterable)}.
|
||||
*
|
||||
* @param targets
|
||||
* the targets to be created.
|
||||
* @return In case all targets could successful created the ResponseEntity
|
||||
* with status code 201 with a list of successfully created
|
||||
* entities. In any failure the JsonResponseExceptionHandler is
|
||||
* handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetsRest> createTargets(@RequestBody final List<TargetRequestBody> targets) {
|
||||
@Override
|
||||
public ResponseEntity<TargetsRest> createTargets(final List<TargetRequestBody> targets) {
|
||||
LOG.debug("creating {} targets", targets.size());
|
||||
final Iterable<Target> createdTargets = targetManagement.createTargets(TargetMapper.fromRequest(targets));
|
||||
final Iterable<Target> createdTargets = this.targetManagement.createTargets(TargetMapper.fromRequest(targets));
|
||||
LOG.debug("{} targets created, return status {}", targets.size(), HttpStatus.CREATED);
|
||||
return new ResponseEntity<>(TargetMapper.toResponse(createdTargets), HttpStatus.CREATED);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the PUT request of updating a target within SP. The ID is within
|
||||
* the URL path of the request. A given ID in the request body is ignored.
|
||||
* It's not possible to set fields to {@code null} values.
|
||||
*
|
||||
* @param targetId
|
||||
* the path parameter which contains the ID of the target
|
||||
* @param targetRest
|
||||
* the request body which contains the fields which should be
|
||||
* updated, fields which are not given are ignored for the
|
||||
* udpate.
|
||||
* @return the updated target response which contains all fields also fields
|
||||
* which have not updated
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{targetId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetRest> updateTarget(@PathVariable final String targetId,
|
||||
@RequestBody final TargetRequestBody targetRest) {
|
||||
@Override
|
||||
public ResponseEntity<TargetRest> updateTarget(final String targetId, final TargetRequestBody targetRest) {
|
||||
final Target existingTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
LOG.debug("updating target {}", existingTarget.getId());
|
||||
if (targetRest.getDescription() != null) {
|
||||
@@ -189,42 +119,21 @@ public class TargetResource {
|
||||
if (targetRest.getName() != null) {
|
||||
existingTarget.setName(targetRest.getName());
|
||||
}
|
||||
final Target updateTarget = targetManagement.updateTarget(existingTarget);
|
||||
final Target updateTarget = this.targetManagement.updateTarget(existingTarget);
|
||||
|
||||
return new ResponseEntity<>(TargetMapper.toResponse(updateTarget), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request of deleting a target within SP.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to be deleted
|
||||
* @return If the given targetId could exists and could be deleted Http OK.
|
||||
* In any failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> deleteTarget(@PathVariable final String targetId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteTarget(final String targetId) {
|
||||
final Target target = findTargetWithExceptionIfNotFound(targetId);
|
||||
targetManagement.deleteTargets(target.getId());
|
||||
this.targetManagement.deleteTargets(target.getId());
|
||||
LOG.debug("{} target deleted, return status {}", targetId, HttpStatus.OK);
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the attributes of a specific
|
||||
* target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve the attributes.
|
||||
* @return the target attributes as map response with status OK
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/attributes", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TargetAttributes> getAttributes(@PathVariable final String targetId) {
|
||||
@Override
|
||||
public ResponseEntity<TargetAttributes> getAttributes(final String targetId) {
|
||||
final Target foundTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
final Map<String, String> controllerAttributes = foundTarget.getTargetInfo().getControllerAttributes();
|
||||
if (controllerAttributes.isEmpty()) {
|
||||
@@ -237,36 +146,9 @@ public class TargetResource {
|
||||
return new ResponseEntity<>(result, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the {@link Action}s of a specific
|
||||
* target.
|
||||
*
|
||||
* @param targetId
|
||||
* to load actions for
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=status==pending}
|
||||
* @return a list of all {@link Action}s for a defined or default page
|
||||
* request with status OK. The response is always paged. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionPagedList> getActionHistory(@PathVariable final String targetId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<ActionPagedList> getActionHistory(final String targetId, final int pagingOffsetParam,
|
||||
final int pagingLimitParam, final String sortParam, final String rsqlParam) {
|
||||
|
||||
final Target foundTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
|
||||
@@ -279,11 +161,11 @@ public class TargetResource {
|
||||
final Long totalActionCount;
|
||||
if (rsqlParam != null) {
|
||||
final Specification<Action> parse = RSQLUtility.parse(rsqlParam, ActionFields.class);
|
||||
activeActions = deploymentManagement.findActionsByTarget(parse, foundTarget, pageable);
|
||||
totalActionCount = deploymentManagement.countActionsByTarget(parse, foundTarget);
|
||||
activeActions = this.deploymentManagement.findActionsByTarget(parse, foundTarget, pageable);
|
||||
totalActionCount = this.deploymentManagement.countActionsByTarget(parse, foundTarget);
|
||||
} else {
|
||||
activeActions = deploymentManagement.findActionsByTarget(foundTarget, pageable);
|
||||
totalActionCount = deploymentManagement.countActionsByTarget(foundTarget);
|
||||
activeActions = this.deploymentManagement.findActionsByTarget(foundTarget, pageable);
|
||||
totalActionCount = this.deploymentManagement.countActionsByTarget(foundTarget);
|
||||
}
|
||||
|
||||
return new ResponseEntity<>(
|
||||
@@ -291,20 +173,8 @@ public class TargetResource {
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a specific {@link Action}s of a
|
||||
* specific {@link Target}.
|
||||
*
|
||||
* @param targetId
|
||||
* to load the action for
|
||||
* @param actionId
|
||||
* to load
|
||||
* @return the action
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions/{actionId}", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionRest> getAction(@PathVariable final String targetId,
|
||||
@PathVariable final Long actionId) {
|
||||
@Override
|
||||
public ResponseEntity<ActionRest> getAction(final String targetId, final Long actionId) {
|
||||
final Target target = findTargetWithExceptionIfNotFound(targetId);
|
||||
|
||||
final Action action = findActionWithExceptionIfNotFound(actionId);
|
||||
@@ -317,14 +187,14 @@ public class TargetResource {
|
||||
|
||||
if (!action.isCancelingOrCanceled()) {
|
||||
result.add(linkTo(
|
||||
methodOn(DistributionSetResource.class).getDistributionSet(action.getDistributionSet().getId()))
|
||||
methodOn(DistributionSetRestApi.class).getDistributionSet(action.getDistributionSet().getId()))
|
||||
.withRel("distributionset"));
|
||||
} else if (action.isCancelingOrCanceled()) {
|
||||
result.add(linkTo(methodOn(TargetResource.class).getAction(targetId, action.getId()))
|
||||
result.add(linkTo(methodOn(TargetRestApi.class).getAction(targetId, action.getId()))
|
||||
.withRel(RestConstants.TARGET_V1_CANCELED_ACTION));
|
||||
}
|
||||
|
||||
result.add(linkTo(methodOn(TargetResource.class).getActionStatusList(targetId, action.getId(), 0,
|
||||
result.add(linkTo(methodOn(TargetRestApi.class).getActionStatusList(targetId, action.getId(), 0,
|
||||
RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT_VALUE,
|
||||
ActionStatusFields.ID.getFieldName() + ":" + SortDirection.DESC))
|
||||
.withRel(RestConstants.TARGET_V1_ACTION_STATUS));
|
||||
@@ -332,32 +202,16 @@ public class TargetResource {
|
||||
return new ResponseEntity<>(result, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request of canceling an specific {@link Action}s of a
|
||||
* specific {@link Target}.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target in the URL path parameter
|
||||
* @param actionId
|
||||
* the ID of the action in the URL path parameter
|
||||
* @param force
|
||||
* optional parameter, which indicates a force cancel
|
||||
* @return status no content in case cancellation was successful
|
||||
* @throws CancelActionNotAllowedException
|
||||
* if the given action is not active and cannot be canceled.
|
||||
* @throws EntityNotFoundException
|
||||
* if the target or the action is not found
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetId}/actions/{actionId}")
|
||||
public ResponseEntity<Void> cancelAction(@PathVariable final String targetId, @PathVariable final Long actionId,
|
||||
@Override
|
||||
public ResponseEntity<Void> cancelAction(final String targetId, final Long actionId,
|
||||
@RequestParam(required = false, defaultValue = "false") final boolean force) {
|
||||
final Target target = findTargetWithExceptionIfNotFound(targetId);
|
||||
final Action action = findActionWithExceptionIfNotFound(actionId);
|
||||
|
||||
if (force) {
|
||||
deploymentManagement.forceQuitAction(action, target);
|
||||
this.deploymentManagement.forceQuitAction(action, target);
|
||||
} else {
|
||||
deploymentManagement.cancelAction(action, target);
|
||||
this.deploymentManagement.cancelAction(action, target);
|
||||
}
|
||||
// both functions will throw an exception, when action is in wrong
|
||||
// state, which is mapped by ResponseExceptionHandler.
|
||||
@@ -365,35 +219,9 @@ public class TargetResource {
|
||||
return new ResponseEntity<>(HttpStatus.NO_CONTENT);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the {@link ActionStatus}s of a
|
||||
* specific target and action.
|
||||
*
|
||||
* @param targetId
|
||||
* of the the action
|
||||
* @param actionId
|
||||
* of the status we are intend to load
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of targets for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @return a list of all {@link ActionStatus}s for a defined or default page
|
||||
* request with status OK. The response is always paged. In any
|
||||
* failure the JsonResponseExceptionHandler is handling the
|
||||
* response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/actions/{actionId}/status", produces = {
|
||||
"application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<ActionStatusPagedList> getActionStatusList(@PathVariable final String targetId,
|
||||
@PathVariable final Long actionId,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam) {
|
||||
@Override
|
||||
public ResponseEntity<ActionStatusPagedList> getActionStatusList(final String targetId, final Long actionId,
|
||||
final int pagingOffsetParam, final int pagingLimitParam, final String sortParam) {
|
||||
|
||||
final Target target = findTargetWithExceptionIfNotFound(targetId);
|
||||
|
||||
@@ -407,7 +235,7 @@ public class TargetResource {
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
final Sort sorting = PagingUtility.sanitizeActionStatusSortParam(sortParam);
|
||||
|
||||
final Page<ActionStatus> statusList = deploymentManagement.findActionStatusMessagesByActionInDescOrder(
|
||||
final Page<ActionStatus> statusList = this.deploymentManagement.findActionStatusMessagesByActionInDescOrder(
|
||||
new OffsetBasedPageRequest(sanitizedOffsetParam, sanitizedLimitParam, sorting), action, true);
|
||||
|
||||
return new ResponseEntity<>(
|
||||
@@ -417,20 +245,8 @@ public class TargetResource {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the assigned distribution set of an
|
||||
* specific target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve the assigned distribution
|
||||
* @return the assigned distribution set with status OK, if none is assigned
|
||||
* than {@code null} content (e.g. "{}")
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/assignedDS", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getAssignedDistributionSet(@PathVariable final String targetId) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetRest> getAssignedDistributionSet(final String targetId) {
|
||||
final Target findTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
final DistributionSetRest distributionSetRest = DistributionSetMapper
|
||||
.toResponse(findTarget.getAssignedDistributionSet());
|
||||
@@ -443,28 +259,14 @@ public class TargetResource {
|
||||
return new ResponseEntity<>(distributionSetRest, retStatus);
|
||||
}
|
||||
|
||||
/**
|
||||
* Changes the assigned distribution set of a target.
|
||||
*
|
||||
* @param targetId
|
||||
* of the target to change
|
||||
* @param dsId
|
||||
* of the distributionset that is to be assigned
|
||||
* @return {@link HttpStatus#OK}
|
||||
*
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = "/{targetId}/assignedDS", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<Void> postAssignedDistributionSet(@PathVariable final String targetId,
|
||||
@RequestBody final DistributionSetAssigmentRest dsId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> postAssignedDistributionSet(final String targetId,
|
||||
final DistributionSetAssigmentRest dsId) {
|
||||
|
||||
findTargetWithExceptionIfNotFound(targetId);
|
||||
final ActionType type = (dsId.getType() != null)
|
||||
? RestResourceConversionHelper.convertActionType(dsId.getType()) : ActionType.FORCED;
|
||||
final Iterator<Target> changed = deploymentManagement
|
||||
final Iterator<Target> changed = this.deploymentManagement
|
||||
.assignDistributionSet(dsId.getId(), type, dsId.getForcetime(), targetId).getAssignedTargets()
|
||||
.iterator();
|
||||
if (changed.hasNext()) {
|
||||
@@ -477,20 +279,8 @@ public class TargetResource {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving the installed distribution set of
|
||||
* an specific target.
|
||||
*
|
||||
* @param targetId
|
||||
* the ID of the target to retrieve
|
||||
* @return the assigned installed set with status OK, if none is installed
|
||||
* than {@code null} content (e.g. "{}")
|
||||
* @throws EntityNotFoundException
|
||||
* in case no target with the given {@code targetId} exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetId}/installedDS", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<DistributionSetRest> getInstalledDistributionSet(@PathVariable final String targetId) {
|
||||
@Override
|
||||
public ResponseEntity<DistributionSetRest> getInstalledDistributionSet(final String targetId) {
|
||||
final Target findTarget = findTargetWithExceptionIfNotFound(targetId);
|
||||
final DistributionSetRest distributionSetRest = DistributionSetMapper
|
||||
.toResponse(findTarget.getTargetInfo().getInstalledDistributionSet());
|
||||
@@ -504,7 +294,7 @@ public class TargetResource {
|
||||
}
|
||||
|
||||
private Target findTargetWithExceptionIfNotFound(final String targetId) {
|
||||
final Target findTarget = targetManagement.findTargetByControllerID(targetId);
|
||||
final Target findTarget = this.targetManagement.findTargetByControllerID(targetId);
|
||||
if (findTarget == null) {
|
||||
throw new EntityNotFoundException("Target with Id {" + targetId + "} does not exist");
|
||||
}
|
||||
@@ -512,7 +302,7 @@ public class TargetResource {
|
||||
}
|
||||
|
||||
private Action findActionWithExceptionIfNotFound(final Long actionId) {
|
||||
final Action findAction = deploymentManagement.findAction(actionId);
|
||||
final Action findAction = this.deploymentManagement.findAction(actionId);
|
||||
if (findAction == null) {
|
||||
throw new EntityNotFoundException("Action with Id {" + actionId + "} does not exist");
|
||||
}
|
||||
|
||||
@@ -11,8 +11,6 @@ package org.eclipse.hawkbit.rest.resource;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import javax.persistence.EntityManager;
|
||||
|
||||
import org.eclipse.hawkbit.repository.TagFields;
|
||||
import org.eclipse.hawkbit.repository.TagManagement;
|
||||
import org.eclipse.hawkbit.repository.TargetManagement;
|
||||
@@ -21,6 +19,7 @@ import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.model.TargetTag;
|
||||
import org.eclipse.hawkbit.repository.model.TargetTagAssigmentResult;
|
||||
import org.eclipse.hawkbit.repository.rsql.RSQLUtility;
|
||||
import org.eclipse.hawkbit.rest.resource.api.TargetTagRestApi;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.AssignedTargetRequestBody;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagPagedList;
|
||||
import org.eclipse.hawkbit.rest.resource.model.tag.TagRequestBodyPut;
|
||||
@@ -36,13 +35,8 @@ import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Slice;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMethod;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
@@ -50,10 +44,8 @@ import org.springframework.web.bind.annotation.RestController;
|
||||
*
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping(RestConstants.TARGET_TAG_V1_REQUEST_MAPPING)
|
||||
public class TargetTagResource {
|
||||
public class TargetTagResource implements TargetTagRestApi {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(TargetTagResource.class);
|
||||
private static final String TARGET_TAG_TAGERTS_REQUEST_MAPPING = RestConstants.TARGET_TAG_TAGERTS_REQUEST_MAPPING;
|
||||
|
||||
@Autowired
|
||||
private TagManagement tagManagement;
|
||||
@@ -61,34 +53,9 @@ public class TargetTagResource {
|
||||
@Autowired
|
||||
private TargetManagement targetManagement;
|
||||
|
||||
@Autowired
|
||||
private EntityManager entityManager;
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all target tags.
|
||||
*
|
||||
* @param pagingOffsetParam
|
||||
* the offset of list of target tags for pagination, might not be
|
||||
* present in the rest request then default value will be applied
|
||||
* @param pagingLimitParam
|
||||
* the limit of the paged request, might not be present in the
|
||||
* rest request then default value will be applied
|
||||
* @param sortParam
|
||||
* the sorting parameter in the request URL, syntax
|
||||
* {@code field:direction, field:direction}
|
||||
* @param rsqlParam
|
||||
* the search parameter in the request URL, syntax
|
||||
* {@code q=name==abc}
|
||||
* @return a list of all target tags for a defined or default page request
|
||||
* with status OK. The response is always paged. In any failure the
|
||||
* JsonResponseExceptionHandler is handling the response.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagPagedList> getTargetTags(
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_OFFSET, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_OFFSET) final int pagingOffsetParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_PAGING_LIMIT, defaultValue = RestConstants.REQUEST_PARAMETER_PAGING_DEFAULT_LIMIT) final int pagingLimitParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SORTING, required = false) final String sortParam,
|
||||
@RequestParam(value = RestConstants.REQUEST_PARAMETER_SEARCH, required = false) final String rsqlParam) {
|
||||
@Override
|
||||
public ResponseEntity<TagPagedList> getTargetTags(final int pagingOffsetParam, final int pagingLimitParam,
|
||||
final String sortParam, final String rsqlParam) {
|
||||
|
||||
final int sanitizedOffsetParam = PagingUtility.sanitizeOffsetParam(pagingOffsetParam);
|
||||
final int sanitizedLimitParam = PagingUtility.sanitizePageLimitParam(pagingLimitParam);
|
||||
@@ -98,11 +65,11 @@ public class TargetTagResource {
|
||||
final Slice<TargetTag> findTargetsAll;
|
||||
final Long countTargetsAll;
|
||||
if (rsqlParam == null) {
|
||||
findTargetsAll = tagManagement.findAllTargetTags(pageable);
|
||||
countTargetsAll = tagManagement.countTargetTags();
|
||||
findTargetsAll = this.tagManagement.findAllTargetTags(pageable);
|
||||
countTargetsAll = this.tagManagement.countTargetTags();
|
||||
|
||||
} else {
|
||||
final Page<TargetTag> findTargetPage = tagManagement
|
||||
final Page<TargetTag> findTargetPage = this.tagManagement
|
||||
.findAllTargetTags(RSQLUtility.parse(rsqlParam, TagFields.class), pageable);
|
||||
countTargetsAll = findTargetPage.getTotalElements();
|
||||
findTargetsAll = findTargetPage;
|
||||
@@ -113,127 +80,57 @@ public class TargetTagResource {
|
||||
return new ResponseEntity<>(new TagPagedList(rest, countTargetsAll), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving a single target tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
*
|
||||
* @return a single target tag with status OK.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = "/{targetTagId}", produces = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> getTargetTag(@PathVariable final Long targetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<TagRest> getTargetTag(final Long targetTagId) {
|
||||
final TargetTag tag = findTargetTagById(targetTagId);
|
||||
return new ResponseEntity<>(TagMapper.toResponse(tag), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request of creating new target tag. The request body
|
||||
* must always be a list of tags.
|
||||
*
|
||||
* @param tags
|
||||
* the target tags to be created.
|
||||
* @return In case all modules could successful created the ResponseEntity
|
||||
* with status code 201 - Created. The Response Body are the created
|
||||
* target tags but without ResponseBody.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
@Override
|
||||
public ResponseEntity<TagsRest> createTargetTags(@RequestBody final List<TagRequestBodyPut> tags) {
|
||||
LOG.debug("creating {} target tags", tags.size());
|
||||
final List<TargetTag> createdTargetTags = tagManagement
|
||||
final List<TargetTag> createdTargetTags = this.tagManagement
|
||||
.createTargetTags(TagMapper.mapTargeTagFromRequest(tags));
|
||||
return new ResponseEntity<>(TagMapper.toResponse(createdTargetTags), HttpStatus.CREATED);
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Handles the PUT request of updating a single targetr tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @param restTargetTagRest
|
||||
* the the request body to be updated
|
||||
* @return status OK if update is successful and the updated target tag.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.PUT, value = "/{targetTagId}", consumes = { "application/hal+json",
|
||||
MediaType.APPLICATION_JSON_VALUE }, produces = { "application/hal+json", MediaType.APPLICATION_JSON_VALUE })
|
||||
public ResponseEntity<TagRest> updateTagretTag(@PathVariable final Long targetTagId,
|
||||
@RequestBody final TagRequestBodyPut restTargetTagRest) {
|
||||
@Override
|
||||
public ResponseEntity<TagRest> updateTagretTag(final Long targetTagId, final TagRequestBodyPut restTargetTagRest) {
|
||||
LOG.debug("update {} target tag", restTargetTagRest);
|
||||
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
TagMapper.updateTag(restTargetTagRest, targetTag);
|
||||
final TargetTag updateTargetTag = tagManagement.updateTargetTag(targetTag);
|
||||
final TargetTag updateTargetTag = this.tagManagement.updateTargetTag(targetTag);
|
||||
|
||||
LOG.debug("target tag updated");
|
||||
|
||||
return new ResponseEntity<>(TagMapper.toResponse(updateTargetTag), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request for a single target tag.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @return status OK if delete as successfully.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = "/{targetTagId}")
|
||||
public ResponseEntity<Void> deleteTargetTag(@PathVariable final Long targetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> deleteTargetTag(final Long targetTagId) {
|
||||
LOG.debug("Delete {} target tag", targetTagId);
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
|
||||
tagManagement.deleteTargetTag(targetTag.getName());
|
||||
this.tagManagement.deleteTargetTag(targetTag.getName());
|
||||
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the GET request of retrieving all assigned targets by the given
|
||||
* tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
*
|
||||
* @return the list of assigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.GET, value = TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<TargetsRest> getAssignedTargets(@PathVariable final Long targetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<TargetsRest> getAssignedTargets(final Long targetTagId) {
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
return new ResponseEntity<>(TargetMapper.toResponseWithLinksAndPollStatus(targetTag.getAssignedToTargets()),
|
||||
HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request to toggle the assignment of targets by the given
|
||||
* tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @param assignedTargetRequestBodies
|
||||
* list of target ids to be toggled
|
||||
*
|
||||
* @return the list of assigned targets and unassigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = TARGET_TAG_TAGERTS_REQUEST_MAPPING + "/toggleTagAssignment")
|
||||
public ResponseEntity<TargetTagAssigmentResultRest> toggleTagAssignment(@PathVariable final Long targetTagId,
|
||||
@RequestBody final List<AssignedTargetRequestBody> assignedTargetRequestBodies) {
|
||||
@Override
|
||||
public ResponseEntity<TargetTagAssigmentResultRest> toggleTagAssignment(final Long targetTagId,
|
||||
final List<AssignedTargetRequestBody> assignedTargetRequestBodies) {
|
||||
LOG.debug("Toggle Target assignment {} for target tag {}", assignedTargetRequestBodies.size(), targetTagId);
|
||||
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
final TargetTagAssigmentResult assigmentResult = targetManagement
|
||||
final TargetTagAssigmentResult assigmentResult = this.targetManagement
|
||||
.toggleTagAssignment(findTargetControllerIds(assignedTargetRequestBodies), targetTag.getName());
|
||||
|
||||
final TargetTagAssigmentResultRest tagAssigmentResultRest = new TargetTagAssigmentResultRest();
|
||||
@@ -242,71 +139,38 @@ public class TargetTagResource {
|
||||
return new ResponseEntity<>(tagAssigmentResultRest, HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the POST request to assign targets to the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @param assignedTargetRequestBodies
|
||||
* list of target ids to be assigned
|
||||
*
|
||||
* @return the list of assigned targets.
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.POST, value = TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<TargetsRest> assignTargets(@PathVariable final Long targetTagId,
|
||||
@RequestBody final List<AssignedTargetRequestBody> assignedTargetRequestBodies) {
|
||||
@Override
|
||||
public ResponseEntity<TargetsRest> assignTargets(final Long targetTagId,
|
||||
final List<AssignedTargetRequestBody> assignedTargetRequestBodies) {
|
||||
LOG.debug("Assign Targets {} for target tag {}", assignedTargetRequestBodies.size(), targetTagId);
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
final List<Target> assignedTarget = targetManagement
|
||||
final List<Target> assignedTarget = this.targetManagement
|
||||
.assignTag(findTargetControllerIds(assignedTargetRequestBodies), targetTag);
|
||||
return new ResponseEntity<>(TargetMapper.toResponseWithLinksAndPollStatus(assignedTarget), HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign all targets from the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag to retrieve
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = TARGET_TAG_TAGERTS_REQUEST_MAPPING)
|
||||
public ResponseEntity<Void> unassignTargets(@PathVariable final Long targetTagId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> unassignTargets(final Long targetTagId) {
|
||||
LOG.debug("Unassign all Targets for target tag {}", targetTagId);
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
if (targetTag.getAssignedToTargets() == null) {
|
||||
LOG.debug("No assigned targets found");
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
targetManagement.unAssignAllTargetsByTag(targetTag);
|
||||
this.targetManagement.unAssignAllTargetsByTag(targetTag);
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the DELETE request to unassign one target from the given tag id.
|
||||
*
|
||||
* @param targetTagId
|
||||
* the ID of the target tag
|
||||
* @param controllerId
|
||||
* the ID of the target to unassign
|
||||
* @return http status code
|
||||
* @throws EntityNotFoundException
|
||||
* in case the given {@code targetTagId} doesn't exists.
|
||||
*/
|
||||
@RequestMapping(method = RequestMethod.DELETE, value = TARGET_TAG_TAGERTS_REQUEST_MAPPING + "/{controllerId}")
|
||||
public ResponseEntity<Void> unassignTarget(@PathVariable final Long targetTagId,
|
||||
@PathVariable final String controllerId) {
|
||||
@Override
|
||||
public ResponseEntity<Void> unassignTarget(final Long targetTagId, final String controllerId) {
|
||||
LOG.debug("Unassign target {} for target tag {}", controllerId, targetTagId);
|
||||
final TargetTag targetTag = findTargetTagById(targetTagId);
|
||||
targetManagement.unAssignTag(controllerId, targetTag);
|
||||
this.targetManagement.unAssignTag(controllerId, targetTag);
|
||||
return new ResponseEntity<>(HttpStatus.OK);
|
||||
}
|
||||
|
||||
private TargetTag findTargetTagById(final Long targetTagId) {
|
||||
final TargetTag tag = tagManagement.findTargetTagById(targetTagId);
|
||||
final TargetTag tag = this.tagManagement.findTargetTagById(targetTagId);
|
||||
if (tag == null) {
|
||||
throw new EntityNotFoundException("Target Tag with Id {" + targetTagId + "} does not exist");
|
||||
}
|
||||
|
||||
@@ -57,9 +57,6 @@ import ru.yandex.qatools.allure.annotations.Stories;
|
||||
/**
|
||||
* Test artifact downloads from the controller.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
@ActiveProfiles({ "im", "test" })
|
||||
@@ -285,7 +282,8 @@ public class ArtifactDownloadTest extends AbstractIntegrationTestWithMongoDB {
|
||||
.andExpect(header().string("Content-Disposition", "attachment;filename=" + artifact.getFilename()))
|
||||
.andReturn();
|
||||
|
||||
assertTrue(Arrays.equals(result.getResponse().getContentAsByteArray(), random));
|
||||
assertTrue("The same file that was uploaded is expected when downloaded",
|
||||
Arrays.equals(result.getResponse().getContentAsByteArray(), random));
|
||||
|
||||
// download complete
|
||||
assertThat(downLoadProgress).isEqualTo(10);
|
||||
@@ -393,7 +391,8 @@ public class ArtifactDownloadTest extends AbstractIntegrationTestWithMongoDB {
|
||||
.andExpect(header().longValue("Last-Modified", artifact.getCreatedAt()))
|
||||
.andExpect(header().string("Content-Disposition", "attachment;filename=file1")).andReturn();
|
||||
|
||||
assertTrue(Arrays.equals(result.getResponse().getContentAsByteArray(), random));
|
||||
assertTrue("The same file that was uploaded is expected when downloaded",
|
||||
Arrays.equals(result.getResponse().getContentAsByteArray(), random));
|
||||
|
||||
// one (update) action
|
||||
assertThat(actionRepository.findByTargetAndDistributionSet(pageReq, target, ds).getContent()).hasSize(1);
|
||||
|
||||
@@ -8,7 +8,8 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.rest.resource;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.fest.assertions.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.fail;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@@ -16,9 +17,15 @@ import org.eclipse.hawkbit.repository.TargetFields;
|
||||
import org.junit.Test;
|
||||
import org.springframework.data.domain.Sort.Order;
|
||||
|
||||
import ru.yandex.qatools.allure.annotations.Description;
|
||||
import ru.yandex.qatools.allure.annotations.Features;
|
||||
import ru.yandex.qatools.allure.annotations.Stories;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
@Features("Component Tests - Management RESTful API")
|
||||
@Stories("Sorting parameter")
|
||||
public class SortUtilityTest {
|
||||
private static final String SORT_PARAM_1 = "NAME:ASC";
|
||||
private static final String SORT_PARAM_2 = "NAME:ASC, DESCRIPTION:DESC";
|
||||
@@ -29,36 +36,55 @@ public class SortUtilityTest {
|
||||
private static final String WRONG_FIELD_PARAM = "ASDF:ASC";
|
||||
|
||||
@Test
|
||||
@Description("Ascending sorting based on name.")
|
||||
public void parseSortParam1() {
|
||||
|
||||
final List<Order> parse = SortUtility.parse(TargetFields.class, SORT_PARAM_1);
|
||||
assertEquals(1, parse.size());
|
||||
assertThat(1).as("Count of parsing parameter").isEqualTo(parse.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Ascending sorting based on name and descending sorting based on description.")
|
||||
public void parseSortParam2() {
|
||||
final List<Order> parse = SortUtility.parse(TargetFields.class, SORT_PARAM_2);
|
||||
assertEquals(2, parse.size());
|
||||
}
|
||||
|
||||
@Test(expected = SortParameterSyntaxErrorException.class)
|
||||
public void parseWrongSyntaxParam() {
|
||||
SortUtility.parse(TargetFields.class, SYNTAX_FAILURE_SORT_PARAM);
|
||||
assertThat(2).as("Count of parsing parameter").isEqualTo(parse.size());
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Sorting with wrong syntax leads to SortParameterSyntaxErrorException.")
|
||||
public void parseWrongSyntaxParam() {
|
||||
try {
|
||||
SortUtility.parse(TargetFields.class, SYNTAX_FAILURE_SORT_PARAM);
|
||||
fail("SortParameterSyntaxErrorException expected because of wrong syntax");
|
||||
} catch (final SortParameterSyntaxErrorException e) {
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Sorting based on name with case sensitive is possible.")
|
||||
public void parsingIsNotCaseSensitive() {
|
||||
SortUtility.parse(TargetFields.class, CASE_INSENSITIVE_DIRECTION_PARAM);
|
||||
SortUtility.parse(TargetFields.class, CASE_INSENSITIVE_DIRECTION_PARAM_1);
|
||||
}
|
||||
|
||||
@Test(expected = SortParameterUnsupportedDirectionException.class)
|
||||
@Test
|
||||
@Description("Sorting with unknown direction order leads to SortParameterUnsupportedDirectionException.")
|
||||
public void parseWrongDirectionParam() {
|
||||
SortUtility.parse(TargetFields.class, WRONG_DIRECTION_PARAM);
|
||||
try {
|
||||
SortUtility.parse(TargetFields.class, WRONG_DIRECTION_PARAM);
|
||||
fail("SortParameterUnsupportedDirectionException expected because of unknown direction order");
|
||||
} catch (final SortParameterUnsupportedDirectionException e) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = SortParameterUnsupportedFieldException.class)
|
||||
@Test
|
||||
@Description("Sorting with unknown field leads to SortParameterUnsupportedFieldException.")
|
||||
public void parseWrongFieldParam() {
|
||||
SortUtility.parse(TargetFields.class, WRONG_FIELD_PARAM);
|
||||
try {
|
||||
SortUtility.parse(TargetFields.class, WRONG_FIELD_PARAM);
|
||||
fail("SortParameterUnsupportedFieldException expected because of unknown field");
|
||||
} catch (final SortParameterUnsupportedFieldException e) {
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -75,7 +75,7 @@ public class HawkbitUI extends DefaultHawkbitUI implements DetachListener {
|
||||
private SpringViewProvider viewProvider;
|
||||
|
||||
@Autowired
|
||||
private ApplicationContext context;
|
||||
private transient ApplicationContext context;
|
||||
|
||||
@Autowired
|
||||
private I18N i18n;
|
||||
@@ -89,13 +89,13 @@ public class HawkbitUI extends DefaultHawkbitUI implements DetachListener {
|
||||
private ErrorView errorview;
|
||||
|
||||
@Autowired
|
||||
protected EventBus.SessionEventBus eventBus;
|
||||
protected transient EventBus.SessionEventBus eventBus;
|
||||
|
||||
/**
|
||||
* An {@link com.google.common.eventbus.EventBus} subscriber which
|
||||
* subscribes {@link EntityEvent} from the repository to dispatch these
|
||||
* events to the UI {@link SessionEventBus}.
|
||||
*
|
||||
*
|
||||
* @param event
|
||||
* the entity event which has been published from the repository
|
||||
*/
|
||||
@@ -103,21 +103,28 @@ public class HawkbitUI extends DefaultHawkbitUI implements DetachListener {
|
||||
@AllowConcurrentEvents
|
||||
public void dispatch(final org.eclipse.hawkbit.eventbus.event.Event event) {
|
||||
final VaadinSession session = getSession();
|
||||
if (session != null && session.getState() == State.OPEN) {
|
||||
final WrappedSession wrappedSession = session.getSession();
|
||||
if (wrappedSession != null) {
|
||||
final SecurityContext userContext = (SecurityContext) wrappedSession
|
||||
.getAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY);
|
||||
if (eventSecurityCheck(userContext, event)) {
|
||||
final SecurityContext oldContext = SecurityContextHolder.getContext();
|
||||
try {
|
||||
access(new DispatcherRunnable(eventBus, session, userContext, event));
|
||||
} finally {
|
||||
SecurityContextHolder.setContext(oldContext);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (session == null || session.getState() != State.OPEN) {
|
||||
return;
|
||||
}
|
||||
|
||||
final WrappedSession wrappedSession = session.getSession();
|
||||
if (wrappedSession == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final SecurityContext userContext = (SecurityContext) wrappedSession
|
||||
.getAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY);
|
||||
if (!eventSecurityCheck(userContext, event)) {
|
||||
return;
|
||||
}
|
||||
|
||||
final SecurityContext oldContext = SecurityContextHolder.getContext();
|
||||
try {
|
||||
access(new DispatcherRunnable(eventBus, session, userContext, event));
|
||||
} finally {
|
||||
SecurityContextHolder.setContext(oldContext);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
protected boolean eventSecurityCheck(final SecurityContext userContext,
|
||||
@@ -134,7 +141,7 @@ public class HawkbitUI extends DefaultHawkbitUI implements DetachListener {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see
|
||||
* com.vaadin.server.ClientConnector.DetachListener#detach(com.vaadin.server
|
||||
* .ClientConnector. DetachEvent)
|
||||
@@ -225,7 +232,7 @@ public class HawkbitUI extends DefaultHawkbitUI implements DetachListener {
|
||||
|
||||
/**
|
||||
* Get Specific Locale.
|
||||
*
|
||||
*
|
||||
* @param availableLocalesInApp
|
||||
* as set
|
||||
* @return String as preferred locale
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.ui.artifacts.footer;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
@@ -21,6 +22,7 @@ import org.eclipse.hawkbit.ui.common.footer.AbstractDeleteActionsLayout;
|
||||
import org.eclipse.hawkbit.ui.management.event.DragEvent;
|
||||
import org.eclipse.hawkbit.ui.utils.I18N;
|
||||
import org.eclipse.hawkbit.ui.utils.SPUIComponetIdProvider;
|
||||
import org.eclipse.hawkbit.ui.utils.SPUIDefinitions;
|
||||
import org.eclipse.hawkbit.ui.utils.SPUILabelDefinitions;
|
||||
import org.eclipse.hawkbit.ui.utils.UINotification;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
@@ -36,6 +38,7 @@ import com.vaadin.ui.Component;
|
||||
import com.vaadin.ui.Label;
|
||||
import com.vaadin.ui.Table;
|
||||
import com.vaadin.ui.UI;
|
||||
import com.vaadin.ui.Table.TableTransferable;
|
||||
|
||||
/**
|
||||
* Upload view footer layout implementation.
|
||||
@@ -196,7 +199,7 @@ public class SMDeleteActionsLayout extends AbstractDeleteActionsLayout {
|
||||
final Component sourceComponent = event.getTransferable().getSourceComponent();
|
||||
if (sourceComponent instanceof Table) {
|
||||
final Table sourceTable = (Table) event.getTransferable().getSourceComponent();
|
||||
addToDeleteList(sourceTable);
|
||||
addToDeleteList(sourceTable,(TableTransferable) event.getTransferable());
|
||||
updateSWActionCount();
|
||||
}
|
||||
if (sourceComponent.getId().startsWith(SPUIComponetIdProvider.UPLOAD_TYPE_BUTTON_PREFIX)) {
|
||||
@@ -220,16 +223,23 @@ public class SMDeleteActionsLayout extends AbstractDeleteActionsLayout {
|
||||
private void deleteSWModuleType(final String swModuleTypeName) {
|
||||
artifactUploadState.getSelectedDeleteSWModuleTypes().add(swModuleTypeName);
|
||||
}
|
||||
|
||||
private void addToDeleteList(final Table sourceTable) {
|
||||
final Set<Long> swModuleIds = (Set<Long>) sourceTable.getValue();
|
||||
swModuleIds.forEach(id -> {
|
||||
|
||||
private void addToDeleteList(final Table sourceTable, final TableTransferable transferable) {
|
||||
@SuppressWarnings("unchecked")
|
||||
final Set<Long> swModuleSelected = (Set<Long>) sourceTable.getValue();
|
||||
final Set<Long> swModuleIdNameSet = new HashSet<Long>();
|
||||
if (!swModuleSelected.contains(transferable.getData(SPUIDefinitions.ITEMID))) {
|
||||
swModuleIdNameSet.add((Long) transferable.getData(SPUIDefinitions.ITEMID));
|
||||
} else {
|
||||
swModuleIdNameSet.addAll(swModuleSelected);
|
||||
}
|
||||
swModuleIdNameSet.forEach(id -> {
|
||||
final String swModuleName = (String) sourceTable.getContainerDataSource().getItem(id)
|
||||
.getItemProperty(SPUILabelDefinitions.NAME_VERSION).getValue();
|
||||
artifactUploadState.getDeleteSofwareModules().put(id, swModuleName);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Update the software module delete count.
|
||||
*/
|
||||
|
||||
@@ -44,9 +44,9 @@ import com.vaadin.ui.themes.ValoTheme;
|
||||
|
||||
/**
|
||||
* Abstract layout of confirm actions window.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@SpringComponent
|
||||
@ViewScope
|
||||
@@ -84,13 +84,13 @@ public class UploadViewConfirmationWindowLayout extends AbstractConfirmationWind
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see org.eclipse.hawkbit.server.ui.common.confirmwindow.layout.
|
||||
* AbstractConfirmationWindowLayout# getConfimrationTabs()
|
||||
*/
|
||||
@Override
|
||||
protected Map<String, ConfirmationTab> getConfimrationTabs() {
|
||||
final Map<String, ConfirmationTab> tabs = new HashMap<String, ConfirmationTab>();
|
||||
final Map<String, ConfirmationTab> tabs = new HashMap<>();
|
||||
if (!artifactUploadState.getDeleteSofwareModules().isEmpty()) {
|
||||
tabs.put(i18n.get("caption.delete.swmodule.accordion.tab"), createSMDeleteConfirmationTab());
|
||||
}
|
||||
@@ -145,7 +145,7 @@ public class UploadViewConfirmationWindowLayout extends AbstractConfirmationWind
|
||||
|
||||
/**
|
||||
* Get SWModule table container.
|
||||
*
|
||||
*
|
||||
* @return IndexedContainer
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
@@ -153,9 +153,8 @@ public class UploadViewConfirmationWindowLayout extends AbstractConfirmationWind
|
||||
final IndexedContainer swcontactContainer = new IndexedContainer();
|
||||
swcontactContainer.addContainerProperty("SWModuleId", String.class, "");
|
||||
swcontactContainer.addContainerProperty(SW_MODULE_NAME_MSG, String.class, "");
|
||||
Item item = null;
|
||||
for (final Long swModuleID : artifactUploadState.getDeleteSofwareModules().keySet()) {
|
||||
item = swcontactContainer.addItem(swModuleID);
|
||||
final Item item = swcontactContainer.addItem(swModuleID);
|
||||
item.getItemProperty("SWModuleId").setValue(swModuleID.toString());
|
||||
item.getItemProperty(SW_MODULE_NAME_MSG)
|
||||
.setValue(artifactUploadState.getDeleteSofwareModules().get(swModuleID));
|
||||
@@ -197,7 +196,7 @@ public class UploadViewConfirmationWindowLayout extends AbstractConfirmationWind
|
||||
for (final CustomFile customFile : artifactUploadState.getFileSelected()) {
|
||||
final String swNameVersion = HawkbitCommonUtil.getFormattedNameVersion(
|
||||
customFile.getBaseSoftwareModuleName(), customFile.getBaseSoftwareModuleVersion());
|
||||
if (HawkbitCommonUtil.bothSame(deleteSoftwareNameVersion, swNameVersion)) {
|
||||
if (deleteSoftwareNameVersion != null && deleteSoftwareNameVersion.equals(swNameVersion)) {
|
||||
tobeRemoved.add(customFile);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -38,13 +38,13 @@ public class ArtifactUploadState implements Serializable {
|
||||
|
||||
private final Map<Long, String> deleteSofwareModules = new HashMap<>();
|
||||
|
||||
private final Set<CustomFile> fileSelected = new HashSet<CustomFile>();
|
||||
private final Set<CustomFile> fileSelected = new HashSet<>();
|
||||
|
||||
private Long selectedBaseSwModuleId;
|
||||
|
||||
private SoftwareModule selectedBaseSoftwareModule;
|
||||
|
||||
private final Map<String, SoftwareModule> baseSwModuleList = new HashMap<String, SoftwareModule>();
|
||||
private final Map<String, SoftwareModule> baseSwModuleList = new HashMap<>();
|
||||
|
||||
private Set<Long> selectedSoftwareModules = Collections.emptySet();
|
||||
|
||||
@@ -60,7 +60,7 @@ public class ArtifactUploadState implements Serializable {
|
||||
|
||||
/**
|
||||
* Set software.
|
||||
*
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
public SoftwareModuleFilters getSoftwareModuleFilters() {
|
||||
@@ -85,7 +85,7 @@ public class ArtifactUploadState implements Serializable {
|
||||
* @return the selectedBaseSwModuleId
|
||||
*/
|
||||
public Optional<Long> getSelectedBaseSwModuleId() {
|
||||
return this.selectedBaseSwModuleId != null ? Optional.of(this.selectedBaseSwModuleId) : Optional.empty();
|
||||
return selectedBaseSwModuleId != null ? Optional.of(selectedBaseSwModuleId) : Optional.empty();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -100,8 +100,7 @@ public class ArtifactUploadState implements Serializable {
|
||||
* @return the selectedBaseSoftwareModule
|
||||
*/
|
||||
public Optional<SoftwareModule> getSelectedBaseSoftwareModule() {
|
||||
return this.selectedBaseSoftwareModule == null ? Optional.empty()
|
||||
: Optional.of(this.selectedBaseSoftwareModule);
|
||||
return selectedBaseSoftwareModule == null ? Optional.empty() : Optional.of(selectedBaseSoftwareModule);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -10,8 +10,6 @@ package org.eclipse.hawkbit.ui.artifacts.state;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
import org.eclipse.hawkbit.ui.utils.HawkbitCommonUtil;
|
||||
|
||||
/**
|
||||
* Custom file to hold details of uploaded file.
|
||||
*
|
||||
@@ -168,36 +166,50 @@ public class CustomFile implements Serializable {
|
||||
return failureReason;
|
||||
}
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
* @see java.lang.Object#hashCode()
|
||||
*/
|
||||
@Override
|
||||
public int hashCode() { // NOSONAR - as this is generated
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + (fileName == null ? 0 : fileName.hashCode());
|
||||
result = prime * result + ((baseSoftwareModuleName == null) ? 0 : baseSoftwareModuleName.hashCode());
|
||||
result = prime * result + ((baseSoftwareModuleVersion == null) ? 0 : baseSoftwareModuleVersion.hashCode());
|
||||
result = prime * result + ((fileName == null) ? 0 : fileName.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
* @see java.lang.Object#equals(java.lang.Object)
|
||||
*/
|
||||
@Override
|
||||
public boolean equals(final Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (!(obj instanceof CustomFile)) {
|
||||
if (obj == null) {
|
||||
return false;
|
||||
}
|
||||
if (getClass() != obj.getClass()) {
|
||||
return false;
|
||||
}
|
||||
final CustomFile other = (CustomFile) obj;
|
||||
return HawkbitCommonUtil.bothSame(fileName, other.fileName)
|
||||
&& HawkbitCommonUtil.bothSame(baseSoftwareModuleName, other.baseSoftwareModuleName)
|
||||
&& HawkbitCommonUtil.bothSame(baseSoftwareModuleVersion, other.baseSoftwareModuleVersion);
|
||||
if (baseSoftwareModuleName == null) {
|
||||
if (other.baseSoftwareModuleName != null) {
|
||||
return false;
|
||||
}
|
||||
} else if (!baseSoftwareModuleName.equals(other.baseSoftwareModuleName)) {
|
||||
return false;
|
||||
}
|
||||
if (baseSoftwareModuleVersion == null) {
|
||||
if (other.baseSoftwareModuleVersion != null) {
|
||||
return false;
|
||||
}
|
||||
} else if (!baseSoftwareModuleVersion.equals(other.baseSoftwareModuleVersion)) {
|
||||
return false;
|
||||
}
|
||||
if (fileName == null) {
|
||||
if (other.fileName != null) {
|
||||
return false;
|
||||
}
|
||||
} else if (!fileName.equals(other.fileName)) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -8,8 +8,6 @@
|
||||
*/
|
||||
package org.eclipse.hawkbit.ui.common.filterlayout;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
import org.eclipse.hawkbit.ui.utils.SPUIStyleDefinitions;
|
||||
|
||||
import com.vaadin.ui.Button;
|
||||
@@ -17,20 +15,20 @@ import com.vaadin.ui.Button.ClickEvent;
|
||||
|
||||
/**
|
||||
* Abstract Single button click behaviour of filter buttons layout.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
public abstract class AbstractFilterSingleButtonClick extends AbstractFilterButtonClickBehaviour {
|
||||
|
||||
private static final long serialVersionUID = 478874092615793581L;
|
||||
|
||||
private Optional<Button> alreadyClickedButton = Optional.empty();
|
||||
private Button alreadyClickedButton;
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see org.eclipse.hawkbit.server.ui.layouts.SPFilterButtonClick#
|
||||
* processFilterButtonClick(com.vaadin.ui. Button.ClickEvent)
|
||||
*/
|
||||
@@ -40,18 +38,18 @@ public abstract class AbstractFilterSingleButtonClick extends AbstractFilterButt
|
||||
if (isButtonUnClicked(clickedButton)) {
|
||||
/* If same button clicked */
|
||||
clickedButton.removeStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
alreadyClickedButton = Optional.empty();
|
||||
alreadyClickedButton = null;
|
||||
filterUnClicked(clickedButton);
|
||||
} else if (alreadyClickedButton.isPresent()) {
|
||||
} else if (alreadyClickedButton != null) {
|
||||
/* If button clicked and some other button is already clicked */
|
||||
alreadyClickedButton.get().removeStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
alreadyClickedButton.removeStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
clickedButton.addStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
alreadyClickedButton = Optional.of(clickedButton);
|
||||
alreadyClickedButton = clickedButton;
|
||||
filterClicked(clickedButton);
|
||||
} else {
|
||||
/* If button clicked and not other button is clicked currently */
|
||||
clickedButton.addStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
alreadyClickedButton = Optional.of(clickedButton);
|
||||
alreadyClickedButton = clickedButton;
|
||||
filterClicked(clickedButton);
|
||||
}
|
||||
}
|
||||
@@ -61,21 +59,19 @@ public abstract class AbstractFilterSingleButtonClick extends AbstractFilterButt
|
||||
* @return
|
||||
*/
|
||||
private boolean isButtonUnClicked(final Button clickedButton) {
|
||||
return alreadyClickedButton.isPresent() && alreadyClickedButton.get().equals(clickedButton);
|
||||
return alreadyClickedButton != null && alreadyClickedButton.equals(clickedButton);
|
||||
}
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see org.eclipse.hawkbit.server.ui.layouts.SPFilterButtonClickBehaviour#
|
||||
* setDefaultClickedButton(com.vaadin .ui.Button)
|
||||
*/
|
||||
@Override
|
||||
protected void setDefaultClickedButton(final Button button) {
|
||||
if (button == null) {
|
||||
alreadyClickedButton = Optional.empty();
|
||||
} else {
|
||||
alreadyClickedButton = Optional.of(button);
|
||||
alreadyClickedButton = button;
|
||||
if (button != null) {
|
||||
button.addStyleName(SPUIStyleDefinitions.SP_FILTER_BTN_CLICKED_STYLE);
|
||||
}
|
||||
}
|
||||
@@ -83,7 +79,7 @@ public abstract class AbstractFilterSingleButtonClick extends AbstractFilterButt
|
||||
/**
|
||||
* @return the alreadyClickedButton
|
||||
*/
|
||||
public Optional<Button> getAlreadyClickedButton() {
|
||||
public Button getAlreadyClickedButton() {
|
||||
return alreadyClickedButton;
|
||||
}
|
||||
|
||||
@@ -91,7 +87,7 @@ public abstract class AbstractFilterSingleButtonClick extends AbstractFilterButt
|
||||
* @param alreadyClickedButton
|
||||
* the alreadyClickedButton to set
|
||||
*/
|
||||
public void setAlreadyClickedButton(final Optional<Button> alreadyClickedButton) {
|
||||
public void setAlreadyClickedButton(final Button alreadyClickedButton) {
|
||||
this.alreadyClickedButton = alreadyClickedButton;
|
||||
}
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ import com.vaadin.ui.themes.ValoTheme;
|
||||
|
||||
/**
|
||||
* Abstract class for target/ds tag token layout.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
@@ -47,9 +47,9 @@ public abstract class AbstractTagToken implements Serializable {
|
||||
|
||||
protected IndexedContainer container;
|
||||
|
||||
protected final Map<Long, TagData> tagDetails = new HashMap<Long, TagData>();
|
||||
protected final Map<Long, TagData> tagDetails = new HashMap<>();
|
||||
|
||||
protected final Map<Long, TagData> tokensAdded = new HashMap<Long, TagData>();
|
||||
protected final Map<Long, TagData> tokensAdded = new HashMap<>();
|
||||
|
||||
protected CssLayout tokenLayout = new CssLayout();
|
||||
|
||||
@@ -123,7 +123,7 @@ public abstract class AbstractTagToken implements Serializable {
|
||||
class CustomTokenField extends TokenField {
|
||||
private static final long serialVersionUID = 694216966472937436L;
|
||||
|
||||
final Container tokenContainer;
|
||||
Container tokenContainer;
|
||||
|
||||
CustomTokenField(final CssLayout cssLayout, final Container tokenContainer) {
|
||||
super(cssLayout);
|
||||
@@ -235,9 +235,11 @@ public abstract class AbstractTagToken implements Serializable {
|
||||
|
||||
/**
|
||||
* Tag details.
|
||||
*
|
||||
*
|
||||
*/
|
||||
public static class TagData {
|
||||
public static class TagData implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private String name;
|
||||
|
||||
@@ -247,7 +249,7 @@ public abstract class AbstractTagToken implements Serializable {
|
||||
|
||||
/**
|
||||
* Tag data constructor.
|
||||
*
|
||||
*
|
||||
* @param id
|
||||
* @param name
|
||||
* @param color
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
package org.eclipse.hawkbit.ui.distributions.dstable;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
@@ -57,7 +58,7 @@ import com.vaadin.ui.Window;
|
||||
|
||||
/**
|
||||
* Distribution set details layout.
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
@@ -153,12 +154,13 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
@SuppressWarnings("unchecked")
|
||||
private void showUnsavedAssignment() {
|
||||
Item item;
|
||||
final Map<DistributionSetIdName, Set<SoftwareModuleIdName>> assignedList = manageDistUIState.getAssignedList();
|
||||
final Map<DistributionSetIdName, HashSet<SoftwareModuleIdName>> assignedList = manageDistUIState
|
||||
.getAssignedList();
|
||||
final Long selectedDistId = manageDistUIState.getLastSelectedDistribution().isPresent()
|
||||
? manageDistUIState.getLastSelectedDistribution().get().getId() : null;
|
||||
Set<SoftwareModuleIdName> softwareModuleIdNameList = null;
|
||||
|
||||
for (final Map.Entry<DistributionSetIdName, Set<SoftwareModuleIdName>> entry : assignedList.entrySet()) {
|
||||
for (final Map.Entry<DistributionSetIdName, HashSet<SoftwareModuleIdName>> entry : assignedList.entrySet()) {
|
||||
if (entry.getKey().getId().equals(selectedDistId)) {
|
||||
softwareModuleIdNameList = entry.getValue();
|
||||
break;
|
||||
@@ -321,7 +323,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* onEdit(com.vaadin.ui .Button.ClickEvent)
|
||||
*/
|
||||
@@ -336,7 +338,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* getEditButtonId()
|
||||
*/
|
||||
@@ -347,7 +349,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* onLoadIsSwModuleSelected ()
|
||||
*/
|
||||
@@ -359,7 +361,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* onLoadIsTableMaximized ()
|
||||
*/
|
||||
@@ -370,7 +372,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* populateDetailsWidget()
|
||||
*/
|
||||
@@ -381,7 +383,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* getDefaultCaption()
|
||||
*/
|
||||
@@ -392,7 +394,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* addTabs(com.vaadin. ui.TabSheet)
|
||||
*/
|
||||
@@ -407,7 +409,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* clearDetails()
|
||||
*/
|
||||
@@ -418,7 +420,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* hasEditSoftwareModulePermission()
|
||||
*/
|
||||
@@ -507,7 +509,7 @@ public class DistributionSetDetails extends AbstractTableDetailsLayout {
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
*
|
||||
* @see hawkbit.server.ui.common.detailslayout.AbstractTableDetailsLayout#
|
||||
* getTabSheetId()
|
||||
*/
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user