From aa019291b6fb588ba021cc57354344b90a273383 Mon Sep 17 00:00:00 2001 From: pratu16x7 Date: Thu, 10 Nov 2016 17:35:36 +0530 Subject: [PATCH 1/7] Add a span showing the number of selected entries (#2286) * Add a span showing the number of selected entries * Make the item status string translatable * Indentation fix --- frappe/public/js/frappe/list/doclistview.js | 8 +++++++- frappe/public/js/frappe/ui/page.html | 1 + frappe/public/js/frappe/ui/page.js | 1 + 3 files changed, 9 insertions(+), 1 deletion(-) diff --git a/frappe/public/js/frappe/list/doclistview.js b/frappe/public/js/frappe/list/doclistview.js index 3662994560..d5bc5818d7 100644 --- a/frappe/public/js/frappe/list/doclistview.js +++ b/frappe/public/js/frappe/list/doclistview.js @@ -781,13 +781,19 @@ frappe.views.DocListView = frappe.ui.Listing.extend({ toggle_delete: function() { var me = this; - if (this.$page.find(".list-delete:checked").length) { + var no_of_checked_items = this.$page.find(".list-delete:checked").length; + if (no_of_checked_items) { this.page.set_primary_action(__("Delete"), function() { me.delete_items() }, "octicon octicon-trashcan"); this.page.btn_primary.addClass("btn-danger"); + this.page.checked_items_status.text(no_of_checked_items == 1 + ? __("1 item selected") + : __("{0} items selected", [no_of_checked_items])) + this.page.checked_items_status.removeClass("hide"); } else { this.page.btn_primary.removeClass("btn-danger"); this.set_primary_action(); + this.page.checked_items_status.addClass("hide"); } }, diff --git a/frappe/public/js/frappe/ui/page.html b/frappe/public/js/frappe/ui/page.html index 1b378f5574..f3ad393657 100644 --- a/frappe/public/js/frappe/ui/page.html +++ b/frappe/public/js/frappe/ui/page.html @@ -12,6 +12,7 @@
+
diff --git a/frappe/public/js/frappe/ui/page.js b/frappe/public/js/frappe/ui/page.js index 0439f5b4ae..685384ce57 100644 --- a/frappe/public/js/frappe/ui/page.js +++ b/frappe/public/js/frappe/ui/page.js @@ -80,6 +80,7 @@ frappe.ui.Page = Class.extend({ this.page_actions = this.wrapper.find(".page-actions"); + this.checked_items_status = this.page_actions.find(".checked-items-status"); this.btn_primary = this.page_actions.find(".primary-action"); this.btn_secondary = this.page_actions.find(".btn-secondary"); From fc454e014dec364565e927d9e16eeb02bbff3e90 Mon Sep 17 00:00:00 2001 From: Rohit Waghchaure Date: Thu, 10 Nov 2016 19:16:15 +0530 Subject: [PATCH 2/7] [Fix] break fieldtype issue in the auto email report, object split issue for the columns which has list and dictionary --- frappe/core/doctype/report/report.py | 9 ++++++++- .../doctype/auto_email_report/auto_email_report.js | 10 ++++++++++ 2 files changed, 18 insertions(+), 1 deletion(-) diff --git a/frappe/core/doctype/report/report.py b/frappe/core/doctype/report/report.py index c5505b1b13..a5dfeafb6c 100644 --- a/frappe/core/doctype/report/report.py +++ b/frappe/core/doctype/report/report.py @@ -57,7 +57,14 @@ class Report(Document): if self.report_type in ('Query Report', 'Script Report'): # query and script reports data = frappe.desk.query_report.run(self.name, filters=filters, user=user) - out.append([d.split(':')[0] for d in data.get('columns')]) + columns_list = [] + for d in data.get('columns'): + if isinstance(d, dict): + columns_list.append(d.get('label')) + else: + columns_list.append(d.split(':')[0]) + + out.append(columns_list) out += data.get('result') else: # standard report diff --git a/frappe/email/doctype/auto_email_report/auto_email_report.js b/frappe/email/doctype/auto_email_report/auto_email_report.js index f01fec1c76..456ddff18f 100644 --- a/frappe/email/doctype/auto_email_report/auto_email_report.js +++ b/frappe/email/doctype/auto_email_report/auto_email_report.js @@ -60,9 +60,19 @@ frappe.ui.form.on('Auto Email Report', { '+__('Filter')+''+__('Value')+'\ ').appendTo(wrapper); $('

' + __("Click table to edit") + '

').appendTo(wrapper); + var filters = JSON.parse(frm.doc.filters || '{}'); var report_filters = frappe.query_reports[frm.doc.report].filters; + report_filters_list = [] + $.each(report_filters, function(key, val){ + // Remove break fieldtype from the filters + if(val.fieldtype != 'Break') { + report_filters_list.push(val) + } + }) + report_filters = report_filters_list; + report_filters.forEach(function(f) { $('' + f.label + ''+ frappe.format(filters[f.fieldname], f) +'') .appendTo(table.find('tbody')); From 33a48cd957e021e2511e9630f377b8e0d83efbf3 Mon Sep 17 00:00:00 2001 From: Rushabh Mehta Date: Fri, 11 Nov 2016 13:24:11 +0530 Subject: [PATCH 3/7] [fix] z-index for datepicker should be above grid row --- frappe/public/css/desk.css | 2 +- frappe/public/less/desk.less | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/frappe/public/css/desk.css b/frappe/public/css/desk.css index 7b5149f542..e45d440ba6 100644 --- a/frappe/public/css/desk.css +++ b/frappe/public/css/desk.css @@ -355,7 +355,7 @@ fieldset[disabled] .form-control { } /* jquery ui */ .ui-datepicker { - z-index: 100 !important; + z-index: 9999 !important; } .ui-datepicker .ui-datepicker-header { border-radius: 0px !important; diff --git a/frappe/public/less/desk.less b/frappe/public/less/desk.less index c3fb6bc098..ffcdcbce18 100644 --- a/frappe/public/less/desk.less +++ b/frappe/public/less/desk.less @@ -146,7 +146,7 @@ textarea.form-control { /* jquery ui */ .ui-datepicker { - z-index: 100 !important; + z-index: 9999 !important; } .ui-datepicker .ui-datepicker-header { From 80a3a3f8f180248bb2968c3bf06679e76be24efc Mon Sep 17 00:00:00 2001 From: Rushabh Mehta Date: Fri, 11 Nov 2016 14:50:12 +0530 Subject: [PATCH 4/7] [fix] global variable import issue --- frappe/api.py | 40 ++++++++++++++++++++++------------------ 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/frappe/api.py b/frappe/api.py index 0092067ffb..640bce582a 100644 --- a/frappe/api.py +++ b/frappe/api.py @@ -10,7 +10,6 @@ from frappe.utils.response import build_response from frappe import _ from urlparse import urlparse from urllib import urlencode -from frappe.integration_broker.oauth2 import oauth_server def handle(): """ @@ -37,24 +36,8 @@ def handle(): """ form_dict = frappe.local.form_dict - authorization_header = frappe.get_request_header("Authorization").split(" ") if frappe.get_request_header("Authorization") else None - if authorization_header and authorization_header[0].lower() == "bearer": - token = authorization_header[1] - r = frappe.request - parsed_url = urlparse(r.url) - access_token = { "access_token": token} - uri = parsed_url.scheme + "://" + parsed_url.netloc + parsed_url.path + "?" + urlencode(access_token) - http_method = r.method - body = r.get_data() - headers = r.headers - required_scopes = frappe.db.get_value("OAuth Bearer Token", token, "scopes").split(";") - - valid, oauthlib_request = oauth_server.verify_request(uri, http_method, body, headers, required_scopes) - - if valid: - frappe.set_user(frappe.db.get_value("OAuth Bearer Token", token, "user")) - frappe.local.form_dict = form_dict + validate_oauth() parts = frappe.request.path[1:].split("/",3) call = doctype = name = None @@ -146,3 +129,24 @@ def handle(): raise frappe.DoesNotExistError return build_response("json") + +def validate_oauth(): + authorization_header = frappe.get_request_header("Authorization").split(" ") if frappe.get_request_header("Authorization") else None + if authorization_header and authorization_header[0].lower() == "bearer": + from frappe.integration_broker.oauth2 import oauth_server + token = authorization_header[1] + r = frappe.request + parsed_url = urlparse(r.url) + access_token = { "access_token": token} + uri = parsed_url.scheme + "://" + parsed_url.netloc + parsed_url.path + "?" + urlencode(access_token) + http_method = r.method + body = r.get_data() + headers = r.headers + + required_scopes = frappe.db.get_value("OAuth Bearer Token", token, "scopes").split(";") + + valid, oauthlib_request = oauth_server.verify_request(uri, http_method, body, headers, required_scopes) + + if valid: + frappe.set_user(frappe.db.get_value("OAuth Bearer Token", token, "user")) + frappe.local.form_dict = form_dict From 924510610b2a0a4252c3e8b78aa25d3caa1b10b3 Mon Sep 17 00:00:00 2001 From: Rushabh Mehta Date: Fri, 11 Nov 2016 14:57:13 +0530 Subject: [PATCH 5/7] [fix] remove global variables in oauth --- frappe/api.py | 7 +++---- frappe/integration_broker/oauth2.py | 30 +++++++++++++++-------------- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/frappe/api.py b/frappe/api.py index 640bce582a..afdc3b8630 100644 --- a/frappe/api.py +++ b/frappe/api.py @@ -35,8 +35,6 @@ def handle(): `/api/resource/{doctype}/{name}?run_method={method}` will run a whitelisted controller method """ - form_dict = frappe.local.form_dict - validate_oauth() parts = frappe.request.path[1:].split("/",3) @@ -131,9 +129,10 @@ def handle(): return build_response("json") def validate_oauth(): + form_dict = frappe.local.form_dict authorization_header = frappe.get_request_header("Authorization").split(" ") if frappe.get_request_header("Authorization") else None if authorization_header and authorization_header[0].lower() == "bearer": - from frappe.integration_broker.oauth2 import oauth_server + from frappe.integration_broker.oauth2 import get_oauth_server token = authorization_header[1] r = frappe.request parsed_url = urlparse(r.url) @@ -145,7 +144,7 @@ def validate_oauth(): required_scopes = frappe.db.get_value("OAuth Bearer Token", token, "scopes").split(";") - valid, oauthlib_request = oauth_server.verify_request(uri, http_method, body, headers, required_scopes) + valid, oauthlib_request = get_oauth_server().verify_request(uri, http_method, body, headers, required_scopes) if valid: frappe.set_user(frappe.db.get_value("OAuth Bearer Token", token, "user")) diff --git a/frappe/integration_broker/oauth2.py b/frappe/integration_broker/oauth2.py index 422b6c9d4e..82e6c1d735 100644 --- a/frappe/integration_broker/oauth2.py +++ b/frappe/integration_broker/oauth2.py @@ -6,10 +6,12 @@ from urllib import quote, urlencode from urlparse import urlparse from frappe.integrations.doctype.oauth_provider_settings.oauth_provider_settings import get_oauth_settings -#Variables required across requests -oauth_validator = OAuthWebRequestValidator() -oauth_server = WebApplicationServer(oauth_validator) -credentials = None +def get_oauth_server(): + if not getattr(frappe.local, 'oauth_server'): + oauth_validator = OAuthWebRequestValidator() + frappe.local.oauth_server = WebApplicationServer(oauth_validator) + + return frappe.local.oauth_server def get_urlparams_from_kwargs(param_kwargs): arguments = param_kwargs @@ -29,10 +31,10 @@ def approve(*args, **kwargs): headers = r.headers try: - scopes, credentials = oauth_server.validate_authorization_request(uri, http_method, body, headers) + scopes, frappe.flags.oauth_credentials = get_oauth_server().validate_authorization_request(uri, http_method, body, headers) - headers, body, status = oauth_server.create_authorization_response(uri=credentials['redirect_uri'], \ - body=body, headers=headers, scopes=scopes, credentials=credentials) + headers, body, status = get_oauth_server().create_authorization_response(uri=frappe.flags.oauth_credentials['redirect_uri'], \ + body=body, headers=headers, scopes=scopes, credentials=frappe.flags.oauth_credentials) uri = headers.get('Location', None) frappe.local.response["type"] = "redirect" @@ -50,7 +52,7 @@ def authorize(*args, **kwargs): params = get_urlparams_from_kwargs(kwargs) request_url = urlparse(frappe.request.url) success_url = request_url.scheme + "://" + request_url.netloc + "/api/method/frappe.integration_broker.oauth2.approve?" + params - failure_url = frappe.form_dict["redirect_uri"] + "?error=access_denied" + failure_url = frappe.form_dict["redirect_uri"] + "?error=access_denied" if frappe.session['user']=='Guest': #Force login, redirect to preauth again. @@ -65,9 +67,9 @@ def authorize(*args, **kwargs): body = r.get_data() headers = r.headers - scopes, credentials = oauth_server.validate_authorization_request(uri, http_method, body, headers) + scopes, frappe.flags.oauth_credentials = get_oauth_server().validate_authorization_request(uri, http_method, body, headers) - skip_auth = frappe.db.get_value("OAuth Client", credentials['client_id'], "skip_authorization") + skip_auth = frappe.db.get_value("OAuth Client", frappe.flags.oauth_credentials['client_id'], "skip_authorization") unrevoked_tokens = frappe.get_all("OAuth Bearer Token", filters={"status":"Active"}) if skip_auth or (oauth_settings["skip_authorization"] == "Auto" and len(unrevoked_tokens)): @@ -100,7 +102,7 @@ def get_token(*args, **kwargs): headers = r.headers try: - headers, body, status = oauth_server.create_token_response(uri, http_method, body, headers, credentials) + headers, body, status = get_oauth_server().create_token_response(uri, http_method, body, headers, frappe.flags.oauth_credentials) frappe.local.response = frappe._dict(json.loads(body)) except FatalClientError as e: return e @@ -113,9 +115,9 @@ def revoke_token(*args, **kwargs): http_method = r.method body = r.form headers = r.headers - - headers, body, status = oauth_server.create_revocation_response(uri, headers=headers, body=body, http_method=http_method) - + + headers, body, status = get_oauth_server().create_revocation_response(uri, headers=headers, body=body, http_method=http_method) + frappe.local.response['http_status_code'] = status if status == 200: return "success" From 462972ec84edaf494b3e859cfb078fd638e2fa96 Mon Sep 17 00:00:00 2001 From: Rushabh Mehta Date: Fri, 11 Nov 2016 14:59:27 +0530 Subject: [PATCH 6/7] [fix] remove global variables in oauth --- frappe/integration_broker/oauth2.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frappe/integration_broker/oauth2.py b/frappe/integration_broker/oauth2.py index 82e6c1d735..ed48b83a4c 100644 --- a/frappe/integration_broker/oauth2.py +++ b/frappe/integration_broker/oauth2.py @@ -7,7 +7,7 @@ from urlparse import urlparse from frappe.integrations.doctype.oauth_provider_settings.oauth_provider_settings import get_oauth_settings def get_oauth_server(): - if not getattr(frappe.local, 'oauth_server'): + if not getattr(frappe.local, 'oauth_server', None): oauth_validator = OAuthWebRequestValidator() frappe.local.oauth_server = WebApplicationServer(oauth_validator) From db9fad8e51ebf20d9da422c42d5e7540b58cc9bd Mon Sep 17 00:00:00 2001 From: Nabin Hait Date: Fri, 11 Nov 2016 15:36:58 +0600 Subject: [PATCH 7/7] bumped to version 7.1.11 --- frappe/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frappe/__init__.py b/frappe/__init__.py index 990af664e4..280bd480b7 100644 --- a/frappe/__init__.py +++ b/frappe/__init__.py @@ -13,7 +13,7 @@ import os, sys, importlib, inspect, json from .exceptions import * from .utils.jinja import get_jenv, get_template, render_template -__version__ = '7.1.10' +__version__ = '7.1.11' __title__ = "Frappe Framework" local = Local()