Merge branch 'develop' into filter-email-recipients
This commit is contained in:
commit
d649d2cf6f
21 changed files with 262 additions and 171 deletions
19
.github/helper/install.sh
vendored
19
.github/helper/install.sh
vendored
|
|
@ -2,9 +2,11 @@
|
|||
set -e
|
||||
cd ~ || exit
|
||||
|
||||
echo "Setting Up Bench..."
|
||||
|
||||
echo "::group::Install Bench"
|
||||
pip install frappe-bench
|
||||
echo "::endgroup::"
|
||||
|
||||
echo "::group::Init Bench"
|
||||
bench -v init frappe-bench --skip-assets --python "$(which python)" --frappe-path "${GITHUB_WORKSPACE}"
|
||||
cd ./frappe-bench || exit
|
||||
|
||||
|
|
@ -13,9 +15,9 @@ if [ "$TYPE" == "ui" ]
|
|||
then
|
||||
bench -v setup requirements --node;
|
||||
fi
|
||||
echo "::endgroup::"
|
||||
|
||||
echo "Setting Up Sites & Database..."
|
||||
|
||||
echo "::group::Create Test Site"
|
||||
mkdir ~/frappe-bench/sites/test_site
|
||||
cp "${GITHUB_WORKSPACE}/.github/helper/db/$DB.json" ~/frappe-bench/sites/test_site/site_config.json
|
||||
|
||||
|
|
@ -35,9 +37,9 @@ then
|
|||
echo "travis" | psql -h 127.0.0.1 -p 5432 -c "CREATE DATABASE test_frappe" -U postgres;
|
||||
echo "travis" | psql -h 127.0.0.1 -p 5432 -c "CREATE USER test_frappe WITH PASSWORD 'test_frappe'" -U postgres;
|
||||
fi
|
||||
echo "::endgroup::"
|
||||
|
||||
echo "Setting Up Procfile..."
|
||||
|
||||
echo "::group::Modify processes"
|
||||
sed -i 's/^watch:/# watch:/g' Procfile
|
||||
sed -i 's/^schedule:/# schedule:/g' Procfile
|
||||
|
||||
|
|
@ -51,11 +53,11 @@ if [ "$TYPE" == "ui" ]
|
|||
then
|
||||
sed -i 's/^web: bench serve/web: bench serve --with-coverage/g' Procfile
|
||||
fi
|
||||
|
||||
echo "Starting Bench..."
|
||||
echo "::endgroup::"
|
||||
|
||||
bench start &> ~/frappe-bench/bench_start.log &
|
||||
|
||||
echo "::group::Install site"
|
||||
if [ "$TYPE" == "server" ]
|
||||
then
|
||||
CI=Yes bench build --app frappe &
|
||||
|
|
@ -69,3 +71,4 @@ then
|
|||
# wait till assets are built successfully
|
||||
wait $build_pid
|
||||
fi
|
||||
echo "::endgroup::"
|
||||
|
|
|
|||
2
.github/helper/install_dependencies.sh
vendored
2
.github/helper/install_dependencies.sh
vendored
|
|
@ -3,6 +3,7 @@ set -e
|
|||
|
||||
echo "Setting Up System Dependencies..."
|
||||
|
||||
echo "::group::apt packages"
|
||||
sudo apt update
|
||||
sudo apt remove mysql-server mysql-client
|
||||
sudo apt install libcups2-dev redis-server mariadb-client-10.6
|
||||
|
|
@ -12,3 +13,4 @@ install_wkhtmltopdf() {
|
|||
sudo apt install ./wkhtmltox_0.12.6-1.focal_amd64.deb
|
||||
}
|
||||
install_wkhtmltopdf &
|
||||
echo "::endgroup::"
|
||||
|
|
|
|||
|
|
@ -36,9 +36,8 @@ context("Awesome Bar", () => {
|
|||
cy.get(".title-text").should("contain", "To Do");
|
||||
cy.wait(200); // Wait a bit longer before checking the filter.
|
||||
cy.get('[data-original-title="ID"] > input').should("have.value", "%test%");
|
||||
});
|
||||
|
||||
it("filter preserved, now finds something else", () => {
|
||||
// filter preserved, now finds something else
|
||||
cy.visit("/app/todo");
|
||||
cy.get(".title-text").should("contain", "To Do");
|
||||
cy.wait(200); // Wait a bit longer before checking the filter.
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ context("List Paging", () => {
|
|||
|
||||
it("test load more with count selection buttons", () => {
|
||||
cy.visit("/app/todo/view/report");
|
||||
cy.get(".filter-x-button").click();
|
||||
cy.clear_filters();
|
||||
|
||||
cy.get(".list-paging-area .list-count").should("contain.text", "20 of");
|
||||
cy.get(".list-paging-area .btn-more").click();
|
||||
|
|
|
|||
|
|
@ -450,7 +450,7 @@ Cypress.Commands.add("click_menu_button", (name) => {
|
|||
|
||||
Cypress.Commands.add("clear_filters", () => {
|
||||
cy.get(".filter-x-button").click({ force: true });
|
||||
cy.wait(500);
|
||||
cy.wait(1000);
|
||||
});
|
||||
|
||||
Cypress.Commands.add("click_modal_primary_button", (btn_name) => {
|
||||
|
|
|
|||
|
|
@ -1,4 +1,14 @@
|
|||
frappe.ui.form.on("User", {
|
||||
setup: function (frm) {
|
||||
frm.set_query("default_workspace", () => {
|
||||
return {
|
||||
filters: {
|
||||
for_user: ["in", [null, frappe.session.user]],
|
||||
title: ["!=", "Welcome Workspace"],
|
||||
},
|
||||
};
|
||||
});
|
||||
},
|
||||
before_load: function (frm) {
|
||||
let update_tz_options = function () {
|
||||
frm.fields_dict.time_zone.set_data(frappe.all_timezones);
|
||||
|
|
|
|||
|
|
@ -71,6 +71,8 @@
|
|||
"send_me_a_copy",
|
||||
"allowed_in_mentions",
|
||||
"user_emails",
|
||||
"workspace_section",
|
||||
"default_workspace",
|
||||
"sb2",
|
||||
"defaults",
|
||||
"sb3",
|
||||
|
|
@ -711,6 +713,19 @@
|
|||
"label": "Role Profiles",
|
||||
"options": "User Role Profile",
|
||||
"permlevel": 1
|
||||
},
|
||||
{
|
||||
"description": "If left empty, the default workspace will be the last visited workspace",
|
||||
"fieldname": "default_workspace",
|
||||
"fieldtype": "Link",
|
||||
"label": "Default Workspace",
|
||||
"options": "Workspace"
|
||||
},
|
||||
{
|
||||
"collapsible": 1,
|
||||
"fieldname": "workspace_section",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Workspace"
|
||||
}
|
||||
],
|
||||
"icon": "fa fa-user",
|
||||
|
|
@ -773,7 +788,7 @@
|
|||
"link_fieldname": "user"
|
||||
}
|
||||
],
|
||||
"modified": "2024-02-11 13:16:29.574666",
|
||||
"modified": "2024-03-20 17:15:19.200383",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Core",
|
||||
"name": "User",
|
||||
|
|
|
|||
|
|
@ -63,6 +63,7 @@ class User(Document):
|
|||
birth_date: DF.Date | None
|
||||
block_modules: DF.Table[BlockModule]
|
||||
bypass_restrict_ip_check_if_2fa_enabled: DF.Check
|
||||
default_workspace: DF.Link | None
|
||||
defaults: DF.Table[DefaultValue]
|
||||
desk_theme: DF.Literal["Light", "Dark", "Automatic"]
|
||||
document_follow_frequency: DF.Literal["Hourly", "Daily", "Weekly"]
|
||||
|
|
|
|||
|
|
@ -3,12 +3,6 @@ frappe.listview_settings["ToDo"] = {
|
|||
add_fields: ["reference_type", "reference_name"],
|
||||
|
||||
onload: function (me) {
|
||||
if (!Object.keys(frappe.route_options).length) {
|
||||
frappe.route_options = {
|
||||
allocated_to: frappe.session.user,
|
||||
status: "Open",
|
||||
};
|
||||
}
|
||||
me.page.set_title(__("To Do"));
|
||||
},
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,9 @@
|
|||
"""build query for doclistview and return results"""
|
||||
|
||||
import json
|
||||
from functools import lru_cache
|
||||
|
||||
from sql_metadata import Parser
|
||||
|
||||
import frappe
|
||||
import frappe.permissions
|
||||
|
|
@ -102,7 +105,10 @@ def validate_fields(data):
|
|||
wildcard = update_wildcard_field_param(data)
|
||||
|
||||
for field in list(data.fields or []):
|
||||
fieldname = extract_fieldname(field)
|
||||
fieldname = extract_fieldnames(field)[0]
|
||||
if not fieldname:
|
||||
raise_invalid_field(fieldname)
|
||||
|
||||
if is_standard(fieldname):
|
||||
continue
|
||||
|
||||
|
|
@ -182,23 +188,21 @@ def is_standard(fieldname):
|
|||
return fieldname in default_fields or fieldname in optional_fields or fieldname in child_table_fields
|
||||
|
||||
|
||||
def extract_fieldname(field):
|
||||
for text in (",", "/*", "#"):
|
||||
if text in field:
|
||||
raise_invalid_field(field)
|
||||
@lru_cache
|
||||
def extract_fieldnames(field):
|
||||
from frappe.database.schema import SPECIAL_CHAR_PATTERN
|
||||
|
||||
fieldname = field
|
||||
for sep in (" as ", " AS "):
|
||||
if sep in fieldname:
|
||||
fieldname = fieldname.split(sep, 1)[0]
|
||||
if not SPECIAL_CHAR_PATTERN.findall(field):
|
||||
return [field]
|
||||
|
||||
# certain functions allowed, extract the fieldname from the function
|
||||
if fieldname.startswith("count(") or fieldname.startswith("sum(") or fieldname.startswith("avg("):
|
||||
if not fieldname.strip().endswith(")"):
|
||||
raise_invalid_field(field)
|
||||
fieldname = fieldname.split("(", 1)[1][:-1]
|
||||
columns = Parser(f"select {field} from _dummy").columns
|
||||
|
||||
return fieldname
|
||||
if not columns:
|
||||
f = field.lower()
|
||||
if ("count(" in f or "sum(" in f or "avg(" in f) and "*" in f:
|
||||
return ["*"]
|
||||
|
||||
return columns
|
||||
|
||||
|
||||
def get_meta_and_docfield(fieldname, data):
|
||||
|
|
@ -249,13 +253,13 @@ def get_parenttype_and_fieldname(field, data):
|
|||
parts = field.split(".")
|
||||
parenttype = parts[0]
|
||||
fieldname = parts[1]
|
||||
if parenttype.startswith("`tab"):
|
||||
# `tabChild DocType`.`fieldname`
|
||||
parenttype = parenttype[4:-1]
|
||||
fieldname = fieldname.strip("`")
|
||||
df = frappe.get_meta(data.doctype).get_field(parenttype)
|
||||
if not df and parenttype.startswith("tab"):
|
||||
# tabChild DocType.fieldname
|
||||
parenttype = parenttype[3:]
|
||||
else:
|
||||
# tablefield.fieldname
|
||||
parenttype = frappe.get_meta(data.doctype).get_field(parenttype).options
|
||||
parenttype = df.options
|
||||
else:
|
||||
parenttype = data.doctype
|
||||
fieldname = field.strip("`")
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ msgstr ""
|
|||
"Project-Id-Version: frappe\n"
|
||||
"Report-Msgid-Bugs-To: developers@frappe.io\n"
|
||||
"POT-Creation-Date: 2024-03-17 09:33+0000\n"
|
||||
"PO-Revision-Date: 2024-03-18 10:48\n"
|
||||
"PO-Revision-Date: 2024-03-20 11:37\n"
|
||||
"Last-Translator: developers@frappe.io\n"
|
||||
"Language-Team: German\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
|
|
@ -11322,7 +11322,7 @@ msgstr "Wenn Sie die automatische Beantwortung für ein eingehendes E-Mail-Konto
|
|||
#: integrations/doctype/push_notification_settings/push_notification_settings.json
|
||||
msgctxt "Push Notification Settings"
|
||||
msgid "Enabling this will register your site on a central relay server to send push notifications for all installed apps through Firebase Cloud Messaging. This server only stores user tokens and error logs, and no messages are saved. "
|
||||
msgstr ""
|
||||
msgstr "Falls aktiviert, wird Ihre Website auf einem zentralen Relay-Server registriert, um Push-Benachrichtigungen für alle installierten Apps über Firebase Cloud Messaging zu senden. Dieser Server speichert nur Benutzer-Tokens und Fehlerprotokolle, und es werden keine Nachrichten gespeichert. "
|
||||
|
||||
#. Description of the 'Queue in Background (BETA)' (Check) field in DocType
|
||||
#. 'Customize Form'
|
||||
|
|
@ -19374,80 +19374,80 @@ msgstr "Zusammenführung ist nur möglich zwischen Gruppen oder Knoten"
|
|||
#: public/js/frappe/views/communication.js:111 www/message.html:3
|
||||
#: www/message.html:25
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text Editor field in DocType 'Activity Log'
|
||||
#: core/doctype/activity_log/activity_log.json
|
||||
msgctxt "Activity Log"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Section Break field in DocType 'Auto Email Report'
|
||||
#. Label of a Text Editor field in DocType 'Auto Email Report'
|
||||
#: email/doctype/auto_email_report/auto_email_report.json
|
||||
msgctxt "Auto Email Report"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text field in DocType 'Auto Repeat'
|
||||
#: automation/doctype/auto_repeat/auto_repeat.json
|
||||
msgctxt "Auto Repeat"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text Editor field in DocType 'Communication'
|
||||
#: core/doctype/communication/communication.json
|
||||
msgctxt "Communication"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#: __init__.py:614 public/js/frappe/ui/messages.js:265
|
||||
msgctxt "Default title of the message dialog"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Code field in DocType 'Email Queue'
|
||||
#: email/doctype/email_queue/email_queue.json
|
||||
msgctxt "Email Queue"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text Editor field in DocType 'Newsletter'
|
||||
#: email/doctype/newsletter/newsletter.json
|
||||
msgctxt "Newsletter"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Section Break field in DocType 'Notification'
|
||||
#. Label of a Code field in DocType 'Notification'
|
||||
#: email/doctype/notification/notification.json
|
||||
msgctxt "Notification"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text Editor field in DocType 'Notification Log'
|
||||
#: desk/doctype/notification_log/notification_log.json
|
||||
msgctxt "Notification Log"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Small Text field in DocType 'SMS Log'
|
||||
#: core/doctype/sms_log/sms_log.json
|
||||
msgctxt "SMS Log"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Data field in DocType 'Success Action'
|
||||
#: core/doctype/success_action/success_action.json
|
||||
msgctxt "Success Action"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a Text field in DocType 'Workflow Document State'
|
||||
#: workflow/doctype/workflow_document_state/workflow_document_state.json
|
||||
msgctxt "Workflow Document State"
|
||||
msgid "Message"
|
||||
msgstr "Botschaft"
|
||||
msgstr "Nachricht"
|
||||
|
||||
#. Label of a HTML Editor field in DocType 'Newsletter'
|
||||
#: email/doctype/newsletter/newsletter.json
|
||||
|
|
@ -19471,13 +19471,13 @@ msgstr "Mitteilungsbeispiele"
|
|||
#: core/doctype/communication/communication.json
|
||||
msgctxt "Communication"
|
||||
msgid "Message ID"
|
||||
msgstr "Message-ID"
|
||||
msgstr "Nachrichten-ID"
|
||||
|
||||
#. Label of a Small Text field in DocType 'Email Queue'
|
||||
#: email/doctype/email_queue/email_queue.json
|
||||
msgctxt "Email Queue"
|
||||
msgid "Message ID"
|
||||
msgstr "Message-ID"
|
||||
msgstr "Nachrichten-ID"
|
||||
|
||||
#. Label of a Data field in DocType 'SMS Settings'
|
||||
#: core/doctype/sms_settings/sms_settings.json
|
||||
|
|
@ -19513,7 +19513,7 @@ msgstr "Nachricht, die nach erfolgreichem Abschluss angezeigt werden soll"
|
|||
#: email/doctype/unhandled_email/unhandled_email.json
|
||||
msgctxt "Unhandled Email"
|
||||
msgid "Message-id"
|
||||
msgstr "Nachrichten ID"
|
||||
msgstr "Nachrichten-ID"
|
||||
|
||||
#. Label of a Code field in DocType 'Data Import Log'
|
||||
#: core/doctype/data_import_log/data_import_log.json
|
||||
|
|
@ -21271,12 +21271,12 @@ msgstr "Nein {0} mail"
|
|||
|
||||
#: public/js/form_builder/utils.js:117
|
||||
msgid "No."
|
||||
msgstr "Nein."
|
||||
msgstr "Nr."
|
||||
|
||||
#: public/js/frappe/form/grid_row.js:252
|
||||
msgctxt "Title of the 'row number' column"
|
||||
msgid "No."
|
||||
msgstr "Nein."
|
||||
msgstr "Nr."
|
||||
|
||||
#. Label of a Check field in DocType 'Custom Field'
|
||||
#: custom/doctype/custom_field/custom_field.json
|
||||
|
|
@ -36633,7 +36633,7 @@ msgstr "Ja"
|
|||
#: public/js/frappe/utils/user.js:33
|
||||
msgctxt "Name of the current user. For example: You edited this 5 hours ago."
|
||||
msgid "You"
|
||||
msgstr "Benutzer"
|
||||
msgstr "Sie"
|
||||
|
||||
#: public/js/frappe/form/footer/form_timeline.js:462
|
||||
msgid "You Liked"
|
||||
|
|
@ -37448,7 +37448,7 @@ msgstr "Kommentar"
|
|||
|
||||
#: public/js/frappe/form/templates/timeline_message_box.html:33
|
||||
msgid "commented"
|
||||
msgstr "kommentierte"
|
||||
msgstr "kommentierte(n)"
|
||||
|
||||
#. Option for the 'Permission Type' (Select) field in DocType 'Permission
|
||||
#. Inspector'
|
||||
|
|
@ -39080,7 +39080,7 @@ msgstr "{0} d"
|
|||
|
||||
#: public/js/frappe/utils/pretty_date.js:60
|
||||
msgid "{0} days ago"
|
||||
msgstr "vor {0} Tag(en)"
|
||||
msgstr "vor {0} Tagen"
|
||||
|
||||
#: website/doctype/website_settings/website_settings.py:96
|
||||
#: website/doctype/website_settings/website_settings.py:116
|
||||
|
|
@ -39325,11 +39325,11 @@ msgstr "{0} hat dich in einem Kommentar in {1} {2} erwähnt"
|
|||
|
||||
#: public/js/frappe/utils/pretty_date.js:50
|
||||
msgid "{0} minutes ago"
|
||||
msgstr "vor {0} Minute(n)"
|
||||
msgstr "vor {0} Minuten"
|
||||
|
||||
#: public/js/frappe/utils/pretty_date.js:68
|
||||
msgid "{0} months ago"
|
||||
msgstr "vor {0} Monate(n)"
|
||||
msgstr "vor {0} Monaten"
|
||||
|
||||
#: model/document.py:1594
|
||||
msgid "{0} must be after {1}"
|
||||
|
|
@ -39508,7 +39508,7 @@ msgstr "{0} W"
|
|||
|
||||
#: public/js/frappe/utils/pretty_date.js:64
|
||||
msgid "{0} weeks ago"
|
||||
msgstr "vor {0} Woche(n)"
|
||||
msgstr "vor {0} Wochen"
|
||||
|
||||
#: public/js/frappe/utils/pretty_date.js:39
|
||||
msgid "{0} y"
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ msgstr ""
|
|||
"Project-Id-Version: frappe\n"
|
||||
"Report-Msgid-Bugs-To: developers@frappe.io\n"
|
||||
"POT-Creation-Date: 2024-03-17 09:33+0000\n"
|
||||
"PO-Revision-Date: 2024-03-18 10:48\n"
|
||||
"PO-Revision-Date: 2024-03-20 11:37\n"
|
||||
"Last-Translator: developers@frappe.io\n"
|
||||
"Language-Team: Spanish\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
|
|
@ -1091,7 +1091,7 @@ msgstr "Acción Fallida"
|
|||
#: desk/doctype/onboarding_step/onboarding_step.json
|
||||
msgctxt "Onboarding Step"
|
||||
msgid "Action Label"
|
||||
msgstr ""
|
||||
msgstr "Etiqueta de Acción"
|
||||
|
||||
#. Label of a Int field in DocType 'Success Action'
|
||||
#: core/doctype/success_action/success_action.json
|
||||
|
|
@ -1392,16 +1392,16 @@ msgstr "Añadir Suscriptores"
|
|||
|
||||
#: public/js/frappe/list/bulk_operations.js:395
|
||||
msgid "Add Tags"
|
||||
msgstr ""
|
||||
msgstr "Añadir etiquetas"
|
||||
|
||||
#: public/js/frappe/list/list_view.js:1897
|
||||
msgctxt "Button in list view actions menu"
|
||||
msgid "Add Tags"
|
||||
msgstr ""
|
||||
msgstr "Añadir etiquetas"
|
||||
|
||||
#: public/js/frappe/views/communication.js:399
|
||||
msgid "Add Template"
|
||||
msgstr ""
|
||||
msgstr "Añadir plantilla"
|
||||
|
||||
#. Label of a Check field in DocType 'Report'
|
||||
#: core/doctype/report/report.json
|
||||
|
|
@ -1758,7 +1758,7 @@ msgstr "Alertas y Notificaciones"
|
|||
#: printing/doctype/letter_head/letter_head.json
|
||||
msgctxt "Letter Head"
|
||||
msgid "Align"
|
||||
msgstr ""
|
||||
msgstr "Alinear"
|
||||
|
||||
#. Label of a Check field in DocType 'Print Format'
|
||||
#: printing/doctype/print_format/print_format.json
|
||||
|
|
@ -2206,7 +2206,7 @@ msgstr "Permitido"
|
|||
#: core/doctype/system_settings/system_settings.json
|
||||
msgctxt "System Settings"
|
||||
msgid "Allowed File Extensions"
|
||||
msgstr ""
|
||||
msgstr "Extensiones de Archivos permitidas"
|
||||
|
||||
#. Label of a Check field in DocType 'User'
|
||||
#: core/doctype/user/user.json
|
||||
|
|
@ -3387,25 +3387,25 @@ msgstr ""
|
|||
#: custom/doctype/custom_field/custom_field.json
|
||||
msgctxt "Custom Field"
|
||||
msgid "Autocomplete"
|
||||
msgstr ""
|
||||
msgstr "Autocompletar"
|
||||
|
||||
#. Option for the 'Type' (Select) field in DocType 'Customize Form Field'
|
||||
#: custom/doctype/customize_form_field/customize_form_field.json
|
||||
msgctxt "Customize Form Field"
|
||||
msgid "Autocomplete"
|
||||
msgstr ""
|
||||
msgstr "Autocompletar"
|
||||
|
||||
#. Option for the 'Type' (Select) field in DocType 'DocField'
|
||||
#: core/doctype/docfield/docfield.json
|
||||
msgctxt "DocField"
|
||||
msgid "Autocomplete"
|
||||
msgstr ""
|
||||
msgstr "Autocompletar"
|
||||
|
||||
#. Option for the 'Naming Rule' (Select) field in DocType 'DocType'
|
||||
#: core/doctype/doctype/doctype.json
|
||||
msgctxt "DocType"
|
||||
msgid "Autoincrement"
|
||||
msgstr ""
|
||||
msgstr "Autoincremento"
|
||||
|
||||
#. Option for the 'Communication Type' (Select) field in DocType
|
||||
#. 'Communication'
|
||||
|
|
@ -4442,7 +4442,7 @@ msgstr "CC"
|
|||
#: core/doctype/recorder/recorder.json
|
||||
msgctxt "Recorder"
|
||||
msgid "CMD"
|
||||
msgstr ""
|
||||
msgstr "CMD"
|
||||
|
||||
#: public/js/frappe/color_picker/color_picker.js:20
|
||||
msgid "COLOR PICKER"
|
||||
|
|
@ -4797,15 +4797,15 @@ msgstr "No se puede cancelar antes de enviar. Ver transmisión {0}"
|
|||
|
||||
#: public/js/frappe/list/bulk_operations.js:264
|
||||
msgid "Cannot cancel {0}."
|
||||
msgstr ""
|
||||
msgstr "No se puede cancelar {0}."
|
||||
|
||||
#: model/document.py:848
|
||||
msgid "Cannot change docstatus from 0 (Draft) to 2 (Cancelled)"
|
||||
msgstr ""
|
||||
msgstr "No se puede cambiar el estado del documento de 0 (Borrador) a 2 (Cancelado)"
|
||||
|
||||
#: model/document.py:862
|
||||
msgid "Cannot change docstatus from 1 (Submitted) to 0 (Draft)"
|
||||
msgstr ""
|
||||
msgstr "No se puede cambiar el estado del documento de 1 (Enviado) a 0 (Borrador)"
|
||||
|
||||
#: public/js/workflow_builder/utils.js:170
|
||||
msgid "Cannot change state of Cancelled Document <b>({0} State)</b>"
|
||||
|
|
@ -4873,7 +4873,7 @@ msgstr "No se puede eliminar {0}, ya que contiene sub-grupos"
|
|||
|
||||
#: desk/doctype/dashboard/dashboard.py:48
|
||||
msgid "Cannot edit Standard Dashboards"
|
||||
msgstr ""
|
||||
msgstr "No se pueden editar los Tableros estándar"
|
||||
|
||||
#: email/doctype/notification/notification.py:121
|
||||
msgid "Cannot edit Standard Notification. To edit, please disable this and duplicate it"
|
||||
|
|
@ -4949,7 +4949,7 @@ msgstr ""
|
|||
|
||||
#: public/js/frappe/list/bulk_operations.js:261
|
||||
msgid "Cannot submit {0}."
|
||||
msgstr ""
|
||||
msgstr "No se puede enviar {0}."
|
||||
|
||||
#: desk/doctype/workspace/workspace.py:345
|
||||
msgid "Cannot update private workspace of other users"
|
||||
|
|
@ -5187,7 +5187,7 @@ msgstr "Gráficos"
|
|||
#: core/doctype/communication/communication.json
|
||||
msgctxt "Communication"
|
||||
msgid "Chat"
|
||||
msgstr ""
|
||||
msgstr "Chat"
|
||||
|
||||
#. Option for the 'Field Type' (Select) field in DocType 'Custom Field'
|
||||
#: custom/doctype/custom_field/custom_field.json
|
||||
|
|
@ -5237,7 +5237,7 @@ msgstr "Verificar URL de Solicitud"
|
|||
|
||||
#: email/doctype/newsletter/newsletter.js:18
|
||||
msgid "Check broken links"
|
||||
msgstr ""
|
||||
msgstr "Comprobar enlaces rotos"
|
||||
|
||||
#: printing/page/print_format_builder/print_format_builder_column_selector.html:1
|
||||
msgid "Check columns to select, drag to set order."
|
||||
|
|
@ -5260,7 +5260,7 @@ msgstr "Seleccione esta opción si desea obligar al usuario a seleccionar una se
|
|||
|
||||
#: email/doctype/newsletter/newsletter.js:20
|
||||
msgid "Checking broken links..."
|
||||
msgstr ""
|
||||
msgstr "Comprobando enlaces rotos..."
|
||||
|
||||
#: public/js/frappe/desk.js:214
|
||||
msgid "Checking one moment"
|
||||
|
|
@ -5325,11 +5325,11 @@ msgstr ""
|
|||
|
||||
#: public/js/frappe/form/controls/color.js:5
|
||||
msgid "Choose a color"
|
||||
msgstr ""
|
||||
msgstr "Elegir color"
|
||||
|
||||
#: public/js/frappe/form/controls/icon.js:5
|
||||
msgid "Choose an icon"
|
||||
msgstr ""
|
||||
msgstr "Elegir icono"
|
||||
|
||||
#. Description of the 'Two Factor Authentication method' (Select) field in
|
||||
#. DocType 'System Settings'
|
||||
|
|
@ -5461,7 +5461,7 @@ msgstr "Haga clic para establecer Filtros Dinámicos"
|
|||
#: desk/doctype/number_card/number_card.js:270
|
||||
#: website/doctype/web_form/web_form.js:252
|
||||
msgid "Click to Set Filters"
|
||||
msgstr ""
|
||||
msgstr "Clic para establecer filtros"
|
||||
|
||||
#: public/js/frappe/list/list_view.js:678
|
||||
msgid "Click to sort by {0}"
|
||||
|
|
@ -6395,25 +6395,25 @@ msgstr "Conexión perdida. Algunas características pueden no funcionar."
|
|||
|
||||
#: public/js/frappe/form/dashboard.js:54
|
||||
msgid "Connections"
|
||||
msgstr ""
|
||||
msgstr "Conexiones"
|
||||
|
||||
#. Label of a Tab Break field in DocType 'DocType'
|
||||
#: core/doctype/doctype/doctype.json
|
||||
msgctxt "DocType"
|
||||
msgid "Connections"
|
||||
msgstr ""
|
||||
msgstr "Conexiones"
|
||||
|
||||
#. Label of a Tab Break field in DocType 'Module Def'
|
||||
#: core/doctype/module_def/module_def.json
|
||||
msgctxt "Module Def"
|
||||
msgid "Connections"
|
||||
msgstr ""
|
||||
msgstr "Conexiones"
|
||||
|
||||
#. Label of a Tab Break field in DocType 'User'
|
||||
#: core/doctype/user/user.json
|
||||
msgctxt "User"
|
||||
msgid "Connections"
|
||||
msgstr ""
|
||||
msgstr "Conexiones"
|
||||
|
||||
#. Label of a Code field in DocType 'System Console'
|
||||
#: desk/doctype/system_console/system_console.json
|
||||
|
|
@ -6838,7 +6838,7 @@ msgstr "Crear contactos a partir de correos electrónicos entrantes"
|
|||
#. Title of an Onboarding Step
|
||||
#: custom/onboarding_step/custom_field/custom_field.json
|
||||
msgid "Create Custom Fields"
|
||||
msgstr ""
|
||||
msgstr "Crear Campos Personalizados"
|
||||
|
||||
#: public/js/frappe/views/workspace/workspace.js:931
|
||||
msgid "Create Duplicate"
|
||||
|
|
@ -6947,7 +6947,7 @@ msgstr "Creado"
|
|||
#: core/doctype/submission_queue/submission_queue.json
|
||||
msgctxt "Submission Queue"
|
||||
msgid "Created At"
|
||||
msgstr ""
|
||||
msgstr "Creado el"
|
||||
|
||||
#: model/meta.py:51 public/js/frappe/list/list_sidebar_group_by.js:73
|
||||
#: public/js/frappe/model/meta.js:203 public/js/frappe/model/model.js:113
|
||||
|
|
@ -7196,14 +7196,14 @@ msgstr "URL Base Personalizada"
|
|||
#: desk/doctype/workspace_custom_block/workspace_custom_block.json
|
||||
msgctxt "Workspace Custom Block"
|
||||
msgid "Custom Block Name"
|
||||
msgstr ""
|
||||
msgstr "Nombre de bloque personalizado"
|
||||
|
||||
#. Label of a Tab Break field in DocType 'Workspace'
|
||||
#. Label of a Table field in DocType 'Workspace'
|
||||
#: desk/doctype/workspace/workspace.json
|
||||
msgctxt "Workspace"
|
||||
msgid "Custom Blocks"
|
||||
msgstr ""
|
||||
msgstr "Bloques personalizados"
|
||||
|
||||
#. Label of a Code field in DocType 'Print Format'
|
||||
#: printing/doctype/print_format/print_format.json
|
||||
|
|
@ -7317,7 +7317,7 @@ msgstr "HTML Personalizado"
|
|||
#. Name of a DocType
|
||||
#: desk/doctype/custom_html_block/custom_html_block.json
|
||||
msgid "Custom HTML Block"
|
||||
msgstr ""
|
||||
msgstr "Bloque HTML personalizado"
|
||||
|
||||
#. Label of a HTML field in DocType 'Print Format'
|
||||
#: printing/doctype/print_format/print_format.json
|
||||
|
|
@ -7390,7 +7390,7 @@ msgstr "Menú Lateral Personalizado"
|
|||
#: core/workspace/build/build.json
|
||||
msgctxt "Translation"
|
||||
msgid "Custom Translation"
|
||||
msgstr ""
|
||||
msgstr "Traducción personalizada"
|
||||
|
||||
#: custom/doctype/custom_field/custom_field.py:373
|
||||
msgid "Custom field renamed to {0} successfully."
|
||||
|
|
@ -7472,7 +7472,7 @@ msgstr ""
|
|||
|
||||
#: public/js/frappe/views/dashboard/dashboard_view.js:37
|
||||
msgid "Customize Dashboard"
|
||||
msgstr ""
|
||||
msgstr "Personalizar el Tablero"
|
||||
|
||||
#. Name of a DocType
|
||||
#: automation/doctype/auto_repeat/auto_repeat.js:33
|
||||
|
|
@ -8180,14 +8180,14 @@ msgstr "Encabezado Predeterminado"
|
|||
#: core/doctype/amended_document_naming_settings/amended_document_naming_settings.json
|
||||
msgctxt "Amended Document Naming Settings"
|
||||
msgid "Default Naming"
|
||||
msgstr ""
|
||||
msgstr "Nomenclatura por defecto"
|
||||
|
||||
#. Option for the 'Default Amendment Naming' (Select) field in DocType
|
||||
#. 'Document Naming Settings'
|
||||
#: core/doctype/document_naming_settings/document_naming_settings.json
|
||||
msgctxt "Document Naming Settings"
|
||||
msgid "Default Naming"
|
||||
msgstr ""
|
||||
msgstr "Nomenclatura por defecto"
|
||||
|
||||
#: email/doctype/email_account/email_account.py:209
|
||||
msgid "Default Outgoing"
|
||||
|
|
@ -8293,13 +8293,13 @@ msgstr "Valor predeterminado"
|
|||
#: custom/doctype/customize_form/customize_form.json
|
||||
msgctxt "Customize Form"
|
||||
msgid "Default View"
|
||||
msgstr ""
|
||||
msgstr "Vista predeterminada"
|
||||
|
||||
#. Label of a Select field in DocType 'DocType'
|
||||
#: core/doctype/doctype/doctype.json
|
||||
msgctxt "DocType"
|
||||
msgid "Default View"
|
||||
msgstr ""
|
||||
msgstr "Vista predeterminada"
|
||||
|
||||
#: core/doctype/doctype/doctype.py:1325
|
||||
msgid "Default for 'Check' type of field {0} must be either '0' or '1'"
|
||||
|
|
@ -8506,13 +8506,13 @@ msgstr "Estado del envío"
|
|||
|
||||
#: templates/includes/oauth_confirmation.html:14
|
||||
msgid "Deny"
|
||||
msgstr ""
|
||||
msgstr "Denegar"
|
||||
|
||||
#. Option for the 'Sign ups' (Select) field in DocType 'Social Login Key'
|
||||
#: integrations/doctype/social_login_key/social_login_key.json
|
||||
msgctxt "Social Login Key"
|
||||
msgid "Deny"
|
||||
msgstr ""
|
||||
msgstr "Denegar"
|
||||
|
||||
#. Label of a Data field in DocType 'Contact'
|
||||
#: contacts/doctype/contact/contact.json
|
||||
|
|
@ -8800,7 +8800,7 @@ msgstr "Deshabilitar la notificación del Registro de Cambios"
|
|||
#: desk/doctype/list_view_settings/list_view_settings.json
|
||||
msgctxt "List View Settings"
|
||||
msgid "Disable Comment Count"
|
||||
msgstr ""
|
||||
msgstr "Desactivar recuento de comentarios"
|
||||
|
||||
#. Label of a Check field in DocType 'Blog Post'
|
||||
#: website/doctype/blog_post/blog_post.json
|
||||
|
|
@ -9013,7 +9013,7 @@ msgstr "Mostrar Depende de"
|
|||
#: core/doctype/docfield/docfield.json
|
||||
msgctxt "DocField"
|
||||
msgid "Display Depends On (JS)"
|
||||
msgstr ""
|
||||
msgstr "La visualización depende de (JS)"
|
||||
|
||||
#. Label of a Check field in DocType 'LDAP Settings'
|
||||
#: integrations/doctype/ldap_settings/ldap_settings.json
|
||||
|
|
@ -10011,7 +10011,7 @@ msgstr "Duplicar"
|
|||
|
||||
#: printing/doctype/print_format_field_template/print_format_field_template.py:53
|
||||
msgid "Duplicate Entry"
|
||||
msgstr ""
|
||||
msgstr "Entrada duplicada"
|
||||
|
||||
#: public/js/frappe/list/list_filter.js:137
|
||||
msgid "Duplicate Filter Name"
|
||||
|
|
@ -10028,7 +10028,7 @@ msgstr "Duplicar Área de Trabajo"
|
|||
|
||||
#: public/js/frappe/form/form.js:208
|
||||
msgid "Duplicate current row"
|
||||
msgstr ""
|
||||
msgstr "Duplicar fila actual"
|
||||
|
||||
#: public/js/frappe/views/workspace/workspace.js:996
|
||||
msgid "Duplicate of {0} named as {1} is created successfully"
|
||||
|
|
@ -10242,7 +10242,7 @@ msgstr "Editar formato"
|
|||
|
||||
#: public/js/frappe/form/quick_entry.js:280
|
||||
msgid "Edit Full Form"
|
||||
msgstr ""
|
||||
msgstr "Editar formulario completo"
|
||||
|
||||
#: printing/page/print_format_builder/print_format_builder_field.html:26
|
||||
msgid "Edit HTML"
|
||||
|
|
@ -10313,7 +10313,7 @@ msgstr "Editar Área de Trabajo"
|
|||
|
||||
#: desk/doctype/note/note.js:11
|
||||
msgid "Edit mode"
|
||||
msgstr ""
|
||||
msgstr "Modo edición"
|
||||
|
||||
#: printing/page/print_format_builder/print_format_builder.js:713
|
||||
msgid "Edit to add content"
|
||||
|
|
@ -10700,7 +10700,7 @@ msgstr "Correo Electrónico Enviado"
|
|||
#: email/doctype/newsletter/newsletter.json
|
||||
msgctxt "Newsletter"
|
||||
msgid "Email Sent At"
|
||||
msgstr ""
|
||||
msgstr "Correo enviado el"
|
||||
|
||||
#. Label of a Section Break field in DocType 'Auto Email Report'
|
||||
#: email/doctype/auto_email_report/auto_email_report.json
|
||||
|
|
@ -10879,7 +10879,7 @@ msgstr "Habilite la API de Google en la configuración de Google."
|
|||
#: website/doctype/website_settings/website_settings.json
|
||||
msgctxt "Website Settings"
|
||||
msgid "Enable Google indexing"
|
||||
msgstr ""
|
||||
msgstr "Habilitar la indexación de Google"
|
||||
|
||||
#: email/doctype/email_account/email_account.py:202
|
||||
msgid "Enable Incoming"
|
||||
|
|
@ -11128,14 +11128,14 @@ msgstr "Ejecución programada habilitada para la secuencia de comandos {0}"
|
|||
#: custom/doctype/customize_form/customize_form.json
|
||||
msgctxt "Customize Form"
|
||||
msgid "Enables Calendar and Gantt views."
|
||||
msgstr ""
|
||||
msgstr "Habilita las vistas Calendario y Gantt."
|
||||
|
||||
#. Description of the 'Is Calendar and Gantt' (Check) field in DocType
|
||||
#. 'DocType'
|
||||
#: core/doctype/doctype/doctype.json
|
||||
msgctxt "DocType"
|
||||
msgid "Enables Calendar and Gantt views."
|
||||
msgstr ""
|
||||
msgstr "Habilita las vistas Calendario y Gantt."
|
||||
|
||||
#: email/doctype/email_account/email_account.js:232
|
||||
msgid "Enabling auto reply on an incoming email account will send automated replies to all the synchronized emails. Do you wish to continue?"
|
||||
|
|
@ -11374,61 +11374,61 @@ msgstr "Iguales"
|
|||
#: desk/page/backups/backups.js:35 model/base_document.py:723
|
||||
#: model/base_document.py:729 public/js/frappe/ui/messages.js:22
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Option for the 'Delivery Status' (Select) field in DocType 'Communication'
|
||||
#: core/doctype/communication/communication.json
|
||||
msgctxt "Communication"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Option for the 'Status' (Select) field in DocType 'Data Import'
|
||||
#: core/doctype/data_import/data_import.json
|
||||
msgctxt "Data Import"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Option for the 'Status' (Select) field in DocType 'Email Queue'
|
||||
#. Label of a Code field in DocType 'Email Queue'
|
||||
#: email/doctype/email_queue/email_queue.json
|
||||
msgctxt "Email Queue"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Label of a Code field in DocType 'Email Queue Recipient'
|
||||
#: email/doctype/email_queue_recipient/email_queue_recipient.json
|
||||
msgctxt "Email Queue Recipient"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Label of a Code field in DocType 'Error Log'
|
||||
#: core/doctype/error_log/error_log.json
|
||||
msgctxt "Error Log"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Label of a Code field in DocType 'Integration Request'
|
||||
#: integrations/doctype/integration_request/integration_request.json
|
||||
msgctxt "Integration Request"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Option for the 'Status' (Select) field in DocType 'Prepared Report'
|
||||
#: core/doctype/prepared_report/prepared_report.json
|
||||
msgctxt "Prepared Report"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#: public/js/frappe/web_form/web_form.js:240
|
||||
msgctxt "Title of error message in web form"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#. Label of a Text field in DocType 'Webhook Request Log'
|
||||
#: integrations/doctype/webhook_request_log/webhook_request_log.json
|
||||
msgctxt "Webhook Request Log"
|
||||
msgid "Error"
|
||||
msgstr ""
|
||||
msgstr "Error"
|
||||
|
||||
#: www/error.html:34
|
||||
msgid "Error Code: {0}"
|
||||
|
|
@ -11443,7 +11443,7 @@ msgstr "Registro de Errores"
|
|||
#: core/workspace/build/build.json
|
||||
msgctxt "Error Log"
|
||||
msgid "Error Logs"
|
||||
msgstr ""
|
||||
msgstr "Registros de errores"
|
||||
|
||||
#. Label of a Text field in DocType 'Prepared Report'
|
||||
#: core/doctype/prepared_report/prepared_report.json
|
||||
|
|
@ -11457,11 +11457,11 @@ msgstr "Error al conectarse a la aplicación QZ Tray...<br><br> Debe tener la ap
|
|||
|
||||
#: email/doctype/email_domain/email_domain.py:32
|
||||
msgid "Error connecting via IMAP/POP3: {e}"
|
||||
msgstr ""
|
||||
msgstr "Error al conectar vía IMAP/POP3: {e}"
|
||||
|
||||
#: email/doctype/email_domain/email_domain.py:33
|
||||
msgid "Error connecting via SMTP: {e}"
|
||||
msgstr ""
|
||||
msgstr "Error de conexión vía SMTP: {e}"
|
||||
|
||||
#: email/doctype/email_domain/email_domain.py:100
|
||||
msgid "Error has occurred in {0}"
|
||||
|
|
@ -11648,7 +11648,7 @@ msgstr "Excel"
|
|||
|
||||
#: public/js/frappe/form/controls/password.js:91
|
||||
msgid "Excellent"
|
||||
msgstr ""
|
||||
msgstr "Excelente"
|
||||
|
||||
#. Label of a Text field in DocType 'Data Import Log'
|
||||
#: core/doctype/data_import_log/data_import_log.json
|
||||
|
|
@ -13265,7 +13265,7 @@ msgstr "Forzar al usuario a restablecer la contraseña"
|
|||
#: core/doctype/system_settings/system_settings.json
|
||||
msgctxt "System Settings"
|
||||
msgid "Force Web Capture Mode for Uploads"
|
||||
msgstr ""
|
||||
msgstr "Forzar el modo de captura web para las cargas"
|
||||
|
||||
#: www/login.html:35
|
||||
msgid "Forgot Password?"
|
||||
|
|
@ -13844,7 +13844,7 @@ msgstr "Regresa"
|
|||
|
||||
#: desk/doctype/notification_settings/notification_settings.js:17
|
||||
msgid "Go to Notification Settings List"
|
||||
msgstr ""
|
||||
msgstr "Ir a la Lista de Ajustes de Notificaciones"
|
||||
|
||||
#. Option for the 'Action' (Select) field in DocType 'Onboarding Step'
|
||||
#: desk/doctype/onboarding_step/onboarding_step.json
|
||||
|
|
@ -18704,7 +18704,7 @@ msgstr ""
|
|||
|
||||
#: public/js/frappe/ui/notifications/notifications.js:308
|
||||
msgid "Looks like you haven’t received any notifications."
|
||||
msgstr ""
|
||||
msgstr "Parece que no has recibido ninguna notificación."
|
||||
|
||||
#: public/js/frappe/form/sidebar/assign_to.js:190
|
||||
msgid "Low"
|
||||
|
|
@ -20832,7 +20832,7 @@ msgstr "Sin nombre especificado para {0}"
|
|||
|
||||
#: public/js/frappe/ui/notifications/notifications.js:308
|
||||
msgid "No New notifications"
|
||||
msgstr ""
|
||||
msgstr "No hay nuevas notificaciones"
|
||||
|
||||
#: core/doctype/doctype/doctype.py:1682
|
||||
msgid "No Permissions Specified"
|
||||
|
|
@ -21000,7 +21000,7 @@ msgstr "No hay nuevos contactos de Google sincronizados."
|
|||
|
||||
#: public/js/frappe/ui/toolbar/navbar.html:46
|
||||
msgid "No new notifications"
|
||||
msgstr ""
|
||||
msgstr "No hay nuevas notificaciones"
|
||||
|
||||
#: printing/page/print_format_builder/print_format_builder.js:415
|
||||
msgid "No of Columns"
|
||||
|
|
@ -26559,7 +26559,7 @@ msgstr "Restablecer gráfico"
|
|||
|
||||
#: public/js/frappe/views/dashboard/dashboard_view.js:38
|
||||
msgid "Reset Dashboard Customizations"
|
||||
msgstr ""
|
||||
msgstr "Restablecer personalizaciones del Tablero"
|
||||
|
||||
#: public/js/frappe/list/list_settings.js:227
|
||||
msgid "Reset Fields"
|
||||
|
|
@ -26598,7 +26598,7 @@ msgstr ""
|
|||
#: core/doctype/system_settings/system_settings.json
|
||||
msgctxt "System Settings"
|
||||
msgid "Reset Password Template"
|
||||
msgstr ""
|
||||
msgstr "Plantilla para Restablecer Contraseña"
|
||||
|
||||
#: core/page/permission_manager/permission_manager.js:109
|
||||
msgid "Reset Permissions for {0}?"
|
||||
|
|
@ -27688,7 +27688,7 @@ msgstr "Guardar como"
|
|||
|
||||
#: public/js/frappe/views/dashboard/dashboard_view.js:62
|
||||
msgid "Save Customizations"
|
||||
msgstr ""
|
||||
msgstr "Guardar Personalización"
|
||||
|
||||
#: public/js/frappe/list/list_sidebar.html:73
|
||||
msgid "Save Filter"
|
||||
|
|
@ -29067,7 +29067,7 @@ msgstr "Sesión expirada"
|
|||
#: core/doctype/system_settings/system_settings.json
|
||||
msgctxt "System Settings"
|
||||
msgid "Session Expiry (idle timeout)"
|
||||
msgstr ""
|
||||
msgstr "Expiración de la sesión (tiempo de inactivad)"
|
||||
|
||||
#: core/doctype/system_settings/system_settings.py:111
|
||||
msgid "Session Expiry must be in format {0}"
|
||||
|
|
|
|||
|
|
@ -44,7 +44,6 @@ FIELD_COMMA_PATTERN = re.compile(r"[0-9a-zA-Z]+\s*,")
|
|||
STRICT_FIELD_PATTERN = re.compile(r".*/\*.*")
|
||||
STRICT_UNION_PATTERN = re.compile(r".*\s(union).*\s")
|
||||
ORDER_GROUP_PATTERN = re.compile(r".*[^a-z0-9-_ ,`'\"\.\(\)].*")
|
||||
FN_PARAMS_PATTERN = re.compile(r".*?\((.*)\).*")
|
||||
SPECIAL_FIELD_CHARS = frozenset(("(", "`", ".", "'", '"', "*"))
|
||||
|
||||
|
||||
|
|
@ -619,6 +618,8 @@ class DatabaseQuery:
|
|||
- Query: fields=["*"]
|
||||
- Result: fields=["title", ...] // will also include Frappe's meta field like `name`, `owner`, etc.
|
||||
"""
|
||||
from frappe.desk.reportview import extract_fieldnames
|
||||
|
||||
if self.flags.ignore_permissions:
|
||||
return
|
||||
|
||||
|
|
@ -631,23 +632,18 @@ class DatabaseQuery:
|
|||
)
|
||||
|
||||
for i, field in enumerate(self.fields):
|
||||
if "distinct" in field.lower():
|
||||
# field: 'count(distinct `tabPhoto`.name) as total_count'
|
||||
# column: 'tabPhoto.name'
|
||||
if _fn := FN_PARAMS_PATTERN.findall(field):
|
||||
column = _fn[0].replace("distinct ", "").replace("DISTINCT ", "").replace("`", "")
|
||||
# field: 'distinct name'
|
||||
# column: 'name'
|
||||
else:
|
||||
column = field.split(" ", 2)[1].replace("`", "")
|
||||
else:
|
||||
# field: 'count(`tabPhoto`.name) as total_count'
|
||||
# column: 'tabPhoto.name'
|
||||
column = field.split("(")[-1].split(")", 1)[0]
|
||||
column = strip_alias(column).replace("`", "")
|
||||
# field: 'count(distinct `tabPhoto`.name) as total_count'
|
||||
# column: 'tabPhoto.name'
|
||||
# field: 'count(`tabPhoto`.name) as total_count'
|
||||
# column: 'tabPhoto.name'
|
||||
columns = extract_fieldnames(field)
|
||||
if not columns:
|
||||
continue
|
||||
|
||||
if column == "*" and not in_function("*", field):
|
||||
asterisk_fields.append(i)
|
||||
column = columns[0]
|
||||
if column == "*" and "*" in field:
|
||||
if not in_function("*", field):
|
||||
asterisk_fields.append(i)
|
||||
continue
|
||||
|
||||
# handle pseudo columns
|
||||
|
|
@ -686,21 +682,12 @@ class DatabaseQuery:
|
|||
elif "(" in field:
|
||||
if "*" in field:
|
||||
continue
|
||||
elif _params := FN_PARAMS_PATTERN.findall(field):
|
||||
params = (x.strip() for x in _params[0].split(","))
|
||||
for param in params:
|
||||
if not (
|
||||
not param
|
||||
or param in permitted_fields
|
||||
or param.isnumeric()
|
||||
or "'" in param
|
||||
or '"' in param
|
||||
):
|
||||
else:
|
||||
for column in columns:
|
||||
if column not in permitted_fields:
|
||||
self.remove_field(i)
|
||||
break
|
||||
continue
|
||||
self.remove_field(i)
|
||||
|
||||
# remove if access not allowed
|
||||
else:
|
||||
self.remove_field(i)
|
||||
|
|
|
|||
|
|
@ -351,7 +351,12 @@ frappe.views.Workspace = class Workspace {
|
|||
get_page_to_show() {
|
||||
let default_page;
|
||||
|
||||
if (
|
||||
if (frappe.boot.user.default_workspace) {
|
||||
default_page = {
|
||||
name: frappe.boot.user.default_workspace.name,
|
||||
public: frappe.boot.user.default_workspace.public,
|
||||
};
|
||||
} else if (
|
||||
localStorage.current_page &&
|
||||
this.all_pages.filter((page) => page.title == localStorage.current_page).length != 0
|
||||
) {
|
||||
|
|
|
|||
|
|
@ -1173,6 +1173,11 @@ class TestDBQuery(FrappeTestCase):
|
|||
data = get()
|
||||
self.assertEqual(len(data["values"]), 1)
|
||||
|
||||
def test_select_star_expansion(self):
|
||||
count = frappe.get_list("Language", ["SUM(1)", "COUNT(*)"], as_list=1, order_by=None)[0]
|
||||
self.assertEqual(count[0], frappe.db.count("Language"))
|
||||
self.assertEqual(count[1], frappe.db.count("Language"))
|
||||
|
||||
|
||||
class TestReportView(FrappeTestCase):
|
||||
@run_only_if(db_type_is.MARIADB) # TODO: postgres name casting is messed up
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
# License: MIT. See LICENSE
|
||||
|
||||
import frappe
|
||||
from frappe.desk.reportview import export_query
|
||||
from frappe.desk.reportview import export_query, extract_fieldnames
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
|
||||
|
||||
|
|
@ -32,3 +32,58 @@ class TestReportview(FrappeTestCase):
|
|||
for row in reader:
|
||||
self.assertEqual(int(row["Is Single"]), 1)
|
||||
self.assertEqual(row["Module"], "Core")
|
||||
|
||||
def test_extract_fieldname(self):
|
||||
self.assertEqual(
|
||||
extract_fieldnames("count(distinct `tabPhoto`.name) as total_count")[0], "tabPhoto.name"
|
||||
)
|
||||
|
||||
self.assertEqual(extract_fieldnames("owner")[0], "owner")
|
||||
self.assertEqual(extract_fieldnames("from")[0], "from")
|
||||
|
||||
self.assertEqual(extract_fieldnames("module")[0], "module")
|
||||
|
||||
self.assertEqual(extract_fieldnames("count(`tabPhoto`.name) as total_count")[0], "tabPhoto.name")
|
||||
|
||||
self.assertEqual(extract_fieldnames("count(distinct `tabPhoto`.name)")[0], "tabPhoto.name")
|
||||
|
||||
self.assertEqual(extract_fieldnames("count(`tabPhoto`.name)")[0], "tabPhoto.name")
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("count(distinct `tabJob Applicant`.name) as total_count")[0],
|
||||
"tabJob Applicant.name",
|
||||
)
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("(1 / nullif(locate('a', `tabAddress`.`name`), 0)) as `_relevance`")[0],
|
||||
"tabAddress.name",
|
||||
)
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("(1 / nullif(locate('(a)', `tabAddress`.`name`), 0)) as `_relevance`")[0],
|
||||
"tabAddress.name",
|
||||
)
|
||||
|
||||
self.assertEqual(extract_fieldnames("EXTRACT(MONTH FROM date_column) AS month")[0], "date_column")
|
||||
|
||||
self.assertEqual(extract_fieldnames("COUNT(*) AS count")[0], "*")
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("first_name + ' ' + last_name AS full_name"), ["first_name", "last_name"]
|
||||
)
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("CONCAT(first_name, ' ', last_name) AS full_name"),
|
||||
["first_name", "last_name"],
|
||||
)
|
||||
|
||||
self.assertEqual(
|
||||
extract_fieldnames("CONCAT(id, '/', name, '/', age, '/', marks) AS student"),
|
||||
["id", "name", "age", "marks"],
|
||||
)
|
||||
|
||||
self.assertEqual(extract_fieldnames("tablefield.fiedname")[0], "tablefield.fiedname")
|
||||
|
||||
self.assertEqual(extract_fieldnames("`tabChild DocType`.`fiedname`")[0], "tabChild DocType.fiedname")
|
||||
|
||||
self.assertEqual(extract_fieldnames("sum(1)"), [])
|
||||
|
|
|
|||
|
|
@ -176,6 +176,11 @@ class TestSearch(FrappeTestCase):
|
|||
frappe.db.set_value("Language", "es", "idx", 10)
|
||||
self.assertEqual("es", search(txt="es")[0]["value"])
|
||||
|
||||
def test_search_with_paren(self):
|
||||
search = partial(search_link, doctype="Language", filters=None, page_length=10)
|
||||
result = search(txt="(txt)")
|
||||
self.assertEqual(result, [])
|
||||
|
||||
|
||||
@frappe.validate_and_sanitize_search_inputs
|
||||
def get_data(doctype, txt, searchfield, start, page_len, filters):
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ class FrappeTestCase(unittest.TestCase):
|
|||
TEST_SITE = "test_site"
|
||||
|
||||
SHOW_TRANSACTION_COMMIT_WARNINGS = False
|
||||
maxDiff = None # prints long diffs but useful in CI
|
||||
maxDiff = 10_000 # prints long diffs but useful in CI
|
||||
|
||||
@classmethod
|
||||
def setUpClass(cls) -> None:
|
||||
|
|
|
|||
|
|
@ -226,6 +226,7 @@ class UserPermissions:
|
|||
"send_me_a_copy",
|
||||
"user_type",
|
||||
"onboarding_status",
|
||||
"default_workspace",
|
||||
],
|
||||
as_dict=True,
|
||||
)
|
||||
|
|
@ -233,6 +234,10 @@ class UserPermissions:
|
|||
if not self.can_read:
|
||||
self.build_permissions()
|
||||
|
||||
if d.get("default_workspace"):
|
||||
public = frappe.get_cached_value("Workspace", d.default_workspace, "public")
|
||||
d.default_workspace = {"name": d.default_workspace, "public": public}
|
||||
|
||||
d.name = self.name
|
||||
d.onboarding_status = frappe.parse_json(d.onboarding_status)
|
||||
d.roles = self.get_roles()
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ html, body {
|
|||
<script>
|
||||
frappe.ready(function() {
|
||||
if (window.location.hash || window.location.href.includes('/app')) {
|
||||
localStorage.setItem('session_last_route', window.location.pathname + window.location.hash + window.location.search);
|
||||
localStorage.setItem('session_last_route', window.location.pathname);
|
||||
}
|
||||
|
||||
$('.btn-primary').focus();
|
||||
|
|
|
|||
|
|
@ -67,6 +67,7 @@ dependencies = [
|
|||
"semantic-version~=2.10.0",
|
||||
"sentry-sdk~=1.37.1",
|
||||
"sqlparse~=0.4.4",
|
||||
"sql_metadata~=2.9.0",
|
||||
"tenacity~=8.2.2",
|
||||
"terminaltables~=3.1.10",
|
||||
"traceback-with-variables~=2.0.4",
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue