Début du refactoring
This commit is contained in:
parent
9fa96adda8
commit
43b06d30f4
|
@ -40,7 +40,4 @@ public class MaterialType implements IModel {
|
|||
@NotNull
|
||||
@ColumnDefault("false")
|
||||
private Boolean usePercentages;
|
||||
|
||||
@OneToMany
|
||||
private List<Material> materials;
|
||||
}
|
||||
|
|
|
@ -30,6 +30,7 @@ public class Mix implements IModel {
|
|||
private MixType mixType;
|
||||
|
||||
@OneToMany(cascade = CascadeType.ALL)
|
||||
@JoinColumn(name = "mix")
|
||||
private List<MixQuantity> mixQuantities;
|
||||
|
||||
// Casier
|
||||
|
|
|
@ -44,9 +44,9 @@ public class Recipe implements IModel {
|
|||
private String note;
|
||||
|
||||
@JsonIgnore
|
||||
@OneToMany(cascade = CascadeType.ALL)
|
||||
@OneToMany(mappedBy = "recipe", cascade = CascadeType.ALL)
|
||||
private List<Mix> mixes;
|
||||
|
||||
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
|
||||
@OneToMany(mappedBy = "recipe", cascade = CascadeType.ALL, fetch = FetchType.LAZY)
|
||||
private List<RecipeStep> recipeSteps;
|
||||
}
|
||||
|
|
|
@ -105,7 +105,7 @@ public abstract class GenericService<T extends IModel, R extends JpaRepository<T
|
|||
* @return Si l'entité est valide pour l'édition.
|
||||
*/
|
||||
public boolean isValidForUpdate(@NonNull T entity) {
|
||||
return exists(entity);
|
||||
return entity.getId() != null && exists(entity);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -116,7 +116,7 @@ public abstract class GenericService<T extends IModel, R extends JpaRepository<T
|
|||
*/
|
||||
@Override
|
||||
public boolean exists(T entity) {
|
||||
return entity != null && existsById(entity.getId());
|
||||
return entity != null && entity.getId() != null && existsById(entity.getId());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -71,8 +71,8 @@ public class MaterialService extends GenericService<Material, MaterialDao> {
|
|||
public boolean isValidForUpdate(Material material) {
|
||||
if (material == null) return false;
|
||||
|
||||
Optional<Material> materialByCode = dao.findByMaterialCode(material.getMaterialCode());
|
||||
return super.isValidForUpdate(material) && (materialByCode.isEmpty() || material.getMaterialID().equals(materialByCode.get().getMaterialID()));
|
||||
Optional<Material> materialByCode = dao.findByName(material.getName());
|
||||
return super.isValidForUpdate(material) && (materialByCode.isEmpty() || material.getId().equals(materialByCode.get().getId()));
|
||||
}
|
||||
|
||||
@Deprecated(since = "1.2.0")
|
||||
|
|
|
@ -38,8 +38,8 @@ public class MixService extends GenericService<Mix, MixDao> {
|
|||
.getAll()
|
||||
.stream()
|
||||
.filter(m -> !m.isMixType() || recipeMixTypes.contains(mixTypeService.getByMaterial(m).get()))
|
||||
.sorted(Comparator.comparing(Material::getMaterialCode))
|
||||
.sorted(Comparator.comparing(m -> m.getMaterialType().getMaterialTypeName()))
|
||||
.sorted(Comparator.comparing(Material::getName))
|
||||
.sorted(Comparator.comparing(m -> m.getMaterialType().getName()))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
|
@ -109,16 +109,20 @@ public class MixService extends GenericService<Mix, MixDao> {
|
|||
mix.getMixType().setName(formDto.getMixTypeName());
|
||||
material.setName(formDto.getMixTypeName());
|
||||
|
||||
List<MixQuantity> oldQuantities = mix.getMixQuantities();
|
||||
List<MixQuantity> mixQuantities = createMixQuantities(mix, materials, formDto.getQuantities());
|
||||
|
||||
// Supprime les anciens MixQuantity pour éviter les doublons et les entrées inutiles dans la base de données
|
||||
if (!mixQuantityService.deleteAll(mix.getMixQuantities())) {
|
||||
if (!mixQuantityService.deleteAll(oldQuantities)) {
|
||||
return modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
}
|
||||
|
||||
mix.setMixQuantities(mixQuantities);
|
||||
if (materialService.update(material).isPresent() && update(mix).isPresent()) return null;
|
||||
else return modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
if (materialService.update(material).isPresent() && update(mix).isPresent()) {
|
||||
return null;
|
||||
} else {
|
||||
return modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
}
|
||||
}
|
||||
|
||||
public boolean deleteMix(Mix mix) {
|
||||
|
|
|
@ -46,7 +46,7 @@ public class RecipeService extends GenericService<Recipe, RecipeDao> {
|
|||
public List<Mix> getSortedMixes(Recipe recipe) {
|
||||
List<Mix> mixes = recipe.getMixes();
|
||||
mixes.sort(Comparator.comparing(Mix::getId));
|
||||
return mixes;
|
||||
return new ArrayList<>(mixes); // Convertit le PersistentBag en ArrayList
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -67,7 +67,7 @@ public class WebsitePaths {
|
|||
public static final String EDITOR_MATERIAL_TYPE_SPECIFIC = "materialType/editor/{id}";
|
||||
public static final String EDITOR_MATERIAL_TYPE_EDITOR = "materialType/edit";
|
||||
|
||||
// Mélanges(
|
||||
// Mélanges
|
||||
public static final String CREATOR_MIX = "mix/creator";
|
||||
public static final String CREATOR_MIX_SPECIFIC = "mix/creator/{id}";
|
||||
public static final String EDITOR_MIX = "mix/editor";
|
||||
|
|
|
@ -43,21 +43,6 @@ public class IndexController {
|
|||
.build();
|
||||
}
|
||||
|
||||
// @GetMapping(value = SEARCH, produces = MediaType.APPLICATION_JSON_VALUE)
|
||||
// @ResponseBody
|
||||
public Map<String, Object> searchWord(@RequestParam String searchString) {
|
||||
Map<Company, List<Recipe>> searchResult = recipeService.getRecipesForSearchString(searchString);
|
||||
Map<Long, List<Long>> outputResult = new HashMap<>();
|
||||
|
||||
for (Company c : searchResult.keySet()) {
|
||||
outputResult.put(c.getId(), searchResult.get(c).stream().map(Recipe::getId).collect(Collectors.toList()));
|
||||
}
|
||||
|
||||
return new JSONResponseBuilder()
|
||||
.addAttribute("result", outputResult)
|
||||
.build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Valide un mot de passe reçu dans une requête HTTP POST, dans le champ "password".
|
||||
*
|
||||
|
|
|
@ -16,8 +16,8 @@ import org.springframework.web.servlet.ModelAndView;
|
|||
import javax.validation.Valid;
|
||||
import java.util.Optional;
|
||||
|
||||
import static dev.fyloz.trial.colorrecipesexplorer.web.PagesPaths.CREATOR_COMPANY;
|
||||
import static dev.fyloz.trial.colorrecipesexplorer.web.PagesPaths.INDEX;
|
||||
import static dev.fyloz.trial.colorrecipesexplorer.web.WebsitePaths.CREATOR_COMPANY;
|
||||
import static dev.fyloz.trial.colorrecipesexplorer.web.WebsitePaths.INDEX;
|
||||
|
||||
@Controller
|
||||
public class CompanyCreatorController {
|
||||
|
@ -63,13 +63,13 @@ public class CompanyCreatorController {
|
|||
|
||||
if (savedCompany.isPresent()) {
|
||||
return modelResponseBuilder
|
||||
.addResponseData(ResponseDataType.COMPANY_NAME, savedCompany.get().getCompanyName())
|
||||
.addResponseData(ResponseDataType.COMPANY_NAME, savedCompany.get().getName())
|
||||
.build();
|
||||
} else {
|
||||
modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
}
|
||||
} else {
|
||||
modelResponseBuilder.addResponseCode(ResponseCode.COMPANY_ALREADY_EXIST, company.getCompanyName());
|
||||
modelResponseBuilder.addResponseCode(ResponseCode.COMPANY_ALREADY_EXIST, company.getName());
|
||||
}
|
||||
|
||||
return showCreationPage(modelResponseBuilder.build(), company);
|
||||
|
|
|
@ -44,7 +44,7 @@ public class MaterialTypeCreatorController {
|
|||
Optional<MaterialType> optionalMaterialType = materialTypeService.save(materialType);
|
||||
if (optionalMaterialType.isPresent()) {
|
||||
return getPage(modelResponseBuilder
|
||||
.addResponseCode(ResponseCode.SUCCESS_SAVING_MATERIAL_TYPE, optionalMaterialType.get().getMaterialTypeName())
|
||||
.addResponseCode(ResponseCode.SUCCESS_SAVING_MATERIAL_TYPE, optionalMaterialType.get().getName())
|
||||
.build(), null);
|
||||
} else {
|
||||
modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
|
|
|
@ -67,7 +67,7 @@ public class RecipeCreatorController {
|
|||
Optional<Recipe> savedRecipe = recipeService.save(recipe);
|
||||
if (savedRecipe.isPresent()) {
|
||||
return modelResponseBuilder
|
||||
.withRedirect(EDITOR_RECIPE_SPECIFIC, savedRecipe.get().getRecipeID())
|
||||
.withRedirect(EDITOR_RECIPE_SPECIFIC, savedRecipe.get().getId())
|
||||
.build();
|
||||
}
|
||||
modelResponseBuilder.addResponseCode(ResponseCode.ERROR_SAVING);
|
||||
|
|
|
@ -76,7 +76,7 @@ public class MaterialTypeEditorController {
|
|||
responseBuilder
|
||||
.addResponseCode(ResponseCode.MATERIAL_TYPE_ALREADY_EXIST, materialType.getName())
|
||||
.build(),
|
||||
materialType.getMaterialTypeID(), materialType);
|
||||
materialType.getId(), materialType);
|
||||
} else if (!materialTypeService.isValidForUpdatePrefix(materialType)) {
|
||||
return showEditPage(
|
||||
responseBuilder
|
||||
|
|
|
@ -10,10 +10,7 @@ import dev.fyloz.trial.colorrecipesexplorer.core.utils.ControllerUtils;
|
|||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.stereotype.Controller;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.ModelAttribute;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import org.springframework.web.servlet.ModelAndView;
|
||||
|
||||
import javax.validation.Valid;
|
||||
|
@ -51,7 +48,7 @@ public class MixEditorController {
|
|||
@GetMapping(EDITOR_MIX_SPECIFIC)
|
||||
public ModelAndView getPage(ModelAndView model, @PathVariable Long id) {
|
||||
ModelResponseBuilder modelResponseBuilder = new ModelResponseBuilder(model)
|
||||
.withView(EDITOR_MIX_SPECIFIC.replaceAll("/\\{" + MIX_ID + "}", ""));
|
||||
.withView(EDITOR_MIX_SPECIFIC.replaceAll("/\\{id}", ""));
|
||||
|
||||
Optional<Mix> optionalMix = mixService.getById(id);
|
||||
if (optionalMix.isEmpty()) {
|
||||
|
@ -90,7 +87,7 @@ public class MixEditorController {
|
|||
* @return La page à afficher.
|
||||
*/
|
||||
@PostMapping(value = EDITOR_MIX, consumes = MediaType.APPLICATION_FORM_URLENCODED_VALUE)
|
||||
public ModelAndView saveMix(@ModelAttribute @Valid MixCreationFormDto formDto, Long id) {
|
||||
public ModelAndView saveMix(@ModelAttribute @Valid MixCreationFormDto formDto, @RequestParam("mixId") Long id) {
|
||||
ModelResponseBuilder modelResponseBuilder = new ModelResponseBuilder();
|
||||
|
||||
Optional<Mix> optionalMix = mixService.getById(id);
|
||||
|
|
|
@ -73,7 +73,7 @@ public class RecipeEditorController {
|
|||
return modelResponseBuilder
|
||||
.addResponseData(ResponseDataType.RECIPE, recipe)
|
||||
.addResponseData(ResponseDataType.COMPANIES, companyService.getAll())
|
||||
.addResponseData(ResponseDataType.MIXES, new ArrayList<>(recipeService.getSortedMixes(recipe))) // Convertit le PersistentBag en ArrayList
|
||||
.addResponseData(ResponseDataType.MIXES, recipeService.getSortedMixes(recipe))
|
||||
.addResponseData(ResponseDataType.IMAGES, recipeService.getImageFiles(recipe))
|
||||
.addAttribute("recipeJSON", recipeService.asJson(recipe))
|
||||
.build();
|
||||
|
|
|
@ -105,7 +105,7 @@ public class ImageFilesController {
|
|||
.build(), id);
|
||||
}
|
||||
|
||||
Optional<Recipe> optionalRecipe = recipeService.getByID(id);
|
||||
Optional<Recipe> optionalRecipe = recipeService.getById(id);
|
||||
if (optionalRecipe.isEmpty()) {
|
||||
return getPage(modelResponseBuilder
|
||||
.addResponseCode(ResponseCode.RECIPE_NOT_FOUND, id)
|
||||
|
|
|
@ -36,10 +36,10 @@ public class XlsExporterController {
|
|||
}
|
||||
|
||||
@GetMapping(RECIPE_XLS)
|
||||
public ResponseEntity<byte[]> getXlsForRecipe(HttpServletRequest request, @PathVariable int recipeID) {
|
||||
public ResponseEntity<byte[]> getXlsForRecipe(HttpServletRequest request, @PathVariable Long id) {
|
||||
HttpHeaders headers = new HttpHeaders();
|
||||
|
||||
Optional<Recipe> optionalRecipe = recipeService.getByID(recipeID);
|
||||
Optional<Recipe> optionalRecipe = recipeService.getById(id);
|
||||
if (optionalRecipe.isEmpty()) {
|
||||
headers.add(HttpHeaders.LOCATION, request.getHeader("referer"));
|
||||
return new ResponseEntity<>(headers, HttpStatus.FOUND);
|
||||
|
@ -69,7 +69,7 @@ public class XlsExporterController {
|
|||
byte[] recipeXLS = new XlsxExporter().generate(recipe);
|
||||
if (recipeXLS.length <= 0) return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).build();
|
||||
|
||||
out.putNextEntry(new ZipEntry(String.format("%s_%s.xlsx", recipe.getCompany().getCompanyName(), recipe.getRecipeCode())));
|
||||
out.putNextEntry(new ZipEntry(String.format("%s_%s.xlsx", recipe.getCompany().getName(), recipe.getName())));
|
||||
out.write(recipeXLS, 0, recipeXLS.length);
|
||||
out.closeEntry();
|
||||
}
|
||||
|
|
|
@ -75,9 +75,10 @@ nav a {
|
|||
.dropdown-content {
|
||||
display: none;
|
||||
position: absolute;
|
||||
top: 70px;
|
||||
background-color: #0d0d0d;
|
||||
min-width: 160px;
|
||||
box-shadow: 0px 8px 16px 0px rgba(0, 0, 0, 0.2);
|
||||
box-shadow: 0 8px 16px 0 rgba(0, 0, 0, 0.2);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
|
|
|
@ -73,10 +73,14 @@
|
|||
background-color: #fafafa;
|
||||
}
|
||||
|
||||
.material, .material *, .quantity, .quantity * {
|
||||
.material, .quantity {
|
||||
width: 200px;
|
||||
}
|
||||
|
||||
.material *, .quantity * {
|
||||
width: 180px;
|
||||
}
|
||||
|
||||
.material input {
|
||||
text-align: left;
|
||||
padding: 0 10px;
|
||||
|
|
|
@ -58,7 +58,6 @@ $(() => {
|
|||
const removerForm = $(".requireAuth-remover");
|
||||
removerForm.find(".remover").on({
|
||||
click: function () {
|
||||
console.log($(this));
|
||||
removerForm.attr({
|
||||
action: removerForm.attr("action") + $(this).data("entityid")
|
||||
});
|
||||
|
@ -234,7 +233,6 @@ function changeUnits(unitSelect, quantitiesSelector, unitsDisplay) {
|
|||
$(this).text(currentUnit);
|
||||
|
||||
const quantityElem = $(this).parents(".materialRow").find(quantitiesSelector);
|
||||
console.log(quantityElem);
|
||||
if (quantityElem) {
|
||||
const originalQuantity = parseInt(quantityElem.data("quantityml"));
|
||||
quantityElem.text(convertMlToUnit(originalQuantity));
|
||||
|
|
|
@ -8,10 +8,10 @@ let materialSelectorHtml;
|
|||
let recipeID;
|
||||
|
||||
$(() => {
|
||||
recipeID = $("#recipeID").val();
|
||||
recipeID = $("#recipeId").val();
|
||||
|
||||
const mixIDInput = $("#mixID");
|
||||
const mixID = mixIDInput ? mixIDInput.val() : -1;
|
||||
const mixID = mixIDInput.val() ? mixIDInput.val() : -1;
|
||||
|
||||
axios.get(`/mix/selector/${recipeID}/${mixID}`)
|
||||
.then(r => {
|
||||
|
@ -35,10 +35,6 @@ $(document).on("click", ".materialSelector", function (event) {
|
|||
showMaterialList($(this)[0]);
|
||||
});
|
||||
|
||||
// $(document).on("click", ".materialList p", function () {
|
||||
// $(this).parents(".materialSelector").find("input").val($(this).data("materialcode"));
|
||||
// });
|
||||
|
||||
$(document).on("click", ".removeMaterial", function () {
|
||||
const id = $(this).data("removerow");
|
||||
if ($(".materialListRow").length > 1) $(`#${id}`).remove();
|
||||
|
@ -232,7 +228,6 @@ function searchMaterial(input) {
|
|||
|
||||
function checkUnits(materialSelector) {
|
||||
const quantityUnits = $(materialSelector).parents(".materialListRow").find(".quantityUnits");
|
||||
console.log($(quantityUnits));
|
||||
if ($(materialSelector).data("usepercentages")) quantityUnits.text("%");
|
||||
else quantityUnits.text("mL");
|
||||
}
|
||||
|
|
|
@ -93,7 +93,7 @@
|
|||
<!--Produits-->
|
||||
<tr class="materialRow" th:each="material : ${materials}"
|
||||
th:data-materialType="${material.materialType.id}"
|
||||
th:data-materialId="${material.materialId}">
|
||||
th:data-materialId="${material.id}">
|
||||
<td class="materialCode" th:data-materialId="${material.id}"
|
||||
th:text="${material.name}"></td>
|
||||
<td class="inventoryQuantity" th:data-quantityML="${material.inventoryQuantity}"
|
||||
|
|
|
@ -6,10 +6,10 @@
|
|||
<body>
|
||||
|
||||
<!-- Fragment de l'entête -->
|
||||
<header th:include="fragments.html :: header"></header>
|
||||
<header th:include="fragments.html :: header(false)"></header>
|
||||
<!-- Corps de la page -->
|
||||
<section>
|
||||
<p th:if="${materialCode != null}" th:text="#{material.success.created(${materialCode})}" class="success"></p>
|
||||
<p th:if="${name != null}" th:text="#{material.success.created(${name})}" class="success"></p>
|
||||
<div th:include="fragments.html :: messages"></div>
|
||||
|
||||
<h1 th:text="#{material.add.title}"></h1>
|
||||
|
@ -20,7 +20,7 @@
|
|||
<div class="formWrap">
|
||||
<div class="formColumn">
|
||||
<div>
|
||||
<label th:for="${#ids.next('materialCode')}" th:text="#{material.code} + ':'"></label>
|
||||
<label th:for="${#ids.next('name')}" th:text="#{material.code} + ':'"></label>
|
||||
</div>
|
||||
<div>
|
||||
<label for="quantity" th:text="#{material.inventoryQuantity} + ':'"></label>
|
||||
|
@ -29,14 +29,14 @@
|
|||
<label th:for="${#ids.next('materialType')}" th:text="#{material.type} + ':'"></label>
|
||||
</div>
|
||||
<div>
|
||||
<label for="simdut" th:text="#{material.simdutFile} + ':'"></label>
|
||||
<label for="simdut" th:text="#{material.simdut} + ':'"></label>
|
||||
</div>
|
||||
</div>
|
||||
<div class="formColumn">
|
||||
<div>
|
||||
<input type="text"
|
||||
class="rawInput"
|
||||
th:field="*{materialCode}"
|
||||
th:field="*{name}"
|
||||
style="width: 145px"
|
||||
required/>
|
||||
</div>
|
||||
|
@ -66,8 +66,8 @@
|
|||
</div>
|
||||
<div>
|
||||
<select th:field="*{materialType}" required>
|
||||
<option th:each="materialType : ${materialTypes}" th:value="${materialType.materialTypeID}"
|
||||
th:text="${materialType.materialTypeName}"></option>
|
||||
<option th:each="materialType : ${materialTypes}" th:value="${materialType.id}"
|
||||
th:text="${materialType.name}"></option>
|
||||
</select>
|
||||
</div>
|
||||
<div>
|
||||
|
|
|
@ -97,7 +97,7 @@
|
|||
|
||||
// Ajoute les produits déjà présents dans la recette
|
||||
mix.mixQuantities.forEach(q => {
|
||||
addMaterial(q.material.materialCode, q.quantity);
|
||||
addMaterial(q.material.name, q.quantity);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -55,11 +55,11 @@
|
|||
<div class="content">
|
||||
<!-- Informations -->
|
||||
<div class="flexContent" style="padding-top: 40px">
|
||||
<input type="hidden" th:field="*{recipeId}"/>
|
||||
<input type="hidden" th:field="*{id}"/>
|
||||
<div class="formWrap">
|
||||
<div class="formColumn">
|
||||
<div>
|
||||
<label th:for="${#ids.next('recipeId')}" th:text="#{keyword.id}"></label>
|
||||
<label th:for="${#ids.next('id')}" th:text="#{keyword.id}"></label>
|
||||
</div>
|
||||
<div>
|
||||
<label th:for="${#ids.next('name')}" th:text="#{recipe.color}"></label>
|
||||
|
@ -82,7 +82,7 @@
|
|||
</div>
|
||||
<div class="formColumn">
|
||||
<div>
|
||||
<input type="number" th:field="*{recipeId}" required disabled/>
|
||||
<input type="number" th:field="*{id}" required disabled/>
|
||||
</div>
|
||||
<div>
|
||||
<input type="text" th:field="*{name}" required/>
|
||||
|
|
|
@ -1,3 +0,0 @@
|
|||
[Dolphin]
|
||||
Timestamp=2019,5,9,10,28,30
|
||||
Version=4
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Loading…
Reference in New Issue