not yet finished manipulations of camp registrations
This commit is contained in:
		| @@ -15,6 +15,7 @@ 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.servlet.mvc.support.RedirectAttributes; | ||||
|  | ||||
| import de.jottyfan.camporganizer.module.camplist.CommonController; | ||||
| import de.jottyfan.camporganizer.module.mail.MailBean; | ||||
| @@ -143,4 +144,64 @@ public class AdminController extends CommonController { | ||||
| 		service.deleteLocation(id); | ||||
| 		return "redirect:/admin/location"; | ||||
| 	} | ||||
|  | ||||
| 	@GetMapping("/admin/camp") | ||||
| 	public String getCamplist(Model model, HttpServletRequest request) { | ||||
| 		super.setupSession(model, request); | ||||
| 		model.addAttribute("camps", service.getAllCamps()); | ||||
| 		model.addAttribute("locations", service.getLocations()); | ||||
| 		return "/admin/camp"; | ||||
| 	} | ||||
|  | ||||
| 	@GetMapping("/admin/camp/add") | ||||
| 	public String prepareAddCamp(Model model, HttpServletRequest request) { | ||||
| 		super.setupSession(model, request); | ||||
| 		model.addAttribute("bean", new CampBean()); | ||||
| 		model.addAttribute("documents", service.getCampDocuments()); | ||||
| 		model.addAttribute("locations", service.getLocations()); | ||||
| 		model.addAttribute("profiles", service.getProfiles()); | ||||
| 		return "/admin/camp_edit"; | ||||
| 	} | ||||
|  | ||||
| 	@GetMapping("/admin/camp/edit/{id}") | ||||
| 	public String prepareEditCamp(@PathVariable Integer id, Model model, HttpServletRequest request) { | ||||
| 		super.setupSession(model, request); | ||||
| 		model.addAttribute("bean", service.getCamp(id)); | ||||
| 		model.addAttribute("documents", service.getCampDocuments()); | ||||
| 		model.addAttribute("locations", service.getLocations()); | ||||
| 		model.addAttribute("profiles", service.getProfiles()); | ||||
| 		String error = (String) request.getAttribute("error"); | ||||
| 		if (error != null) { | ||||
| 			model.addAttribute("error", error); | ||||
| 		} | ||||
| 		return "/admin/camp_edit"; | ||||
| 	} | ||||
|  | ||||
| 	@PostMapping("/admin/camp/update") | ||||
| 	public String updateDocument(@Valid @ModelAttribute("bean") CampBean bean, | ||||
| 			final BindingResult bindingResult, Model model, HttpServletRequest request, RedirectAttributes redirect) { | ||||
| 		super.setupSession(model, request); | ||||
| 		if (bindingResult.hasErrors()) { | ||||
| 			for (ObjectError error : bindingResult.getAllErrors()) { | ||||
| 				LOGGER.error("error {}: {}", error.getCode(), error.getDefaultMessage()); | ||||
| 			} | ||||
| 			model.addAttribute("documents", service.getCampDocuments()); | ||||
| 			model.addAttribute("locations", service.getLocations()); | ||||
| 			model.addAttribute("profiles", service.getProfiles()); | ||||
| 			return "/admin/camp_edit"; | ||||
| 		} | ||||
| 		String error = service.upsertCamp(bean); | ||||
| 		redirect.addAttribute("error", error); | ||||
| 		Integer pk = bean.getPk(); | ||||
| 		String errorDest = pk == null ? "redirect:/admin/camp/add" : "redirect:/admin/camp/edit/" + bean.getPk(); | ||||
| 		return error != null ? errorDest : "redirect:/admin/camp"; | ||||
| 	} | ||||
|  | ||||
| 	@GetMapping("/admin/camp/delete/{id}") | ||||
| 	public String deleteCamp(@PathVariable Integer id, Model model, HttpServletRequest request, RedirectAttributes redirect) { | ||||
| 		super.setupSession(model, request); | ||||
| 		String error = service.deleteCamp(id); | ||||
| 		redirect.addAttribute("error", error); | ||||
| 		return error != null ? "redirect:/admin/camp/edit/" + id : "redirect:/admin/camp"; | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -4,6 +4,8 @@ import static de.jottyfan.camporganizer.db.jooq.Tables.T_CAMP; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_DOCUMENT; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_DOCUMENTROLE; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_LOCATION; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_PERSON; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_PROFILE; | ||||
|  | ||||
| import java.util.ArrayList; | ||||
| import java.util.Arrays; | ||||
| @@ -42,6 +44,8 @@ import de.jottyfan.camporganizer.db.jooq.tables.records.TCampRecord; | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TDocumentRecord; | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TDocumentroleRecord; | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TLocationRecord; | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TPersonRecord; | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TProfileRecord; | ||||
| import de.jottyfan.camporganizer.module.camplist.LambdaResultWrapper; | ||||
|  | ||||
| /** | ||||
| @@ -81,7 +85,7 @@ public class AdminRepository { | ||||
| 		// @formatter:on | ||||
| 		LOGGER.debug(sql.toString()); | ||||
| 		Record5<Integer, String, EnumDocument, EnumFiletype, EnumCamprole[]> r = sql.fetchOne(); | ||||
| 		if (r != null ) { | ||||
| 		if (r != null) { | ||||
| 			DocumentBean bean = new DocumentBean(); | ||||
| 			bean.setPk(r.get(T_DOCUMENT.PK)); | ||||
| 			bean.setName(r.get(T_DOCUMENT.NAME)); | ||||
| @@ -234,8 +238,7 @@ public class AdminRepository { | ||||
| 	/** | ||||
| 	 * delete entry from t_document where pk = ? | ||||
| 	 * | ||||
| 	 * @param pk | ||||
| 	 *          to be used as reference | ||||
| 	 * @param pk to be used as reference | ||||
| 	 * @return number of affected database lines | ||||
| 	 * @throws DataAccessException | ||||
| 	 */ | ||||
| @@ -353,4 +356,83 @@ public class AdminRepository { | ||||
| 		}); | ||||
| 		return lrw.getCounter(); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get all camps from the database | ||||
| 	 * | ||||
| 	 * @return a list of camps; an empty list at least | ||||
| 	 */ | ||||
| 	public List<CampBean> getAllCamps() { | ||||
| 		SelectWhereStep<TCampRecord> sql = jooq.selectFrom(T_CAMP); | ||||
| 		LOGGER.debug(sql.toString()); | ||||
| 		List<CampBean> list = new ArrayList<>(); | ||||
| 		for (TCampRecord r : sql.fetch()) { | ||||
| 			list.add(CampBean.of(r)); | ||||
| 		} | ||||
| 		return list; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get the camp of id | ||||
| 	 * | ||||
| 	 * @param id the ID of the camp | ||||
| 	 * @return the camp or null | ||||
| 	 */ | ||||
| 	public CampBean getCamp(Integer id) { | ||||
| 		SelectConditionStep<TCampRecord> sql = jooq.selectFrom(T_CAMP).where(T_CAMP.PK.eq(id)); | ||||
| 		LOGGER.debug(sql.toString()); | ||||
| 		return CampBean.of(sql.fetchOne()); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * delete the camp and all of its dependencies | ||||
| 	 * | ||||
| 	 * @param id the ID of the camp | ||||
| 	 * @return error message | ||||
| 	 */ | ||||
| 	public String deleteCamp(Integer id) { | ||||
| 		LambdaResultWrapper lrw = new LambdaResultWrapper(); | ||||
| 		jooq.transaction(t -> { | ||||
| 			SelectConditionStep<TPersonRecord> sql1 = DSL.using(t).selectFrom(T_PERSON).where(T_PERSON.FK_CAMP.eq(id)); | ||||
| 			LOGGER.debug(sql1.toString()); | ||||
| 			Integer registrations = sql1.fetch().size(); | ||||
| 			if (registrations < 1) { | ||||
| 				DeleteConditionStep<TCampRecord> sql2 = DSL.using(t).deleteFrom(T_CAMP).where(T_CAMP.PK.eq(id)); | ||||
| 				LOGGER.debug(sql2.toString()); | ||||
| 				sql2.execute(); | ||||
| 			} else { | ||||
| 				lrw.putString("error", String.format("Es gibt bereits %d Anmeldungen. Die Freizeit kann daher nicht gelöscht werden.", registrations)); | ||||
| 			} | ||||
| 		}); | ||||
| 		return lrw.getString("error"); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * upsert the camp | ||||
| 	 * | ||||
| 	 * @param bean the bean | ||||
| 	 */ | ||||
| 	public String upsertCamp(@Valid CampBean bean) { | ||||
| 		if (bean.getPk() == null) { | ||||
| 			// TODO: insert | ||||
| 		} else { | ||||
| 			// TODO: update | ||||
| 		} | ||||
| 		return "not yet implemented"; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get all profiles from the db | ||||
| 	 * | ||||
| 	 * @return the profiles | ||||
| 	 */ | ||||
| 	public List<ProfileBean> getProfiles() { | ||||
| 		SelectWhereStep<TProfileRecord> sql = jooq.selectFrom(T_PROFILE); | ||||
| 		LOGGER.debug(sql.toString()); | ||||
| 		List<ProfileBean> list = new ArrayList<>(); | ||||
| 		for (TProfileRecord r : sql.fetch()) { | ||||
| 			list.add(ProfileBean.of(r)); | ||||
| 		} | ||||
| 		return list; | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -9,7 +9,6 @@ import javax.validation.Valid; | ||||
|  | ||||
| import org.apache.logging.log4j.LogManager; | ||||
| import org.apache.logging.log4j.Logger; | ||||
| import org.jooq.exception.DataAccessException; | ||||
| import org.springframework.beans.factory.annotation.Autowired; | ||||
| import org.springframework.stereotype.Service; | ||||
|  | ||||
| @@ -115,7 +114,7 @@ public class AdminService { | ||||
| 	 */ | ||||
| 	public void deleteLocation(Integer id) { | ||||
| 		// TODO: if a location is still in use by a camp, forbid deleting it | ||||
| 	     adminRepository.deleteLocation(id); | ||||
| 		adminRepository.deleteLocation(id); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| @@ -126,4 +125,61 @@ public class AdminService { | ||||
| 	public List<DocumentBean> getLocationDocuments() { | ||||
| 		return adminRepository.getAllDocumentsWith(T_DOCUMENT.DOCTYPE.eq(EnumDocument.location)); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get all documents that fit to the camp definitions | ||||
| 	 * | ||||
| 	 * @return the camp documents | ||||
| 	 */ | ||||
| 	public List<DocumentBean> getCampDocuments() { | ||||
| 		return adminRepository.getAllDocumentsWith(T_DOCUMENT.DOCTYPE.eq(EnumDocument.camp)); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get all camp beans from the database | ||||
| 	 * | ||||
| 	 * @return all camp beans; an empty list at least | ||||
| 	 */ | ||||
| 	public List<CampBean> getAllCamps() { | ||||
| 		return adminRepository.getAllCamps(); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get all profiles from the db | ||||
| 	 * | ||||
| 	 * @return the profiles | ||||
| 	 */ | ||||
| 	public List<ProfileBean> getProfiles() { | ||||
| 		return adminRepository.getProfiles(); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get the camp of id | ||||
| 	 * | ||||
| 	 * @param id the ID of the camp | ||||
| 	 * @return the camp or null | ||||
| 	 */ | ||||
| 	public CampBean getCamp(Integer id) { | ||||
| 		return adminRepository.getCamp(id); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * upsert the camp | ||||
| 	 * | ||||
| 	 * @param bean the bean | ||||
| 	 * @return the error message, if any | ||||
| 	 */ | ||||
| 	public String upsertCamp(@Valid CampBean bean) { | ||||
| 		return adminRepository.upsertCamp(bean); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * delete the camp and all of its dependencies | ||||
| 	 * | ||||
| 	 * @param id the ID of the camp | ||||
| 	 * @return the error message, if any | ||||
| 	 */ | ||||
| 	public String deleteCamp(Integer id) { | ||||
| 		return adminRepository.deleteCamp(id); | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -0,0 +1,234 @@ | ||||
| package de.jottyfan.camporganizer.module.admin; | ||||
|  | ||||
| import java.io.Serializable; | ||||
| import java.time.LocalDateTime; | ||||
|  | ||||
| import javax.validation.constraints.NotBlank; | ||||
| import javax.validation.constraints.NotNull; | ||||
|  | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TCampRecord; | ||||
|  | ||||
| /** | ||||
|  * | ||||
|  * @author jotty | ||||
|  * | ||||
|  */ | ||||
| public class CampBean implements Serializable { | ||||
| 	private static final long serialVersionUID = 1L; | ||||
|  | ||||
| 	private Integer pk; | ||||
| 	@NotBlank | ||||
| 	private String name; | ||||
| 	@NotNull | ||||
| 	private Integer fkDocument; | ||||
| 	@NotNull | ||||
| 	private Integer fkLocation; | ||||
| 	@NotNull | ||||
| 	private Integer fkProfile; | ||||
| 	private Boolean lockSales; | ||||
| 	@NotNull | ||||
| 	private Integer maxAge; | ||||
| 	@NotNull | ||||
| 	private Integer minAge; | ||||
| 	@NotNull | ||||
| 	private LocalDateTime arrive; | ||||
| 	@NotNull | ||||
| 	private LocalDateTime depart; | ||||
| 	private String countries; | ||||
| 	@NotNull | ||||
| 	private String price; | ||||
|  | ||||
| 	/** | ||||
| 	 * generate a camp bean out of r | ||||
| 	 * | ||||
| 	 * @param r the record | ||||
| 	 * @return the camp bean | ||||
| 	 */ | ||||
| 	public static final CampBean of(TCampRecord r) { | ||||
| 		if (r == null) { | ||||
| 			return null; | ||||
| 		} | ||||
| 		CampBean bean = new CampBean(); | ||||
| 		bean.setArrive(r.getArrive()); | ||||
| 		bean.setCountries(r.getCountries()); | ||||
| 		bean.setDepart(r.getDepart()); | ||||
| 		bean.setFkDocument(r.getFkDocument()); | ||||
| 		bean.setFkLocation(r.getFkLocation()); | ||||
| 		bean.setFkProfile(r.getFkProfile()); | ||||
| 		bean.setLockSales(r.getLockSales()); | ||||
| 		bean.setMaxAge(r.getMaxAge()); | ||||
| 		bean.setMinAge(r.getMinAge()); | ||||
| 		bean.setName(r.getName()); | ||||
| 		bean.setPk(r.getPk()); | ||||
| 		bean.setPrice(r.getPrice()); | ||||
| 		return bean; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the pk | ||||
| 	 */ | ||||
| 	public Integer getPk() { | ||||
| 		return pk; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param pk the pk to set | ||||
| 	 */ | ||||
| 	public void setPk(Integer pk) { | ||||
| 		this.pk = pk; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the name | ||||
| 	 */ | ||||
| 	public String getName() { | ||||
| 		return name; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param name the name to set | ||||
| 	 */ | ||||
| 	public void setName(String name) { | ||||
| 		this.name = name; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the fkDocument | ||||
| 	 */ | ||||
| 	public Integer getFkDocument() { | ||||
| 		return fkDocument; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param fkDocument the fkDocument to set | ||||
| 	 */ | ||||
| 	public void setFkDocument(Integer fkDocument) { | ||||
| 		this.fkDocument = fkDocument; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the fkLocation | ||||
| 	 */ | ||||
| 	public Integer getFkLocation() { | ||||
| 		return fkLocation; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param fkLocation the fkLocation to set | ||||
| 	 */ | ||||
| 	public void setFkLocation(Integer fkLocation) { | ||||
| 		this.fkLocation = fkLocation; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the fkProfile | ||||
| 	 */ | ||||
| 	public Integer getFkProfile() { | ||||
| 		return fkProfile; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param fkProfile the fkProfile to set | ||||
| 	 */ | ||||
| 	public void setFkProfile(Integer fkProfile) { | ||||
| 		this.fkProfile = fkProfile; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the lockSales | ||||
| 	 */ | ||||
| 	public Boolean getLockSales() { | ||||
| 		return lockSales; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param lockSales the lockSales to set | ||||
| 	 */ | ||||
| 	public void setLockSales(Boolean lockSales) { | ||||
| 		this.lockSales = lockSales; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the maxAge | ||||
| 	 */ | ||||
| 	public Integer getMaxAge() { | ||||
| 		return maxAge; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param maxAge the maxAge to set | ||||
| 	 */ | ||||
| 	public void setMaxAge(Integer maxAge) { | ||||
| 		this.maxAge = maxAge; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the minAge | ||||
| 	 */ | ||||
| 	public Integer getMinAge() { | ||||
| 		return minAge; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param minAge the minAge to set | ||||
| 	 */ | ||||
| 	public void setMinAge(Integer minAge) { | ||||
| 		this.minAge = minAge; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the arrive | ||||
| 	 */ | ||||
| 	public LocalDateTime getArrive() { | ||||
| 		return arrive; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param arrive the arrive to set | ||||
| 	 */ | ||||
| 	public void setArrive(LocalDateTime arrive) { | ||||
| 		this.arrive = arrive; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the depart | ||||
| 	 */ | ||||
| 	public LocalDateTime getDepart() { | ||||
| 		return depart; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param depart the depart to set | ||||
| 	 */ | ||||
| 	public void setDepart(LocalDateTime depart) { | ||||
| 		this.depart = depart; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the countries | ||||
| 	 */ | ||||
| 	public String getCountries() { | ||||
| 		return countries; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param countries the countries to set | ||||
| 	 */ | ||||
| 	public void setCountries(String countries) { | ||||
| 		this.countries = countries; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the price | ||||
| 	 */ | ||||
| 	public String getPrice() { | ||||
| 		return price; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param price the price to set | ||||
| 	 */ | ||||
| 	public void setPrice(String price) { | ||||
| 		this.price = price; | ||||
| 	} | ||||
| } | ||||
| @@ -0,0 +1,71 @@ | ||||
| package de.jottyfan.camporganizer.module.admin; | ||||
|  | ||||
| import java.io.Serializable; | ||||
|  | ||||
| import de.jottyfan.camporganizer.db.jooq.tables.records.TProfileRecord; | ||||
|  | ||||
| /** | ||||
|  * | ||||
|  * @author jotty | ||||
|  * | ||||
|  */ | ||||
| public class ProfileBean implements Serializable { | ||||
| 	private static final long serialVersionUID = 1L; | ||||
|  | ||||
| 	private Integer pk; | ||||
| 	private String forename; | ||||
| 	private String surname; | ||||
|  | ||||
| 	public static final ProfileBean of(TProfileRecord r) { | ||||
| 		if (r == null) { | ||||
| 			return null; | ||||
| 		} | ||||
| 		ProfileBean bean = new ProfileBean(); | ||||
| 		bean.setPk(r.getPk()); | ||||
| 		bean.setForename(r.getForename()); | ||||
| 		bean.setSurname(r.getSurname()); | ||||
| 		return bean; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the pk | ||||
| 	 */ | ||||
| 	public Integer getPk() { | ||||
| 		return pk; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param pk the pk to set | ||||
| 	 */ | ||||
| 	public void setPk(Integer pk) { | ||||
| 		this.pk = pk; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the forename | ||||
| 	 */ | ||||
| 	public String getForename() { | ||||
| 		return forename; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param forename the forename to set | ||||
| 	 */ | ||||
| 	public void setForename(String forename) { | ||||
| 		this.forename = forename; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the surname | ||||
| 	 */ | ||||
| 	public String getSurname() { | ||||
| 		return surname; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param surname the surname to set | ||||
| 	 */ | ||||
| 	public void setSurname(String surname) { | ||||
| 		this.surname = surname; | ||||
| 	} | ||||
| } | ||||
							
								
								
									
										41
									
								
								src/main/resources/templates/admin/camp.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										41
									
								
								src/main/resources/templates/admin/camp.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,41 @@ | ||||
| <!DOCTYPE html> | ||||
| <html xmlns:th="http://www.thymeleaf.org" layout:decorate="~{template}" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout" xmlns:sec="http://www.thymeleaf.org/extras/spring-security"> | ||||
| <body> | ||||
| 	<th:block layout:fragment="content"> | ||||
| 		<div class="tablebox" sec:authorize="hasRole('admin')"> | ||||
| 			<table id="docs" class="table table-striped" style="width: 100% !important"> | ||||
| 				<thead> | ||||
| 					<tr> | ||||
| 						<td>Name</td> | ||||
| 						<td>Ort</td> | ||||
| 						<td>Zeitraum</td> | ||||
| 						<td>Bestätigung</td> | ||||
| 					</tr> | ||||
| 				</thead> | ||||
| 				<tbody> | ||||
| 					<tr th:each="c : ${camps}"> | ||||
| 						<td><a th:href="@{/admin/camp/edit/{id}(id=${c.pk})}"><span th:text="${c.name}"></span></a></td> | ||||
| 						<td><th:block th:each="l : ${locations}"> | ||||
| 								<span th:if="${l.pk == c.fkLocation}" th:text="${l.name}"></span> | ||||
| 							</th:block></td> | ||||
| 						<td><span th:text="${#temporals.format(c.arrive, 'dd.MM.')}"></span> - <span th:text="${#temporals.format(c.depart, 'dd.MM.yyyy')}"></span></td> | ||||
| 						<td><a th:href="@{/document/{id}(id=${c.fkDocument})}"><i class="fas fa-download"></i></a></td> | ||||
| 					</tr> | ||||
| 				</tbody> | ||||
| 				<tfoot> | ||||
| 					<tr> | ||||
| 						<td colspan="6" style="text-align: center"><a th:href="@{/admin/camp/add}" class="btn btn-outline-primary">neue Freizeit anlegen</a></td> | ||||
| 					</tr> | ||||
| 				</tfoot> | ||||
| 			</table> | ||||
| 			<script> | ||||
| 				$(document).ready(function() { | ||||
| 					$("#docs").DataTable({ | ||||
| 						language : locale_de | ||||
| 					}); | ||||
| 				}); | ||||
| 			</script> | ||||
| 		</div> | ||||
| 	</th:block> | ||||
| </body> | ||||
| </html> | ||||
							
								
								
									
										122
									
								
								src/main/resources/templates/admin/camp_edit.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										122
									
								
								src/main/resources/templates/admin/camp_edit.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,122 @@ | ||||
| <!DOCTYPE html> | ||||
| <html xmlns:th="http://www.thymeleaf.org" layout:decorate="~{template}" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout" xmlns:sec="http://www.thymeleaf.org/extras/spring-security"> | ||||
| <body> | ||||
| 	<th:block layout:fragment="content"> | ||||
| 		<div sec:authorize="hasRole('admin')"> | ||||
| 			<form th:action="@{/admin/camp/update}" th:object="${bean}" method="post" enctype="multipart/form-data"> | ||||
| 				<div class="tablebox"> | ||||
| 					<div class="container"> | ||||
| 						<input type="hidden" th:field="*{pk}" /> | ||||
| 						<div class="row mb-2"> | ||||
| 							<div class="col-sm-12"> | ||||
| 								<div class="alert alter-danger" th:if="${error}" th:text="${error}"></div> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputName" class="col-sm-2 col-form-label">Name</label> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('name')}">[[${error}]]<br /></span> <input id="inputName" type="text" th:field="*{name}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('name') ? 'inputerror' : '')}"> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputLocation" class="col-sm-2 col-form-label">Ort</label> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('fkLocation')}">[[${error}]]<br /></span> | ||||
| 								<select id="inputLocation" th:field="*{fkLocation}" th:class="${'form-select ' + (#fields.hasErrors('fkLocation') ? 'inputerror' : '')}"> | ||||
| 									<option value="">--- bitte wählen ---</option> | ||||
| 									<option th:each="l : ${locations}" th:value="${l.pk}" th:text="${l.name}"></option> | ||||
| 								</select> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputArrive" class="col-sm-2 col-form-label">von</label> | ||||
| 							<div class="col-sm-4"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('arrive')}">[[${error}]]<br /></span> <input id="inputArrive" type="date" th:field="*{arrive}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('arrive') ? 'inputerror' : '')}"> | ||||
| 							</div> | ||||
| 							<label for="inputDepart" class="col-sm-2 col-form-label">bis</label> | ||||
| 							<div class="col-sm-4"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('depart')}">[[${error}]]<br /></span> <input id="inputDepart" type="date" th:field="*{depart}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('depart') ? 'inputerror' : '')}"> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputMinAge" class="col-sm-2 col-form-label">Mindestalter</label> | ||||
| 							<div class="col-sm-4"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('minAge')}">[[${error}]]<br /></span> <input id="inputMinAge" type="number" th:field="*{minAge}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('minAge') ? 'inputerror' : '')}"> | ||||
| 							</div> | ||||
| 							<label for="inputMaxAge" class="col-sm-2 col-form-label">Maximalalter</label> | ||||
| 							<div class="col-sm-4"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('maxAge')}">[[${error}]]<br /></span> <input id="inputMaxAge" type="number" th:field="*{maxAge}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('maxAge') ? 'inputerror' : '')}"> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputPrice" class="col-sm-2 col-form-label">Preis</label> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('price')}">[[${error}]]<br /></span> <textarea id="inputPrice" type="text" th:field="*{price}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('price') ? 'inputerror' : '')}"></textarea> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputCountries" class="col-sm-2 col-form-label">Ferien in</label> | ||||
| 							<div class="col-sm-10"><!-- TODO: input helper for finding Bundesland by typing --> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('countries')}">[[${error}]]<br /></span> <textarea id="inputCountries" type="text" th:field="*{countries}" | ||||
| 									th:class="${'form-control ' + (#fields.hasErrors('countries') ? 'inputerror' : '')}"></textarea> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputDoc" class="col-sm-2 col-form-label">Bestätigung</label> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('fkDocument')}">[[${error}]]<br /></span> <select id="inputDoc" th:field="*{fkDocument}" | ||||
| 									th:class="${'form-select ' + (#fields.hasErrors('fkDocument') ? 'inputerror' : '')}"> | ||||
| 									<option value="">--- bitte wählen ---</option> | ||||
| 									<option th:each="d : ${documents}" th:value="${d.pk}" th:text="${d.name}"></option> | ||||
| 								</select> | ||||
| 								<script type="text/javascript"> | ||||
| 									$("#inputDoc").select2({ | ||||
| 										theme : 'bootstrap-5', | ||||
| 									}); | ||||
| 								</script> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<div class="row mb-2"> | ||||
| 							<label for="inputProfile" class="col-sm-2 col-form-label">Verantwortlicher</label> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<span class="error" th:each="error : ${#fields.errors('fkProfile')}">[[${error}]]<br /></span> <select id="inputProfile" th:field="*{fkProfile}" | ||||
| 									th:class="${'form-select ' + (#fields.hasErrors('fkProfile') ? 'inputerror' : '')}"> | ||||
| 									<option value="">--- bitte wählen ---</option> | ||||
| 									<option th:each="p : ${profiles}" th:value="${p.pk}" th:text="${p.forename} + ' ' + ${p.surname}"></option> | ||||
| 								</select> | ||||
| 								<script type="text/javascript"> | ||||
| 									$("#inputProfile").select2({ | ||||
| 										theme : 'bootstrap-5', | ||||
| 									}); | ||||
| 								</script> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 						<!-- TODO: lock sales - boolean - Kassenschluss --> | ||||
| 						<div class="row mb-2"> | ||||
| 							<div class="col-sm-2"></div> | ||||
| 							<div class="col-sm-10"> | ||||
| 								<input type="submit" class="btn btn-success" value="Ok" /> | ||||
| 								<a th:href="@{/admin/camp}" class="btn btn-outline-secondary">Abbrechen</a> | ||||
| 								<div class="dropdown" style="display: inline" th:if="${bean.pk}"> | ||||
| 									<button class="btn btn-outline-danger dropdown-toggle" type="button" data-bs-toggle="dropdown" aria-expanded="false"> | ||||
| 										<i class="fas fa-trash-alt"></i> | ||||
| 									</button> | ||||
| 									<ul class="dropdown-menu"> | ||||
| 										<li><a class="dropdown-item" th:href="@{/admin/camp/delete/{id}(id=${bean.pk})}">Freizeit endgültig löschen</a> | ||||
| 									</ul> | ||||
| 								</div> | ||||
| 							</div> | ||||
| 						</div> | ||||
| 					</div> | ||||
| 				</div> | ||||
| 			</form> | ||||
| 		</div> | ||||
| 	</th:block> | ||||
| </body> | ||||
| </html> | ||||
| @@ -123,6 +123,7 @@ | ||||
| 								<li><a th:href="@{/admin/mail}" class="dropdown-item menufont">Testmail</a></li> | ||||
| 								<li><a th:href="@{/admin/document}" class="dropdown-item menufont">Dokumente</a></li> | ||||
| 								<li><a th:href="@{/admin/location}" class="dropdown-item menufont">Freizeitheime</a></li> | ||||
| 								<li><a th:href="@{/admin/camp}" class="dropdown-item menufont">Freizeiten</a> | ||||
| 							</ul> | ||||
| 						</div> | ||||
| 					</li> | ||||
|   | ||||
		Reference in New Issue
	
	Block a user