8000 Add warnings when adding workbook to schedule (#551) · scuml/server-client-python@10381bc · GitHub
[go: up one dir, main page]

Skip to content
8000

Commit 10381bc

Browse files
guodahChris Shin
authored and
Chris Shin
committed
Add warnings when adding workbook to schedule (tableau#551)
* fixing a bug due to bool(time(0,0)) is false * check warnings in Schedules.add_to_schedule * fixed a typo * removed unused comment * handle the case where a task was indeed created, but there is a warning * remove unnecessary import
1 parent a5caa7c commit 10381bc

File tree

6 files changed

+87
-16
lines changed

6 files changed

+87
-16
lines changed

tableauserverclient/models/schedule_item.py

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -162,10 +162,7 @@ def from_response(cls, resp, ns):
162162

163163
@classmethod
164164
def from_element(cls, parsed_response, ns):
165-
all_warning_xml = parsed_response.findall('.//t:warning', namespaces=ns)
166-
warnings = list() if len(all_warning_xml) > 0 else None
167-
for warning_xml in all_warning_xml:
168-
warnings.append(warning_xml.get('message', None))
165+
warnings = cls._read_warnings(parsed_response, ns)
169166

170167
all_schedule_items = []
171168
all_schedule_xml = parsed_response.findall('.//t:schedule', namespaces=ns)
@@ -248,3 +245,22 @@ def _parse_element(schedule_xml, ns):
248245

249246
return id, name, state, created_at, updated_at, schedule_type, \
250247
next_run_at, end_schedule_at, execution_order, priority, interval_item
248+
249+
@staticmethod
250+
def parse_add_to_schedule_response(response, ns):
251+
parsed_response = ET.fromstring(response.content)
252+
warnings = ScheduleItem._read_warnings(parsed_response, ns)
253+
all_task_xml = parsed_response.findall('.//t:task', namespaces=ns)
254+
255+
error = "Status {}: {}".format(response.status_code, response.reason) \
256+
if response.status_code < 200 or response.status_code >= 300 else None
257+
task_created = len(all_task_xml) > 0
258+
return error, warnings, task_created
259+
260+
@staticmethod
261+
def _read_warnings(parsed_response, ns):
262+
all_warning_xml = parsed_response.findall('.//t:warning', namespaces=ns)
263+
warnings = list() if len(all_warning_xml) > 0 else None
264+
for warning_xml in all_warning_xml:
265+
warnings.append(warning_xml.get('message', None))
266+
return warnings

tableauserverclient/server/endpoint/schedules_endpoint.py

Lines changed: 12 additions & 8 deletions
8000
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@
77

88
logger = logging.getLogger('tableau.endpoint.schedules')
99
# Oh to have a first class Result concept in Python...
10-
AddResponse = namedtuple('AddResponse', ('result', 'error'))
11-
OK = AddResponse(result=True, error=None)
10+
AddResponse = namedtuple('AddResponse', ('result', 'error', 'warnings', 'task_created'))
11+
OK = AddResponse(result=True, error=None, warnings=None, task_created=None)
1212

1313

1414
class Schedules(Endpoint):
@@ -70,17 +70,21 @@ def create(self, schedule_item):
7070
@api(version="2.8")
7171
def add_to_schedule(self, schedule_id, workbook=None, datasource=None,
7272
task_type=TaskItem.Type.ExtractRefresh):
73-
7473
def add_to(resource, type_, req_factory):
7574
id_ = resource.id
7675
url = "{0}/{1}/{2}s".format(self.siteurl, schedule_id, type_)
7776
add_req = req_factory(id_, task_type=task_type)
7877
response = self.put_request(url, add_req)
79-
if response.status_code < 200 or response.status_code >= 300:
80-
return AddResponse(result=False,
81-
error="Status {}: {}".format(response.status_code, response.reason))
82-
logger.info("Added {} to {} to schedule {}".format(type_, id_, schedule_id))
83-
return OK
78+
79+
error, warnings, task_created = ScheduleItem.parse_add_to_schedule_response(
80+
response, self.parent_srv.namespace)
81+
if task_created:
82+
logger.info("Added {} to {} to schedule {}".format(type_, id_, schedule_id))
83+
84+
if error is not None or warnings is not None:
85+
return AddResponse(result=False, error=error, warnings=warnings, task_created=task_created)
86+
else:
87+
return OK
8488

8589
items = []
8690

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<?xml version='1.0' encoding='UTF-8'?>
2+
<tsResponse xmlns="http://tableau.com/api" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://tableau.com/api http://tableau.com/api/ts-api-2.3.xsd">
3+
<task>
4+
<extractRefresh>
5+
<schedule id="schedule-id" />
6+
<datasource id="datasource-id" />
7+
</extractRefresh>
8+
</task>
9+
</tsResponse>

test/assets/schedule_add_workbook.xml

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<?xml version='1.0' encoding='UTF-8'?>
2+
<tsResponse xmlns="http://tableau.com/api" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://tableau.com/api http://tableau.com/api/ts-api-2.3.xsd">
3+
<task>
4+
<materializeView>
5+
<schedule id="schedule-id" />
6+
<workbook id="workbook-id" />
7+
</materializeView>
8+
</task>
9+
</tsResponse>
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
<tsResponse xmlns="http://tableau.com/api" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://tableau.com/api http://tableau.com/api/ts-api-2.3.xsd">
2+
<task>
3+
<materializeView>
4+
<schedule id="schedule-id" />
5+
<workbook id="workbook-id" />
6+
</materializeView>
7+
</task>
8+
<warnings>
9+
<warning message="warning 1"/>
10+
<warning message="warning 2"/>
11+
</warnings>
12+
</tsResponse>

test/test_schedule.py

Lines changed: 25 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,9 @@
1414
CREATE_WEEKLY_XML = os.path.join(TEST_ASSET_DIR, "schedule_create_weekly.xml")
1515
CREATE_MONTHLY_XML = os.path.join(TEST_ASSET_DIR, "schedule_create_monthly.xml")
1616
UPDATE_XML = os.path.join(TEST_ASSET_DIR, "schedule_update.xml")
17+
ADD_WORKBOOK_TO_SCHEDULE = os.path.join(TEST_ASSET_DIR, "schedule_add_workbook.xml")
18+
ADD_WORKBOOK_TO_SCHEDULE_WITH_WARNINGS = os.path.join(TEST_ASSET_DIR, "schedule_add_workbook_with_warnings.xml")
19+
ADD_DATASOURCE_TO_SCHEDULE = os.path.join(TEST_ASSET_DIR, "schedule_add_datasource.xml")
1720

1821
WORKBOOK_GET_BY_ID_XML = os.path.join(TEST_ASSET_DIR, 'workbook_get_by_id.xml')
1922
DATASOURCE_GET_BY_ID_XML = os.path.join(TEST_ASSET_DIR, 'datasource_get_by_id.xml')
@@ -208,24 +211,42 @@ def test_add_workbook(self):
208211

209212
with open(WORKBOOK_GET_BY_ID_XML, "rb") as f:
210213
workbook_response = f.read().decode("utf-8")
214+
with open(ADD_WORKBOOK_TO_SCHEDULE, "rb") as f:
215+
add_workbook_response = f.read().decode("utf-8")
211216
with requests_mock.mock() as m:
212-
# TODO: Replace with real response
213217
m.get(self.server.workbooks.baseurl + '/bar', text=workbook_response)
214-
m.put(baseurl + '/foo/workbooks', text="OK")
218+
m.put(baseurl + '/foo/workbooks', text=add_workbook_response)
215219
workbook = self.server.workbooks.get_by_id("bar")
216220
result = self.server.schedules.add_to_schedule('foo', workbook=workbook)
217221
self.assertEqual(0, len(result), "Added properly")
218222

223+
def test_add_workbook_with_warnings(self):
224+
self.server.version = "2.8"
225+
baseurl = "{}/sites/{}/schedules".format(self.server.baseurl, self.server.site_id)
226+
227+
with open(WORKBOOK_GET_BY_ID_XML, "rb") as f:
228+
workbook_response = f.read().decode("utf-8")
229+
with open(ADD_WORKBOOK_TO_SCHEDULE_WITH_WARNINGS, "rb") as f:
230+
add_workbook_response = f.read().decode("utf-8")
231+
with requests_mock.mock() as m:
232+
m.get(self.server.workbooks.baseurl + '/bar', text=workbook_response)
233+
m.put(baseurl + '/foo/workbooks', text=add_workbook_response)
234+
workbook = self.server.workbooks.get_by_id("bar")
235+
result = self.server.schedules.add_to_schedule('foo', workbook=workbook)
236+
self.assertEqual(1, len(result), "Not added properly")
237+
self.assertEqual(2, len(result[0].warnings))
238+
219239
def test_add_datasource(self):
220240
self.server.version = "2.8"
221241
baseurl = "{}/sites/{}/schedules".format(self.server.baseurl, self.server.site_id)
222242

223243
with open(DATASOURCE_GET_BY_ID_XML, "rb") as f:
224244
datasource_response = f.read().decode("utf-8")
245+
with open(ADD_DATASOURCE_TO_SCHEDULE, "rb") as f:
246+
add_datasource_response = f.read().decode("utf-8")
225247
with requests_mock.mock() as m:
226-
# TODO: Replace with real response
227248
m.get(self.server.datasources.baseurl + '/bar', text=datasource_response)
228-
m.put(baseurl + '/foo/datasources', text="OK")
249+
m.put(baseurl + '/foo/datasources', text=add_datasource_response)
229250
datasource = self.server.datasources.get_by_id("bar")
230251
result = self.server.schedules.add_to_schedule('foo', datasource=datasource)
231252
self.assertEqual(0, len(result), "Added properly")

0 commit comments

Comments
 (0)
0