This commit is contained in:
		| @@ -52,4 +52,14 @@ public interface IConfirmationService { | ||||
| 	 * @return the list of rejected bookings | ||||
| 	 */ | ||||
| 	public List<BookingBean> getRejected(HttpServletRequest request); | ||||
|  | ||||
| 	/** | ||||
| 	 * get the result of a search for needle in the database | ||||
| 	 * | ||||
| 	 * @param needle the needle; may be a name of anything | ||||
| 	 * @param linkURL the URL of the link for clicking on the found entity | ||||
| 	 * @param request the request | ||||
| 	 * @return the result in html format (for now) | ||||
| 	 */ | ||||
| 	public String search(String needle, String linkURL, HttpServletRequest request); | ||||
| } | ||||
|   | ||||
| @@ -0,0 +1,31 @@ | ||||
| package de.jottyfan.camporganizer.module.confirmation.confirmation; | ||||
|  | ||||
| import javax.servlet.http.HttpServletRequest; | ||||
| import javax.websocket.server.PathParam; | ||||
|  | ||||
| import org.springframework.beans.factory.annotation.Autowired; | ||||
| import org.springframework.stereotype.Controller; | ||||
| import org.springframework.ui.Model; | ||||
| import org.springframework.web.bind.annotation.GetMapping; | ||||
| import org.springframework.web.bind.annotation.ResponseBody; | ||||
|  | ||||
| /** | ||||
|  * | ||||
|  * @author jotty | ||||
|  * | ||||
|  */ | ||||
| @Controller | ||||
| public class SearchController { | ||||
|  | ||||
| 	@Autowired | ||||
| 	private HttpServletRequest request; | ||||
|  | ||||
| 	@Autowired | ||||
| 	private IConfirmationService service; | ||||
|  | ||||
| 	@GetMapping("/confirmation/search") | ||||
| 	@ResponseBody | ||||
| 	public String search(@PathParam(value = "needle") String needle, Model model) { | ||||
| 		return service.search(needle, request.getRequestURI().replace("search", "person"), request); | ||||
| 	} | ||||
| } | ||||
| @@ -4,6 +4,7 @@ import static de.jottyfan.camporganizer.db.jooq.Tables.T_CAMP; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_CAMPPROFILE; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_PERSON; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.T_PROFILE; | ||||
| import static de.jottyfan.camporganizer.db.jooq.Tables.V_CAMP; | ||||
|  | ||||
| import java.time.LocalDateTime; | ||||
| import java.util.ArrayList; | ||||
| @@ -127,7 +128,6 @@ public class ConfirmationGateway { | ||||
| 			list.add(bean); | ||||
| 		} | ||||
| 		return list; | ||||
|  | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| @@ -159,4 +159,48 @@ public class ConfirmationGateway { | ||||
| 	public List<BookingBean> getRejected(String currentUser) { | ||||
| 		return getListWithCondition(currentUser, T_PERSON.ACCEPT.isFalse()); | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * get the result of the search | ||||
| 	 * | ||||
| 	 * @param needle the needle | ||||
| 	 * @param currentUser the current user | ||||
| 	 * @return a list of found beans; an empty one at least | ||||
| 	 */ | ||||
| 	public List<BookingBean> getSearchResult(String needle, String currentUser) { | ||||
| 		Condition condition = T_PERSON.FORENAME.containsIgnoreCase(needle) | ||||
| 		// @formatter:off | ||||
| 				.or(T_PERSON.SURNAME.containsIgnoreCase(needle)) | ||||
| 				.or(V_CAMP.NAME.containsIgnoreCase(needle)) | ||||
| 				.or(V_CAMP.YEAR.cast(String.class).containsIgnoreCase(needle)); | ||||
| 		// @formatter:on | ||||
|  | ||||
| 		SelectSeekStep1<Record7<Integer, String, String, EnumCamprole, String, Double, String>, LocalDateTime> sql = jooq | ||||
| 		// @formatter:off | ||||
| 			.select(T_PERSON.PK, T_PERSON.FORENAME, T_PERSON.SURNAME, T_PERSON.CAMPROLE, V_CAMP.NAME, V_CAMP.YEAR, V_CAMP.LOCATION_NAME) | ||||
| 			.from(T_PERSON) | ||||
| 			.leftJoin(V_CAMP).on(V_CAMP.PK.eq(T_PERSON.FK_CAMP)) | ||||
| 			.leftJoin(T_CAMPPROFILE).on(T_CAMPPROFILE.FK_CAMP.eq(T_PERSON.FK_CAMP)) | ||||
| 			.leftJoin(T_PROFILE).on(T_PROFILE.PK.eq(T_CAMPPROFILE.FK_PROFILE)) | ||||
| 			.where(condition) | ||||
| 			.and(T_CAMPPROFILE.MODULE.eq(EnumModule.registration)) | ||||
| 			.and(T_PROFILE.USERNAME.eq(currentUser)) | ||||
| 			.orderBy(T_PERSON.CREATED.desc()); | ||||
| 		// @formatter:on | ||||
| 		LOGGER.debug(sql.toString()); | ||||
| 		List<BookingBean> list = new ArrayList<>(); | ||||
| 		for (Record7<Integer, String, String, EnumCamprole, String, Double, String> r : sql.fetch()) { | ||||
| 			Integer pkPerson = r.get(T_PERSON.PK); | ||||
| 			String forename = r.get(T_PERSON.FORENAME); | ||||
| 			String surname = r.get(T_PERSON.SURNAME); | ||||
| 			EnumCamprole role = r.get(T_PERSON.CAMPROLE); | ||||
| 			String campname = r.get(V_CAMP.NAME); | ||||
| 			Double year = r.get(V_CAMP.YEAR); | ||||
| 			BookingBean bean = new BookingBean(pkPerson, null, String.format("%s %4.0f", campname, year)); | ||||
| 			bean.setRole(role == null ? null : role.getLiteral()); | ||||
| 			bean.setFullname(new StringBuilder().append(forename).append(" ").append(surname).toString()); | ||||
| 			list.add(bean); | ||||
| 		} | ||||
| 		return list; | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -50,4 +50,14 @@ public class ConfirmationService implements IConfirmationService { | ||||
| 	public List<BookingBean> getRejected(HttpServletRequest request) { | ||||
| 		return gateway.getRejected(getCurrentUser(request)); | ||||
| 	} | ||||
|  | ||||
| 	@Override | ||||
| 	public String search(String needle, String linkURL, HttpServletRequest request) { | ||||
| 		StringBuilder buf = new StringBuilder("<table class=\"table table-striped\"><thead><tr><th>Name</th><th>Freizeit</th><th>Rolle</th></tr><tbody>"); | ||||
| 		for (BookingBean bean : gateway.getSearchResult(needle, getCurrentUser(request))) { | ||||
| 			buf.append(String.format("<tr><td><a href=\"%s/%d\">%s</a></td><td>%s</td><td>%s</td></tr>", linkURL, bean.getPkPerson(), bean.getFullname(), bean.getCamp(), bean.getRolename())); | ||||
| 		} | ||||
| 		buf.append("</tbody></table>"); | ||||
| 		return buf.toString(); | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -0,0 +1,84 @@ | ||||
| package de.jottyfan.camporganizer.module.confirmation.confirmation.impl; | ||||
|  | ||||
| import java.io.Serializable; | ||||
|  | ||||
| /** | ||||
|  * | ||||
|  * @author jotty | ||||
|  * | ||||
|  */ | ||||
| public class FoundBean implements Serializable { | ||||
|  | ||||
| 	private static final long serialVersionUID = 1L; | ||||
|  | ||||
| 	private Integer fkPerson; | ||||
| 	private String forename; | ||||
| 	private String surname; | ||||
| 	private String campname; | ||||
| 	private Integer year; | ||||
|  | ||||
| 	/** | ||||
| 	 * @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; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the campname | ||||
| 	 */ | ||||
| 	public String getCampname() { | ||||
| 		return campname; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param campname the campname to set | ||||
| 	 */ | ||||
| 	public void setCampname(String campname) { | ||||
| 		this.campname = campname; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @return the year | ||||
| 	 */ | ||||
| 	public Integer getYear() { | ||||
| 		return year; | ||||
| 	} | ||||
|  | ||||
| 	/** | ||||
| 	 * @param year the year to set | ||||
| 	 */ | ||||
| 	public void setYear(Integer year) { | ||||
| 		this.year = year; | ||||
| 	} | ||||
|  | ||||
| 	public Integer getFkPerson() { | ||||
| 		return fkPerson; | ||||
| 	} | ||||
|  | ||||
| 	public void setFkPerson(Integer fkPerson) { | ||||
| 		this.fkPerson = fkPerson; | ||||
| 	} | ||||
|  | ||||
| } | ||||
							
								
								
									
										9
									
								
								src/main/resources/static/js/myAjax.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										9
									
								
								src/main/resources/static/js/myAjax.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,9 @@ | ||||
| class MyAjax { | ||||
| 	constructor(url) { | ||||
| 		this.url = url; | ||||
| 	} | ||||
|  | ||||
| 	call(destdivid, needle) { | ||||
| 		$("[id='" + destdivid + "']").load(this.url + '?needle=' + encodeURI(needle)); | ||||
| 	} | ||||
| } | ||||
| @@ -157,10 +157,22 @@ | ||||
| 			</div> | ||||
| 			<div class="accordion-item"> | ||||
| 				<h2 class="accordion-header" id="searchpanel"> | ||||
| 					<button class="accordion-button" type="button" data-bs-toggle="collapse" data-bs-target="#searchdiv" aria-expanded="true" aria-control="searchdiv">Suchmaske</button> | ||||
| 					<button class="accordion-button" type="button" data-bs-toggle="collapse" data-bs-target="#searchdiv" aria-expanded="true" aria-control="searchdiv">Suchmaske (einzelne Begriffe)</button> | ||||
| 				</h2> | ||||
| 				<div id="searchdiv" class="accordion-collapse collapse dist8" aria-labelled="searchpanel" data-bs-parent="#mainacc">TODO: add an ajax based search field for persons to directly edit | ||||
| 					them</div> | ||||
| 				<div id="searchdiv" class="accordion-collapse collapse dist8" aria-labelled="searchpanel" data-bs-parent="#mainacc"> | ||||
| 					<script th:inline="javascript"> | ||||
| 					/*<![CDATA[*/ | ||||
| 					  var searchUrl = /*[[@{/confirmation/search}]]*/ '?'; | ||||
| 						var myAjax = new MyAjax(searchUrl); | ||||
| 					/*]]>*/ | ||||
| 					</script> | ||||
| 					<input type="text" placeholder="bitte Suchtext eingeben" class="form-control" onchange="myAjax.call('searchresult', this.value)" /> | ||||
| 					<div id="searchresult"> | ||||
| 						Die Suche ist eine einfache Textsuche. Bestenfalls sollte nur ein Begriff zum Suchen verwendet werden, also z.B. nur der Vor- ODER der Nachname, nicht beides.<br /> | ||||
| 						Es werden nur wenige Felder in der Datenbank durchsucht: Vorname, Nachname, Freizeitname und Freizeitjahr.<br /> | ||||
| 						Die Suche wird nach dem Verlassen des Suchtext-Eingabefeldes aktiviert. | ||||
| 					</div> | ||||
| 				</div> | ||||
| 			</div> | ||||
| 		</div> | ||||
| 	</div> | ||||
|   | ||||
| @@ -14,6 +14,7 @@ | ||||
| <script th:src="@{/webjars/select2/4.0.13/js/select2.full.min.js}"></script> | ||||
| <script th:src="@{/js/dataTables.de.js}"></script> | ||||
| <script th:src="@{/js/mytoggle.js}"></script> | ||||
| <script th:src="@{/js/myAjax.js}"></script> | ||||
| <meta th:replace="${libs}"></meta> | ||||
| </head> | ||||
| <body> | ||||
|   | ||||
		Reference in New Issue
	
	Block a user