diff --git a/src/main/java/be/seeseepuff/pcinv/controllers/WebController.java b/src/main/java/be/seeseepuff/pcinv/controllers/WebController.java index ba863b2..7ad845b 100644 --- a/src/main/java/be/seeseepuff/pcinv/controllers/WebController.java +++ b/src/main/java/be/seeseepuff/pcinv/controllers/WebController.java @@ -35,6 +35,8 @@ public class WebController { private static final String ACTION = "action"; /// The name of the model attribute that holds the current time in milliseconds. private static final String TIME = "time"; + /// The name of the model attribute that holds the input lists for creating or editing assets. + private static final String INPUT_LIST = "inputLists"; private final AssetService assetService; @@ -157,6 +159,7 @@ public class WebController { model.addAttribute(ACTION, "create"); model.addAttribute(DESCRIPTORS, assetService.getAssetDescriptorTree(type)); model.addAttribute(DESCRIPTOR, assetService.getAssetDescriptor(type)); + model.addAttribute(INPUT_LIST, assetService.getInputList(type)); return "create_asset"; } @@ -177,6 +180,7 @@ public class WebController { model.addAttribute(ASSET, asset); model.addAttribute(DESCRIPTORS, assetService.getAssetDescriptorTree(assetType)); model.addAttribute(DESCRIPTOR, assetService.getAssetDescriptor(assetType)); + model.addAttribute(INPUT_LIST, assetService.getInputList(assetType)); return "create_asset"; } diff --git a/src/main/java/be/seeseepuff/pcinv/meta/AssetProperty.java b/src/main/java/be/seeseepuff/pcinv/meta/AssetProperty.java index 8e40f90..68e606a 100644 --- a/src/main/java/be/seeseepuff/pcinv/meta/AssetProperty.java +++ b/src/main/java/be/seeseepuff/pcinv/meta/AssetProperty.java @@ -43,6 +43,8 @@ public class AssetProperty { private final Function getter; /// Whether the property is an input list. private final boolean inputList; + /// Whether the property should be hidden in the overview. + private final boolean hideInOverview; /** * Enum representing the possible types of asset properties. @@ -87,6 +89,7 @@ public class AssetProperty { .type(type) .required(annotation.required()) .inputList(property.isAnnotationPresent(InputList.class)) + .hideInOverview(property.isAnnotationPresent(HideInOverview.class)) .setter((obj, value) -> { try { property.setAccessible(true); diff --git a/src/main/java/be/seeseepuff/pcinv/meta/HideInOverview.java b/src/main/java/be/seeseepuff/pcinv/meta/HideInOverview.java new file mode 100644 index 0000000..a25f732 --- /dev/null +++ b/src/main/java/be/seeseepuff/pcinv/meta/HideInOverview.java @@ -0,0 +1,14 @@ +package be.seeseepuff.pcinv.meta; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +/** + * Indicates that the field should not be included in the overview of an asset. + */ +@Retention(RetentionPolicy.RUNTIME) +@Target(ElementType.FIELD) +public @interface HideInOverview { +} diff --git a/src/main/java/be/seeseepuff/pcinv/models/GenericAsset.java b/src/main/java/be/seeseepuff/pcinv/models/GenericAsset.java index ef170de..cbbfe47 100644 --- a/src/main/java/be/seeseepuff/pcinv/models/GenericAsset.java +++ b/src/main/java/be/seeseepuff/pcinv/models/GenericAsset.java @@ -2,6 +2,7 @@ package be.seeseepuff.pcinv.models; import be.seeseepuff.pcinv.meta.AssetInfo; import be.seeseepuff.pcinv.meta.InputList; +import be.seeseepuff.pcinv.meta.HideInOverview; import be.seeseepuff.pcinv.meta.Property; import jakarta.persistence.*; import lombok.Getter; @@ -52,6 +53,7 @@ public class GenericAsset /// A description of the asset, providing additional details. @Property("Description") + @HideInOverview private String description; /// The state of the asset, indicating its condition. diff --git a/src/main/java/be/seeseepuff/pcinv/models/HddAsset.java b/src/main/java/be/seeseepuff/pcinv/models/HddAsset.java index d77cff3..44ea113 100644 --- a/src/main/java/be/seeseepuff/pcinv/models/HddAsset.java +++ b/src/main/java/be/seeseepuff/pcinv/models/HddAsset.java @@ -2,6 +2,7 @@ package be.seeseepuff.pcinv.models; import be.seeseepuff.pcinv.meta.AssetInfo; import be.seeseepuff.pcinv.meta.Capacity; +import be.seeseepuff.pcinv.meta.InputList; import be.seeseepuff.pcinv.meta.Property; import jakarta.persistence.*; import lombok.Getter; @@ -36,9 +37,11 @@ public class HddAsset implements Asset /// The drive's interface type, such as SATA, IDE, ISA-16, ... @Property("Interface Type") + @InputList private String interfaceType; /// The drive's form factor, such as 2.5", 3.5", etc. @Property("Form Factor") + @InputList private String formFactor; } diff --git a/src/main/java/be/seeseepuff/pcinv/services/AssetService.java b/src/main/java/be/seeseepuff/pcinv/services/AssetService.java index 88bd8e2..37db028 100644 --- a/src/main/java/be/seeseepuff/pcinv/services/AssetService.java +++ b/src/main/java/be/seeseepuff/pcinv/services/AssetService.java @@ -12,9 +12,7 @@ import lombok.RequiredArgsConstructor; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; -import java.util.Collection; -import java.util.List; -import java.util.Map; +import java.util.*; /** * Service for managing assets in the repository. @@ -173,6 +171,12 @@ public class AssetService { private void fillIn(Object asset, AssetDescriptor assetDescriptor, Map formData) { for (var property : assetDescriptor.getProperties()) { var value = parseValue(assetDescriptor, property, formData); + if (property.isInputList()) { + var selectedItem = formData.get(assetDescriptor.asString(property) + "-list"); + if (selectedItem != null && !selectedItem.isBlank() && !selectedItem.equals("__new__")) { + value = selectedItem; + } + } if (value == null && property.isRequired()) { throw new IllegalArgumentException("Property '" + property.getName() + "' is required but not provided."); } @@ -237,4 +241,50 @@ public class AssetService { genericRepository.delete(genericAsset); genericRepository.flush(); } + + /** + * Retrieves the input list mapping for a specific asset type. + * + * @param type the type of asset to retrieve the input list for + * @return a map of input names to their corresponding list + */ + public Map> getInputList(String type) { + var map = new HashMap>(); + var tree = getAssetDescriptorTree(type); + for (var descriptor : tree) { + for (var property : descriptor.getProperties()) { + if (property.isInputList()) { + var inputList = getInputList(descriptor, property); + map.put(descriptor.asString(property), inputList); + } + } + } + return map; + } + + /** + * Retrieves the input list for a specific asset descriptor and property. + * + * @param descriptor the asset descriptor containing the property + * @param property the asset property to retrieve the input list for + * @return a set of input values for the specified property + */ + private Set getInputList(AssetDescriptor descriptor, AssetProperty property) { + List entries; + if (descriptor.getType().equals(GenericAsset.TYPE)) { + entries = genericRepository.findAll(); + } else { + var repository = getRepositoryFor(descriptor.getType()); + entries = repository.findAll(); + } + + Set inputList = new TreeSet<>(); + for (var entry : entries) { + var value = property.getValue(entry); + if (value != null) { + inputList.add(value.toString()); + } + } + return inputList; + } } diff --git a/src/main/resources/templates/browse_type.html b/src/main/resources/templates/browse_type.html index ad0420f..64373d9 100644 --- a/src/main/resources/templates/browse_type.html +++ b/src/main/resources/templates/browse_type.html @@ -3,11 +3,11 @@ There are in the database. - + - diff --git a/src/main/resources/templates/create_asset.html b/src/main/resources/templates/create_asset.html index 90cec0f..09ab10d 100644 --- a/src/main/resources/templates/create_asset.html +++ b/src/main/resources/templates/create_asset.html @@ -8,6 +8,14 @@
Actions
+
+ + + or + +