Feature target metadata ui (#765)

* add metadata tab and popup to target UI

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* send event to update UI

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* send event on target meta data delete and update

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* display selected element name in details layout and metadata popup of UI

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* add comments to explain manual event publishing

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* remove option to hide metadata button in details layout

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* fix typos and refactor

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* fix typos

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>

* fix wrong method call

Signed-off-by: Stefan Klotz <stefan.klotz@bosch-si.com>
This commit is contained in:
Stefan Klotz
2018-11-26 11:10:49 +01:00
committed by Dominic Schabel
parent 9d38f76c43
commit be348030b2
17 changed files with 313 additions and 65 deletions

View File

@@ -764,5 +764,5 @@ public interface TargetManagement {
* updated * updated
*/ */
@PreAuthorize(SpringEvalExpressions.HAS_AUTH_UPDATE_REPOSITORY) @PreAuthorize(SpringEvalExpressions.HAS_AUTH_UPDATE_REPOSITORY)
TargetMetadata updateMetaData(@NotEmpty String controllerId, @NotNull MetaData metadata); TargetMetadata updateMetadata(@NotEmpty String controllerId, @NotNull MetaData metadata);
} }

View File

@@ -35,6 +35,7 @@ import org.eclipse.hawkbit.repository.builder.TargetCreate;
import org.eclipse.hawkbit.repository.builder.TargetUpdate; import org.eclipse.hawkbit.repository.builder.TargetUpdate;
import org.eclipse.hawkbit.repository.event.remote.TargetAttributesRequestedEvent; import org.eclipse.hawkbit.repository.event.remote.TargetAttributesRequestedEvent;
import org.eclipse.hawkbit.repository.event.remote.TargetDeletedEvent; import org.eclipse.hawkbit.repository.event.remote.TargetDeletedEvent;
import org.eclipse.hawkbit.repository.event.remote.entity.TargetUpdatedEvent;
import org.eclipse.hawkbit.repository.exception.EntityAlreadyExistsException; import org.eclipse.hawkbit.repository.exception.EntityAlreadyExistsException;
import org.eclipse.hawkbit.repository.exception.EntityNotFoundException; import org.eclipse.hawkbit.repository.exception.EntityNotFoundException;
import org.eclipse.hawkbit.repository.jpa.builder.JpaTargetCreate; import org.eclipse.hawkbit.repository.jpa.builder.JpaTargetCreate;
@@ -182,10 +183,16 @@ public class JpaTargetManagement implements TargetManagement {
final JpaTarget updatedTarget = touch(target); final JpaTarget updatedTarget = touch(target);
return Collections.unmodifiableList(md.stream() final List<TargetMetadata> createdMetadata = Collections.unmodifiableList(md.stream()
.map(meta -> targetMetadataRepository .map(meta -> targetMetadataRepository
.save(new JpaTargetMetadata(meta.getKey(), meta.getValue(), updatedTarget))) .save(new JpaTargetMetadata(meta.getKey(), meta.getValue(), updatedTarget)))
.collect(Collectors.toList())); .collect(Collectors.toList()));
// TargetUpdatedEvent is not sent within the touch() method due to the
// "lastModifiedAt" field being ignored in JpaTarget
eventPublisher.publishEvent(new TargetUpdatedEvent(updatedTarget, applicationContext.getId()));
return createdMetadata;
} }
private void checkAndThrowIfTargetMetadataAlreadyExists(final TargetMetadataCompositeKey metadataId) { private void checkAndThrowIfTargetMetadataAlreadyExists(final TargetMetadataCompositeKey metadataId) {
@@ -219,16 +226,21 @@ public class JpaTargetManagement implements TargetManagement {
@Transactional @Transactional
@Retryable(include = { @Retryable(include = {
ConcurrencyFailureException.class }, maxAttempts = Constants.TX_RT_MAX, backoff = @Backoff(delay = Constants.TX_RT_DELAY)) ConcurrencyFailureException.class }, maxAttempts = Constants.TX_RT_MAX, backoff = @Backoff(delay = Constants.TX_RT_DELAY))
public TargetMetadata updateMetaData(final String controllerId, final MetaData md) { public TargetMetadata updateMetadata(final String controllerId, final MetaData md) {
// check if exists otherwise throw entity not found exception // check if exists otherwise throw entity not found exception
final JpaTargetMetadata toUpdate = (JpaTargetMetadata) getMetaDataByControllerId(controllerId, md.getKey()) final JpaTargetMetadata updatedMetadata = (JpaTargetMetadata) getMetaDataByControllerId(controllerId,
md.getKey())
.orElseThrow(() -> new EntityNotFoundException(TargetMetadata.class, controllerId, md.getKey())); .orElseThrow(() -> new EntityNotFoundException(TargetMetadata.class, controllerId, md.getKey()));
toUpdate.setValue(md.getValue()); updatedMetadata.setValue(md.getValue());
// touch it to update the lock revision because we are modifying the // touch it to update the lock revision because we are modifying the
// target indirectly // target indirectly
touch(controllerId); final JpaTarget target = touch(controllerId);
return targetMetadataRepository.save(toUpdate); final JpaTargetMetadata matadata = targetMetadataRepository.save(updatedMetadata);
// target update event is set to ignore "lastModifiedAt" field so it is
// not send automatically within the touch() method
eventPublisher.publishEvent(new TargetUpdatedEvent(target, applicationContext.getId()));
return matadata;
} }
@Override @Override
@@ -239,8 +251,11 @@ public class JpaTargetManagement implements TargetManagement {
final JpaTargetMetadata metadata = (JpaTargetMetadata) getMetaDataByControllerId(controllerId, key) final JpaTargetMetadata metadata = (JpaTargetMetadata) getMetaDataByControllerId(controllerId, key)
.orElseThrow(() -> new EntityNotFoundException(TargetMetadata.class, controllerId, key)); .orElseThrow(() -> new EntityNotFoundException(TargetMetadata.class, controllerId, key));
touch(controllerId); final JpaTarget target = touch(controllerId);
targetMetadataRepository.delete(metadata.getId()); targetMetadataRepository.delete(metadata.getId());
// target update event is set to ignore "lastModifiedAt" field so it is
// not send automatically within the touch() method
eventPublisher.publishEvent(new TargetUpdatedEvent(target, applicationContext.getId()));
} }
@Override @Override

View File

@@ -152,9 +152,9 @@ public class TargetManagementTest extends AbstractJpaIntegrationTest {
verifyThrownExceptionBy(() -> targetManagement.findMetaDataByControllerIdAndRsql(PAGE, NOT_EXIST_ID, "name==*"), verifyThrownExceptionBy(() -> targetManagement.findMetaDataByControllerIdAndRsql(PAGE, NOT_EXIST_ID, "name==*"),
"Target"); "Target");
verifyThrownExceptionBy( verifyThrownExceptionBy(
() -> targetManagement.updateMetaData(NOT_EXIST_ID, entityFactory.generateTargetMetadata("xxx", "xxx")), () -> targetManagement.updateMetadata(NOT_EXIST_ID, entityFactory.generateTargetMetadata("xxx", "xxx")),
"Target"); "Target");
verifyThrownExceptionBy(() -> targetManagement.updateMetaData(target.getControllerId(), verifyThrownExceptionBy(() -> targetManagement.updateMetadata(target.getControllerId(),
entityFactory.generateTargetMetadata(NOT_EXIST_ID, "xxx")), "TargetMetadata"); entityFactory.generateTargetMetadata(NOT_EXIST_ID, "xxx")), "TargetMetadata");
} }
@@ -1002,7 +1002,7 @@ public class TargetManagementTest extends AbstractJpaIntegrationTest {
Thread.sleep(100); Thread.sleep(100);
// update the target metadata // update the target metadata
final JpaTargetMetadata updated = (JpaTargetMetadata) targetManagement.updateMetaData(target.getControllerId(), final JpaTargetMetadata updated = (JpaTargetMetadata) targetManagement.updateMetadata(target.getControllerId(),
entityFactory.generateTargetMetadata(knownKey, knownUpdateValue)); entityFactory.generateTargetMetadata(knownKey, knownUpdateValue));
// we are updating the target meta data so also modifying the base // we are updating the target meta data so also modifying the base
// software // software

View File

@@ -388,7 +388,7 @@ public class MgmtTargetResource implements MgmtTargetRestApi {
@Override @Override
public ResponseEntity<MgmtMetadata> updateMetadata(@PathVariable("targetId") final String targetId, public ResponseEntity<MgmtMetadata> updateMetadata(@PathVariable("targetId") final String targetId,
@PathVariable("metadataKey") final String metadataKey, @RequestBody final MgmtMetadataBodyPut metadata) { @PathVariable("metadataKey") final String metadataKey, @RequestBody final MgmtMetadataBodyPut metadata) {
final TargetMetadata updated = targetManagement.updateMetaData(targetId, final TargetMetadata updated = targetManagement.updateMetadata(targetId,
entityFactory.generateTargetMetadata(metadataKey, metadata.getValue())); entityFactory.generateTargetMetadata(metadataKey, metadata.getValue()));
return ResponseEntity.ok(MgmtTargetMapper.toResponseTargetMetadata(updated)); return ResponseEntity.ok(MgmtTargetMapper.toResponseTargetMetadata(updated));
} }

View File

@@ -12,7 +12,7 @@ import java.util.List;
import java.util.Set; import java.util.Set;
import org.eclipse.hawkbit.repository.model.MetaData; import org.eclipse.hawkbit.repository.model.MetaData;
import org.eclipse.hawkbit.repository.model.NamedVersionedEntity; import org.eclipse.hawkbit.repository.model.NamedEntity;
import org.eclipse.hawkbit.ui.SpPermissionChecker; import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.common.CommonDialogWindow.SaveDialogCloseListener; import org.eclipse.hawkbit.ui.common.CommonDialogWindow.SaveDialogCloseListener;
import org.eclipse.hawkbit.ui.common.builder.LabelBuilder; import org.eclipse.hawkbit.ui.common.builder.LabelBuilder;
@@ -61,7 +61,7 @@ import com.vaadin.ui.renderers.ClickableRenderer.RendererClickEvent;
* M is the metadata * M is the metadata
* *
*/ */
public abstract class AbstractMetadataPopupLayout<E extends NamedVersionedEntity, M extends MetaData> public abstract class AbstractMetadataPopupLayout<E extends NamedEntity, M extends MetaData>
extends CustomComponent { extends CustomComponent {
private static final String DELETE_BUTTON = "DELETE_BUTTON"; private static final String DELETE_BUTTON = "DELETE_BUTTON";
@@ -140,10 +140,9 @@ public abstract class AbstractMetadataPopupLayout<E extends NamedVersionedEntity
*/ */
public CommonDialogWindow getWindow(final E entity, final String metaDatakey) { public CommonDialogWindow getWindow(final E entity, final String metaDatakey) {
selectedEntity = entity; selectedEntity = entity;
final String nameVersion = HawkbitCommonUtil.getFormattedNameVersion(entity.getName(), entity.getVersion());
metadataWindow = new WindowBuilder(SPUIDefinitions.CREATE_UPDATE_WINDOW) metadataWindow = new WindowBuilder(SPUIDefinitions.CREATE_UPDATE_WINDOW)
.caption(getMetadataCaption(nameVersion)).content(this).cancelButtonClickListener(event -> onCancel()) .caption(getMetadataCaption()).content(this).cancelButtonClickListener(event -> onCancel())
.id(UIComponentIdProvider.METADATA_POPUP_ID).layout(mainLayout).i18n(i18n) .id(UIComponentIdProvider.METADATA_POPUP_ID).layout(mainLayout).i18n(i18n)
.saveDialogCloseListener(new SaveOnDialogCloseListener()).buildCommonDialogWindow(); .saveDialogCloseListener(new SaveOnDialogCloseListener()).buildCommonDialogWindow();
@@ -440,14 +439,18 @@ public abstract class AbstractMetadataPopupLayout<E extends NamedVersionedEntity
return true; return true;
} }
private String getMetadataCaption(final String nameVersionStr) { private String getMetadataCaption() {
final StringBuilder caption = new StringBuilder(); final StringBuilder caption = new StringBuilder();
caption.append(HawkbitCommonUtil.DIV_DESCRIPTION_START + i18n.getMessage("caption.metadata.popup") + " " caption.append(HawkbitCommonUtil.DIV_DESCRIPTION_START + i18n.getMessage("caption.metadata.popup") + " "
+ HawkbitCommonUtil.getBoldHTMLText(nameVersionStr)); + HawkbitCommonUtil.getBoldHTMLText(getElementTitle()));
caption.append(HawkbitCommonUtil.DIV_DESCRIPTION_END); caption.append(HawkbitCommonUtil.DIV_DESCRIPTION_END);
return caption.toString(); return caption.toString();
} }
protected String getElementTitle() {
return getSelectedEntity().getName();
}
private void onCancel() { private void onCancel() {
metadataWindow.close(); metadataWindow.close();
UI.getCurrent().removeWindow(metadataWindow); UI.getCurrent().removeWindow(metadataWindow);

View File

@@ -0,0 +1,44 @@
/**
* 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.ui.common;
import org.eclipse.hawkbit.repository.model.MetaData;
import org.eclipse.hawkbit.repository.model.NamedVersionedEntity;
import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.utils.HawkbitCommonUtil;
import org.eclipse.hawkbit.ui.utils.UINotification;
import org.eclipse.hawkbit.ui.utils.VaadinMessageSource;
import org.vaadin.spring.events.EventBus.UIEventBus;
/**
*
* Abstract pop up layout
*
* @param <E>
* E id the entity for which metadata is displayed
* @param <M>
* M is the metadata
*
*/
public abstract class AbstractMetadataPopupLayoutVersioned<E extends NamedVersionedEntity, M extends MetaData>
extends AbstractMetadataPopupLayout<E, M> {
private static final long serialVersionUID = 1L;
protected AbstractMetadataPopupLayoutVersioned(final VaadinMessageSource i18n, final UINotification uiNotification,
final UIEventBus eventBus, final SpPermissionChecker permChecker) {
super(i18n, uiNotification, eventBus, permChecker);
}
@Override
protected String getElementTitle() {
return HawkbitCommonUtil.getFormattedNameVersion(getSelectedEntity().getName(),
getSelectedEntity().getVersion());
}
}

View File

@@ -128,11 +128,6 @@ public abstract class AbstractDistributionSetDetails
return UIComponentIdProvider.DISTRIBUTION_DETAILS_HEADER_LABEL_ID; return UIComponentIdProvider.DISTRIBUTION_DETAILS_HEADER_LABEL_ID;
} }
@Override
protected boolean isMetadataIconToBeDisplayed() {
return true;
}
@Override @Override
protected void showMetadata(final ClickEvent event) { protected void showMetadata(final ClickEvent event) {
final Optional<DistributionSet> ds = distributionSetManagement.get(getSelectedBaseEntityId()); final Optional<DistributionSet> ds = distributionSetManagement.get(getSelectedBaseEntityId());

View File

@@ -112,11 +112,6 @@ public abstract class AbstractSoftwareModuleDetails
return UIComponentIdProvider.SOFTWARE_MODULE_DETAILS_HEADER_LABEL_ID; return UIComponentIdProvider.SOFTWARE_MODULE_DETAILS_HEADER_LABEL_ID;
} }
@Override
protected boolean isMetadataIconToBeDisplayed() {
return true;
}
@Override @Override
protected void showMetadata(final ClickEvent event) { protected void showMetadata(final ClickEvent event) {
softwareModuleManagement.get(getSelectedBaseEntityId()) softwareModuleManagement.get(getSelectedBaseEntityId())

View File

@@ -248,10 +248,8 @@ public abstract class AbstractTableDetailsLayout<T extends NamedEntity> extends
if (hasEditPermission()) { if (hasEditPermission()) {
nameEditLayout.addComponent(editButton); nameEditLayout.addComponent(editButton);
nameEditLayout.setComponentAlignment(editButton, Alignment.TOP_RIGHT); nameEditLayout.setComponentAlignment(editButton, Alignment.TOP_RIGHT);
if (isMetadataIconToBeDisplayed()) { nameEditLayout.addComponent(manageMetadataBtn);
nameEditLayout.addComponent(manageMetadataBtn); nameEditLayout.setComponentAlignment(manageMetadataBtn, Alignment.TOP_RIGHT);
nameEditLayout.setComponentAlignment(manageMetadataBtn, Alignment.TOP_RIGHT);
}
} }
nameEditLayout.setExpandRatio(caption, 1.0F); nameEditLayout.setExpandRatio(caption, 1.0F);
nameEditLayout.addStyleName(SPUIStyleDefinitions.WIDGET_TITLE); nameEditLayout.addStyleName(SPUIStyleDefinitions.WIDGET_TITLE);
@@ -300,6 +298,10 @@ public abstract class AbstractTableDetailsLayout<T extends NamedEntity> extends
return selectedBaseEntity == null ? null : selectedBaseEntity.getId(); return selectedBaseEntity == null ? null : selectedBaseEntity.getId();
} }
protected String getName() {
return getSelectedBaseEntity().getName();
}
protected abstract void populateDetailsWidget(); protected abstract void populateDetailsWidget();
protected abstract void populateMetadataDetails(); protected abstract void populateMetadataDetails();
@@ -331,10 +333,6 @@ public abstract class AbstractTableDetailsLayout<T extends NamedEntity> extends
protected abstract String getDetailsHeaderCaptionId(); protected abstract String getDetailsHeaderCaptionId();
protected abstract String getName();
protected abstract boolean isMetadataIconToBeDisplayed();
protected abstract void showMetadata(Button.ClickEvent event); protected abstract void showMetadata(Button.ClickEvent event);
public HorizontalLayout getNameEditLayout() { public HorizontalLayout getNameEditLayout() {

View File

@@ -54,7 +54,7 @@ public class DistributionSetMetadataDetailsLayout extends AbstractMetadataDetail
} }
/** /**
* Populate software module metadata. * Populate distribution set metadata.
* *
* @param distributionSet * @param distributionSet
*/ */
@@ -70,7 +70,6 @@ public class DistributionSetMetadataDetailsLayout extends AbstractMetadataDetail
if (null != dsMetadataList && !dsMetadataList.isEmpty()) { if (null != dsMetadataList && !dsMetadataList.isEmpty()) {
dsMetadataList.forEach(this::setMetadataProperties); dsMetadataList.forEach(this::setMetadataProperties);
} }
} }
@Override @Override

View File

@@ -0,0 +1,87 @@
/**
* 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.ui.common.detailslayout;
import java.util.List;
import org.eclipse.hawkbit.repository.TargetManagement;
import org.eclipse.hawkbit.repository.model.Target;
import org.eclipse.hawkbit.repository.model.TargetMetadata;
import org.eclipse.hawkbit.ui.management.targettable.TargetMetadataPopupLayout;
import org.eclipse.hawkbit.ui.utils.UIComponentIdProvider;
import org.eclipse.hawkbit.ui.utils.VaadinMessageSource;
import org.springframework.data.domain.PageRequest;
import com.vaadin.ui.UI;
/**
* Target Metadata details layout.
*
*/
public class TargetMetadataDetailsLayout extends AbstractMetadataDetailsLayout {
private static final long serialVersionUID = 1L;
private final transient TargetManagement targetManagement;
private final TargetMetadataPopupLayout targetMetadataPopupLayout;
private Long selectedTargetId;
/**
* Initialize the layout.
*
* @param i18n
* the i18n service
* @param targetManagement
* the target management service
* @param targetMetadataPopupLayout
* the target metadata popup layout
*/
public TargetMetadataDetailsLayout(final VaadinMessageSource i18n,
final TargetManagement targetManagement,
final TargetMetadataPopupLayout targetMetadataPopupLayout) {
super(i18n);
this.targetManagement = targetManagement;
this.targetMetadataPopupLayout = targetMetadataPopupLayout;
}
/**
* Populate target metadata.
*
* @param target
*/
public void populateMetadata(final Target target) {
removeAllItems();
if (target == null) {
return;
}
selectedTargetId = target.getId();
final List<TargetMetadata> targetMetadataList = targetManagement
.findMetaDataByControllerId(new PageRequest(0, MAX_METADATA_QUERY), target.getControllerId())
.getContent();
if (targetMetadataList != null && !targetMetadataList.isEmpty()) {
targetMetadataList.forEach(this::setMetadataProperties);
}
}
@Override
protected String getDetailLinkId(final String name) {
return new StringBuilder(UIComponentIdProvider.TARGET_METADATA_DETAIL_LINK).append('.').append(name).toString();
}
@Override
protected void showMetadataDetails(final String metadataKey) {
targetManagement.get(selectedTargetId).ifPresent(
target -> UI.getCurrent().addWindow(targetMetadataPopupLayout.getWindow(target, metadataKey)));
}
}

View File

@@ -8,7 +8,6 @@
*/ */
package org.eclipse.hawkbit.ui.distributions.dstable; package org.eclipse.hawkbit.ui.distributions.dstable;
import java.util.Arrays;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
@@ -18,7 +17,7 @@ import org.eclipse.hawkbit.repository.model.DistributionSet;
import org.eclipse.hawkbit.repository.model.DistributionSetMetadata; import org.eclipse.hawkbit.repository.model.DistributionSetMetadata;
import org.eclipse.hawkbit.repository.model.MetaData; import org.eclipse.hawkbit.repository.model.MetaData;
import org.eclipse.hawkbit.ui.SpPermissionChecker; import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.common.AbstractMetadataPopupLayout; import org.eclipse.hawkbit.ui.common.AbstractMetadataPopupLayoutVersioned;
import org.eclipse.hawkbit.ui.utils.UINotification; import org.eclipse.hawkbit.ui.utils.UINotification;
import org.eclipse.hawkbit.ui.utils.VaadinMessageSource; import org.eclipse.hawkbit.ui.utils.VaadinMessageSource;
import org.springframework.data.domain.PageRequest; import org.springframework.data.domain.PageRequest;
@@ -27,9 +26,9 @@ import org.vaadin.spring.events.EventBus.UIEventBus;
/** /**
* Pop up layout to display distribution metadata. * Pop up layout to display distribution metadata.
*/ */
public class DsMetadataPopupLayout extends AbstractMetadataPopupLayout<DistributionSet, MetaData> { public class DsMetadataPopupLayout extends AbstractMetadataPopupLayoutVersioned<DistributionSet, MetaData> {
private static final long serialVersionUID = -7778944849012048106L; private static final long serialVersionUID = 1L;
private final transient DistributionSetManagement distributionSetManagement; private final transient DistributionSetManagement distributionSetManagement;
@@ -52,7 +51,8 @@ public class DsMetadataPopupLayout extends AbstractMetadataPopupLayout<Distribut
protected DistributionSetMetadata createMetadata(final DistributionSet entity, final String key, protected DistributionSetMetadata createMetadata(final DistributionSet entity, final String key,
final String value) { final String value) {
final DistributionSetMetadata dsMetaData = distributionSetManagement final DistributionSetMetadata dsMetaData = distributionSetManagement
.createMetaData(entity.getId(), Arrays.asList(entityFactory.generateDsMetadata(key, value))).get(0); .createMetaData(entity.getId(), Collections.singletonList(entityFactory.generateDsMetadata(key, value)))
.get(0);
setSelectedEntity(dsMetaData.getDistributionSet()); setSelectedEntity(dsMetaData.getDistributionSet());
return dsMetaData; return dsMetaData;
} }

View File

@@ -16,7 +16,7 @@ import org.eclipse.hawkbit.repository.SoftwareModuleManagement;
import org.eclipse.hawkbit.repository.model.SoftwareModule; import org.eclipse.hawkbit.repository.model.SoftwareModule;
import org.eclipse.hawkbit.repository.model.SoftwareModuleMetadata; import org.eclipse.hawkbit.repository.model.SoftwareModuleMetadata;
import org.eclipse.hawkbit.ui.SpPermissionChecker; import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.common.AbstractMetadataPopupLayout; import org.eclipse.hawkbit.ui.common.AbstractMetadataPopupLayoutVersioned;
import org.eclipse.hawkbit.ui.utils.UIComponentIdProvider; import org.eclipse.hawkbit.ui.utils.UIComponentIdProvider;
import org.eclipse.hawkbit.ui.utils.UINotification; import org.eclipse.hawkbit.ui.utils.UINotification;
import org.eclipse.hawkbit.ui.utils.VaadinMessageSource; import org.eclipse.hawkbit.ui.utils.VaadinMessageSource;
@@ -32,7 +32,7 @@ import com.vaadin.ui.VerticalLayout;
/** /**
* Pop up layout to display software module metadata. * Pop up layout to display software module metadata.
*/ */
public class SwMetadataPopupLayout extends AbstractMetadataPopupLayout<SoftwareModule, SoftwareModuleMetadata> { public class SwMetadataPopupLayout extends AbstractMetadataPopupLayoutVersioned<SoftwareModule, SoftwareModuleMetadata> {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;

View File

@@ -10,6 +10,7 @@ package org.eclipse.hawkbit.ui.management.targettable;
import java.net.URI; import java.net.URI;
import java.util.Map; import java.util.Map;
import java.util.Optional;
import org.eclipse.hawkbit.repository.DeploymentManagement; import org.eclipse.hawkbit.repository.DeploymentManagement;
import org.eclipse.hawkbit.repository.EntityFactory; import org.eclipse.hawkbit.repository.EntityFactory;
@@ -20,6 +21,7 @@ import org.eclipse.hawkbit.repository.model.SoftwareModule;
import org.eclipse.hawkbit.repository.model.Target; import org.eclipse.hawkbit.repository.model.Target;
import org.eclipse.hawkbit.ui.SpPermissionChecker; import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.common.detailslayout.AbstractTableDetailsLayout; import org.eclipse.hawkbit.ui.common.detailslayout.AbstractTableDetailsLayout;
import org.eclipse.hawkbit.ui.common.detailslayout.TargetMetadataDetailsLayout;
import org.eclipse.hawkbit.ui.common.tagdetails.TargetTagToken; import org.eclipse.hawkbit.ui.common.tagdetails.TargetTagToken;
import org.eclipse.hawkbit.ui.components.SPUIComponentProvider; import org.eclipse.hawkbit.ui.components.SPUIComponentProvider;
import org.eclipse.hawkbit.ui.decorators.SPUIButtonStyleNoBorder; import org.eclipse.hawkbit.ui.decorators.SPUIButtonStyleNoBorder;
@@ -56,10 +58,16 @@ public class TargetDetails extends AbstractTableDetailsLayout<Target> {
private final TargetTagToken targetTagToken; private final TargetTagToken targetTagToken;
private final TargetMetadataDetailsLayout targetMetadataTable;
private final TargetAddUpdateWindowLayout targetAddUpdateWindowLayout; private final TargetAddUpdateWindowLayout targetAddUpdateWindowLayout;
private final transient TargetManagement targetManagement; private final transient TargetManagement targetManagement;
private final TargetMetadataPopupLayout targetMetadataPopupLayout;
private final UINotification uiNotification;
private final transient DeploymentManagement deploymentManagement; private final transient DeploymentManagement deploymentManagement;
private VerticalLayout assignedDistLayout; private VerticalLayout assignedDistLayout;
@@ -69,15 +77,21 @@ public class TargetDetails extends AbstractTableDetailsLayout<Target> {
TargetDetails(final VaadinMessageSource i18n, final UIEventBus eventBus, TargetDetails(final VaadinMessageSource i18n, final UIEventBus eventBus,
final SpPermissionChecker permissionChecker, final ManagementUIState managementUIState, final SpPermissionChecker permissionChecker, final ManagementUIState managementUIState,
final UINotification uiNotification, final TargetTagManagement tagManagement, final UINotification uiNotification, final TargetTagManagement tagManagement,
final TargetManagement targetManagement, final DeploymentManagement deploymentManagement, final TargetManagement targetManagement, final TargetMetadataPopupLayout targetMetadataPopupLayout,
final EntityFactory entityFactory, final TargetTable targetTable) { final DeploymentManagement deploymentManagement, final EntityFactory entityFactory,
final TargetTable targetTable) {
super(i18n, eventBus, permissionChecker, managementUIState); super(i18n, eventBus, permissionChecker, managementUIState);
this.targetTagToken = new TargetTagToken(permissionChecker, i18n, uiNotification, eventBus, managementUIState, this.targetTagToken = new TargetTagToken(permissionChecker, i18n, uiNotification, eventBus, managementUIState,
tagManagement, targetManagement); tagManagement, targetManagement);
targetAddUpdateWindowLayout = new TargetAddUpdateWindowLayout(i18n, targetManagement, eventBus, uiNotification, this.targetAddUpdateWindowLayout = new TargetAddUpdateWindowLayout(i18n, targetManagement, eventBus,
uiNotification,
entityFactory, targetTable); entityFactory, targetTable);
this.uiNotification = uiNotification;
this.targetManagement = targetManagement; this.targetManagement = targetManagement;
this.deploymentManagement = deploymentManagement; this.deploymentManagement = deploymentManagement;
this.targetMetadataPopupLayout = targetMetadataPopupLayout;
this.targetMetadataTable = new TargetMetadataDetailsLayout(i18n, targetManagement,
targetMetadataPopupLayout);
addDetailsTab(); addDetailsTab();
restoreState(); restoreState();
} }
@@ -95,6 +109,7 @@ public class TargetDetails extends AbstractTableDetailsLayout<Target> {
getDetailsTab().addTab(createInstalledDistLayout(), getI18n().getMessage("header.target.installed"), null); getDetailsTab().addTab(createInstalledDistLayout(), getI18n().getMessage("header.target.installed"), null);
getDetailsTab().addTab(getTagsLayout(), getI18n().getMessage("caption.tags.tab"), null); getDetailsTab().addTab(getTagsLayout(), getI18n().getMessage("caption.tags.tab"), null);
getDetailsTab().addTab(getLogLayout(), getI18n().getMessage("caption.logs.tab"), null); getDetailsTab().addTab(getLogLayout(), getI18n().getMessage("caption.logs.tab"), null);
getDetailsTab().addTab(targetMetadataTable, getI18n().getMessage("caption.metadata"), null);
} }
private Component createInstalledDistLayout() { private Component createInstalledDistLayout() {
@@ -157,11 +172,7 @@ public class TargetDetails extends AbstractTableDetailsLayout<Target> {
populateDistributionDtls(assignedDistLayout, null); populateDistributionDtls(assignedDistLayout, null);
} }
populateTags(targetTagToken); populateTags(targetTagToken);
} populateMetadataDetails();
@Override
protected String getName() {
return getSelectedBaseEntity().getName();
} }
private void updateDetailsLayout(final String controllerId, final URI address, final String securityToken, private void updateDetailsLayout(final String controllerId, final URI address, final String securityToken,
@@ -324,25 +335,24 @@ public class TargetDetails extends AbstractTableDetailsLayout<Target> {
return UIComponentIdProvider.TARGET_DETAILS_HEADER_LABEL_ID; return UIComponentIdProvider.TARGET_DETAILS_HEADER_LABEL_ID;
} }
@Override
protected boolean isMetadataIconToBeDisplayed() {
return false;
}
@Override @Override
protected void showMetadata(final ClickEvent event) { protected void showMetadata(final ClickEvent event) {
// No implementation required final Optional<Target> target = targetManagement.get(getSelectedBaseEntityId());
if (!target.isPresent()) {
uiNotification.displayWarning(getI18n().getMessage("targets.not.exists"));
return;
}
UI.getCurrent().addWindow(targetMetadataPopupLayout.getWindow(target.get(), null));
} }
@Override @Override
protected void populateMetadataDetails() { protected void populateMetadataDetails() {
// No implementation required targetMetadataTable.populateMetadata(getSelectedBaseEntity());
} }
@Override @Override
protected String getMetadataButtonId() { protected String getMetadataButtonId() {
// No implementation required return UIComponentIdProvider.TARGET_METADATA_BUTTON;
return null;
} }
} }

View File

@@ -0,0 +1,90 @@
/**
* 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.ui.management.targettable;
import java.util.Collections;
import java.util.List;
import org.eclipse.hawkbit.repository.EntityFactory;
import org.eclipse.hawkbit.repository.TargetManagement;
import org.eclipse.hawkbit.repository.model.MetaData;
import org.eclipse.hawkbit.repository.model.Target;
import org.eclipse.hawkbit.repository.model.TargetMetadata;
import org.eclipse.hawkbit.ui.SpPermissionChecker;
import org.eclipse.hawkbit.ui.common.AbstractMetadataPopupLayout;
import org.eclipse.hawkbit.ui.utils.UINotification;
import org.eclipse.hawkbit.ui.utils.VaadinMessageSource;
import org.springframework.data.domain.PageRequest;
import org.vaadin.spring.events.EventBus.UIEventBus;
/**
* Pop up layout to display target metadata.
*/
public class TargetMetadataPopupLayout extends AbstractMetadataPopupLayout<Target, MetaData> {
private static final long serialVersionUID = 1L;
private final transient TargetManagement targetManagement;
private final transient EntityFactory entityFactory;
public TargetMetadataPopupLayout(final VaadinMessageSource i18n, final UINotification uiNotification,
final UIEventBus eventBus, final TargetManagement targetManagement, final EntityFactory entityFactory,
final SpPermissionChecker permChecker) {
super(i18n, uiNotification, eventBus, permChecker);
this.targetManagement = targetManagement;
this.entityFactory = entityFactory;
}
@Override
protected boolean checkForDuplicate(final Target entity, final String value) {
return targetManagement.getMetaDataByControllerId(entity.getControllerId(), value).isPresent();
}
@Override
protected MetaData createMetadata(final Target entity, final String key, final String value) {
final TargetMetadata metaData = targetManagement
.createMetaData(entity.getControllerId(),
Collections.singletonList(entityFactory.generateTargetMetadata(key, value)))
.get(0);
setSelectedEntity(metaData.getTarget());
return metaData;
}
@Override
protected MetaData updateMetadata(final Target entity, final String key, final String value) {
final TargetMetadata metaData = targetManagement.updateMetadata(entity.getControllerId(),
entityFactory.generateTargetMetadata(key, value));
setSelectedEntity(metaData.getTarget());
return metaData;
}
@Override
protected List<MetaData> getMetadataList() {
return Collections.unmodifiableList(targetManagement
.findMetaDataByControllerId(new PageRequest(0, 500), getSelectedEntity().getControllerId())
.getContent());
}
@Override
protected void deleteMetadata(final Target entity, final String key) {
targetManagement.deleteMetaData(entity.getControllerId(), key);
}
@Override
protected boolean hasCreatePermission() {
return permChecker.hasCreateRepositoryPermission();
}
@Override
protected boolean hasUpdatePermission() {
return permChecker.hasUpdateRepositoryPermission();
}
}

View File

@@ -47,9 +47,11 @@ public class TargetTableLayout extends AbstractTableLayout<TargetTable> {
final DeploymentManagement deploymentManagement, final UiProperties uiProperties, final DeploymentManagement deploymentManagement, final UiProperties uiProperties,
final SpPermissionChecker permissionChecker, final TargetTagManagement tagManagement, final SpPermissionChecker permissionChecker, final TargetTagManagement tagManagement,
final DistributionSetManagement distributionSetManagement, final Executor uiExecutor) { final DistributionSetManagement distributionSetManagement, final Executor uiExecutor) {
final TargetMetadataPopupLayout targetMetadataPopupLayout = new TargetMetadataPopupLayout(i18n, uiNotification,
eventBus, targetManagement, entityFactory, permissionChecker);
this.eventBus = eventBus; this.eventBus = eventBus;
this.targetDetails = new TargetDetails(i18n, eventBus, permissionChecker, managementUIState, uiNotification, this.targetDetails = new TargetDetails(i18n, eventBus, permissionChecker, managementUIState, uiNotification,
tagManagement, targetManagement, deploymentManagement, entityFactory, targetTable); tagManagement, targetManagement, targetMetadataPopupLayout, deploymentManagement, entityFactory, targetTable);
this.targetTableHeader = new TargetTableHeader(i18n, permissionChecker, eventBus, uiNotification, this.targetTableHeader = new TargetTableHeader(i18n, permissionChecker, eventBus, uiNotification,
managementUIState, managementViewClientCriterion, targetManagement, deploymentManagement, uiProperties, managementUIState, managementViewClientCriterion, targetManagement, deploymentManagement, uiProperties,
entityFactory, uiNotification, tagManagement, distributionSetManagement, uiExecutor, targetTable); entityFactory, uiNotification, tagManagement, distributionSetManagement, uiExecutor, targetTable);

View File

@@ -470,6 +470,11 @@ public final class UIComponentIdProvider {
*/ */
public static final String SHOW_TARGET_TAGS = "show.target.tags.icon"; public static final String SHOW_TARGET_TAGS = "show.target.tags.icon";
/**
* Target metadata button id.
*/
public static final String TARGET_METADATA_BUTTON = "target.metadata.button";
/** /**
* ID-Target tag table. * ID-Target tag table.
*/ */
@@ -1131,7 +1136,7 @@ public final class UIComponentIdProvider {
public static final String DS_TABLE_MANAGE_METADATA_ID = "dstable.manage.metadata.id"; public static final String DS_TABLE_MANAGE_METADATA_ID = "dstable.manage.metadata.id";
/** /**
* DistributionSet - Metadata button id. * DistributionSet - Metadata detail link.
*/ */
public static final String DS_METADATA_DETAIL_LINK = "distributionset.metadata.detail.link"; public static final String DS_METADATA_DETAIL_LINK = "distributionset.metadata.detail.link";
@@ -1151,10 +1156,15 @@ public final class UIComponentIdProvider {
public static final String DIST_SW_MODULE_DETAILS_TABSHEET_ID = "dist.sw.module.details.tabsheet"; public static final String DIST_SW_MODULE_DETAILS_TABSHEET_ID = "dist.sw.module.details.tabsheet";
/** /**
* Software Module - Metadata button id. * Software Module - Metadata detail link.
*/ */
public static final String SW_METADATA_DETAIL_LINK = "softwaremodule.metadata.detail.link"; public static final String SW_METADATA_DETAIL_LINK = "softwaremodule.metadata.detail.link";
/**
* Target - Metadata detail link.
*/
public static final String TARGET_METADATA_DETAIL_LINK = "target.metadata.detail.link";
/** /**
* Table multiselect for selecting DistType * Table multiselect for selecting DistType
*/ */