From a9f0c9599133ba67c761c0f23ab5559ca21bdddb Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Wed, 25 Apr 2018 14:31:17 -0400 Subject: [PATCH 01/11] error message that catches responses with HTTP and not HTTPS --- plotly/api/v2/utils.py | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/plotly/api/v2/utils.py b/plotly/api/v2/utils.py index 21bd0ddd016..5023a784d80 100644 --- a/plotly/api/v2/utils.py +++ b/plotly/api/v2/utils.py @@ -8,6 +8,37 @@ from plotly.api.utils import basic_auth +HTTP_ERROR_MESSAGE = ( + """Your plotly_domain and plotly_api_domain must be HTTPS and not HTTP.\n + If you are not using On-Prem then run the following code to ensure your + plotly_domain and plotly_api_domain start with 'https': + + ``` + import plotly + plotly.tools.set_config_file( + plotly_domain='https://plot.ly', + plotly_api_domain='https://api.plot.ly' + ) + ``` + + If you are using On-Prem then you will need to use your company's + domain and api_domain urls: + + ``` + import plotly + plotly.tools.set_config_file( + plotly_domain='https://plotly.your-company.com', + plotly_api_domain='https://plotly.your-company.com' + ) + ``` + + Make sure to replace "your-company.com" with the URL of your Plotly On-Premise server. + + See https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users + for more tips for getting started with Plotly.""" +) + + def make_params(**kwargs): """ Helper to create a params dict, skipping undefined entries. @@ -76,6 +107,10 @@ def validate_response(response): if not message: message = content if content else 'No Content' + if not response.history[0].url.startswith('https:'): + raise exceptions.PlotlyRequestError(HTTP_ERROR_MESSAGE, + status_code, content) + raise exceptions.PlotlyRequestError(message, status_code, content) From 556ef45a76eae87b033abab40a3f46f07172de85 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Wed, 25 Apr 2018 14:42:05 -0400 Subject: [PATCH 02/11] make sure history is not an empty list --- plotly/api/v2/utils.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/plotly/api/v2/utils.py b/plotly/api/v2/utils.py index 5023a784d80..13a867e6d3e 100644 --- a/plotly/api/v2/utils.py +++ b/plotly/api/v2/utils.py @@ -107,9 +107,10 @@ def validate_response(response): if not message: message = content if content else 'No Content' - if not response.history[0].url.startswith('https:'): - raise exceptions.PlotlyRequestError(HTTP_ERROR_MESSAGE, - status_code, content) + if len(response.history) > 0: + if not response.history[0].url.startswith('https:'): + raise exceptions.PlotlyRequestError(HTTP_ERROR_MESSAGE, + status_code, content) raise exceptions.PlotlyRequestError(message, status_code, content) From 6b12bf2edec96f7ae3c228d294c7a01759727caa Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Thu, 26 Apr 2018 16:45:29 -0400 Subject: [PATCH 03/11] made a warning instead --- plotly/api/v2/utils.py | 36 ------------------------------------ plotly/tools.py | 37 +++++++++++++++++++++++++++++++++++-- 2 files changed, 35 insertions(+), 38 deletions(-) diff --git a/plotly/api/v2/utils.py b/plotly/api/v2/utils.py index 13a867e6d3e..21bd0ddd016 100644 --- a/plotly/api/v2/utils.py +++ b/plotly/api/v2/utils.py @@ -8,37 +8,6 @@ from plotly.api.utils import basic_auth -HTTP_ERROR_MESSAGE = ( - """Your plotly_domain and plotly_api_domain must be HTTPS and not HTTP.\n - If you are not using On-Prem then run the following code to ensure your - plotly_domain and plotly_api_domain start with 'https': - - ``` - import plotly - plotly.tools.set_config_file( - plotly_domain='https://plot.ly', - plotly_api_domain='https://api.plot.ly' - ) - ``` - - If you are using On-Prem then you will need to use your company's - domain and api_domain urls: - - ``` - import plotly - plotly.tools.set_config_file( - plotly_domain='https://plotly.your-company.com', - plotly_api_domain='https://plotly.your-company.com' - ) - ``` - - Make sure to replace "your-company.com" with the URL of your Plotly On-Premise server. - - See https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users - for more tips for getting started with Plotly.""" -) - - def make_params(**kwargs): """ Helper to create a params dict, skipping undefined entries. @@ -107,11 +76,6 @@ def validate_response(response): if not message: message = content if content else 'No Content' - if len(response.history) > 0: - if not response.history[0].url.startswith('https:'): - raise exceptions.PlotlyRequestError(HTTP_ERROR_MESSAGE, - status_code, content) - raise exceptions.PlotlyRequestError(message, status_code, content) diff --git a/plotly/tools.py b/plotly/tools.py index b24c391833f..7488d7fce73 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -49,6 +49,36 @@ ALTERNATIVE_HISTNORM = 'probability' +http_msg = ( + "The plotly_domain and plotly_api_domain of your config file must start " + "with 'https', 'http'.\n If you are not using On-Prem then run the " + "following code to ensure your plotly_domain and plotly_api_domain start " + "with 'https':\n\n\n" + "import plotly\n" + "plotly.tools.set_config_file(\n" + " plotly_domain='https://plot.ly',\n" + " plotly_api_domain='https://api.plot.ly'\n" + ")\n\n\n" + "If you are using On-Prem then you will need to use your company's " + "domain and api_domain urls:\n\n\n" + "import plotly\n" + "plotly.tools.set_config_file(\n" + " plotly_domain='https://plotly.your-company.com',\n" + " plotly_api_domain='https://plotly.your-company.com'\n" + ")\n\n\n" + "Make sure to replace `your-company.com` with the URL of your Plotly " + "On-Premise server.\nSee " + "https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users " + "for more help with getting started with On-Prem." +) + + +def validate_config_file(*domains): + for d in domains: + if not d.lower().startswith('https'): + warnings.warn(http_msg) + + # Warning format def warning_on_one_line(message, category, filename, lineno, file=None, line=None): @@ -194,6 +224,7 @@ def set_config_file(plotly_domain=None, 'sharing': sharing, 'world_readable': world_readable}) settings = get_config_file() if isinstance(plotly_domain, six.string_types): + validate_config_file(plotly_domain) settings['plotly_domain'] = plotly_domain elif plotly_domain is not None: raise TypeError('plotly_domain should be a string') @@ -202,6 +233,7 @@ def set_config_file(plotly_domain=None, elif plotly_streaming_domain is not None: raise TypeError('plotly_streaming_domain should be a string') if isinstance(plotly_api_domain, six.string_types): + validate_config_file(plotly_api_domain) settings['plotly_api_domain'] = plotly_api_domain elif plotly_api_domain is not None: raise TypeError('plotly_api_domain should be a string') @@ -244,9 +276,10 @@ def get_config_file(*args): """ if check_file_permissions(): ensure_local_plotly_files() # make sure what's there is OK - return utils.load_json_dict(CONFIG_FILE, *args) + returned_obj = utils.load_json_dict(CONFIG_FILE, *args) else: - return FILE_CONTENT[CONFIG_FILE] + returned_obj = FILE_CONTENT[CONFIG_FILE] + return returned_obj def reset_config_file(): From 0c189f21a673f529c6e786c598a3eb8102c2c6c8 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Mon, 30 Apr 2018 11:33:20 -0400 Subject: [PATCH 04/11] changed validate_config_file to validate_domains --- plotly/tools.py | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/plotly/tools.py b/plotly/tools.py index 7488d7fce73..83e88f56bf1 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -73,7 +73,7 @@ ) -def validate_config_file(*domains): +def validate_domains(*domains): for d in domains: if not d.lower().startswith('https'): warnings.warn(http_msg) @@ -224,7 +224,7 @@ def set_config_file(plotly_domain=None, 'sharing': sharing, 'world_readable': world_readable}) settings = get_config_file() if isinstance(plotly_domain, six.string_types): - validate_config_file(plotly_domain) + #validate_domains(plotly_domain) settings['plotly_domain'] = plotly_domain elif plotly_domain is not None: raise TypeError('plotly_domain should be a string') @@ -233,7 +233,7 @@ def set_config_file(plotly_domain=None, elif plotly_streaming_domain is not None: raise TypeError('plotly_streaming_domain should be a string') if isinstance(plotly_api_domain, six.string_types): - validate_config_file(plotly_api_domain) + #validate_domains(plotly_api_domain) settings['plotly_api_domain'] = plotly_api_domain elif plotly_api_domain is not None: raise TypeError('plotly_api_domain should be a string') @@ -276,10 +276,9 @@ def get_config_file(*args): """ if check_file_permissions(): ensure_local_plotly_files() # make sure what's there is OK - returned_obj = utils.load_json_dict(CONFIG_FILE, *args) + return utils.load_json_dict(CONFIG_FILE, *args) else: - returned_obj = FILE_CONTENT[CONFIG_FILE] - return returned_obj + return FILE_CONTENT[CONFIG_FILE] def reset_config_file(): From 6e4622cc4f8ac6fe5c4ef54e126c6a4a29aac58d Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Mon, 30 Apr 2018 11:34:07 -0400 Subject: [PATCH 05/11] refactor get_config_file guts so returned_objs is validated after grabbed --- plotly/tools.py | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/plotly/tools.py b/plotly/tools.py index 83e88f56bf1..d23682373f0 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -276,9 +276,20 @@ def get_config_file(*args): """ if check_file_permissions(): ensure_local_plotly_files() # make sure what's there is OK - return utils.load_json_dict(CONFIG_FILE, *args) + returned_obj = utils.load_json_dict(CONFIG_FILE, *args) else: - return FILE_CONTENT[CONFIG_FILE] + returned_obj = FILE_CONTENT[CONFIG_FILE] + + list_of_domains = [] + for domain in ['plotly_domain', 'plotly_api_domain']: + if domain in returned_obj: + list_of_domains.append(returned_obj[domain]) + + validate_domains(*list_of_domains) + + return returned_obj + + def reset_config_file(): From c063f23030232d228afb2abd749acd3697e17e89 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Mon, 30 Apr 2018 11:54:39 -0400 Subject: [PATCH 06/11] validation warning can be triggered on get_config and set_config --- plotly/tools.py | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/plotly/tools.py b/plotly/tools.py index d23682373f0..71b87b5925e 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -222,9 +222,9 @@ def set_config_file(plotly_domain=None, ensure_local_plotly_files() # make sure what's there is OK utils.validate_world_readable_and_sharing_settings({ 'sharing': sharing, 'world_readable': world_readable}) - settings = get_config_file() + + settings = get_config_file(validate=False) if isinstance(plotly_domain, six.string_types): - #validate_domains(plotly_domain) settings['plotly_domain'] = plotly_domain elif plotly_domain is not None: raise TypeError('plotly_domain should be a string') @@ -233,7 +233,6 @@ def set_config_file(plotly_domain=None, elif plotly_streaming_domain is not None: raise TypeError('plotly_streaming_domain should be a string') if isinstance(plotly_api_domain, six.string_types): - #validate_domains(plotly_api_domain) settings['plotly_api_domain'] = plotly_api_domain elif plotly_api_domain is not None: raise TypeError('plotly_api_domain should be a string') @@ -250,6 +249,14 @@ def set_config_file(plotly_domain=None, elif auto_open is not None: raise TypeError('auto_open should be a boolean') + # validate plotly_domain and plotly_api_domain + list_of_domains = [] + if plotly_domain is not None: + list_of_domains.append(plotly_domain) + if plotly_api_domain is not None: + list_of_domains.append(plotly_api_domain) + validate_domains(*list_of_domains) + if isinstance(world_readable, bool): settings['world_readable'] = world_readable settings.pop('sharing') @@ -265,7 +272,7 @@ def set_config_file(plotly_domain=None, ensure_local_plotly_files() # make sure what we just put there is OK -def get_config_file(*args): +def get_config_file(*args, validate=True): """Return specified args from `~/.plotly/.config`. as tuple. Returns all if no arguments are specified. @@ -285,7 +292,8 @@ def get_config_file(*args): if domain in returned_obj: list_of_domains.append(returned_obj[domain]) - validate_domains(*list_of_domains) + if validate: + validate_domains(*list_of_domains) return returned_obj @@ -325,7 +333,7 @@ def get_embed(file_owner_or_url, file_id=None, width="100%", height=525): """ plotly_rest_url = (session.get_session_config().get('plotly_domain') or - get_config_file()['plotly_domain']) + get_config_file(validate=False)['plotly_domain']) if file_id is None: # assume we're using a url url = file_owner_or_url if url[:len(plotly_rest_url)] != plotly_rest_url: @@ -422,7 +430,7 @@ def embed(file_owner_or_url, file_id=None, width="100%", height=525): if file_id: plotly_domain = ( session.get_session_config().get('plotly_domain') or - get_config_file()['plotly_domain'] + get_config_file(validate=False)['plotly_domain'] ) url = "{plotly_domain}/~{un}/{fid}".format( plotly_domain=plotly_domain, @@ -448,7 +456,7 @@ def embed(file_owner_or_url, file_id=None, width="100%", height=525): ### mpl-related tools ### -@utils.template_doc(**get_config_file()) +@utils.template_doc(**get_config_file(validate=False)) def mpl_to_plotly(fig, resize=False, strip_style=False, verbose=False): """Convert a matplotlib figure to plotly dictionary and send. From fe31851e4e4ce6fe9c5e9e552eab95ae46d5eee8 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Mon, 30 Apr 2018 13:28:24 -0400 Subject: [PATCH 07/11] started on tests --- .../tests/test_core/test_tools/test_file_tools.py | 14 +++++++++++++- plotly/tools.py | 12 +++++------- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/plotly/tests/test_core/test_tools/test_file_tools.py b/plotly/tests/test_core/test_tools/test_file_tools.py index f28aff058f5..a9072630c11 100644 --- a/plotly/tests/test_core/test_tools/test_file_tools.py +++ b/plotly/tests/test_core/test_tools/test_file_tools.py @@ -1,6 +1,9 @@ from plotly import tools, session from plotly.tests.utils import PlotlyTestCase +import ipdb +import warnings + class FileToolsTest(PlotlyTestCase): @@ -43,7 +46,6 @@ def test_set_config_file_two_entries(self): self.assertEqual(config['plotly_streaming_domain'], streaming_domain) tools.reset_config_file() - def test_set_config_file_world_readable(self): # Return TypeError when world_readable type is not a bool @@ -51,6 +53,16 @@ def test_set_config_file_world_readable(self): kwargs = {'world_readable': 'True'} self.assertRaises(TypeError, tools.set_config_file, **kwargs) + def test_set_config_expected_error_msg(self): + kwargs = {'plotly_domain': 'http://www.foo-bar.com'} + #self.assertRaises(UserWarning, tools.set_config_file, **kwargs) + print 'abcd' + b = tools.set_config_file(**kwargs) + print type(b) + + + + def test_reset_config_file(self): # Check reset_config and get_config return the same values diff --git a/plotly/tools.py b/plotly/tools.py index 71b87b5925e..6ac8069ca24 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -73,10 +73,10 @@ ) -def validate_domains(*domains): +def _validate_domains(*domains): for d in domains: if not d.lower().startswith('https'): - warnings.warn(http_msg) + warnings.warn(http_msg, category=UserWarning) # Warning format @@ -255,7 +255,7 @@ def set_config_file(plotly_domain=None, list_of_domains.append(plotly_domain) if plotly_api_domain is not None: list_of_domains.append(plotly_api_domain) - validate_domains(*list_of_domains) + _validate_domains(*list_of_domains) if isinstance(world_readable, bool): settings['world_readable'] = world_readable @@ -272,7 +272,7 @@ def set_config_file(plotly_domain=None, ensure_local_plotly_files() # make sure what we just put there is OK -def get_config_file(*args, validate=True): +def get_config_file(validate=True, *args): """Return specified args from `~/.plotly/.config`. as tuple. Returns all if no arguments are specified. @@ -293,13 +293,11 @@ def get_config_file(*args, validate=True): list_of_domains.append(returned_obj[domain]) if validate: - validate_domains(*list_of_domains) + _validate_domains(*list_of_domains) return returned_obj - - def reset_config_file(): ensure_local_plotly_files() # make sure what's there is OK f = open(CONFIG_FILE, 'w') From e55e81c5556fda8ba8ac09d60a01452c0be55624 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Tue, 1 May 2018 16:38:43 -0400 Subject: [PATCH 08/11] moved validation function to utils//test working --- .../test_core/test_stream/test_stream.py | 2 +- .../test_core/test_tools/test_file_tools.py | 15 +++-- plotly/tools.py | 64 ++++--------------- plotly/utils.py | 38 ++++++++++- 4 files changed, 57 insertions(+), 62 deletions(-) diff --git a/plotly/tests/test_core/test_stream/test_stream.py b/plotly/tests/test_core/test_stream/test_stream.py index 190f18a9f39..869fd8d2d3c 100644 --- a/plotly/tests/test_core/test_stream/test_stream.py +++ b/plotly/tests/test_core/test_stream/test_stream.py @@ -18,7 +18,7 @@ tk = 'vaia8trjjb' config = {'plotly_domain': 'https://plot.ly', 'plotly_streaming_domain': 'stream.plot.ly', - 'plotly_api_domain': 'https://api.plot.ly', + 'plotly_api_domain': 'https://api.plot.ly', 'plotly_ssl_verification': False} diff --git a/plotly/tests/test_core/test_tools/test_file_tools.py b/plotly/tests/test_core/test_tools/test_file_tools.py index a9072630c11..47a54675e4a 100644 --- a/plotly/tests/test_core/test_tools/test_file_tools.py +++ b/plotly/tests/test_core/test_tools/test_file_tools.py @@ -1,7 +1,6 @@ from plotly import tools, session from plotly.tests.utils import PlotlyTestCase -import ipdb import warnings @@ -54,14 +53,16 @@ def test_set_config_file_world_readable(self): self.assertRaises(TypeError, tools.set_config_file, **kwargs) def test_set_config_expected_error_msg(self): - kwargs = {'plotly_domain': 'http://www.foo-bar.com'} - #self.assertRaises(UserWarning, tools.set_config_file, **kwargs) - print 'abcd' - b = tools.set_config_file(**kwargs) - print type(b) - + # Check that UserWarning is being called with http plotly_domain + with warnings.catch_warnings(record=True) as w: + warnings.simplefilter("always") + kwargs = {'plotly_domain': 'http://www.foo-bar.com'} + tools.set_config_file(**kwargs) + assert len(w) == 1 + assert issubclass(w[-1].category, UserWarning) + assert "plotly_domain" in str(w[-1].message) def test_reset_config_file(self): diff --git a/plotly/tools.py b/plotly/tools.py index 6ac8069ca24..46e7c856e55 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -49,36 +49,6 @@ ALTERNATIVE_HISTNORM = 'probability' -http_msg = ( - "The plotly_domain and plotly_api_domain of your config file must start " - "with 'https', 'http'.\n If you are not using On-Prem then run the " - "following code to ensure your plotly_domain and plotly_api_domain start " - "with 'https':\n\n\n" - "import plotly\n" - "plotly.tools.set_config_file(\n" - " plotly_domain='https://plot.ly',\n" - " plotly_api_domain='https://api.plot.ly'\n" - ")\n\n\n" - "If you are using On-Prem then you will need to use your company's " - "domain and api_domain urls:\n\n\n" - "import plotly\n" - "plotly.tools.set_config_file(\n" - " plotly_domain='https://plotly.your-company.com',\n" - " plotly_api_domain='https://plotly.your-company.com'\n" - ")\n\n\n" - "Make sure to replace `your-company.com` with the URL of your Plotly " - "On-Premise server.\nSee " - "https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users " - "for more help with getting started with On-Prem." -) - - -def _validate_domains(*domains): - for d in domains: - if not d.lower().startswith('https'): - warnings.warn(http_msg, category=UserWarning) - - # Warning format def warning_on_one_line(message, category, filename, lineno, file=None, line=None): @@ -216,6 +186,7 @@ def set_config_file(plotly_domain=None, :param (bool) world_readable: True = public, False = private """ + # import ipdb; ipdb.set_trace() if not check_file_permissions(): raise exceptions.PlotlyError("You don't have proper file permissions " "to run this function.") @@ -223,7 +194,7 @@ def set_config_file(plotly_domain=None, utils.validate_world_readable_and_sharing_settings({ 'sharing': sharing, 'world_readable': world_readable}) - settings = get_config_file(validate=False) + settings = get_config_file() if isinstance(plotly_domain, six.string_types): settings['plotly_domain'] = plotly_domain elif plotly_domain is not None: @@ -250,12 +221,9 @@ def set_config_file(plotly_domain=None, raise TypeError('auto_open should be a boolean') # validate plotly_domain and plotly_api_domain - list_of_domains = [] - if plotly_domain is not None: - list_of_domains.append(plotly_domain) - if plotly_api_domain is not None: - list_of_domains.append(plotly_api_domain) - _validate_domains(*list_of_domains) + utils.validate_plotly_domains( + {'plotly_domain': plotly_domain, 'plotly_api_domain': plotly_api_domain} + ) if isinstance(world_readable, bool): settings['world_readable'] = world_readable @@ -272,7 +240,7 @@ def set_config_file(plotly_domain=None, ensure_local_plotly_files() # make sure what we just put there is OK -def get_config_file(validate=True, *args): +def get_config_file(*args): """Return specified args from `~/.plotly/.config`. as tuple. Returns all if no arguments are specified. @@ -283,19 +251,9 @@ def get_config_file(validate=True, *args): """ if check_file_permissions(): ensure_local_plotly_files() # make sure what's there is OK - returned_obj = utils.load_json_dict(CONFIG_FILE, *args) + return utils.load_json_dict(CONFIG_FILE, *args) else: - returned_obj = FILE_CONTENT[CONFIG_FILE] - - list_of_domains = [] - for domain in ['plotly_domain', 'plotly_api_domain']: - if domain in returned_obj: - list_of_domains.append(returned_obj[domain]) - - if validate: - _validate_domains(*list_of_domains) - - return returned_obj + return FILE_CONTENT[CONFIG_FILE] def reset_config_file(): @@ -331,7 +289,7 @@ def get_embed(file_owner_or_url, file_id=None, width="100%", height=525): """ plotly_rest_url = (session.get_session_config().get('plotly_domain') or - get_config_file(validate=False)['plotly_domain']) + get_config_file()['plotly_domain']) if file_id is None: # assume we're using a url url = file_owner_or_url if url[:len(plotly_rest_url)] != plotly_rest_url: @@ -428,7 +386,7 @@ def embed(file_owner_or_url, file_id=None, width="100%", height=525): if file_id: plotly_domain = ( session.get_session_config().get('plotly_domain') or - get_config_file(validate=False)['plotly_domain'] + get_config_file()['plotly_domain'] ) url = "{plotly_domain}/~{un}/{fid}".format( plotly_domain=plotly_domain, @@ -454,7 +412,7 @@ def embed(file_owner_or_url, file_id=None, width="100%", height=525): ### mpl-related tools ### -@utils.template_doc(**get_config_file(validate=False)) +@utils.template_doc(**get_config_file()) def mpl_to_plotly(fig, resize=False, strip_style=False, verbose=False): """Convert a matplotlib figure to plotly dictionary and send. diff --git a/plotly/utils.py b/plotly/utils.py index 7d623014b5b..0102d4c38fd 100644 --- a/plotly/utils.py +++ b/plotly/utils.py @@ -7,11 +7,12 @@ """ from __future__ import absolute_import +import decimal import os.path import re import sys import threading -import decimal +import warnings from collections import deque import pytz @@ -32,6 +33,30 @@ lock = threading.Lock() +http_msg = ( + "The plotly_domain and plotly_api_domain of your config file must start " + "with 'https', 'http'.\n If you are not using On-Prem then run the " + "following code to ensure your plotly_domain and plotly_api_domain start " + "with 'https':\n\n\n" + "import plotly\n" + "plotly.tools.set_config_file(\n" + " plotly_domain='https://plot.ly',\n" + " plotly_api_domain='https://api.plot.ly'\n" + ")\n\n\n" + "If you are using On-Prem then you will need to use your company's " + "domain and api_domain urls:\n\n\n" + "import plotly\n" + "plotly.tools.set_config_file(\n" + " plotly_domain='https://plotly.your-company.com',\n" + " plotly_api_domain='https://plotly.your-company.com'\n" + ")\n\n\n" + "Make sure to replace `your-company.com` with the URL of your Plotly " + "On-Premise server.\nSee " + "https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users " + "for more help with getting started with On-Prem." +) + + ### general file setup tools ### def load_json_dict(filename, *args): @@ -297,6 +322,7 @@ def encode_as_decimal(obj): else: raise NotEncodable + ### unicode stuff ### def decode_unicode(coll): if isinstance(coll, list): @@ -436,6 +462,16 @@ def validate_world_readable_and_sharing_settings(option_set): ) +def validate_plotly_domains(option_set): + domains_not_none = [] + for d in ['plotly_domain', 'plotly_api_domain']: + if d in option_set and option_set[d]: + domains_not_none.append(option_set[d]) + + if not all(d.lower().startswith('https') for d in domains_not_none): + warnings.warn(http_msg, category=UserWarning) + + def set_sharing_and_world_readable(option_set): if 'world_readable' in option_set and 'sharing' not in option_set: option_set['sharing'] = ( From efc36a2da84469da9526d97c081a8aa1dc7905a0 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Wed, 2 May 2018 14:19:17 -0400 Subject: [PATCH 09/11] removed commented line --- plotly/tools.py | 1 - 1 file changed, 1 deletion(-) diff --git a/plotly/tools.py b/plotly/tools.py index 46e7c856e55..00daae4c161 100644 --- a/plotly/tools.py +++ b/plotly/tools.py @@ -186,7 +186,6 @@ def set_config_file(plotly_domain=None, :param (bool) world_readable: True = public, False = private """ - # import ipdb; ipdb.set_trace() if not check_file_permissions(): raise exceptions.PlotlyError("You don't have proper file permissions " "to run this function.") From 46d3cc9ec58a9184f1015437d8e7e16ebcf5e1d7 Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Thu, 3 May 2018 13:53:51 -0400 Subject: [PATCH 10/11] chuck's requestsed changes from review --- .../tests/test_core/test_tools/test_file_tools.py | 14 +++++++++++++- plotly/utils.py | 6 +++--- 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/plotly/tests/test_core/test_tools/test_file_tools.py b/plotly/tests/test_core/test_tools/test_file_tools.py index 47a54675e4a..c0a434ca71a 100644 --- a/plotly/tests/test_core/test_tools/test_file_tools.py +++ b/plotly/tests/test_core/test_tools/test_file_tools.py @@ -52,7 +52,7 @@ def test_set_config_file_world_readable(self): kwargs = {'world_readable': 'True'} self.assertRaises(TypeError, tools.set_config_file, **kwargs) - def test_set_config_expected_error_msg(self): + def test_set_config_expected_warning_msg(self): # Check that UserWarning is being called with http plotly_domain @@ -64,6 +64,18 @@ def test_set_config_expected_error_msg(self): assert issubclass(w[-1].category, UserWarning) assert "plotly_domain" in str(w[-1].message) + + def test_set_config_no_warning_msg_if_plotly_domain_is_https(self): + + # Check that no UserWarning is being called with https plotly_domain + + with warnings.catch_warnings(record=True) as w: + warnings.simplefilter("always") + kwargs = {'plotly_domain': 'https://www.foo-bar.com'} + tools.set_config_file(**kwargs) + assert len(w) == 0 + + def test_reset_config_file(self): # Check reset_config and get_config return the same values diff --git a/plotly/utils.py b/plotly/utils.py index 0102d4c38fd..0d9a81580fd 100644 --- a/plotly/utils.py +++ b/plotly/utils.py @@ -35,7 +35,7 @@ http_msg = ( "The plotly_domain and plotly_api_domain of your config file must start " - "with 'https', 'http'.\n If you are not using On-Prem then run the " + "with 'https', not 'http'.\n If you are not using On-Premise then run the " "following code to ensure your plotly_domain and plotly_api_domain start " "with 'https':\n\n\n" "import plotly\n" @@ -43,7 +43,7 @@ " plotly_domain='https://plot.ly',\n" " plotly_api_domain='https://api.plot.ly'\n" ")\n\n\n" - "If you are using On-Prem then you will need to use your company's " + "If you are using On-Premise then you will need to use your company's " "domain and api_domain urls:\n\n\n" "import plotly\n" "plotly.tools.set_config_file(\n" @@ -53,7 +53,7 @@ "Make sure to replace `your-company.com` with the URL of your Plotly " "On-Premise server.\nSee " "https://plot.ly/python/getting-started/#special-instructions-for-plotly-onpremise-users " - "for more help with getting started with On-Prem." + "for more help with getting started with On-Premise." ) From 2a0872c71766f85dbdd77a7cec12f91165f8829a Mon Sep 17 00:00:00 2001 From: Adam Kulidjian Date: Fri, 4 May 2018 14:53:00 -0400 Subject: [PATCH 11/11] remove \n from msg --- plotly/utils.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plotly/utils.py b/plotly/utils.py index 0d9a81580fd..b39426bf65f 100644 --- a/plotly/utils.py +++ b/plotly/utils.py @@ -35,7 +35,7 @@ http_msg = ( "The plotly_domain and plotly_api_domain of your config file must start " - "with 'https', not 'http'.\n If you are not using On-Premise then run the " + "with 'https', not 'http'. If you are not using On-Premise then run the " "following code to ensure your plotly_domain and plotly_api_domain start " "with 'https':\n\n\n" "import plotly\n"