add NEVER_UNIT automation
This commit is contained in:
parent
5d5eb45b5a
commit
8fa00972bd
@ -4,7 +4,7 @@ import unicodedata
|
|||||||
|
|
||||||
from django.core.cache import caches
|
from django.core.cache import caches
|
||||||
|
|
||||||
from cookbook.models import Unit, Food, Automation, Ingredient
|
from cookbook.models import Automation, Food, Ingredient, Unit
|
||||||
|
|
||||||
|
|
||||||
class IngredientParser:
|
class IngredientParser:
|
||||||
@ -12,6 +12,7 @@ class IngredientParser:
|
|||||||
ignore_rules = False
|
ignore_rules = False
|
||||||
food_aliases = {}
|
food_aliases = {}
|
||||||
unit_aliases = {}
|
unit_aliases = {}
|
||||||
|
never_unit = {}
|
||||||
|
|
||||||
def __init__(self, request, cache_mode, ignore_automations=False):
|
def __init__(self, request, cache_mode, ignore_automations=False):
|
||||||
"""
|
"""
|
||||||
@ -40,9 +41,19 @@ class IngredientParser:
|
|||||||
for a in Automation.objects.filter(space=self.request.space, disabled=False, type=Automation.UNIT_ALIAS).only('param_1', 'param_2').order_by('order').all():
|
for a in Automation.objects.filter(space=self.request.space, disabled=False, type=Automation.UNIT_ALIAS).only('param_1', 'param_2').order_by('order').all():
|
||||||
self.unit_aliases[a.param_1] = a.param_2
|
self.unit_aliases[a.param_1] = a.param_2
|
||||||
caches['default'].set(UNIT_CACHE_KEY, self.unit_aliases, 30)
|
caches['default'].set(UNIT_CACHE_KEY, self.unit_aliases, 30)
|
||||||
|
|
||||||
|
NEVER_UNIT_CACHE_KEY = f'automation_never_unit_{self.request.space.pk}'
|
||||||
|
if c := caches['default'].get(NEVER_UNIT_CACHE_KEY, None):
|
||||||
|
self.never_unit = c
|
||||||
|
caches['default'].touch(NEVER_UNIT_CACHE_KEY, 30)
|
||||||
|
else:
|
||||||
|
for a in Automation.objects.filter(space=self.request.space, disabled=False, type=Automation.NEVER_UNIT).only('param_1', 'param_2').order_by('order').all():
|
||||||
|
self.never_unit[a.param_1] = a.param_2
|
||||||
|
caches['default'].set(NEVER_UNIT_CACHE_KEY, self.never_unit, 30)
|
||||||
else:
|
else:
|
||||||
self.food_aliases = {}
|
self.food_aliases = {}
|
||||||
self.unit_aliases = {}
|
self.unit_aliases = {}
|
||||||
|
self.never_unit = {}
|
||||||
|
|
||||||
def apply_food_automation(self, food):
|
def apply_food_automation(self, food):
|
||||||
"""
|
"""
|
||||||
@ -205,6 +216,49 @@ class IngredientParser:
|
|||||||
food, note = self.parse_food_with_comma(tokens)
|
food, note = self.parse_food_with_comma(tokens)
|
||||||
return food, note
|
return food, note
|
||||||
|
|
||||||
|
def apply_never_unit_automations(self, tokens):
|
||||||
|
"""
|
||||||
|
Moves a string that should never be treated as a unit to next token and optionally replaced with default unit
|
||||||
|
e.g. NEVER_UNIT: param1: egg, param2: None would modify ['1', 'egg', 'white'] to ['1', '', 'egg', 'white']
|
||||||
|
or NEVER_UNIT: param1: egg, param2: pcs would modify ['1', 'egg', 'yolk'] to ['1', 'pcs', 'egg', 'yolk']
|
||||||
|
:param1 string: string that should never be considered a unit, will be moved to token[2]
|
||||||
|
:param2 (optional) unit as string: will insert unit string into token[1]
|
||||||
|
:return: unit as string (possibly changed by automation)
|
||||||
|
"""
|
||||||
|
|
||||||
|
if self.ignore_rules:
|
||||||
|
return tokens
|
||||||
|
|
||||||
|
new_unit = None
|
||||||
|
alt_unit = self.apply_unit_automation(tokens[1])
|
||||||
|
never_unit = False
|
||||||
|
if self.never_unit:
|
||||||
|
try:
|
||||||
|
new_unit = self.never_unit[tokens[1]]
|
||||||
|
never_unit = True
|
||||||
|
except KeyError:
|
||||||
|
return tokens
|
||||||
|
|
||||||
|
else:
|
||||||
|
if automation := Automation.objects.filter(space=self.request.space, type=Automation.UNIT_ALIAS, param_1__in=[tokens[1], alt_unit], disabled=False).order_by('order').first():
|
||||||
|
new_unit = automation.param_2
|
||||||
|
never_unit = True
|
||||||
|
|
||||||
|
if never_unit:
|
||||||
|
tokens.insert(1, new_unit)
|
||||||
|
|
||||||
|
return tokens
|
||||||
|
|
||||||
|
def parse_tokens(self, tokens):
|
||||||
|
"""
|
||||||
|
parser that applies automations to unmodified tokens
|
||||||
|
"""
|
||||||
|
|
||||||
|
if self.ignore_rules:
|
||||||
|
return tokens
|
||||||
|
|
||||||
|
return self.apply_never_unit_automations(tokens)
|
||||||
|
|
||||||
def parse(self, ingredient):
|
def parse(self, ingredient):
|
||||||
"""
|
"""
|
||||||
Main parsing function, takes an ingredient string (e.g. '1 l Water') and extracts amount, unit, food, ...
|
Main parsing function, takes an ingredient string (e.g. '1 l Water') and extracts amount, unit, food, ...
|
||||||
@ -257,6 +311,7 @@ class IngredientParser:
|
|||||||
# three arguments if it already has a unit there can't be
|
# three arguments if it already has a unit there can't be
|
||||||
# a fraction for the amount
|
# a fraction for the amount
|
||||||
if len(tokens) > 2:
|
if len(tokens) > 2:
|
||||||
|
tokens = self.parse_tokens(tokens)
|
||||||
try:
|
try:
|
||||||
if unit is not None:
|
if unit is not None:
|
||||||
# a unit is already found, no need to try the second argument for a fraction
|
# a unit is already found, no need to try the second argument for a fraction
|
||||||
|
23
cookbook/migrations/0189_alter_automation_type_and_more.py
Normal file
23
cookbook/migrations/0189_alter_automation_type_and_more.py
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
# Generated by Django 4.1.7 on 2023-04-24 15:00
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('cookbook', '0188_space_no_sharing_limit'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AlterField(
|
||||||
|
model_name='automation',
|
||||||
|
name='type',
|
||||||
|
field=models.CharField(choices=[('FOOD_ALIAS', 'Food Alias'), ('UNIT_ALIAS', 'Unit Alias'), ('KEYWORD_ALIAS', 'Keyword Alias'), ('DESCRIPTION_REPLACE', 'Description Replace'), ('INSTRUCTION_REPLACE', 'Instruction Replace'), ('NEVER_UNIT', 'Never Unit')], max_length=128),
|
||||||
|
),
|
||||||
|
migrations.AlterField(
|
||||||
|
model_name='userpreference',
|
||||||
|
name='use_fractions',
|
||||||
|
field=models.BooleanField(default=True),
|
||||||
|
),
|
||||||
|
]
|
@ -5,7 +5,6 @@ import uuid
|
|||||||
from datetime import date, timedelta
|
from datetime import date, timedelta
|
||||||
|
|
||||||
import oauth2_provider.models
|
import oauth2_provider.models
|
||||||
from PIL import Image
|
|
||||||
from annoying.fields import AutoOneToOneField
|
from annoying.fields import AutoOneToOneField
|
||||||
from django.contrib import auth
|
from django.contrib import auth
|
||||||
from django.contrib.auth.models import Group, User
|
from django.contrib.auth.models import Group, User
|
||||||
@ -14,13 +13,14 @@ from django.contrib.postgres.search import SearchVectorField
|
|||||||
from django.core.files.uploadedfile import InMemoryUploadedFile, UploadedFile
|
from django.core.files.uploadedfile import InMemoryUploadedFile, UploadedFile
|
||||||
from django.core.validators import MinLengthValidator
|
from django.core.validators import MinLengthValidator
|
||||||
from django.db import IntegrityError, models
|
from django.db import IntegrityError, models
|
||||||
from django.db.models import Index, ProtectedError, Q, Avg, Max
|
from django.db.models import Avg, Index, Max, ProtectedError, Q
|
||||||
from django.db.models.fields.related import ManyToManyField
|
from django.db.models.fields.related import ManyToManyField
|
||||||
from django.db.models.functions import Substr
|
from django.db.models.functions import Substr
|
||||||
from django.utils import timezone
|
from django.utils import timezone
|
||||||
from django.utils.translation import gettext as _
|
from django.utils.translation import gettext as _
|
||||||
from django_prometheus.models import ExportModelOperationsMixin
|
from django_prometheus.models import ExportModelOperationsMixin
|
||||||
from django_scopes import ScopedManager, scopes_disabled
|
from django_scopes import ScopedManager, scopes_disabled
|
||||||
|
from PIL import Image
|
||||||
from treebeard.mp_tree import MP_Node, MP_NodeManager
|
from treebeard.mp_tree import MP_Node, MP_NodeManager
|
||||||
|
|
||||||
from recipes.settings import (COMMENT_PREF_DEFAULT, FRACTION_PREF_DEFAULT, KJ_PREF_DEFAULT,
|
from recipes.settings import (COMMENT_PREF_DEFAULT, FRACTION_PREF_DEFAULT, KJ_PREF_DEFAULT,
|
||||||
@ -1319,10 +1319,12 @@ class Automation(ExportModelOperationsMixin('automations'), models.Model, Permis
|
|||||||
KEYWORD_ALIAS = 'KEYWORD_ALIAS'
|
KEYWORD_ALIAS = 'KEYWORD_ALIAS'
|
||||||
DESCRIPTION_REPLACE = 'DESCRIPTION_REPLACE'
|
DESCRIPTION_REPLACE = 'DESCRIPTION_REPLACE'
|
||||||
INSTRUCTION_REPLACE = 'INSTRUCTION_REPLACE'
|
INSTRUCTION_REPLACE = 'INSTRUCTION_REPLACE'
|
||||||
|
NEVER_UNIT = 'NEVER_UNIT'
|
||||||
|
|
||||||
type = models.CharField(max_length=128,
|
type = models.CharField(max_length=128,
|
||||||
choices=((FOOD_ALIAS, _('Food Alias')), (UNIT_ALIAS, _('Unit Alias')), (KEYWORD_ALIAS, _('Keyword Alias')),
|
choices=((FOOD_ALIAS, _('Food Alias')), (UNIT_ALIAS, _('Unit Alias')), (KEYWORD_ALIAS, _('Keyword Alias')),
|
||||||
(DESCRIPTION_REPLACE, _('Description Replace')), (INSTRUCTION_REPLACE, _('Instruction Replace')),))
|
(DESCRIPTION_REPLACE, _('Description Replace')), (INSTRUCTION_REPLACE, _('Instruction Replace')),
|
||||||
|
(NEVER_UNIT, _('Never Unit')),))
|
||||||
name = models.CharField(max_length=128, default='')
|
name = models.CharField(max_length=128, default='')
|
||||||
description = models.TextField(blank=True, null=True)
|
description = models.TextField(blank=True, null=True)
|
||||||
|
|
||||||
|
@ -1,39 +1,41 @@
|
|||||||
!!! warning
|
!!! warning
|
||||||
Automations are currently in a beta stage. They work pretty stable but if I encounter any
|
Automations are currently in a beta stage. They work pretty stable but if I encounter any
|
||||||
issues while working on them, I might change how they work breaking existing automations.
|
issues while working on them, I might change how they work breaking existing automations.
|
||||||
I will try to avoid this and am pretty confident it won't happen.
|
I will try to avoid this and am pretty confident it won't happen.
|
||||||
|
|
||||||
|
Automations allow Tandoor to automatically perform certain tasks, especially when importing recipes, that
|
||||||
Automations allow Tandoor to automatically perform certain tasks, especially when importing recipes, that
|
|
||||||
would otherwise have to be done manually. Currently, the following automations are supported.
|
would otherwise have to be done manually. Currently, the following automations are supported.
|
||||||
|
|
||||||
## Unit, Food, Keyword Alias
|
## Unit, Food, Keyword Alias
|
||||||
|
|
||||||
Foods, Units and Keywords can have automations that automatically replace them with another object
|
Foods, Units and Keywords can have automations that automatically replace them with another object
|
||||||
to allow aliasing them.
|
to allow aliasing them.
|
||||||
|
|
||||||
This helps to add consistency to the naming of objects, for example to always use the singular form
|
This helps to add consistency to the naming of objects, for example to always use the singular form
|
||||||
for the main name if a plural form is configured.
|
for the main name if a plural form is configured.
|
||||||
|
|
||||||
These automations are best created by dragging and dropping Foods, Units or Keywords in their respective
|
These automations are best created by dragging and dropping Foods, Units or Keywords in their respective
|
||||||
views and creating the automation there.
|
views and creating the automation there.
|
||||||
|
|
||||||
You can also create them manually by setting the following
|
You can also create them manually by setting the following
|
||||||
- **Parameter 1**: name of food/unit/keyword to match
|
|
||||||
- **Parameter 2**: name of food/unit/keyword to replace matched food with
|
- **Parameter 1**: name of food/unit/keyword to match
|
||||||
|
- **Parameter 2**: name of food/unit/keyword to replace matched food with
|
||||||
|
|
||||||
These rules are processed whenever you are importing recipes from websites or other apps
|
These rules are processed whenever you are importing recipes from websites or other apps
|
||||||
and when using the simple ingredient input (shopping, recipe editor, ...).
|
and when using the simple ingredient input (shopping, recipe editor, ...).
|
||||||
|
|
||||||
## Description Replace
|
## Description Replace
|
||||||
This automation is a bit more complicated than the alis rules. It is run when importing a recipe
|
|
||||||
|
This automation is a bit more complicated than the alias rules. It is run when importing a recipe
|
||||||
from a website.
|
from a website.
|
||||||
|
|
||||||
It uses Regular Expressions (RegEx) to determine if a description should be altered, what exactly to remove
|
It uses Regular Expressions (RegEx) to determine if a description should be altered, what exactly to remove
|
||||||
and what to replace it with.
|
and what to replace it with.
|
||||||
|
|
||||||
- **Parameter 1**: pattern of which sites to match (e.g. `.*.chefkoch.de.*`, `.*`)
|
- **Parameter 1**: pattern of which sites to match (e.g. `.*.chefkoch.de.*`, `.*`)
|
||||||
- **Parameter 2**: pattern of what to replace (e.g. `.*`)
|
- **Parameter 2**: pattern of what to replace (e.g. `.*`)
|
||||||
- **Parameter 3**: value to replace matched occurrence of parameter 2 with. Only one occurrence of the pattern is replaced.
|
- **Parameter 3**: value to replace matched occurrence of parameter 2 with. Only one occurrence of the pattern is replaced.
|
||||||
|
|
||||||
To replace the description the python [re.sub](https://docs.python.org/2/library/re.html#re.sub) function is used
|
To replace the description the python [re.sub](https://docs.python.org/2/library/re.html#re.sub) function is used
|
||||||
like this `re.sub(<parameter 2>, <parameter 2>, <descriotion>, count=1)`
|
like this `re.sub(<parameter 2>, <parameter 2>, <descriotion>, count=1)`
|
||||||
@ -41,24 +43,41 @@ like this `re.sub(<parameter 2>, <parameter 2>, <descriotion>, count=1)`
|
|||||||
To test out your patterns and learn about RegEx you can use [regexr.com](https://regexr.com/)
|
To test out your patterns and learn about RegEx you can use [regexr.com](https://regexr.com/)
|
||||||
|
|
||||||
!!! info
|
!!! info
|
||||||
In order to prevent denial of service attacks on the RegEx engine the number of replace automations
|
In order to prevent denial of service attacks on the RegEx engine the number of replace automations
|
||||||
and the length of the inputs that are processed are limited. Those limits should never be reached
|
and the length of the inputs that are processed are limited. Those limits should never be reached
|
||||||
during normal usage.
|
during normal usage.
|
||||||
|
|
||||||
## Instruction Replace
|
## Instruction Replace
|
||||||
|
|
||||||
This works just like the Description Replace automation but runs against all instruction texts
|
This works just like the Description Replace automation but runs against all instruction texts
|
||||||
in all steps of a recipe during import.
|
in all steps of a recipe during import.
|
||||||
|
|
||||||
Also instead of just replacing a single occurrence of the matched pattern it will replace all.
|
Also instead of just replacing a single occurrence of the matched pattern it will replace all.
|
||||||
|
|
||||||
|
## Never Unit
|
||||||
|
|
||||||
|
Some ingredients have a pattern of AMOUNT and FOOD, if the food has multiple words (e.g. egg yolk) this can cause Tandoor
|
||||||
|
to detect the word "egg" as a unit. This automation will detect the word 'egg' as something that should never be considered
|
||||||
|
a unit.
|
||||||
|
|
||||||
|
You can also create them manually by setting the following
|
||||||
|
|
||||||
|
- **Parameter 1**: string to detect
|
||||||
|
- **Parameter 2**: Optional: unit to insert into ingredient (e.g. 1 whole 'egg yolk' instead of 1 <empty> 'egg yolk')
|
||||||
|
|
||||||
|
These rules are processed whenever you are importing recipes from websites or other apps
|
||||||
|
and when using the simple ingredient input (shopping, recipe editor, ...).
|
||||||
|
|
||||||
# Order
|
# Order
|
||||||
If the Automation type allows for more than one rule to be executed (for example description replace)
|
|
||||||
the rules are processed in ascending order (ordered by the *order* property of the automation).
|
If the Automation type allows for more than one rule to be executed (for example description replace)
|
||||||
The default order is always 1000 to make it easier to add automations before and after other automations.
|
the rules are processed in ascending order (ordered by the _order_ property of the automation).
|
||||||
|
The default order is always 1000 to make it easier to add automations before and after other automations.
|
||||||
|
|
||||||
Example:
|
Example:
|
||||||
|
|
||||||
1. Rule ABC (order 1000) replaces `everything` with `abc`
|
1. Rule ABC (order 1000) replaces `everything` with `abc`
|
||||||
2. Rule DEF (order 2000) replaces `everything` with `def`
|
2. Rule DEF (order 2000) replaces `everything` with `def`
|
||||||
3. Rule XYZ (order 500) replaces `everything` with `xyz`
|
3. Rule XYZ (order 500) replaces `everything` with `xyz`
|
||||||
|
|
||||||
After processing rules XYZ, then ABC and then DEF the description will have the value `def`
|
After processing rules XYZ, then ABC and then DEF the description will have the value `def`
|
||||||
|
@ -525,6 +525,7 @@
|
|||||||
"Use_Plural_Food_Always": "Use plural form for food always",
|
"Use_Plural_Food_Always": "Use plural form for food always",
|
||||||
"Use_Plural_Food_Simple": "Use plural form for food dynamically",
|
"Use_Plural_Food_Simple": "Use plural form for food dynamically",
|
||||||
"plural_usage_info": "Use the plural form for units and food inside this space.",
|
"plural_usage_info": "Use the plural form for units and food inside this space.",
|
||||||
"Create Recipe": "Create Recipe",
|
"Create Recipe": "Create Recipe",
|
||||||
"Import Recipe": "Import Recipe"
|
"Import Recipe": "Import Recipe",
|
||||||
|
"Never_Unit": "Never Unit"
|
||||||
}
|
}
|
||||||
|
@ -23,7 +23,7 @@ export class Models {
|
|||||||
false: undefined,
|
false: undefined,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
tree: {default: undefined},
|
tree: { default: undefined },
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
delete: {
|
delete: {
|
||||||
@ -50,7 +50,7 @@ export class Models {
|
|||||||
type: "lookup",
|
type: "lookup",
|
||||||
field: "target",
|
field: "target",
|
||||||
list: "self",
|
list: "self",
|
||||||
sticky_options: [{id: 0, name: "tree_root"}],
|
sticky_options: [{ id: 0, name: "tree_root" }],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@ -71,7 +71,7 @@ export class Models {
|
|||||||
food_onhand: true,
|
food_onhand: true,
|
||||||
shopping: true,
|
shopping: true,
|
||||||
},
|
},
|
||||||
tags: [{field: "supermarket_category", label: "name", color: "info"}],
|
tags: [{ field: "supermarket_category", label: "name", color: "info" }],
|
||||||
// REQUIRED: unordered array of fields that can be set during create
|
// REQUIRED: unordered array of fields that can be set during create
|
||||||
create: {
|
create: {
|
||||||
// if not defined partialUpdate will use the same parameters, prepending 'id'
|
// if not defined partialUpdate will use the same parameters, prepending 'id'
|
||||||
@ -177,7 +177,7 @@ export class Models {
|
|||||||
field: "substitute_siblings",
|
field: "substitute_siblings",
|
||||||
label: "substitute_siblings", // form.label always translated in utils.getForm()
|
label: "substitute_siblings", // form.label always translated in utils.getForm()
|
||||||
help_text: "substitute_siblings_help", // form.help_text always translated
|
help_text: "substitute_siblings_help", // form.help_text always translated
|
||||||
condition: {field: "parent", value: true, condition: "field_exists"},
|
condition: { field: "parent", value: true, condition: "field_exists" },
|
||||||
},
|
},
|
||||||
substitute_children: {
|
substitute_children: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
@ -186,7 +186,7 @@ export class Models {
|
|||||||
field: "substitute_children",
|
field: "substitute_children",
|
||||||
label: "substitute_children",
|
label: "substitute_children",
|
||||||
help_text: "substitute_children_help",
|
help_text: "substitute_children_help",
|
||||||
condition: {field: "numchild", value: 0, condition: "gt"},
|
condition: { field: "numchild", value: 0, condition: "gt" },
|
||||||
},
|
},
|
||||||
inherit_fields: {
|
inherit_fields: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
@ -196,7 +196,7 @@ export class Models {
|
|||||||
field: "inherit_fields",
|
field: "inherit_fields",
|
||||||
list: "FOOD_INHERIT_FIELDS",
|
list: "FOOD_INHERIT_FIELDS",
|
||||||
label: "InheritFields",
|
label: "InheritFields",
|
||||||
condition: {field: "food_children_exist", value: true, condition: "preference_equals"},
|
condition: { field: "food_children_exist", value: true, condition: "preference_equals" },
|
||||||
help_text: "InheritFields_help",
|
help_text: "InheritFields_help",
|
||||||
},
|
},
|
||||||
child_inherit_fields: {
|
child_inherit_fields: {
|
||||||
@ -207,7 +207,7 @@ export class Models {
|
|||||||
field: "child_inherit_fields",
|
field: "child_inherit_fields",
|
||||||
list: "FOOD_INHERIT_FIELDS",
|
list: "FOOD_INHERIT_FIELDS",
|
||||||
label: "ChildInheritFields", // form.label always translated in utils.getForm()
|
label: "ChildInheritFields", // form.label always translated in utils.getForm()
|
||||||
condition: {field: "numchild", value: 0, condition: "gt"},
|
condition: { field: "numchild", value: 0, condition: "gt" },
|
||||||
help_text: "ChildInheritFields_help", // form.help_text always translated
|
help_text: "ChildInheritFields_help", // form.help_text always translated
|
||||||
},
|
},
|
||||||
reset_inherit: {
|
reset_inherit: {
|
||||||
@ -217,7 +217,7 @@ export class Models {
|
|||||||
field: "reset_inherit",
|
field: "reset_inherit",
|
||||||
label: "reset_children",
|
label: "reset_children",
|
||||||
help_text: "reset_children_help",
|
help_text: "reset_children_help",
|
||||||
condition: {field: "numchild", value: 0, condition: "gt"},
|
condition: { field: "numchild", value: 0, condition: "gt" },
|
||||||
},
|
},
|
||||||
form_function: "FoodCreateDefault",
|
form_function: "FoodCreateDefault",
|
||||||
},
|
},
|
||||||
@ -281,7 +281,7 @@ export class Models {
|
|||||||
apiName: "Unit",
|
apiName: "Unit",
|
||||||
paginated: true,
|
paginated: true,
|
||||||
create: {
|
create: {
|
||||||
params: [["name", "plural_name", "description", "base_unit", "open_data_slug",]],
|
params: [["name", "plural_name", "description", "base_unit", "open_data_slug"]],
|
||||||
form: {
|
form: {
|
||||||
show_help: true,
|
show_help: true,
|
||||||
name: {
|
name: {
|
||||||
@ -311,24 +311,24 @@ export class Models {
|
|||||||
form_field: true,
|
form_field: true,
|
||||||
type: "choice",
|
type: "choice",
|
||||||
options: [
|
options: [
|
||||||
{value: "g", text: "g"},
|
{ value: "g", text: "g" },
|
||||||
{value: "kg", text: "kg"},
|
{ value: "kg", text: "kg" },
|
||||||
{value: "ounce", text: "ounce"},
|
{ value: "ounce", text: "ounce" },
|
||||||
{value: "pound", text: "pound"},
|
{ value: "pound", text: "pound" },
|
||||||
{value: "ml", text: "ml"},
|
{ value: "ml", text: "ml" },
|
||||||
{value: "l", text: "l"},
|
{ value: "l", text: "l" },
|
||||||
{value: "fluid_ounce", text: "fluid_ounce"},
|
{ value: "fluid_ounce", text: "fluid_ounce" },
|
||||||
{value: "pint", text: "pint"},
|
{ value: "pint", text: "pint" },
|
||||||
{value: "quart", text: "quart"},
|
{ value: "quart", text: "quart" },
|
||||||
{value: "gallon", text: "gallon"},
|
{ value: "gallon", text: "gallon" },
|
||||||
{value: "tbsp", text: "tbsp"},
|
{ value: "tbsp", text: "tbsp" },
|
||||||
{value: "tsp", text: "tsp"},
|
{ value: "tsp", text: "tsp" },
|
||||||
{value: "imperial_fluid_ounce", text: "imperial_fluid_ounce"},
|
{ value: "imperial_fluid_ounce", text: "imperial_fluid_ounce" },
|
||||||
{value: "imperial_pint", text: "imperial_pint"},
|
{ value: "imperial_pint", text: "imperial_pint" },
|
||||||
{value: "imperial_quart", text: "imperial_quart"},
|
{ value: "imperial_quart", text: "imperial_quart" },
|
||||||
{value: "imperial_gallon", text: "imperial_gallon"},
|
{ value: "imperial_gallon", text: "imperial_gallon" },
|
||||||
{value: "imperial_tbsp", text: "imperial_tbsp"},
|
{ value: "imperial_tbsp", text: "imperial_tbsp" },
|
||||||
{value: "imperial_tsp", text: "imperial_tsp"},
|
{ value: "imperial_tsp", text: "imperial_tsp" },
|
||||||
],
|
],
|
||||||
field: "base_unit",
|
field: "base_unit",
|
||||||
label: "Base Unit",
|
label: "Base Unit",
|
||||||
@ -470,7 +470,7 @@ export class Models {
|
|||||||
static SUPERMARKET = {
|
static SUPERMARKET = {
|
||||||
name: "Supermarket",
|
name: "Supermarket",
|
||||||
apiName: "Supermarket",
|
apiName: "Supermarket",
|
||||||
ordered_tags: [{field: "category_to_supermarket", label: "category::name", color: "info"}],
|
ordered_tags: [{ field: "category_to_supermarket", label: "category::name", color: "info" }],
|
||||||
create: {
|
create: {
|
||||||
params: [["name", "description", "category_to_supermarket"]],
|
params: [["name", "description", "category_to_supermarket"]],
|
||||||
form: {
|
form: {
|
||||||
@ -553,11 +553,11 @@ export class Models {
|
|||||||
form_field: true,
|
form_field: true,
|
||||||
type: "choice",
|
type: "choice",
|
||||||
options: [
|
options: [
|
||||||
{value: "FOOD_ALIAS", text: "Food_Alias"},
|
{ value: "FOOD_ALIAS", text: "Food_Alias" },
|
||||||
{value: "UNIT_ALIAS", text: "Unit_Alias"},
|
{ value: "UNIT_ALIAS", text: "Unit_Alias" },
|
||||||
{value: "KEYWORD_ALIAS", text: "Keyword_Alias"},
|
{ value: "KEYWORD_ALIAS", text: "Keyword_Alias" },
|
||||||
{value: "DESCRIPTION_REPLACE", text: "Description_Replace"},
|
{ value: "DESCRIPTION_REPLACE", text: "Description_Replace" },
|
||||||
{value: "INSTRUCTION_REPLACE", text: "Instruction_Replace"},
|
{ value: "INSTRUCTION_REPLACE", text: "Instruction_Replace" },
|
||||||
],
|
],
|
||||||
field: "type",
|
field: "type",
|
||||||
label: "Type",
|
label: "Type",
|
||||||
@ -625,9 +625,8 @@ export class Models {
|
|||||||
label: "Disabled",
|
label: "Disabled",
|
||||||
placeholder: "",
|
placeholder: "",
|
||||||
},
|
},
|
||||||
form_function: "AutomationOrderDefault"
|
form_function: "AutomationOrderDefault",
|
||||||
},
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -641,7 +640,7 @@ export class Models {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
create: {
|
create: {
|
||||||
params: [['food', 'base_amount', 'base_unit', 'converted_amount', 'converted_unit', 'open_data_slug']],
|
params: [["food", "base_amount", "base_unit", "converted_amount", "converted_unit", "open_data_slug"]],
|
||||||
form: {
|
form: {
|
||||||
show_help: true,
|
show_help: true,
|
||||||
// TODO add proper help texts for everything
|
// TODO add proper help texts for everything
|
||||||
@ -695,9 +694,7 @@ export class Models {
|
|||||||
help_text: "open_data_help_text",
|
help_text: "open_data_help_text",
|
||||||
optional: true,
|
optional: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -711,7 +708,7 @@ export class Models {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
create: {
|
create: {
|
||||||
params: [['name', 'icon', 'unit', 'description','order']],
|
params: [["name", "icon", "unit", "description", "order"]],
|
||||||
form: {
|
form: {
|
||||||
show_help: true,
|
show_help: true,
|
||||||
name: {
|
name: {
|
||||||
@ -764,7 +761,6 @@ export class Models {
|
|||||||
optional: true,
|
optional: true,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -852,7 +848,7 @@ export class Models {
|
|||||||
params: ["filter_list"],
|
params: ["filter_list"],
|
||||||
},
|
},
|
||||||
create: {
|
create: {
|
||||||
params: [["name",]],
|
params: [["name"]],
|
||||||
form: {
|
form: {
|
||||||
name: {
|
name: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
@ -1017,7 +1013,7 @@ export class Actions {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
ok_label: {function: "translate", phrase: "Save"},
|
ok_label: { function: "translate", phrase: "Save" },
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
static UPDATE = {
|
static UPDATE = {
|
||||||
@ -1052,7 +1048,7 @@ export class Actions {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
ok_label: {function: "translate", phrase: "Delete"},
|
ok_label: { function: "translate", phrase: "Delete" },
|
||||||
instruction: {
|
instruction: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
type: "instruction",
|
type: "instruction",
|
||||||
@ -1079,17 +1075,17 @@ export class Actions {
|
|||||||
suffix: "s",
|
suffix: "s",
|
||||||
params: ["query", "page", "pageSize", "options"],
|
params: ["query", "page", "pageSize", "options"],
|
||||||
config: {
|
config: {
|
||||||
query: {default: undefined},
|
query: { default: undefined },
|
||||||
page: {default: 1},
|
page: { default: 1 },
|
||||||
pageSize: {default: 25},
|
pageSize: { default: 25 },
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
static MERGE = {
|
static MERGE = {
|
||||||
function: "merge",
|
function: "merge",
|
||||||
params: ["source", "target"],
|
params: ["source", "target"],
|
||||||
config: {
|
config: {
|
||||||
source: {type: "string"},
|
source: { type: "string" },
|
||||||
target: {type: "string"},
|
target: { type: "string" },
|
||||||
},
|
},
|
||||||
form: {
|
form: {
|
||||||
title: {
|
title: {
|
||||||
@ -1104,7 +1100,7 @@ export class Actions {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
ok_label: {function: "translate", phrase: "Merge"},
|
ok_label: { function: "translate", phrase: "Merge" },
|
||||||
instruction: {
|
instruction: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
type: "instruction",
|
type: "instruction",
|
||||||
@ -1138,8 +1134,8 @@ export class Actions {
|
|||||||
function: "move",
|
function: "move",
|
||||||
params: ["source", "target"],
|
params: ["source", "target"],
|
||||||
config: {
|
config: {
|
||||||
source: {type: "string"},
|
source: { type: "string" },
|
||||||
target: {type: "string"},
|
target: { type: "string" },
|
||||||
},
|
},
|
||||||
form: {
|
form: {
|
||||||
title: {
|
title: {
|
||||||
@ -1154,7 +1150,7 @@ export class Actions {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
ok_label: {function: "translate", phrase: "Move"},
|
ok_label: { function: "translate", phrase: "Move" },
|
||||||
instruction: {
|
instruction: {
|
||||||
form_field: true,
|
form_field: true,
|
||||||
type: "instruction",
|
type: "instruction",
|
||||||
|
Loading…
Reference in New Issue
Block a user