mirror of
https://github.com/TandoorRecipes/recipes.git
synced 2025-12-23 18:29:23 -05:00
fixed times cooked in saved serarch and improved frontend query binding
This commit is contained in:
@@ -324,9 +324,9 @@ class RecipeSearch():
|
||||
self._queryset = self._queryset.annotate(recent=Coalesce(Max(Case(When(pk__in=num_recent_recipes.values('recipe'), then='viewlog__pk'))), Value(0)))
|
||||
|
||||
def _favorite_recipes(self):
|
||||
if self._sort_includes('favorite') or self._timescooked or self._timescooked_gte or self._timescooked_lte:
|
||||
if self._sort_includes('favorite') or self._timescooked is not None or self._timescooked_gte is not None or self._timescooked_lte is not None:
|
||||
less_than = self._timescooked_lte and not self._sort_includes('-favorite')
|
||||
if less_than or self._timescooked == 0:
|
||||
if less_than:
|
||||
default = 1000
|
||||
else:
|
||||
default = 0
|
||||
@@ -338,11 +338,11 @@ class RecipeSearch():
|
||||
)
|
||||
self._queryset = self._queryset.annotate(favorite=Coalesce(Subquery(favorite_recipes), default))
|
||||
|
||||
if self._timescooked:
|
||||
if self._timescooked is not None:
|
||||
self._queryset = self._queryset.filter(favorite=self._timescooked)
|
||||
elif self._timescooked_lte:
|
||||
elif self._timescooked_lte is not None:
|
||||
self._queryset = self._queryset.filter(favorite__lte=int(self._timescooked_lte)).exclude(favorite=0)
|
||||
elif self._timescooked_gte:
|
||||
elif self._timescooked_gte is not None:
|
||||
self._queryset = self._queryset.filter(favorite__gte=int(self._timescooked_gte))
|
||||
|
||||
def keyword_filters(self, **kwargs):
|
||||
|
||||
@@ -184,7 +184,7 @@ import RecipeCard from "@/components/display/RecipeCard.vue";
|
||||
import {useDisplay} from "vuetify";
|
||||
import {useUserPreferenceStore} from "@/stores/UserPreferenceStore";
|
||||
import {useRouteQuery} from "@vueuse/router";
|
||||
import {routeQueryDateTransformer, stringToBool, toNumberArray} from "@/utils/utils";
|
||||
import {numberOrUndefinedTransformer, routeQueryDateTransformer, stringToBool, toNumberArray} from "@/utils/utils";
|
||||
import RandomIcon from "@/components/display/RandomIcon.vue";
|
||||
import {VSelect, VTextField, VNumberInput} from "vuetify/components";
|
||||
import RatingField from "@/components/inputs/RatingField.vue";
|
||||
@@ -759,27 +759,30 @@ const filters = ref({
|
||||
label: `${t('Rating')} (${t('exact')})`,
|
||||
hint: '',
|
||||
enabled: false,
|
||||
clearable: true,
|
||||
default: undefined,
|
||||
is: RatingField,
|
||||
modelValue: useRouteQuery('rating', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('rating', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
ratingGte: {
|
||||
id: 'ratingGte',
|
||||
label: `${t('Rating')} (>=)`,
|
||||
hint: '',
|
||||
enabled: false,
|
||||
clearable: true,
|
||||
default: undefined,
|
||||
is: RatingField,
|
||||
modelValue: useRouteQuery('ratingGte', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('ratingGte', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
ratingLte: {
|
||||
id: 'ratingLte',
|
||||
label: `${t('Rating')} (<=)`,
|
||||
hint: '',
|
||||
enabled: false,
|
||||
clearable: true,
|
||||
default: undefined,
|
||||
is: RatingField,
|
||||
modelValue: useRouteQuery('ratingLte', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('ratingLte', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
timescooked: {
|
||||
id: 'timescooked',
|
||||
@@ -787,26 +790,29 @@ const filters = ref({
|
||||
hint: 'Recipes that were cooked at least X times',
|
||||
enabled: false,
|
||||
default: undefined,
|
||||
clearable: true,
|
||||
is: VNumberInput,
|
||||
modelValue: useRouteQuery('timescooked', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('timescooked', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
timescookedGte: {
|
||||
id: 'timescookedGte',
|
||||
label: `${t('times_cooked')} (>=)`,
|
||||
hint: '',
|
||||
enabled: false,
|
||||
clearable: true,
|
||||
default: undefined,
|
||||
is: VNumberInput,
|
||||
modelValue: useRouteQuery('timescookedGte', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('timescookedGte', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
timescookedLte: {
|
||||
id: 'timescookedLte',
|
||||
label: `${t('times_cooked')} (<=)`,
|
||||
hint: '',
|
||||
enabled: false,
|
||||
clearable: true,
|
||||
default: undefined,
|
||||
is: VNumberInput,
|
||||
modelValue: useRouteQuery('timescookedLte', undefined, {transform: Number}),
|
||||
modelValue: useRouteQuery('timescookedLte', undefined, {transform: numberOrUndefinedTransformer}),
|
||||
},
|
||||
makenow: {
|
||||
id: 'makenow',
|
||||
|
||||
@@ -80,3 +80,19 @@ export const routeQueryDateTransformer = {
|
||||
get: (value: string | null | Date) => ((value == null) ? null : (new Date(value))),
|
||||
set: (value: string | null | Date) => ((value == null) ? null : (DateTime.fromJSDate(new Date(value)).toISODate()))
|
||||
}
|
||||
|
||||
/**
|
||||
* routeQueryParam transformer for boolean fields converting string bools to real bools
|
||||
*/
|
||||
export const boolOrUndefinedTransformer = {
|
||||
get: (value: string | null | undefined) => ((value == null) ? undefined : value == 'true'),
|
||||
set: (value: boolean | null | undefined) => ((value == null) ? undefined : value.toString())
|
||||
}
|
||||
|
||||
/**
|
||||
* routeQueryParam transformer for number fields converting string numbers to real numbers and allowing undefined for resettable parameters
|
||||
*/
|
||||
export const numberOrUndefinedTransformer = {
|
||||
get: (value: string | null | undefined) => ((value == null) ? undefined : Number(value)),
|
||||
set: (value: string | null | undefined) => ((value == null) ? undefined : value.toString())
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user