diff --git a/.gitignore b/.gitignore index e9bd2b49f..92778cd81 100644 --- a/.gitignore +++ b/.gitignore @@ -155,3 +155,4 @@ $RECYCLE.BIN/ docs/_site/ docs/.jekyll-metadata docs/Gemfile.lock +samples/credentials diff --git a/contributing.md b/contributing.md index 41c339cb6..6404611a9 100644 --- a/contributing.md +++ b/contributing.md @@ -10,8 +10,7 @@ Contribution can include, but are not limited to, any of the following: * Fix an Issue/Bug * Add/Fix documentation -Contributions must follow the guidelines outlined on the [Tableau Organization](http://tableau.github.io/) page, though filing an issue or requesting -a feature do not require the CLA. +Contributions must follow the guidelines outlined on the [Tableau Organization](http://tableau.github.io/) page, though filing an issue or requesting a feature do not require the CLA. ## Issues and Feature Requests diff --git a/samples/getting_started/3_hello_universe.py b/samples/getting_started/3_hello_universe.py index 3ed39fd17..21de97831 100644 --- a/samples/getting_started/3_hello_universe.py +++ b/samples/getting_started/3_hello_universe.py @@ -62,11 +62,6 @@ def main(): print("{} jobs".format(pagination.total_available)) print(jobs[0]) - metrics, pagination = server.metrics.get() - if metrics: - print("{} metrics".format(pagination.total_available)) - print(metrics[0]) - schedules, pagination = server.schedules.get() if schedules: print("{} schedules".format(pagination.total_available)) @@ -82,7 +77,7 @@ def main(): print("{} webhooks".format(pagination.total_available)) print(webhooks[0]) - users, pagination = server.metrics.get() + users, pagination = server.users.get() if users: print("{} users".format(pagination.total_available)) print(users[0]) @@ -92,5 +87,6 @@ def main(): print("{} groups".format(pagination.total_available)) print(groups[0]) - if __name__ == "__main__": - main() + +if __name__ == "__main__": + main() diff --git a/tableauserverclient/models/interval_item.py b/tableauserverclient/models/interval_item.py index f2f159625..537e6c14f 100644 --- a/tableauserverclient/models/interval_item.py +++ b/tableauserverclient/models/interval_item.py @@ -69,7 +69,7 @@ def interval(self): @interval.setter def interval(self, intervals): - VALID_INTERVALS = {0.25, 0.5, 1, 2, 4, 6, 8, 12} + VALID_INTERVALS = {0.25, 0.5, 1, 2, 4, 6, 8, 12, 24} for interval in intervals: # if an hourly interval is a string, then it is a weekDay interval if isinstance(interval, str) and not interval.isnumeric() and not hasattr(IntervalItem.Day, interval): diff --git a/tableauserverclient/server/endpoint/endpoint.py b/tableauserverclient/server/endpoint/endpoint.py index 77a771288..2b7f57069 100644 --- a/tableauserverclient/server/endpoint/endpoint.py +++ b/tableauserverclient/server/endpoint/endpoint.py @@ -1,5 +1,3 @@ -from threading import Thread -from time import sleep from tableauserverclient import datetime_helpers as datetime from packaging.version import Version @@ -76,55 +74,20 @@ def set_user_agent(parameters): return parameters def _blocking_request(self, method, url, parameters={}) -> Optional[Union["Response", Exception]]: - self.async_response = None response = None logger.debug("[{}] Begin blocking request to {}".format(datetime.timestamp(), url)) try: response = method(url, **parameters) - self.async_response = response logger.debug("[{}] Call finished".format(datetime.timestamp())) except Exception as e: logger.debug("Error making request to server: {}".format(e)) - self.async_response = e - finally: - if response and not self.async_response: - logger.debug("Request response not saved") - return None - logger.debug("[{}] Request complete".format(datetime.timestamp())) - return self.async_response + raise e + return response def send_request_while_show_progress_threaded( self, method, url, parameters={}, request_timeout=None ) -> Optional[Union["Response", Exception]]: - try: - request_thread = Thread(target=self._blocking_request, args=(method, url, parameters)) - request_thread.start() - except Exception as e: - logger.debug("Error starting server request on separate thread: {}".format(e)) - return None - seconds = 0.05 - minutes = 0 - last_log_minute = 0 - sleep(seconds) - if self.async_response is not None: - # a quick return for any immediate responses - return self.async_response - timed_out: bool = request_timeout is not None and seconds > request_timeout - while (self.async_response is None) and not timed_out: - sleep(DELAY_SLEEP_SECONDS) - seconds = seconds + DELAY_SLEEP_SECONDS - minutes = int(seconds / 60) - last_log_minute = self.log_wait_time(minutes, last_log_minute, url) - return self.async_response - - def log_wait_time(self, minutes, last_log_minute, url) -> int: - logger.debug("{} Waiting....".format(datetime.timestamp())) - if minutes > last_log_minute: # detailed log message ~every minute - logger.info("[{}] Waiting ({} minutes so far) for request to {}".format(datetime.timestamp(), minutes, url)) - last_log_minute = minutes - else: - logger.debug("[{}] Waiting for request to {}".format(datetime.timestamp(), url)) - return last_log_minute + return self._blocking_request(method, url, parameters) def _make_request( self, diff --git a/test/test_endpoint.py b/test/test_endpoint.py index 3d2d1c995..8635af978 100644 --- a/test/test_endpoint.py +++ b/test/test_endpoint.py @@ -1,4 +1,6 @@ from pathlib import Path +import pytest +import requests import unittest import tableauserverclient as TSC @@ -35,11 +37,12 @@ def test_user_friendly_request_returns(self) -> None: ) self.assertIsNotNone(response) - def test_blocking_request_returns(self) -> None: - url = "http://test/" - endpoint = TSC.server.Endpoint(self.server) - response = endpoint._blocking_request(endpoint.parent_srv.session.get, url=url) - self.assertIsNotNone(response) + def test_blocking_request_raises_request_error(self) -> None: + with pytest.raises(requests.exceptions.ConnectionError): + url = "http://test/" + endpoint = TSC.server.Endpoint(self.server) + response = endpoint._blocking_request(endpoint.parent_srv.session.get, url=url) + self.assertIsNotNone(response) def test_get_request_stream(self) -> None: url = "http://test/"