Refactoring the DDI Offline Distribution set assignment feature (#1798)
* Refactoring the DDI Offline Distribution set assignment feature Signed-off-by: Denislav Prinov <denislav.prinov@bosch.com> * Tests refactoring Signed-off-by: Denislav Prinov <denislav.prinov@bosch.com> * make it more visible the featyre is experimental Signed-off-by: Denislav Prinov <denislav.prinov@bosch.com> --------- Signed-off-by: Denislav Prinov <denislav.prinov@bosch.com>
This commit is contained in:
@@ -13,7 +13,6 @@ import static org.eclipse.hawkbit.repository.model.Action.Status.DOWNLOADED;
|
|||||||
import static org.eclipse.hawkbit.repository.model.Action.Status.FINISHED;
|
import static org.eclipse.hawkbit.repository.model.Action.Status.FINISHED;
|
||||||
import static org.eclipse.hawkbit.repository.model.Target.CONTROLLER_ATTRIBUTE_KEY_SIZE;
|
import static org.eclipse.hawkbit.repository.model.Target.CONTROLLER_ATTRIBUTE_KEY_SIZE;
|
||||||
import static org.eclipse.hawkbit.repository.model.Target.CONTROLLER_ATTRIBUTE_VALUE_SIZE;
|
import static org.eclipse.hawkbit.repository.model.Target.CONTROLLER_ATTRIBUTE_VALUE_SIZE;
|
||||||
import static org.eclipse.hawkbit.security.SecurityContextTenantAware.SYSTEM_USER;
|
|
||||||
|
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
import java.time.Duration;
|
import java.time.Duration;
|
||||||
@@ -54,7 +53,6 @@ import org.eclipse.hawkbit.repository.RepositoryConstants;
|
|||||||
import org.eclipse.hawkbit.repository.RepositoryProperties;
|
import org.eclipse.hawkbit.repository.RepositoryProperties;
|
||||||
import org.eclipse.hawkbit.repository.TargetTypeManagement;
|
import org.eclipse.hawkbit.repository.TargetTypeManagement;
|
||||||
import org.eclipse.hawkbit.repository.TenantConfigurationManagement;
|
import org.eclipse.hawkbit.repository.TenantConfigurationManagement;
|
||||||
import org.eclipse.hawkbit.repository.TargetTypeManagement;
|
|
||||||
import org.eclipse.hawkbit.repository.UpdateMode;
|
import org.eclipse.hawkbit.repository.UpdateMode;
|
||||||
import org.eclipse.hawkbit.repository.builder.ActionStatusCreate;
|
import org.eclipse.hawkbit.repository.builder.ActionStatusCreate;
|
||||||
import org.eclipse.hawkbit.repository.event.remote.CancelTargetAssignmentEvent;
|
import org.eclipse.hawkbit.repository.event.remote.CancelTargetAssignmentEvent;
|
||||||
@@ -1107,19 +1105,18 @@ public class JpaControllerManagement extends JpaActionManagement implements Cont
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean updateOfflineAssignedVersion(@NotEmpty String controllerId, String distributionName, String version){
|
public boolean updateOfflineAssignedVersion(@NotEmpty final String controllerId, final String distributionName, final String version){
|
||||||
List<DistributionSetAssignmentResult> distributionSetAssignmentResults =
|
List<DistributionSetAssignmentResult> distributionSetAssignmentResults =
|
||||||
systemSecurityContext.runAsSystem(() ->
|
systemSecurityContext.runAsSystem(() ->
|
||||||
distributionSetManagement.getByNameAndVersion(distributionName,version).map(
|
distributionSetManagement.getByNameAndVersion(distributionName,version).map(
|
||||||
distributionSet -> deploymentManagement.offlineAssignedDistributionSets(
|
distributionSet -> deploymentManagement.offlineAssignedDistributionSets(
|
||||||
List.of(Map.entry(controllerId, distributionSet.getId())),controllerId))
|
List.of(Map.entry(controllerId, distributionSet.getId())),controllerId))
|
||||||
.orElseThrow(() ->
|
.orElseThrow(() ->
|
||||||
new EntityNotFoundException(DistributionSet.class, Map.entry(distributionName, version)))
|
new EntityNotFoundException(DistributionSet.class, Map.entry(distributionName, version))));
|
||||||
.stream().toList());
|
|
||||||
boolean notAlreadyAssigned = distributionSetAssignmentResults.stream().findFirst()
|
return distributionSetAssignmentResults.stream().findFirst()
|
||||||
.map(result-> result.getAlreadyAssigned()==0)
|
.map(result-> result.getAlreadyAssigned()==0)
|
||||||
.orElseThrow();
|
.orElseThrow();
|
||||||
return notAlreadyAssigned;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void cancelAssignDistributionSetEvent(final Action action) {
|
private void cancelAssignDistributionSetEvent(final Action action) {
|
||||||
|
|||||||
@@ -190,7 +190,7 @@ public class JpaDeploymentManagement extends JpaActionManagement implements Depl
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<DistributionSetAssignmentResult> offlineAssignedDistributionSets(
|
public List<DistributionSetAssignmentResult> offlineAssignedDistributionSets(
|
||||||
Collection<Entry<String, Long>> assignments, String initiatedBy) {
|
final Collection<Entry<String, Long>> assignments, final String initiatedBy) {
|
||||||
final Collection<Entry<String, Long>> distinctAssignments = assignments.stream().distinct().toList();
|
final Collection<Entry<String, Long>> distinctAssignments = assignments.stream().distinct().toList();
|
||||||
enforceMaxAssignmentsPerRequest(distinctAssignments.size());
|
enforceMaxAssignmentsPerRequest(distinctAssignments.size());
|
||||||
|
|
||||||
|
|||||||
@@ -844,6 +844,7 @@ public interface DdiRootControllerRestApi {
|
|||||||
*/
|
*/
|
||||||
@Operation(summary = "Set offline assigned version", description = """
|
@Operation(summary = "Set offline assigned version", description = """
|
||||||
Allow to set current running version.
|
Allow to set current running version.
|
||||||
|
This method is EXPERIMENTAL and may change in future releases.
|
||||||
""")
|
""")
|
||||||
@ApiResponses(value = {
|
@ApiResponses(value = {
|
||||||
@ApiResponse(responseCode = "200", description = "Successfully retrieved"),
|
@ApiResponse(responseCode = "200", description = "Successfully retrieved"),
|
||||||
@@ -858,7 +859,7 @@ public interface DdiRootControllerRestApi {
|
|||||||
@ApiResponse(responseCode = "415", description = "The request was attempt with a media-type which is not supported by the server for this resource.", content = @Content(mediaType = "application/json", schema = @Schema(hidden = true))),
|
@ApiResponse(responseCode = "415", description = "The request was attempt with a media-type which is not supported by the server for this resource.", content = @Content(mediaType = "application/json", schema = @Schema(hidden = true))),
|
||||||
@ApiResponse(responseCode = "429", description = "Too many requests. The server will refuse further attempts and the client has to wait another second.", content = @Content(mediaType = "application/json", schema = @Schema(hidden = true)))
|
@ApiResponse(responseCode = "429", description = "Too many requests. The server will refuse further attempts and the client has to wait another second.", content = @Content(mediaType = "application/json", schema = @Schema(hidden = true)))
|
||||||
})
|
})
|
||||||
@PostMapping(value = DdiRestConstants.BASE_V1_REQUEST_MAPPING + "/{controllerId}/"
|
@PutMapping(value = DdiRestConstants.BASE_V1_REQUEST_MAPPING + "/{controllerId}/"
|
||||||
+ DdiRestConstants.INSTALLED_BASE_ACTION, consumes = {
|
+ DdiRestConstants.INSTALLED_BASE_ACTION, consumes = {
|
||||||
MediaType.APPLICATION_JSON_VALUE, DdiRestConstants.MEDIA_TYPE_CBOR })
|
MediaType.APPLICATION_JSON_VALUE, DdiRestConstants.MEDIA_TYPE_CBOR })
|
||||||
ResponseEntity<Void> setAsssignedOfflineVersion(@Valid DdiAssignedVersion ddiAssignedVersion,
|
ResponseEntity<Void> setAsssignedOfflineVersion(@Valid DdiAssignedVersion ddiAssignedVersion,
|
||||||
|
|||||||
@@ -763,8 +763,9 @@ public class DdiRootController implements DdiRootControllerRestApi {
|
|||||||
@PathVariable("tenant") final String tenant, @PathVariable("controllerId") final String controllerId){
|
@PathVariable("tenant") final String tenant, @PathVariable("controllerId") final String controllerId){
|
||||||
boolean updated = controllerManagement.updateOfflineAssignedVersion(controllerId,
|
boolean updated = controllerManagement.updateOfflineAssignedVersion(controllerId,
|
||||||
ddiAssignedVersion.getName(), ddiAssignedVersion.getVersion());
|
ddiAssignedVersion.getName(), ddiAssignedVersion.getVersion());
|
||||||
if (updated)
|
if (updated) {
|
||||||
return new ResponseEntity<>(HttpStatus.CREATED);
|
return new ResponseEntity<>(HttpStatus.CREATED);
|
||||||
|
}
|
||||||
return new ResponseEntity<>(HttpStatus.OK);
|
return new ResponseEntity<>(HttpStatus.OK);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ package org.eclipse.hawkbit.ddi.rest.resource;
|
|||||||
import static org.hamcrest.CoreMatchers.equalTo;
|
import static org.hamcrest.CoreMatchers.equalTo;
|
||||||
import static org.hamcrest.Matchers.contains;
|
import static org.hamcrest.Matchers.contains;
|
||||||
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
|
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
|
||||||
|
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.put;
|
||||||
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content;
|
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content;
|
||||||
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath;
|
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath;
|
||||||
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
|
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
|
||||||
@@ -137,9 +138,9 @@ public abstract class AbstractDDiApiIntegrationTest extends AbstractRestIntegrat
|
|||||||
statusMatcher);
|
statusMatcher);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected ResultActions postInstalledBase(final String controllerId, final String content,
|
protected ResultActions putInstalledBase(final String controllerId, final String content,
|
||||||
final ResultMatcher statusMatcher) throws Exception {
|
final ResultMatcher statusMatcher) throws Exception {
|
||||||
return mvc.perform(post(INSTALLED_BASE_ROOT, tenantAware.getCurrentTenant(), controllerId)
|
return mvc.perform(put(INSTALLED_BASE_ROOT, tenantAware.getCurrentTenant(), controllerId)
|
||||||
.content(content.getBytes()).contentType(MediaType.APPLICATION_JSON_UTF8))
|
.content(content.getBytes()).contentType(MediaType.APPLICATION_JSON_UTF8))
|
||||||
.andDo(MockMvcResultPrinter.print()).andExpect(statusMatcher);
|
.andDo(MockMvcResultPrinter.print()).andExpect(statusMatcher);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,7 +42,6 @@ import org.eclipse.hawkbit.repository.event.remote.entity.SoftwareModuleCreatedE
|
|||||||
import org.eclipse.hawkbit.repository.event.remote.entity.SoftwareModuleUpdatedEvent;
|
import org.eclipse.hawkbit.repository.event.remote.entity.SoftwareModuleUpdatedEvent;
|
||||||
import org.eclipse.hawkbit.repository.event.remote.entity.TargetCreatedEvent;
|
import org.eclipse.hawkbit.repository.event.remote.entity.TargetCreatedEvent;
|
||||||
import org.eclipse.hawkbit.repository.event.remote.entity.TargetUpdatedEvent;
|
import org.eclipse.hawkbit.repository.event.remote.entity.TargetUpdatedEvent;
|
||||||
import org.eclipse.hawkbit.repository.jpa.JpaManagementHelper;
|
|
||||||
import org.eclipse.hawkbit.repository.jpa.repository.ActionStatusRepository;
|
import org.eclipse.hawkbit.repository.jpa.repository.ActionStatusRepository;
|
||||||
import org.eclipse.hawkbit.repository.model.Action;
|
import org.eclipse.hawkbit.repository.model.Action;
|
||||||
import org.eclipse.hawkbit.repository.model.ActionStatus;
|
import org.eclipse.hawkbit.repository.model.ActionStatus;
|
||||||
@@ -56,9 +55,7 @@ import org.junit.jupiter.api.Test;
|
|||||||
import org.junit.jupiter.params.ParameterizedTest;
|
import org.junit.jupiter.params.ParameterizedTest;
|
||||||
import org.junit.jupiter.params.provider.MethodSource;
|
import org.junit.jupiter.params.provider.MethodSource;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.data.domain.Page;
|
|
||||||
import org.springframework.data.domain.PageRequest;
|
import org.springframework.data.domain.PageRequest;
|
||||||
import org.springframework.data.domain.Pageable;
|
|
||||||
import org.springframework.data.domain.Sort;
|
import org.springframework.data.domain.Sort;
|
||||||
import org.springframework.hateoas.MediaTypes;
|
import org.springframework.hateoas.MediaTypes;
|
||||||
import org.springframework.http.MediaType;
|
import org.springframework.http.MediaType;
|
||||||
@@ -110,14 +107,14 @@ public class DdiInstalledBaseTest extends AbstractDDiApiIntegrationTest {
|
|||||||
|
|
||||||
|
|
||||||
// update assigned version
|
// update assigned version
|
||||||
postInstalledBase(target.getControllerId(),getJsonInstalledBase(ds.getName(),ds.getVersion()),status()
|
putInstalledBase(target.getControllerId(),getJsonInstalledBase(ds.getName(),ds.getVersion()),status()
|
||||||
.isCreated());
|
.isCreated());
|
||||||
|
|
||||||
assertThat(deploymentManagement.getAssignedDistributionSet(target.getControllerId()).get().getId())
|
assertThat(deploymentManagement.getAssignedDistributionSet(target.getControllerId()).get().getId())
|
||||||
.isEqualTo(ds.getId());
|
.isEqualTo(ds.getId());
|
||||||
|
|
||||||
// update assigned version while version already assigned
|
// update assigned version while version already assigned
|
||||||
postInstalledBase(target.getControllerId(),getJsonInstalledBase(ds.getName(),ds.getVersion()),status().isOk());
|
putInstalledBase(target.getControllerId(),getJsonInstalledBase(ds.getName(),ds.getVersion()),status().isOk());
|
||||||
}
|
}
|
||||||
@Test
|
@Test
|
||||||
@Description("Ensure that installedVersion is version self assigned")
|
@Description("Ensure that installedVersion is version self assigned")
|
||||||
@@ -128,7 +125,7 @@ public class DdiInstalledBaseTest extends AbstractDDiApiIntegrationTest {
|
|||||||
|
|
||||||
|
|
||||||
// get installed base
|
// get installed base
|
||||||
postInstalledBase(target.getControllerId(),getJsonInstalledBase(dsName,dsVersion),status().isNotFound());
|
putInstalledBase(target.getControllerId(),getJsonInstalledBase(dsName,dsVersion),status().isNotFound());
|
||||||
|
|
||||||
assertThat(deploymentManagement.getAssignedDistributionSet(target.getControllerId()).isEmpty()).isTrue();
|
assertThat(deploymentManagement.getAssignedDistributionSet(target.getControllerId()).isEmpty()).isTrue();
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user