Added Recipe search types

This commit is contained in:
Tim Holloway 2022-01-09 11:49:04 -05:00
parent f87854d02f
commit 4bf9a1828c
6 changed files with 131 additions and 17 deletions

View File

@ -6,6 +6,7 @@ import javax.annotation.PostConstruct;
import javax.faces.event.AjaxBehaviorEvent; import javax.faces.event.AjaxBehaviorEvent;
import javax.faces.model.DataModel; import javax.faces.model.DataModel;
import javax.faces.model.ListDataModel; import javax.faces.model.ListDataModel;
import javax.faces.model.SelectItem;
import javax.faces.view.ViewScoped; import javax.faces.view.ViewScoped;
import javax.inject.Inject; import javax.inject.Inject;
import javax.inject.Named; import javax.inject.Named;
@ -13,6 +14,7 @@ import javax.inject.Named;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.List; import java.util.List;
import com.mousetech.gourmetj.UserSession; import com.mousetech.gourmetj.UserSession;
@ -42,8 +44,8 @@ public class AdminMainBean implements Serializable {
/* Logger */ /* Logger */
private static final Logger log = LoggerFactory.getLogger(AdminMainBean.class); private static final Logger log =
LoggerFactory.getLogger(AdminMainBean.class);
/** /**
* Persistency service for Recipes * Persistency service for Recipes
@ -119,8 +121,8 @@ public class AdminMainBean implements Serializable {
} }
/** /**
* Return to last search, if any * Return to last search, if any No longer broken (required
* No longer broken (required Maven include for annotation). * Maven include for annotation).
*/ */
@PostConstruct @PostConstruct
void init() { void init() {
@ -131,9 +133,9 @@ public class AdminMainBean implements Serializable {
doFind(); doFind();
} }
/** /**
* Search, driven by AJAX * Search, driven by AJAX
*
* @param event Notused * @param event Notused
*/ */
public void ajaxUpdateList(AjaxBehaviorEvent event) { public void ajaxUpdateList(AjaxBehaviorEvent event) {
@ -148,15 +150,31 @@ public class AdminMainBean implements Serializable {
this.doFind(); this.doFind();
} }
/** /**
* Finder * Finder
* *
* @return Navigation string * @return Navigation string
*/ */
public String doFind() { public String doFind() {
List<Recipe> recipes = List<Recipe> recipes = null;
recipeService.findByTitle(searchText);
switch (this.getSearchType()) {
case rst_BY_NAME:
recipes = recipeService.findByTitle(searchText);
break;
case rst_BY_CATEGORY:
recipes = recipeService.findByCategoryLike(searchText);
break;
case rst_BY_CUISINE:
recipes = recipeService.findByCuisineLike(searchText);
break;
case rst_BY_INGREDIENT:
recipes = recipeService.findByIngredientLike(searchText);
break;
default:
log.error("Invalid recipe search type: " + this.getSearchType());
break;
}
getSearchResults().setWrappedData(recipes); getSearchResults().setWrappedData(recipes);
this.userSession.setLastSearch(this.getSearchText()); this.userSession.setLastSearch(this.getSearchText());
@ -183,7 +201,8 @@ public class AdminMainBean implements Serializable {
*/ */
public String showRecipe() { public String showRecipe() {
long recipeId = getSearchResults().getRowData().getId(); long recipeId = getSearchResults().getRowData().getId();
// Flash Scope is buggy under Mojarra plus now using session // Flash Scope is buggy under Mojarra plus now using
// session
// JSFUtils.flashScope().put("recipeID", // JSFUtils.flashScope().put("recipeID",
// Long.valueOf(recipeId)); // Long.valueOf(recipeId));
userSession.setLastEdit(recipeId); userSession.setLastEdit(recipeId);
@ -194,6 +213,7 @@ public class AdminMainBean implements Serializable {
/** /**
* Get printable preptime. Database version is in seconds. * Get printable preptime. Database version is in seconds.
*
* @deprecated User {@link UserSession#formatTime(Long)} * @deprecated User {@link UserSession#formatTime(Long)}
* *
* @return Formatted time. Called from EL on main page. * @return Formatted time. Called from EL on main page.
@ -214,4 +234,48 @@ public class AdminMainBean implements Serializable {
return sb.toString(); return sb.toString();
} }
// ***
private RecipeSearchType searchType =
RecipeSearchType.rst_BY_NAME;
/**
* @return the searchType
*/
public RecipeSearchType getSearchType() {
return searchType;
}
/**
* @param searchType the searchType to set
*/
public void setSearchType(RecipeSearchType searchType) {
this.searchType = searchType;
}
private List<SelectItem> searchTypeList;
/**
* @return the searchTypeList
*/
public List<SelectItem> getSearchTypeList() {
if (searchTypeList == null) {
searchTypeList = loadSearchTypeList();
}
return searchTypeList;
}
private List<SelectItem> loadSearchTypeList() {
List<SelectItem> list = new ArrayList<SelectItem>(5);
list.add(new SelectItem(RecipeSearchType.rst_BY_NAME,
"Title"));
list.add(new SelectItem(RecipeSearchType.rst_BY_CATEGORY,
"Category"));
list.add(new SelectItem(RecipeSearchType.rst_BY_CUISINE,
"Cuisine"));
list.add(
new SelectItem(RecipeSearchType.rst_BY_INGREDIENT,
"Ingredient"));
return list;
}
} }

View File

@ -0,0 +1,20 @@
/**
* Copyright (C) 2022, Tim Holloway
*
* Date written: Jan 9, 2022
* Author: Tim Holloway <timh@mousetech.com>
*/
package com.mousetech.gourmetj;
/**
* Types of recipe search for mainpage.
*
* @author timh
* @since Jan 9, 2022
*/
public enum RecipeSearchType {
rst_BY_NAME,
rst_BY_CATEGORY,
rst_BY_CUISINE,
rst_BY_INGREDIENT
}

View File

@ -124,7 +124,9 @@ public class UserSession implements Serializable {
return sb.toString(); return sb.toString();
} }
//** Util, consider conversion to JSF Converter /*
* @Deprecated Using TimeConverter.
*/
public String formatTime(Long ltime) { public String formatTime(Long ltime) {
return TimeFormatter.formatTime(ltime); return TimeFormatter.formatTime(ltime);
} }

View File

@ -31,4 +31,11 @@ public interface RecipeRepository
@Query(name = "Recipe.findCusines", nativeQuery = true) @Query(name = "Recipe.findCusines", nativeQuery = true)
List<String> FindCuisinesNative(); List<String> FindCuisinesNative();
List<Recipe> findByCategories_CategoryContains(String searchText);
List<Recipe> findByCuisineContains(String searchText);
List<Recipe> findByIngredientHash_ItemContains(String searchText);
} }

View File

@ -113,4 +113,16 @@ public class RecipeService implements Serializable {
public List<String> findCategories() { public List<String> findCategories() {
return categoryRepository.findDistinctCategoryNative(); return categoryRepository.findDistinctCategoryNative();
} }
public List<Recipe> findByCategoryLike(String searchText) {
return recipeRepository.findByCategories_CategoryContains(searchText);
}
public List<Recipe> findByCuisineLike(String searchText) {
return recipeRepository.findByCuisineContains(searchText);
}
public List<Recipe> findByIngredientLike(String searchText) {
return recipeRepository.findByIngredientHash_ItemContains(searchText);
}
} }

View File

@ -7,6 +7,7 @@
> >
<ui:define name="title">Gourmet Recipe Manager</ui:define> <ui:define name="title">Gourmet Recipe Manager</ui:define>
<ui:define name="content"> <ui:define name="content">
<h:messages/>
<h:form id="form1"> <h:form id="form1">
<div> <div>
<span class="ui-input-icon-left"> <i <span class="ui-input-icon-left"> <i
@ -22,13 +23,21 @@
</p:inputText> </p:inputText>
</span> </span>
<p:commandButton id="find" value="Find" <p:commandButton id="find" value="Find"
icon="ui-icon-search" icon="ui-icon-search" defaultCommand="true"
defaultCommand="true"
action="#{adminMainBean.doFind}" action="#{adminMainBean.doFind}"
/> />
<p:commandButton id="ctlClear" value="Clear" <p:outputLabel for="@next" value="Search for " />
<p:selectOneMenu id="ctlSearchType"
value="#{adminMainBean.searchType}"
immediate="true" immediate="true"
icon="ui-icon-close" >
<f:selectItems
value="#{adminMainBean.searchTypeList}"
/>
<p:ajax/>
</p:selectOneMenu>
<p:commandButton id="ctlClear" value="Clear"
immediate="true" icon="ui-icon-close"
update="form1:searchFor form2:table1" update="form1:searchFor form2:table1"
action="#{adminMainBean.ajaxClearList}" action="#{adminMainBean.ajaxClearList}"
/> />
@ -39,7 +48,8 @@
</div> </div>
</h:form> </h:form>
<h:form id="form2"> <h:form id="form2">
<p:dataTable id="table1" rows="30" style="margin-top: 6px" <p:dataTable id="table1" rows="30"
style="margin-top: 6px"
value="#{adminMainBean.searchResults}" var="row" value="#{adminMainBean.searchResults}" var="row"
paginator="true" paginator="true"
paginatorTemplate="{CurrentPageReport} {FirstPageLink} {PreviousPageLink} {PageLinks} {NextPageLink} {LastPageLink} {RowsPerPageDropdown}" paginatorTemplate="{CurrentPageReport} {FirstPageLink} {PreviousPageLink} {PageLinks} {NextPageLink} {LastPageLink} {RowsPerPageDropdown}"
@ -74,8 +84,7 @@
<h:outputText value="#{row.source}" /> <h:outputText value="#{row.source}" />
</p:column> </p:column>
<p:column headerText="Prep Time"> <p:column headerText="Prep Time">
<h:outputText <h:outputText value="#{row.preptime}"
value="#{row.preptime}"
converter="com.mousetech.gourmetj.utils.TimeConverter" converter="com.mousetech.gourmetj.utils.TimeConverter"
/> />
</p:column> </p:column>