From 3e849a9799b5631924f5965adcb684ca3cfdd6fc Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Tue, 19 Aug 2025 22:17:15 -0500 Subject: [PATCH 1/7] chore: workook tests converted to pytest --- .../server/endpoint/workbooks_endpoint.py | 70 ++- test/test_workbook.py | 533 +++++++++--------- 2 files changed, 321 insertions(+), 282 deletions(-) diff --git a/tableauserverclient/server/endpoint/workbooks_endpoint.py b/tableauserverclient/server/endpoint/workbooks_endpoint.py index 907d2d99..19bceb9b 100644 --- a/tableauserverclient/server/endpoint/workbooks_endpoint.py +++ b/tableauserverclient/server/endpoint/workbooks_endpoint.py @@ -30,9 +30,12 @@ from tableauserverclient.server import RequestFactory from typing import ( + Literal, Optional, TYPE_CHECKING, + TypeVar, Union, + overload, ) from collections.abc import Iterable, Sequence @@ -383,16 +386,33 @@ def update_connections( logger.info(f"Updated connections for workbook {workbook_item.id}: {', '.join(updated_ids)}") return connection_items + T = TypeVar("T", bound=FileObjectW) + @overload + def download( + self, + workbook_id: str, + filepath: T, + include_extract: bool = True, + ) -> T: ... + + @overload + def download( + self, + workbook_id: str, + filepath: Optional[FilePath] = None, + include_extract: bool = True, + ) -> str: ... + # Download workbook contents with option of passing in filepath @api(version="2.0") @parameter_added_in(no_extract="2.5") @parameter_added_in(include_extract="2.5") def download( self, - workbook_id: str, - filepath: Optional[PathOrFileW] = None, - include_extract: bool = True, - ) -> PathOrFileW: + workbook_id, + filepath=None, + include_extract=True, + ): """ Downloads a workbook to the specified directory (optional). @@ -741,6 +761,28 @@ def delete_permission(self, item: WorkbookItem, capability_item: PermissionsRule """ return self._permissions.delete(item, capability_item) + @overload + def publish(self, + workbook_item: WorkbookItem, + file: PathOrFileR, + mode: str, + connections: Optional[Sequence[ConnectionItem]], + as_job: Literal[False], + skip_connection_check: bool, + parameters=None, + ) -> WorkbookItem: ... + + @overload + def publish(self, + workbook_item: WorkbookItem, + file: PathOrFileR, + mode: str, + connections: Optional[Sequence[ConnectionItem]], + as_job: Literal[True], + skip_connection_check: bool, + parameters=None, + ) -> JobItem: ... + @api(version="2.0") @parameter_added_in(as_job="3.0") @parameter_added_in(connections="2.8") @@ -977,15 +1019,25 @@ def _get_workbook_revisions( revisions = RevisionItem.from_response(server_response.content, self.parent_srv.namespace, workbook_item) return revisions + @overload + def download_revision( + self, workbook_id: str, revision_number: Optional[str], filepath: FileObjectW, include_extract: bool + ) -> FileObjectW: ... + + @overload + def download_revision( + self, workbook_id: str, revision_number: Optional[str], filepath: Optional[FilePath], include_extract: bool + ) -> str: ... + # Download 1 workbook revision by revision number @api(version="2.3") def download_revision( self, - workbook_id: str, - revision_number: Optional[str], - filepath: Optional[PathOrFileW] = None, - include_extract: bool = True, - ) -> PathOrFileW: + workbook_id, + revision_number, + filepath, + include_extract=True, + ): """ Downloads a workbook revision to the specified directory (optional). diff --git a/test/test_workbook.py b/test/test_workbook.py index a4242c21..96a43dfd 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -59,33 +59,33 @@ def test_get(self) -> None: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() - self.assertEqual(2, pagination_item.total_available) - self.assertEqual("6d13b0ca-043d-4d42-8c9d-3f3313ea3a00", all_workbooks[0].id) - self.assertEqual("Superstore", all_workbooks[0].name) - self.assertEqual("Superstore", all_workbooks[0].content_url) - self.assertEqual(False, all_workbooks[0].show_tabs) - self.assertEqual("http://tableauserver/#/workbooks/1/views", all_workbooks[0].webpage_url) - self.assertEqual(1, all_workbooks[0].size) - self.assertEqual("2016-08-03T20:34:04Z", format_datetime(all_workbooks[0].created_at)) - self.assertEqual("description for Superstore", all_workbooks[0].description) - self.assertEqual("2016-08-04T17:56:41Z", format_datetime(all_workbooks[0].updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", all_workbooks[0].project_id) - self.assertEqual("default", all_workbooks[0].project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", all_workbooks[0].owner_id) - - self.assertEqual("3cc6cd06-89ce-4fdc-b935-5294135d6d42", all_workbooks[1].id) - self.assertEqual("SafariSample", all_workbooks[1].name) - self.assertEqual("SafariSample", all_workbooks[1].content_url) - self.assertEqual("http://tableauserver/#/workbooks/2/views", all_workbooks[1].webpage_url) - self.assertEqual(False, all_workbooks[1].show_tabs) - self.assertEqual(26, all_workbooks[1].size) - self.assertEqual("2016-07-26T20:34:56Z", format_datetime(all_workbooks[1].created_at)) - self.assertEqual("description for SafariSample", all_workbooks[1].description) - self.assertEqual("2016-07-26T20:35:05Z", format_datetime(all_workbooks[1].updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", all_workbooks[1].project_id) - self.assertEqual("default", all_workbooks[1].project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", all_workbooks[1].owner_id) - self.assertEqual({"Safari", "Sample"}, all_workbooks[1].tags) + assert 2 == pagination_item.total_available + assert "6d13b0ca-043d-4d42-8c9d-3f3313ea3a00" == all_workbooks[0].id + assert "Superstore" == all_workbooks[0].name + assert "Superstore" == all_workbooks[0].content_url + assert not all_workbooks[0].show_tabs + assert "http://tableauserver/#/workbooks/1/views" == all_workbooks[0].webpage_url + assert 1 == all_workbooks[0].size + assert "2016-08-03T20:34:04Z" == format_datetime(all_workbooks[0].created_at) + assert "description for Superstore" == all_workbooks[0].description + assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[0].project_id + assert "default" == all_workbooks[0].project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[0].owner_id + + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == all_workbooks[1].id + assert "SafariSample" == all_workbooks[1].name + assert "SafariSample" == all_workbooks[1].content_url + assert "http://tableauserver/#/workbooks/2/views" == all_workbooks[1].webpage_url + assert not all_workbooks[1].show_tabs + assert 26 == all_workbooks[1].size + assert "2016-07-26T20:34:56Z" == format_datetime(all_workbooks[1].created_at) + assert "description for SafariSample" == all_workbooks[1].description + assert "2016-07-26T20:35:05Z" == format_datetime(all_workbooks[1].updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[1].project_id + assert "default" == all_workbooks[1].project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[1].owner_id + assert {"Safari", "Sample"} == all_workbooks[1].tags def test_get_ignore_invalid_date(self) -> None: with open(GET_INVALID_DATE_XML, "rb") as f: @@ -93,12 +93,13 @@ def test_get_ignore_invalid_date(self) -> None: with requests_mock.mock() as m: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() - self.assertEqual(None, format_datetime(all_workbooks[0].created_at)) - self.assertEqual("2016-08-04T17:56:41Z", format_datetime(all_workbooks[0].updated_at)) + assert format_datetime(all_workbooks[0].created_at) is None + assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) def test_get_before_signin(self) -> None: self.server._auth_token = None - self.assertRaises(TSC.NotSignedInError, self.server.workbooks.get) + with pytest.raises(TSC.NotSignedInError): + self.server.workbooks.get() def test_get_empty(self) -> None: with open(GET_EMPTY_XML, "rb") as f: @@ -107,8 +108,8 @@ def test_get_empty(self) -> None: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() - self.assertEqual(0, pagination_item.total_available) - self.assertEqual([], all_workbooks) + assert 0 == pagination_item.total_available + assert [] == all_workbooks def test_get_by_id(self) -> None: with open(GET_BY_ID_XML, "rb") as f: @@ -117,22 +118,22 @@ def test_get_by_id(self) -> None: m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - self.assertEqual("3cc6cd06-89ce-4fdc-b935-5294135d6d42", single_workbook.id) - self.assertEqual("SafariSample", single_workbook.name) - self.assertEqual("SafariSample", single_workbook.content_url) - self.assertEqual("http://tableauserver/#/workbooks/2/views", single_workbook.webpage_url) - self.assertEqual(False, single_workbook.show_tabs) - self.assertEqual(26, single_workbook.size) - self.assertEqual("2016-07-26T20:34:56Z", format_datetime(single_workbook.created_at)) - self.assertEqual("description for SafariSample", single_workbook.description) - self.assertEqual("2016-07-26T20:35:05Z", format_datetime(single_workbook.updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", single_workbook.project_id) - self.assertEqual("default", single_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", single_workbook.owner_id) - self.assertEqual({"Safari", "Sample"}, single_workbook.tags) - self.assertEqual("d79634e1-6063-4ec9-95ff-50acbf609ff5", single_workbook.views[0].id) - self.assertEqual("ENDANGERED SAFARI", single_workbook.views[0].name) - self.assertEqual("SafariSample/sheets/ENDANGEREDSAFARI", single_workbook.views[0].content_url) + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == single_workbook.id + assert "SafariSample" == single_workbook.name + assert "SafariSample" == single_workbook.content_url + assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url + assert not single_workbook.show_tabs + assert 26 == single_workbook.size + assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) + assert "description for SafariSample" == single_workbook.description + assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == single_workbook.project_id + assert "default" == single_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id + assert {"Safari", "Sample"} == single_workbook.tags + assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id + assert "ENDANGERED SAFARI" == single_workbook.views[0].name + assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url def test_get_by_id_personal(self) -> None: # workbooks in personal space don't have project_id or project_name @@ -142,25 +143,26 @@ def test_get_by_id_personal(self) -> None: m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d43", text=response_xml) single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d43") - self.assertEqual("3cc6cd06-89ce-4fdc-b935-5294135d6d43", single_workbook.id) - self.assertEqual("SafariSample", single_workbook.name) - self.assertEqual("SafariSample", single_workbook.content_url) - self.assertEqual("http://tableauserver/#/workbooks/2/views", single_workbook.webpage_url) - self.assertEqual(False, single_workbook.show_tabs) - self.assertEqual(26, single_workbook.size) - self.assertEqual("2016-07-26T20:34:56Z", format_datetime(single_workbook.created_at)) - self.assertEqual("description for SafariSample", single_workbook.description) - self.assertEqual("2016-07-26T20:35:05Z", format_datetime(single_workbook.updated_at)) - self.assertTrue(single_workbook.project_id) - self.assertIsNone(single_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", single_workbook.owner_id) - self.assertEqual({"Safari", "Sample"}, single_workbook.tags) - self.assertEqual("d79634e1-6063-4ec9-95ff-50acbf609ff5", single_workbook.views[0].id) - self.assertEqual("ENDANGERED SAFARI", single_workbook.views[0].name) - self.assertEqual("SafariSample/sheets/ENDANGEREDSAFARI", single_workbook.views[0].content_url) + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d43" == single_workbook.id + assert "SafariSample" == single_workbook.name + assert "SafariSample" == single_workbook.content_url + assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url + assert not single_workbook.show_tabs + assert 26 == single_workbook.size + assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) + assert "description for SafariSample" == single_workbook.description + assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) + assert single_workbook.project_id + assert single_workbook.project_name is None + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id + assert {"Safari", "Sample"} == single_workbook.tags + assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id + assert "ENDANGERED SAFARI" == single_workbook.views[0].name + assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url def test_get_by_id_missing_id(self) -> None: - self.assertRaises(ValueError, self.server.workbooks.get_by_id, "") + with pytest.raises(ValueError): + self.server.workbooks.get_by_id("") def test_refresh_id(self) -> None: self.server.version = "2.8" @@ -188,7 +190,8 @@ def test_delete(self) -> None: self.server.workbooks.delete("3cc6cd06-89ce-4fdc-b935-5294135d6d42") def test_delete_missing_id(self) -> None: - self.assertRaises(ValueError, self.server.workbooks.delete, "") + with pytest.raises(ValueError): + self.server.workbooks.delete("") def test_update(self) -> None: with open(UPDATE_XML, "rb") as f: @@ -207,17 +210,18 @@ def test_update(self) -> None: } single_workbook = self.server.workbooks.update(single_workbook) - self.assertEqual("1f951daf-4061-451a-9df1-69a8062664f2", single_workbook.id) - self.assertEqual(True, single_workbook.show_tabs) - self.assertEqual("1d0304cd-3796-429f-b815-7258370b9b74", single_workbook.project_id) - self.assertEqual("dd2239f6-ddf1-4107-981a-4cf94e415794", single_workbook.owner_id) - self.assertEqual("renamedWorkbook", single_workbook.name) - self.assertEqual(True, single_workbook.data_acceleration_config["acceleration_enabled"]) - self.assertEqual(False, single_workbook.data_acceleration_config["accelerate_now"]) + assert "1f951daf-4061-451a-9df1-69a8062664f2" == single_workbook.id + assert single_workbook.show_tabs + assert "1d0304cd-3796-429f-b815-7258370b9b74" == single_workbook.project_id + assert "dd2239f6-ddf1-4107-981a-4cf94e415794" == single_workbook.owner_id + assert "renamedWorkbook" == single_workbook.name + assert single_workbook.data_acceleration_config["acceleration_enabled"] + assert not single_workbook.data_acceleration_config["accelerate_now"] def test_update_missing_id(self) -> None: single_workbook = TSC.WorkbookItem("test") - self.assertRaises(TSC.MissingRequiredFieldError, self.server.workbooks.update, single_workbook) + with pytest.raises(TSC.MissingRequiredFieldError): + self.server.workbooks.update(single_workbook) def test_update_copy_fields(self) -> None: with open(POPULATE_CONNECTIONS_XML, "rb") as f: @@ -232,11 +236,11 @@ def test_update_copy_fields(self) -> None: self.server.workbooks.populate_connections(single_workbook) updated_workbook = self.server.workbooks.update(single_workbook) - self.assertEqual(single_workbook._connections, updated_workbook._connections) - self.assertEqual(single_workbook._views, updated_workbook._views) - self.assertEqual(single_workbook.tags, updated_workbook.tags) - self.assertEqual(single_workbook._initial_tags, updated_workbook._initial_tags) - self.assertEqual(single_workbook._preview_image, updated_workbook._preview_image) + assert single_workbook._connections == updated_workbook._connections + assert single_workbook._views == updated_workbook._views + assert single_workbook.tags == updated_workbook.tags + assert single_workbook._initial_tags == updated_workbook._initial_tags + assert single_workbook._preview_image == updated_workbook._preview_image def test_update_tags(self) -> None: with open(ADD_TAGS_XML, "rb") as f: @@ -254,8 +258,8 @@ def test_update_tags(self) -> None: single_workbook.tags.update(["a", "c", "e"]) updated_workbook = self.server.workbooks.update(single_workbook) - self.assertEqual(single_workbook.tags, updated_workbook.tags) - self.assertEqual(single_workbook._initial_tags, updated_workbook._initial_tags) + assert single_workbook.tags == updated_workbook.tags + assert single_workbook._initial_tags == updated_workbook._initial_tags def test_download(self) -> None: with requests_mock.mock() as m: @@ -264,7 +268,7 @@ def test_download(self) -> None: headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, ) file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") - self.assertTrue(os.path.exists(file_path)) + assert os.path.exists(file_path) os.remove(file_path) def test_download_object(self) -> None: @@ -275,7 +279,7 @@ def test_download_object(self) -> None: headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, ) file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", filepath=file_object) - self.assertTrue(isinstance(file_path, BytesIO)) + assert isinstance(file_path, BytesIO) def test_download_sanitizes_name(self) -> None: filename = "Name,With,Commas.twbx" @@ -286,8 +290,8 @@ def test_download_sanitizes_name(self) -> None: headers={"Content-Disposition": disposition}, ) file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") - self.assertEqual(os.path.basename(file_path), "NameWithCommas.twbx") - self.assertTrue(os.path.exists(file_path)) + assert os.path.basename(file_path) == "NameWithCommas.twbx" + assert os.path.exists(file_path) os.remove(file_path) def test_download_extract_only(self) -> None: @@ -303,11 +307,12 @@ def test_download_extract_only(self) -> None: ) # Technically this shouldn't download a twbx, but we are interested in the qs, not the file file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", include_extract=False) - self.assertTrue(os.path.exists(file_path)) + assert os.path.exists(file_path) os.remove(file_path) def test_download_missing_id(self) -> None: - self.assertRaises(ValueError, self.server.workbooks.download, "") + with pytest.raises(ValueError): + self.server.workbooks.download("") def test_populate_views(self) -> None: with open(POPULATE_VIEWS_XML, "rb") as f: @@ -319,17 +324,17 @@ def test_populate_views(self) -> None: self.server.workbooks.populate_views(single_workbook) views_list = single_workbook.views - self.assertEqual("097dbe13-de89-445f-b2c3-02f28bd010c1", views_list[0].id) - self.assertEqual("GDP per capita", views_list[0].name) - self.assertEqual("RESTAPISample/sheets/GDPpercapita", views_list[0].content_url) + assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id + assert "GDP per capita" == views_list[0].name + assert "RESTAPISample/sheets/GDPpercapita" == views_list[0].content_url - self.assertEqual("2c1ab9d7-8d64-4cc6-b495-52e40c60c330", views_list[1].id) - self.assertEqual("Country ranks", views_list[1].name) - self.assertEqual("RESTAPISample/sheets/Countryranks", views_list[1].content_url) + assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id + assert "Country ranks" == views_list[1].name + assert "RESTAPISample/sheets/Countryranks" == views_list[1].content_url - self.assertEqual("0599c28c-6d82-457e-a453-e52c1bdb00f5", views_list[2].id) - self.assertEqual("Interest rates", views_list[2].name) - self.assertEqual("RESTAPISample/sheets/Interestrates", views_list[2].content_url) + assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id + assert "Interest rates" == views_list[2].name + assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url def test_populate_views_with_usage(self) -> None: with open(POPULATE_VIEWS_USAGE_XML, "rb") as f: @@ -344,16 +349,17 @@ def test_populate_views_with_usage(self) -> None: self.server.workbooks.populate_views(single_workbook, usage=True) views_list = single_workbook.views - self.assertEqual("097dbe13-de89-445f-b2c3-02f28bd010c1", views_list[0].id) - self.assertEqual(2, views_list[0].total_views) - self.assertEqual("2c1ab9d7-8d64-4cc6-b495-52e40c60c330", views_list[1].id) - self.assertEqual(37, views_list[1].total_views) - self.assertEqual("0599c28c-6d82-457e-a453-e52c1bdb00f5", views_list[2].id) - self.assertEqual(0, views_list[2].total_views) + assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id + assert 2 == views_list[0].total_views + assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id + assert 37 == views_list[1].total_views + assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id + assert 0 == views_list[2].total_views def test_populate_views_missing_id(self) -> None: single_workbook = TSC.WorkbookItem("test") - self.assertRaises(TSC.MissingRequiredFieldError, self.server.workbooks.populate_views, single_workbook) + with pytest.raises(TSC.MissingRequiredFieldError): + self.server.workbooks.populate_views(single_workbook) def test_populate_connections(self) -> None: with open(POPULATE_CONNECTIONS_XML, "rb") as f: @@ -364,10 +370,10 @@ def test_populate_connections(self) -> None: single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" self.server.workbooks.populate_connections(single_workbook) - self.assertEqual("37ca6ced-58d7-4dcf-99dc-f0a85223cbef", single_workbook.connections[0].id) - self.assertEqual("dataengine", single_workbook.connections[0].connection_type) - self.assertEqual("4506225a-0d32-4ab1-82d3-c24e85f7afba", single_workbook.connections[0].datasource_id) - self.assertEqual("World Indicators", single_workbook.connections[0].datasource_name) + assert "37ca6ced-58d7-4dcf-99dc-f0a85223cbef" == single_workbook.connections[0].id + assert "dataengine" == single_workbook.connections[0].connection_type + assert "4506225a-0d32-4ab1-82d3-c24e85f7afba" == single_workbook.connections[0].datasource_id + assert "World Indicators" == single_workbook.connections[0].datasource_name def test_populate_permissions(self) -> None: with open(POPULATE_PERMISSIONS_XML, "rb") as f: @@ -380,29 +386,24 @@ def test_populate_permissions(self) -> None: self.server.workbooks.populate_permissions(single_workbook) permissions = single_workbook.permissions - self.assertEqual(permissions[0].grantee.tag_name, "group") - self.assertEqual(permissions[0].grantee.id, "5e5e1978-71fa-11e4-87dd-7382f5c437af") - self.assertDictEqual( - permissions[0].capabilities, - { - TSC.Permission.Capability.WebAuthoring: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.Read: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.Filter: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.AddComment: TSC.Permission.Mode.Allow, - }, - ) - self.assertEqual(permissions[1].grantee.tag_name, "user") - self.assertEqual(permissions[1].grantee.id, "7c37ee24-c4b1-42b6-a154-eaeab7ee330a") - self.assertDictEqual( - permissions[1].capabilities, - { - TSC.Permission.Capability.ExportImage: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.ShareView: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.ExportData: TSC.Permission.Mode.Deny, - TSC.Permission.Capability.ViewComments: TSC.Permission.Mode.Deny, - }, - ) + assert permissions[0].grantee.tag_name == "group" + assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" + assert permissions[0].capabilities == { + TSC.Permission.Capability.WebAuthoring: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.Read: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.Filter: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.AddComment: TSC.Permission.Mode.Allow, + } + + assert permissions[1].grantee.tag_name == "user" + assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" + assert permissions[1].capabilities == { + TSC.Permission.Capability.ExportImage: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.ShareView: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.ExportData: TSC.Permission.Mode.Deny, + TSC.Permission.Capability.ViewComments: TSC.Permission.Mode.Deny, + } def test_add_permissions(self) -> None: with open(UPDATE_PERMISSIONS, "rb") as f: @@ -420,17 +421,18 @@ def test_add_permissions(self) -> None: m.put(self.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) permissions = self.server.workbooks.update_permissions(single_workbook, new_permissions) - self.assertEqual(permissions[0].grantee.tag_name, "group") - self.assertEqual(permissions[0].grantee.id, "5e5e1978-71fa-11e4-87dd-7382f5c437af") - self.assertDictEqual(permissions[0].capabilities, {TSC.Permission.Capability.Read: TSC.Permission.Mode.Deny}) - self.assertEqual(permissions[1].grantee.tag_name, "user") - self.assertEqual(permissions[1].grantee.id, "7c37ee24-c4b1-42b6-a154-eaeab7ee330a") - self.assertDictEqual(permissions[1].capabilities, {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow}) + assert permissions[0].grantee.tag_name == "group" + assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" + assert permissions[0].capabilities == {TSC.Permission.Capability.Read: TSC.Permission.Mode.Deny} + assert permissions[1].grantee.tag_name == "user" + assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" + assert permissions[1].capabilities == {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow} def test_populate_connections_missing_id(self) -> None: single_workbook = TSC.WorkbookItem("test") - self.assertRaises(TSC.MissingRequiredFieldError, self.server.workbooks.populate_connections, single_workbook) + with pytest.raises(TSC.MissingRequiredFieldError): + self.server.workbooks.populate_connections(single_workbook) def test_populate_pdf(self) -> None: self.server.version = "3.4" @@ -450,16 +452,13 @@ def test_populate_pdf(self) -> None: req_option = TSC.PDFRequestOptions(type, orientation) self.server.workbooks.populate_pdf(single_workbook, req_option) - self.assertEqual(response, single_workbook.pdf) + assert response == single_workbook.pdf def test_populate_pdf_unsupported(self) -> None: self.server.version = "3.4" self.baseurl = self.server.workbooks.baseurl with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", - content=b"", - ) + m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", content=b"") single_workbook = TSC.WorkbookItem("test") single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" @@ -468,7 +467,7 @@ def test_populate_pdf_unsupported(self) -> None: req_option = TSC.PDFRequestOptions(type, orientation) req_option.vf("Region", "West") - with self.assertRaises(UnsupportedAttributeError): + with pytest.raises(UnsupportedAttributeError): self.server.workbooks.populate_pdf(single_workbook, req_option) def test_populate_pdf_vf_dims(self) -> None: @@ -493,7 +492,7 @@ def test_populate_pdf_vf_dims(self) -> None: req_option.viz_height = 1080 self.server.workbooks.populate_pdf(single_workbook, req_option) - self.assertEqual(response, single_workbook.pdf) + assert response == single_workbook.pdf def test_populate_powerpoint(self) -> None: self.server.version = "3.8" @@ -501,17 +500,14 @@ def test_populate_powerpoint(self) -> None: with open(POPULATE_POWERPOINT, "rb") as f: response = f.read() with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/powerpoint?maxAge=1", - content=response, - ) + m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/powerpoint?maxAge=1", content=response) single_workbook = TSC.WorkbookItem("test") single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" ro = TSC.PPTXRequestOptions(maxage=1) self.server.workbooks.populate_powerpoint(single_workbook, ro) - self.assertEqual(response, single_workbook.powerpoint) + assert response == single_workbook.powerpoint def test_populate_preview_image(self) -> None: with open(POPULATE_PREVIEW_IMAGE, "rb") as f: @@ -522,11 +518,12 @@ def test_populate_preview_image(self) -> None: single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" self.server.workbooks.populate_preview_image(single_workbook) - self.assertEqual(response, single_workbook.preview_image) + assert response == single_workbook.preview_image def test_populate_preview_image_missing_id(self) -> None: single_workbook = TSC.WorkbookItem("test") - self.assertRaises(TSC.MissingRequiredFieldError, self.server.workbooks.populate_preview_image, single_workbook) + with pytest.raises(TSC.MissingRequiredFieldError): + self.server.workbooks.populate_preview_image(single_workbook) def test_publish(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -544,21 +541,20 @@ def test_publish(self) -> None: publish_mode = self.server.PublishMode.CreateNew new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - - self.assertEqual("a8076ca1-e9d8-495e-bae6-c684dbb55836", new_workbook.id) - self.assertEqual("RESTAPISample", new_workbook.name) - self.assertEqual("RESTAPISample_0", new_workbook.content_url) - self.assertEqual(False, new_workbook.show_tabs) - self.assertEqual(1, new_workbook.size) - self.assertEqual("2016-08-18T18:33:24Z", format_datetime(new_workbook.created_at)) - self.assertEqual("2016-08-18T20:31:34Z", format_datetime(new_workbook.updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", new_workbook.project_id) - self.assertEqual("default", new_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", new_workbook.owner_id) - self.assertEqual("fe0b4e89-73f4-435e-952d-3a263fbfa56c", new_workbook.views[0].id) - self.assertEqual("GDP per capita", new_workbook.views[0].name) - self.assertEqual("RESTAPISample_0/sheets/GDPpercapita", new_workbook.views[0].content_url) - self.assertEqual("REST API Testing", new_workbook.description) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + assert "REST API Testing" == new_workbook.description def test_publish_a_packaged_file_object(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -577,19 +573,19 @@ def test_publish_a_packaged_file_object(self) -> None: new_workbook = self.server.workbooks.publish(new_workbook, fp, publish_mode) - self.assertEqual("a8076ca1-e9d8-495e-bae6-c684dbb55836", new_workbook.id) - self.assertEqual("RESTAPISample", new_workbook.name) - self.assertEqual("RESTAPISample_0", new_workbook.content_url) - self.assertEqual(False, new_workbook.show_tabs) - self.assertEqual(1, new_workbook.size) - self.assertEqual("2016-08-18T18:33:24Z", format_datetime(new_workbook.created_at)) - self.assertEqual("2016-08-18T20:31:34Z", format_datetime(new_workbook.updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", new_workbook.project_id) - self.assertEqual("default", new_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", new_workbook.owner_id) - self.assertEqual("fe0b4e89-73f4-435e-952d-3a263fbfa56c", new_workbook.views[0].id) - self.assertEqual("GDP per capita", new_workbook.views[0].name) - self.assertEqual("RESTAPISample_0/sheets/GDPpercapita", new_workbook.views[0].content_url) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_non_packeged_file_object(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -608,19 +604,19 @@ def test_publish_non_packeged_file_object(self) -> None: new_workbook = self.server.workbooks.publish(new_workbook, fp, publish_mode) - self.assertEqual("a8076ca1-e9d8-495e-bae6-c684dbb55836", new_workbook.id) - self.assertEqual("RESTAPISample", new_workbook.name) - self.assertEqual("RESTAPISample_0", new_workbook.content_url) - self.assertEqual(False, new_workbook.show_tabs) - self.assertEqual(1, new_workbook.size) - self.assertEqual("2016-08-18T18:33:24Z", format_datetime(new_workbook.created_at)) - self.assertEqual("2016-08-18T20:31:34Z", format_datetime(new_workbook.updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", new_workbook.project_id) - self.assertEqual("default", new_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", new_workbook.owner_id) - self.assertEqual("fe0b4e89-73f4-435e-952d-3a263fbfa56c", new_workbook.views[0].id) - self.assertEqual("GDP per capita", new_workbook.views[0].name) - self.assertEqual("RESTAPISample_0/sheets/GDPpercapita", new_workbook.views[0].content_url) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_path_object(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -637,19 +633,19 @@ def test_publish_path_object(self) -> None: new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - self.assertEqual("a8076ca1-e9d8-495e-bae6-c684dbb55836", new_workbook.id) - self.assertEqual("RESTAPISample", new_workbook.name) - self.assertEqual("RESTAPISample_0", new_workbook.content_url) - self.assertEqual(False, new_workbook.show_tabs) - self.assertEqual(1, new_workbook.size) - self.assertEqual("2016-08-18T18:33:24Z", format_datetime(new_workbook.created_at)) - self.assertEqual("2016-08-18T20:31:34Z", format_datetime(new_workbook.updated_at)) - self.assertEqual("ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", new_workbook.project_id) - self.assertEqual("default", new_workbook.project_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", new_workbook.owner_id) - self.assertEqual("fe0b4e89-73f4-435e-952d-3a263fbfa56c", new_workbook.views[0].id) - self.assertEqual("GDP per capita", new_workbook.views[0].name) - self.assertEqual("RESTAPISample_0/sheets/GDPpercapita", new_workbook.views[0].content_url) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_with_hidden_views_on_workbook(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -668,8 +664,8 @@ def test_publish_with_hidden_views_on_workbook(self) -> None: new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) request_body = m._adapter.request_history[0]._request.body # order of attributes in xml is unspecified - self.assertTrue(re.search(rb"<\/views>", request_body)) - self.assertTrue(re.search(rb"<\/views>", request_body)) + assert re.search(b'<\\/views>', request_body) + assert re.search(b'<\\/views>', request_body) def test_publish_with_thumbnails_user_id(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -689,7 +685,7 @@ def test_publish_with_thumbnails_user_id(self) -> None: new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) request_body = m._adapter.request_history[0]._request.body # order of attributes in xml is unspecified - self.assertTrue(re.search(rb"thumbnailsUserId=\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\"", request_body)) + assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) def test_publish_with_thumbnails_group_id(self) -> None: with open(PUBLISH_XML, "rb") as f: @@ -708,7 +704,7 @@ def test_publish_with_thumbnails_group_id(self) -> None: publish_mode = self.server.PublishMode.CreateNew new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) request_body = m._adapter.request_history[0]._request.body - self.assertTrue(re.search(rb"thumbnailsGroupId=\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20762\"", request_body)) + assert re.search(b'thumbnailsGroupId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20762\\"', request_body) @pytest.mark.filterwarnings("ignore:'as_job' not available") def test_publish_with_query_params(self) -> None: @@ -729,10 +725,10 @@ def test_publish_with_query_params(self) -> None: ) request_query_params = m._adapter.request_history[0].qs - self.assertTrue("asjob" in request_query_params) - self.assertTrue(request_query_params["asjob"]) - self.assertTrue("skipconnectioncheck" in request_query_params) - self.assertTrue(request_query_params["skipconnectioncheck"]) + assert "asjob" in request_query_params + assert request_query_params["asjob"] + assert "skipconnectioncheck" in request_query_params + assert request_query_params["skipconnectioncheck"] def test_publish_async(self) -> None: self.server.version = "3.0" @@ -751,50 +747,45 @@ def test_publish_async(self) -> None: new_job = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode, as_job=True) - self.assertEqual("7c3d599e-949f-44c3-94a1-f30ba85757e4", new_job.id) - self.assertEqual("PublishWorkbook", new_job.type) - self.assertEqual("0", new_job.progress) - self.assertEqual("2018-06-29T23:22:32Z", format_datetime(new_job.created_at)) - self.assertEqual(1, new_job.finish_code) + assert "7c3d599e-949f-44c3-94a1-f30ba85757e4" == new_job.id + assert "PublishWorkbook" == new_job.type + assert "0" == new_job.progress + assert "2018-06-29T23:22:32Z" == format_datetime(new_job.created_at) + assert 1 == new_job.finish_code def test_publish_invalid_file(self) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") - self.assertRaises(IOError, self.server.workbooks.publish, new_workbook, ".", self.server.PublishMode.CreateNew) + with pytest.raises(IOError): + self.server.workbooks.publish(new_workbook, ".", self.server.PublishMode.CreateNew) def test_publish_invalid_file_type(self) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") - self.assertRaises( - ValueError, - self.server.workbooks.publish, - new_workbook, - os.path.join(TEST_ASSET_DIR, "SampleDS.tds"), - self.server.PublishMode.CreateNew, - ) + with pytest.raises(ValueError): + self.server.workbooks.publish( + new_workbook, os.path.join(TEST_ASSET_DIR, "SampleDS.tds"), self.server.PublishMode.CreateNew + ) def test_publish_unnamed_file_object(self) -> None: new_workbook = TSC.WorkbookItem("test") with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx"), "rb") as f: - self.assertRaises( - ValueError, self.server.workbooks.publish, new_workbook, f, self.server.PublishMode.CreateNew - ) + with pytest.raises(ValueError): + self.server.workbooks.publish(new_workbook, f, self.server.PublishMode.CreateNew) def test_publish_non_bytes_file_object(self) -> None: new_workbook = TSC.WorkbookItem("test") with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx")) as f: - self.assertRaises( - TypeError, self.server.workbooks.publish, new_workbook, f, self.server.PublishMode.CreateNew - ) + with pytest.raises(TypeError): + self.server.workbooks.publish(new_workbook, f, self.server.PublishMode.CreateNew) def test_publish_file_object_of_unknown_type_raises_exception(self) -> None: new_workbook = TSC.WorkbookItem("test") with BytesIO() as file_object: file_object.write(bytes.fromhex("89504E470D0A1A0A")) file_object.seek(0) - self.assertRaises( - ValueError, self.server.workbooks.publish, new_workbook, file_object, self.server.PublishMode.CreateNew - ) + with pytest.raises(ValueError): + self.server.workbooks.publish(new_workbook, file_object, self.server.PublishMode.CreateNew) def test_publish_multi_connection(self) -> None: new_workbook = TSC.WorkbookItem( @@ -811,10 +802,10 @@ def test_publish_multi_connection(self) -> None: # Can't use ConnectionItem parser due to xml namespace problems connection_results = fromstring(response).findall(".//connection") - self.assertEqual(connection_results[0].get("serverAddress", None), "mysql.test.com") - self.assertEqual(connection_results[0].find("connectionCredentials").get("name", None), "test") # type: ignore[union-attr] - self.assertEqual(connection_results[1].get("serverAddress", None), "pgsql.test.com") - self.assertEqual(connection_results[1].find("connectionCredentials").get("password", None), "secret") # type: ignore[union-attr] + assert connection_results[0].get("serverAddress", None) == "mysql.test.com" + assert connection_results[0].find("connectionCredentials").get("name", None) == "test" + assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" + assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" def test_publish_multi_connection_flat(self) -> None: new_workbook = TSC.WorkbookItem( @@ -835,10 +826,10 @@ def test_publish_multi_connection_flat(self) -> None: # Can't use ConnectionItem parser due to xml namespace problems connection_results = fromstring(response).findall(".//connection") - self.assertEqual(connection_results[0].get("serverAddress", None), "mysql.test.com") - self.assertEqual(connection_results[0].find("connectionCredentials").get("name", None), "test") # type: ignore[union-attr] - self.assertEqual(connection_results[1].get("serverAddress", None), "pgsql.test.com") - self.assertEqual(connection_results[1].find("connectionCredentials").get("password", None), "secret") # type: ignore[union-attr] + assert connection_results[0].get("serverAddress", None) == "mysql.test.com" + assert connection_results[0].find("connectionCredentials").get("name", None) == "test" + assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" + assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" def test_synchronous_publish_timeout_error(self) -> None: with requests_mock.mock() as m: @@ -847,14 +838,8 @@ def test_synchronous_publish_timeout_error(self) -> None: new_workbook = TSC.WorkbookItem(project_id="") publish_mode = self.server.PublishMode.CreateNew - self.assertRaisesRegex( - InternalServerError, - "Please use asynchronous publishing to avoid timeouts", - self.server.workbooks.publish, - new_workbook, - asset("SampleWB.twbx"), - publish_mode, - ) + with pytest.raises(InternalServerError, match="Please use asynchronous publishing to avoid timeouts"): + self.server.workbooks.publish(new_workbook, asset("SampleWB.twbx"), publish_mode) def test_delete_extracts_all(self) -> None: self.server.version = "3.10" @@ -907,24 +892,26 @@ def test_revisions(self) -> None: self.server.workbooks.populate_revisions(workbook) revisions = workbook.revisions - self.assertEqual(len(revisions), 3) - self.assertEqual("2016-07-26T20:34:56Z", format_datetime(revisions[0].created_at)) - self.assertEqual("2016-07-27T20:34:56Z", format_datetime(revisions[1].created_at)) - self.assertEqual("2016-07-28T20:34:56Z", format_datetime(revisions[2].created_at)) - - self.assertEqual(False, revisions[0].deleted) - self.assertEqual(False, revisions[0].current) - self.assertEqual(False, revisions[1].deleted) - self.assertEqual(False, revisions[1].current) - self.assertEqual(False, revisions[2].deleted) - self.assertEqual(True, revisions[2].current) - - self.assertEqual("Cassie", revisions[0].user_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", revisions[0].user_id) - self.assertIsNone(revisions[1].user_name) - self.assertIsNone(revisions[1].user_id) - self.assertEqual("Cassie", revisions[2].user_name) - self.assertEqual("5de011f8-5aa9-4d5b-b991-f462c8dd6bb7", revisions[2].user_id) + + + assert len(revisions) == 3 + assert "2016-07-26T20:34:56Z" == format_datetime(revisions[0].created_at) + assert "2016-07-27T20:34:56Z" == format_datetime(revisions[1].created_at) + assert "2016-07-28T20:34:56Z" == format_datetime(revisions[2].created_at) + + assert not revisions[0].deleted + assert not revisions[0].current + assert not revisions[1].deleted + assert not revisions[1].current + assert not revisions[2].deleted + assert revisions[2].current + + assert "Cassie" == revisions[0].user_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[0].user_id + assert revisions[1].user_name is None + assert revisions[1].user_id is None + assert "Cassie" == revisions[2].user_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[2].user_id def test_delete_revision(self) -> None: self.baseurl = self.server.workbooks.baseurl @@ -942,7 +929,7 @@ def test_download_revision(self) -> None: headers={"Content-Disposition": 'name="tableau_datasource"; filename="Sample datasource.tds"'}, ) file_path = self.server.workbooks.download_revision("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", "3", td) - self.assertTrue(os.path.exists(file_path)) + assert os.path.exists(file_path) def test_bad_download_response(self) -> None: with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: @@ -951,7 +938,7 @@ def test_bad_download_response(self) -> None: headers={"Content-Disposition": '''name="tableau_workbook"; filename*=UTF-8''"Sample workbook.twb"'''}, ) file_path = self.server.workbooks.download("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", td) - self.assertTrue(os.path.exists(file_path)) + assert os.path.exists(file_path) def test_odata_connection(self) -> None: self.baseurl = self.server.workbooks.baseurl @@ -979,7 +966,7 @@ def test_odata_connection(self) -> None: xml_connection = xml.find(".//connection") assert xml_connection is not None - self.assertEqual(xml_connection.get("serverAddress"), url) + assert xml_connection.get("serverAddress") == url def test_update_workbook_connections(self) -> None: populate_xml, response_xml = read_xml_assets(POPULATE_CONNECTIONS_XML, UPDATE_CONNECTIONS_XML) @@ -1011,8 +998,8 @@ def test_update_workbook_connections(self) -> None: ) updated_ids = [conn.id for conn in connection_items] - self.assertEqual(updated_ids, connection_luids) - self.assertEqual("AD Service Principal", connection_items[0].auth_type) + assert updated_ids == connection_luids + assert "AD Service Principal" == connection_items[0].auth_type def test_get_workbook_all_fields(self) -> None: self.server.version = "3.21" From 14bca763d967bb45c3c1bab48208089a2293130d Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Tue, 19 Aug 2025 22:48:57 -0500 Subject: [PATCH 2/7] chore: convert all assets to Paths --- test/test_workbook.py | 160 ++++++++++++++++-------------------------- 1 file changed, 60 insertions(+), 100 deletions(-) diff --git a/test/test_workbook.py b/test/test_workbook.py index 96a43dfd..1607206a 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -16,30 +16,30 @@ from tableauserverclient.server.request_factory import RequestFactory from ._utils import read_xml_asset, read_xml_assets, asset -TEST_ASSET_DIR = os.path.join(os.path.dirname(__file__), "assets") - -ADD_TAGS_XML = os.path.join(TEST_ASSET_DIR, "workbook_add_tags.xml") -GET_BY_ID_XML = os.path.join(TEST_ASSET_DIR, "workbook_get_by_id.xml") -GET_BY_ID_XML_PERSONAL = os.path.join(TEST_ASSET_DIR, "workbook_get_by_id_personal.xml") -GET_EMPTY_XML = os.path.join(TEST_ASSET_DIR, "workbook_get_empty.xml") -GET_INVALID_DATE_XML = os.path.join(TEST_ASSET_DIR, "workbook_get_invalid_date.xml") -GET_XML = os.path.join(TEST_ASSET_DIR, "workbook_get.xml") -GET_XML_ALL_FIELDS = os.path.join(TEST_ASSET_DIR, "workbook_get_all_fields.xml") -ODATA_XML = os.path.join(TEST_ASSET_DIR, "odata_connection.xml") -POPULATE_CONNECTIONS_XML = os.path.join(TEST_ASSET_DIR, "workbook_populate_connections.xml") -POPULATE_PDF = os.path.join(TEST_ASSET_DIR, "populate_pdf.pdf") -POPULATE_POWERPOINT = os.path.join(TEST_ASSET_DIR, "populate_powerpoint.pptx") -POPULATE_PERMISSIONS_XML = os.path.join(TEST_ASSET_DIR, "workbook_populate_permissions.xml") -POPULATE_PREVIEW_IMAGE = os.path.join(TEST_ASSET_DIR, "RESTAPISample Image.png") -POPULATE_VIEWS_XML = os.path.join(TEST_ASSET_DIR, "workbook_populate_views.xml") -POPULATE_VIEWS_USAGE_XML = os.path.join(TEST_ASSET_DIR, "workbook_populate_views_usage.xml") -PUBLISH_XML = os.path.join(TEST_ASSET_DIR, "workbook_publish.xml") -PUBLISH_ASYNC_XML = os.path.join(TEST_ASSET_DIR, "workbook_publish_async.xml") -REFRESH_XML = os.path.join(TEST_ASSET_DIR, "workbook_refresh.xml") -REVISION_XML = os.path.join(TEST_ASSET_DIR, "workbook_revision.xml") -UPDATE_XML = os.path.join(TEST_ASSET_DIR, "workbook_update.xml") -UPDATE_PERMISSIONS = os.path.join(TEST_ASSET_DIR, "workbook_update_permissions.xml") -UPDATE_CONNECTIONS_XML = os.path.join(TEST_ASSET_DIR, "workbook_update_connections.xml") +TEST_ASSET_DIR = Path(__file__).parent / "assets" + +ADD_TAGS_XML = TEST_ASSET_DIR / "workbook_add_tags.xml" +GET_BY_ID_XML = TEST_ASSET_DIR / "workbook_get_by_id.xml" +GET_BY_ID_XML_PERSONAL = TEST_ASSET_DIR / "workbook_get_by_id_personal.xml" +GET_EMPTY_XML = TEST_ASSET_DIR / "workbook_get_empty.xml" +GET_INVALID_DATE_XML = TEST_ASSET_DIR / "workbook_get_invalid_date.xml" +GET_XML = TEST_ASSET_DIR / "workbook_get.xml" +GET_XML_ALL_FIELDS = TEST_ASSET_DIR / "workbook_get_all_fields.xml" +ODATA_XML = TEST_ASSET_DIR / "odata_connection.xml" +POPULATE_CONNECTIONS_XML = TEST_ASSET_DIR / "workbook_populate_connections.xml" +POPULATE_PDF = TEST_ASSET_DIR / "populate_pdf.pdf" +POPULATE_POWERPOINT = TEST_ASSET_DIR / "populate_powerpoint.pptx" +POPULATE_PERMISSIONS_XML = TEST_ASSET_DIR / "workbook_populate_permissions.xml" +POPULATE_PREVIEW_IMAGE = TEST_ASSET_DIR / "RESTAPISample Image.png" +POPULATE_VIEWS_XML = TEST_ASSET_DIR / "workbook_populate_views.xml" +POPULATE_VIEWS_USAGE_XML = TEST_ASSET_DIR / "workbook_populate_views_usage.xml" +PUBLISH_XML = TEST_ASSET_DIR / "workbook_publish.xml" +PUBLISH_ASYNC_XML = TEST_ASSET_DIR / "workbook_publish_async.xml" +REFRESH_XML = TEST_ASSET_DIR / "workbook_refresh.xml" +REVISION_XML = TEST_ASSET_DIR / "workbook_revision.xml" +UPDATE_XML = TEST_ASSET_DIR / "workbook_update.xml" +UPDATE_PERMISSIONS = TEST_ASSET_DIR / "workbook_update_permissions.xml" +UPDATE_CONNECTIONS_XML = TEST_ASSET_DIR / "workbook_update_connections.xml" class WorkbookTests(unittest.TestCase): @@ -53,8 +53,7 @@ def setUp(self) -> None: self.baseurl = self.server.workbooks.baseurl def test_get(self) -> None: - with open(GET_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = GET_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() @@ -88,8 +87,7 @@ def test_get(self) -> None: assert {"Safari", "Sample"} == all_workbooks[1].tags def test_get_ignore_invalid_date(self) -> None: - with open(GET_INVALID_DATE_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = GET_INVALID_DATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() @@ -102,8 +100,7 @@ def test_get_before_signin(self) -> None: self.server.workbooks.get() def test_get_empty(self) -> None: - with open(GET_EMPTY_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = GET_EMPTY_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl, text=response_xml) all_workbooks, pagination_item = self.server.workbooks.get() @@ -112,8 +109,7 @@ def test_get_empty(self) -> None: assert [] == all_workbooks def test_get_by_id(self) -> None: - with open(GET_BY_ID_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = GET_BY_ID_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d42") @@ -137,8 +133,7 @@ def test_get_by_id(self) -> None: def test_get_by_id_personal(self) -> None: # workbooks in personal space don't have project_id or project_name - with open(GET_BY_ID_XML_PERSONAL, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = GET_BY_ID_XML_PERSONAL.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d43", text=response_xml) single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d43") @@ -167,8 +162,7 @@ def test_get_by_id_missing_id(self) -> None: def test_refresh_id(self) -> None: self.server.version = "2.8" self.baseurl = self.server.workbooks.baseurl - with open(REFRESH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = REFRESH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) self.server.workbooks.refresh("3cc6cd06-89ce-4fdc-b935-5294135d6d42") @@ -178,8 +172,7 @@ def test_refresh_object(self) -> None: self.baseurl = self.server.workbooks.baseurl workbook = TSC.WorkbookItem("") workbook._id = "3cc6cd06-89ce-4fdc-b935-5294135d6d42" - with open(REFRESH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = REFRESH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) self.server.workbooks.refresh(workbook) @@ -194,8 +187,7 @@ def test_delete_missing_id(self) -> None: self.server.workbooks.delete("") def test_update(self) -> None: - with open(UPDATE_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = UPDATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=response_xml) single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74", show_tabs=True) @@ -224,10 +216,8 @@ def test_update_missing_id(self) -> None: self.server.workbooks.update(single_workbook) def test_update_copy_fields(self) -> None: - with open(POPULATE_CONNECTIONS_XML, "rb") as f: - connection_xml = f.read().decode("utf-8") - with open(UPDATE_XML, "rb") as f: - update_xml = f.read().decode("utf-8") + connection_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") + update_xml = UPDATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=connection_xml) m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) @@ -243,10 +233,8 @@ def test_update_copy_fields(self) -> None: assert single_workbook._preview_image == updated_workbook._preview_image def test_update_tags(self) -> None: - with open(ADD_TAGS_XML, "rb") as f: - add_tags_xml = f.read().decode("utf-8") - with open(UPDATE_XML, "rb") as f: - update_xml = f.read().decode("utf-8") + add_tags_xml = ADD_TAGS_XML.read_text(encoding="utf-8") + update_xml = UPDATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags", text=add_tags_xml) m.delete(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/b", status_code=204) @@ -315,8 +303,7 @@ def test_download_missing_id(self) -> None: self.server.workbooks.download("") def test_populate_views(self) -> None: - with open(POPULATE_VIEWS_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = POPULATE_VIEWS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -337,8 +324,7 @@ def test_populate_views(self) -> None: assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url def test_populate_views_with_usage(self) -> None: - with open(POPULATE_VIEWS_USAGE_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = POPULATE_VIEWS_USAGE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get( self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views?includeUsageStatistics=true", @@ -362,8 +348,7 @@ def test_populate_views_missing_id(self) -> None: self.server.workbooks.populate_views(single_workbook) def test_populate_connections(self) -> None: - with open(POPULATE_CONNECTIONS_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -376,8 +361,7 @@ def test_populate_connections(self) -> None: assert "World Indicators" == single_workbook.connections[0].datasource_name def test_populate_permissions(self) -> None: - with open(POPULATE_PERMISSIONS_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = POPULATE_PERMISSIONS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(self.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -386,7 +370,6 @@ def test_populate_permissions(self) -> None: self.server.workbooks.populate_permissions(single_workbook) permissions = single_workbook.permissions - assert permissions[0].grantee.tag_name == "group" assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" assert permissions[0].capabilities == { @@ -406,8 +389,7 @@ def test_populate_permissions(self) -> None: } def test_add_permissions(self) -> None: - with open(UPDATE_PERMISSIONS, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = UPDATE_PERMISSIONS.read_text(encoding="utf-8") single_workbook = TSC.WorkbookItem("test") single_workbook._id = "21778de4-b7b9-44bc-a599-1506a2639ace" @@ -421,7 +403,6 @@ def test_add_permissions(self) -> None: m.put(self.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) permissions = self.server.workbooks.update_permissions(single_workbook, new_permissions) - assert permissions[0].grantee.tag_name == "group" assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" assert permissions[0].capabilities == {TSC.Permission.Capability.Read: TSC.Permission.Mode.Deny} @@ -437,8 +418,7 @@ def test_populate_connections_missing_id(self) -> None: def test_populate_pdf(self) -> None: self.server.version = "3.4" self.baseurl = self.server.workbooks.baseurl - with open(POPULATE_PDF, "rb") as f: - response = f.read() + response = POPULATE_PDF.read_bytes() with requests_mock.mock() as m: m.get( self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", @@ -473,8 +453,7 @@ def test_populate_pdf_unsupported(self) -> None: def test_populate_pdf_vf_dims(self) -> None: self.server.version = "3.23" self.baseurl = self.server.workbooks.baseurl - with open(POPULATE_PDF, "rb") as f: - response = f.read() + response = POPULATE_PDF.read_bytes() with requests_mock.mock() as m: m.get( self.baseurl @@ -497,8 +476,7 @@ def test_populate_pdf_vf_dims(self) -> None: def test_populate_powerpoint(self) -> None: self.server.version = "3.8" self.baseurl = self.server.workbooks.baseurl - with open(POPULATE_POWERPOINT, "rb") as f: - response = f.read() + response = POPULATE_POWERPOINT.read_bytes() with requests_mock.mock() as m: m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/powerpoint?maxAge=1", content=response) single_workbook = TSC.WorkbookItem("test") @@ -510,8 +488,7 @@ def test_populate_powerpoint(self) -> None: assert response == single_workbook.powerpoint def test_populate_preview_image(self) -> None: - with open(POPULATE_PREVIEW_IMAGE, "rb") as f: - response = f.read() + response = POPULATE_PREVIEW_IMAGE.read_bytes() with requests_mock.mock() as m: m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/previewImage", content=response) single_workbook = TSC.WorkbookItem("test") @@ -526,8 +503,7 @@ def test_populate_preview_image_missing_id(self) -> None: self.server.workbooks.populate_preview_image(single_workbook) def test_publish(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -557,8 +533,7 @@ def test_publish(self) -> None: assert "REST API Testing" == new_workbook.description def test_publish_a_packaged_file_object(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -588,8 +563,7 @@ def test_publish_a_packaged_file_object(self) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_non_packeged_file_object(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -619,8 +593,7 @@ def test_publish_non_packeged_file_object(self) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_path_object(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -648,8 +621,7 @@ def test_publish_path_object(self) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url def test_publish_with_hidden_views_on_workbook(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -668,8 +640,7 @@ def test_publish_with_hidden_views_on_workbook(self) -> None: assert re.search(b'<\\/views>', request_body) def test_publish_with_thumbnails_user_id(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -688,8 +659,7 @@ def test_publish_with_thumbnails_user_id(self) -> None: assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) def test_publish_with_thumbnails_group_id(self) -> None: - with open(PUBLISH_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -708,8 +678,7 @@ def test_publish_with_thumbnails_group_id(self) -> None: @pytest.mark.filterwarnings("ignore:'as_job' not available") def test_publish_with_query_params(self) -> None: - with open(PUBLISH_ASYNC_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(self.baseurl, text=response_xml) @@ -733,8 +702,7 @@ def test_publish_with_query_params(self) -> None: def test_publish_async(self) -> None: self.server.version = "3.0" baseurl = self.server.workbooks.baseurl - with open(PUBLISH_ASYNC_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post(baseurl, text=response_xml) @@ -845,8 +813,7 @@ def test_delete_extracts_all(self) -> None: self.server.version = "3.10" self.baseurl = self.server.workbooks.baseurl - with open(PUBLISH_ASYNC_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", status_code=200, text=response_xml @@ -857,8 +824,7 @@ def test_create_extracts_all(self) -> None: self.server.version = "3.10" self.baseurl = self.server.workbooks.baseurl - with open(PUBLISH_ASYNC_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml @@ -872,8 +838,7 @@ def test_create_extracts_one(self) -> None: datasource = TSC.DatasourceItem("test") datasource._id = "1f951daf-4061-451a-9df1-69a8062664f2" - with open(PUBLISH_ASYNC_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml @@ -885,15 +850,12 @@ def test_revisions(self) -> None: workbook = TSC.WorkbookItem("project", "test") workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" - with open(REVISION_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = REVISION_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.get(f"{self.baseurl}/{workbook.id}/revisions", text=response_xml) self.server.workbooks.populate_revisions(workbook) revisions = workbook.revisions - - assert len(revisions) == 3 assert "2016-07-26T20:34:56Z" == format_datetime(revisions[0].created_at) assert "2016-07-27T20:34:56Z" == format_datetime(revisions[1].created_at) @@ -952,8 +914,7 @@ def test_odata_connection(self) -> None: creds = TSC.ConnectionCredentials("", "", True) connection.connection_credentials = creds - with open(ODATA_XML, "rb") as f: - response_xml = f.read().decode("utf-8") + response_xml = ODATA_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.put(f"{self.baseurl}/{workbook.id}/connections/{connection.id}", text=response_xml) @@ -1005,8 +966,7 @@ def test_get_workbook_all_fields(self) -> None: self.server.version = "3.21" baseurl = self.server.workbooks.baseurl - with open(GET_XML_ALL_FIELDS) as f: - response = f.read() + response = GET_XML_ALL_FIELDS.read_text(encoding="utf-8") ro = TSC.RequestOptions() ro.all_fields = True From e1a8a9de2cff4e062bf0e83818eb88bf3ddbe6ce Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Wed, 20 Aug 2025 20:26:10 -0500 Subject: [PATCH 3/7] chore: convert tests to pytest --- test/test_workbook.py | 1894 ++++++++++++++++++++--------------------- 1 file changed, 946 insertions(+), 948 deletions(-) diff --git a/test/test_workbook.py b/test/test_workbook.py index 1607206a..24e6729d 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -2,7 +2,6 @@ import re import requests_mock import tempfile -import unittest from defusedxml.ElementTree import fromstring from io import BytesIO from pathlib import Path @@ -14,7 +13,7 @@ from tableauserverclient.models import UserItem, GroupItem, PermissionsRule from tableauserverclient.server.endpoint.exceptions import InternalServerError, UnsupportedAttributeError from tableauserverclient.server.request_factory import RequestFactory -from ._utils import read_xml_asset, read_xml_assets, asset +from ._utils import read_xml_assets, asset TEST_ASSET_DIR = Path(__file__).parent / "assets" @@ -41,1025 +40,1024 @@ UPDATE_PERMISSIONS = TEST_ASSET_DIR / "workbook_update_permissions.xml" UPDATE_CONNECTIONS_XML = TEST_ASSET_DIR / "workbook_update_connections.xml" +@pytest.fixture(scope="function") +def server(): + server = TSC.Server("http://test", False) + + # Fake sign in + server._site_id = "dad65087-b08b-4603-af4e-2887b8aafc67" + server._auth_token = "j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM" + + return server + +def test_get(server) -> None: + response_xml = GET_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl, text=response_xml) + all_workbooks, pagination_item = server.workbooks.get() + + assert 2 == pagination_item.total_available + assert "6d13b0ca-043d-4d42-8c9d-3f3313ea3a00" == all_workbooks[0].id + assert "Superstore" == all_workbooks[0].name + assert "Superstore" == all_workbooks[0].content_url + assert not all_workbooks[0].show_tabs + assert "http://tableauserver/#/workbooks/1/views" == all_workbooks[0].webpage_url + assert 1 == all_workbooks[0].size + assert "2016-08-03T20:34:04Z" == format_datetime(all_workbooks[0].created_at) + assert "description for Superstore" == all_workbooks[0].description + assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[0].project_id + assert "default" == all_workbooks[0].project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[0].owner_id + + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == all_workbooks[1].id + assert "SafariSample" == all_workbooks[1].name + assert "SafariSample" == all_workbooks[1].content_url + assert "http://tableauserver/#/workbooks/2/views" == all_workbooks[1].webpage_url + assert not all_workbooks[1].show_tabs + assert 26 == all_workbooks[1].size + assert "2016-07-26T20:34:56Z" == format_datetime(all_workbooks[1].created_at) + assert "description for SafariSample" == all_workbooks[1].description + assert "2016-07-26T20:35:05Z" == format_datetime(all_workbooks[1].updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[1].project_id + assert "default" == all_workbooks[1].project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[1].owner_id + assert {"Safari", "Sample"} == all_workbooks[1].tags + +def test_get_ignore_invalid_date(server) -> None: + response_xml = GET_INVALID_DATE_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl, text=response_xml) + all_workbooks, pagination_item = server.workbooks.get() + assert format_datetime(all_workbooks[0].created_at) is None + assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) + +def test_get_before_signin(server) -> None: + server._auth_token = None + with pytest.raises(TSC.NotSignedInError): + server.workbooks.get() + +def test_get_empty(server) -> None: + response_xml = GET_EMPTY_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl, text=response_xml) + all_workbooks, pagination_item = server.workbooks.get() + + assert 0 == pagination_item.total_available + assert [] == all_workbooks + +def test_get_by_id(server) -> None: + response_xml = GET_BY_ID_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) + single_workbook = server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == single_workbook.id + assert "SafariSample" == single_workbook.name + assert "SafariSample" == single_workbook.content_url + assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url + assert not single_workbook.show_tabs + assert 26 == single_workbook.size + assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) + assert "description for SafariSample" == single_workbook.description + assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == single_workbook.project_id + assert "default" == single_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id + assert {"Safari", "Sample"} == single_workbook.tags + assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id + assert "ENDANGERED SAFARI" == single_workbook.views[0].name + assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url + +def test_get_by_id_personal(server) -> None: + # workbooks in personal space don't have project_id or project_name + response_xml = GET_BY_ID_XML_PERSONAL.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d43", text=response_xml) + single_workbook = server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d43") + + assert "3cc6cd06-89ce-4fdc-b935-5294135d6d43" == single_workbook.id + assert "SafariSample" == single_workbook.name + assert "SafariSample" == single_workbook.content_url + assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url + assert not single_workbook.show_tabs + assert 26 == single_workbook.size + assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) + assert "description for SafariSample" == single_workbook.description + assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) + assert single_workbook.project_id + assert single_workbook.project_name is None + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id + assert {"Safari", "Sample"} == single_workbook.tags + assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id + assert "ENDANGERED SAFARI" == single_workbook.views[0].name + assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url + +def test_get_by_id_missing_id(server) -> None: + with pytest.raises(ValueError): + server.workbooks.get_by_id("") + +def test_refresh_id(server) -> None: + server.version = "2.8" + server.workbooks.baseurl + response_xml = REFRESH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) + server.workbooks.refresh("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + +def test_refresh_object(server) -> None: + server.version = "2.8" + server.workbooks.baseurl + workbook = TSC.WorkbookItem("") + workbook._id = "3cc6cd06-89ce-4fdc-b935-5294135d6d42" + response_xml = REFRESH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) + server.workbooks.refresh(workbook) + +def test_delete(server) -> None: + with requests_mock.mock() as m: + m.delete(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", status_code=204) + server.workbooks.delete("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + +def test_delete_missing_id(server) -> None: + with pytest.raises(ValueError): + server.workbooks.delete("") + +def test_update(server) -> None: + response_xml = UPDATE_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=response_xml) + single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74", show_tabs=True) + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + single_workbook.owner_id = "dd2239f6-ddf1-4107-981a-4cf94e415794" + single_workbook.name = "renamedWorkbook" + single_workbook.data_acceleration_config = { + "acceleration_enabled": True, + "accelerate_now": False, + "last_updated_at": None, + "acceleration_status": None, + } + single_workbook = server.workbooks.update(single_workbook) + + assert "1f951daf-4061-451a-9df1-69a8062664f2" == single_workbook.id + assert single_workbook.show_tabs + assert "1d0304cd-3796-429f-b815-7258370b9b74" == single_workbook.project_id + assert "dd2239f6-ddf1-4107-981a-4cf94e415794" == single_workbook.owner_id + assert "renamedWorkbook" == single_workbook.name + assert single_workbook.data_acceleration_config["acceleration_enabled"] + assert not single_workbook.data_acceleration_config["accelerate_now"] + +def test_update_missing_id(server) -> None: + single_workbook = TSC.WorkbookItem("test") + with pytest.raises(TSC.MissingRequiredFieldError): + server.workbooks.update(single_workbook) + +def test_update_copy_fields(server) -> None: + connection_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") + update_xml = UPDATE_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=connection_xml) + m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) + single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.populate_connections(single_workbook) + updated_workbook = server.workbooks.update(single_workbook) + + assert single_workbook._connections == updated_workbook._connections + assert single_workbook._views == updated_workbook._views + assert single_workbook.tags == updated_workbook.tags + assert single_workbook._initial_tags == updated_workbook._initial_tags + assert single_workbook._preview_image == updated_workbook._preview_image + +def test_update_tags(server) -> None: + add_tags_xml = ADD_TAGS_XML.read_text(encoding="utf-8") + update_xml = UPDATE_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags", text=add_tags_xml) + m.delete(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/b", status_code=204) + m.delete(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/d", status_code=204) + m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) + single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + single_workbook._initial_tags.update(["a", "b", "c", "d"]) + single_workbook.tags.update(["a", "c", "e"]) + updated_workbook = server.workbooks.update(single_workbook) + + assert single_workbook.tags == updated_workbook.tags + assert single_workbook._initial_tags == updated_workbook._initial_tags + +def test_download(server) -> None: + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", + headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, + ) + file_path = server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") + assert os.path.exists(file_path) + os.remove(file_path) -class WorkbookTests(unittest.TestCase): - def setUp(self) -> None: - self.server = TSC.Server("http://test", False) - - # Fake sign in - self.server._site_id = "dad65087-b08b-4603-af4e-2887b8aafc67" - self.server._auth_token = "j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM" - - self.baseurl = self.server.workbooks.baseurl - - def test_get(self) -> None: - response_xml = GET_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl, text=response_xml) - all_workbooks, pagination_item = self.server.workbooks.get() - - assert 2 == pagination_item.total_available - assert "6d13b0ca-043d-4d42-8c9d-3f3313ea3a00" == all_workbooks[0].id - assert "Superstore" == all_workbooks[0].name - assert "Superstore" == all_workbooks[0].content_url - assert not all_workbooks[0].show_tabs - assert "http://tableauserver/#/workbooks/1/views" == all_workbooks[0].webpage_url - assert 1 == all_workbooks[0].size - assert "2016-08-03T20:34:04Z" == format_datetime(all_workbooks[0].created_at) - assert "description for Superstore" == all_workbooks[0].description - assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[0].project_id - assert "default" == all_workbooks[0].project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[0].owner_id - - assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == all_workbooks[1].id - assert "SafariSample" == all_workbooks[1].name - assert "SafariSample" == all_workbooks[1].content_url - assert "http://tableauserver/#/workbooks/2/views" == all_workbooks[1].webpage_url - assert not all_workbooks[1].show_tabs - assert 26 == all_workbooks[1].size - assert "2016-07-26T20:34:56Z" == format_datetime(all_workbooks[1].created_at) - assert "description for SafariSample" == all_workbooks[1].description - assert "2016-07-26T20:35:05Z" == format_datetime(all_workbooks[1].updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == all_workbooks[1].project_id - assert "default" == all_workbooks[1].project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[1].owner_id - assert {"Safari", "Sample"} == all_workbooks[1].tags - - def test_get_ignore_invalid_date(self) -> None: - response_xml = GET_INVALID_DATE_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl, text=response_xml) - all_workbooks, pagination_item = self.server.workbooks.get() - assert format_datetime(all_workbooks[0].created_at) is None - assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) - - def test_get_before_signin(self) -> None: - self.server._auth_token = None - with pytest.raises(TSC.NotSignedInError): - self.server.workbooks.get() - - def test_get_empty(self) -> None: - response_xml = GET_EMPTY_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl, text=response_xml) - all_workbooks, pagination_item = self.server.workbooks.get() - - assert 0 == pagination_item.total_available - assert [] == all_workbooks - - def test_get_by_id(self) -> None: - response_xml = GET_BY_ID_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) - single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - - assert "3cc6cd06-89ce-4fdc-b935-5294135d6d42" == single_workbook.id - assert "SafariSample" == single_workbook.name - assert "SafariSample" == single_workbook.content_url - assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url - assert not single_workbook.show_tabs - assert 26 == single_workbook.size - assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) - assert "description for SafariSample" == single_workbook.description - assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == single_workbook.project_id - assert "default" == single_workbook.project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id - assert {"Safari", "Sample"} == single_workbook.tags - assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id - assert "ENDANGERED SAFARI" == single_workbook.views[0].name - assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url - - def test_get_by_id_personal(self) -> None: - # workbooks in personal space don't have project_id or project_name - response_xml = GET_BY_ID_XML_PERSONAL.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d43", text=response_xml) - single_workbook = self.server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d43") - - assert "3cc6cd06-89ce-4fdc-b935-5294135d6d43" == single_workbook.id - assert "SafariSample" == single_workbook.name - assert "SafariSample" == single_workbook.content_url - assert "http://tableauserver/#/workbooks/2/views" == single_workbook.webpage_url - assert not single_workbook.show_tabs - assert 26 == single_workbook.size - assert "2016-07-26T20:34:56Z" == format_datetime(single_workbook.created_at) - assert "description for SafariSample" == single_workbook.description - assert "2016-07-26T20:35:05Z" == format_datetime(single_workbook.updated_at) - assert single_workbook.project_id - assert single_workbook.project_name is None - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == single_workbook.owner_id - assert {"Safari", "Sample"} == single_workbook.tags - assert "d79634e1-6063-4ec9-95ff-50acbf609ff5" == single_workbook.views[0].id - assert "ENDANGERED SAFARI" == single_workbook.views[0].name - assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url - - def test_get_by_id_missing_id(self) -> None: - with pytest.raises(ValueError): - self.server.workbooks.get_by_id("") - - def test_refresh_id(self) -> None: - self.server.version = "2.8" - self.baseurl = self.server.workbooks.baseurl - response_xml = REFRESH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) - self.server.workbooks.refresh("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - - def test_refresh_object(self) -> None: - self.server.version = "2.8" - self.baseurl = self.server.workbooks.baseurl - workbook = TSC.WorkbookItem("") - workbook._id = "3cc6cd06-89ce-4fdc-b935-5294135d6d42" - response_xml = REFRESH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) - self.server.workbooks.refresh(workbook) - - def test_delete(self) -> None: - with requests_mock.mock() as m: - m.delete(self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", status_code=204) - self.server.workbooks.delete("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - - def test_delete_missing_id(self) -> None: - with pytest.raises(ValueError): - self.server.workbooks.delete("") - - def test_update(self) -> None: - response_xml = UPDATE_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=response_xml) - single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74", show_tabs=True) - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - single_workbook.owner_id = "dd2239f6-ddf1-4107-981a-4cf94e415794" - single_workbook.name = "renamedWorkbook" - single_workbook.data_acceleration_config = { - "acceleration_enabled": True, - "accelerate_now": False, - "last_updated_at": None, - "acceleration_status": None, - } - single_workbook = self.server.workbooks.update(single_workbook) - - assert "1f951daf-4061-451a-9df1-69a8062664f2" == single_workbook.id - assert single_workbook.show_tabs - assert "1d0304cd-3796-429f-b815-7258370b9b74" == single_workbook.project_id - assert "dd2239f6-ddf1-4107-981a-4cf94e415794" == single_workbook.owner_id - assert "renamedWorkbook" == single_workbook.name - assert single_workbook.data_acceleration_config["acceleration_enabled"] - assert not single_workbook.data_acceleration_config["accelerate_now"] - - def test_update_missing_id(self) -> None: - single_workbook = TSC.WorkbookItem("test") - with pytest.raises(TSC.MissingRequiredFieldError): - self.server.workbooks.update(single_workbook) - - def test_update_copy_fields(self) -> None: - connection_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") - update_xml = UPDATE_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=connection_xml) - m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) - single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_connections(single_workbook) - updated_workbook = self.server.workbooks.update(single_workbook) - - assert single_workbook._connections == updated_workbook._connections - assert single_workbook._views == updated_workbook._views - assert single_workbook.tags == updated_workbook.tags - assert single_workbook._initial_tags == updated_workbook._initial_tags - assert single_workbook._preview_image == updated_workbook._preview_image - - def test_update_tags(self) -> None: - add_tags_xml = ADD_TAGS_XML.read_text(encoding="utf-8") - update_xml = UPDATE_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags", text=add_tags_xml) - m.delete(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/b", status_code=204) - m.delete(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/d", status_code=204) - m.put(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) - single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - single_workbook._initial_tags.update(["a", "b", "c", "d"]) - single_workbook.tags.update(["a", "c", "e"]) - updated_workbook = self.server.workbooks.update(single_workbook) - - assert single_workbook.tags == updated_workbook.tags - assert single_workbook._initial_tags == updated_workbook._initial_tags - - def test_download(self) -> None: - with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", - headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, - ) - file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") - assert os.path.exists(file_path) - os.remove(file_path) - - def test_download_object(self) -> None: - with BytesIO() as file_object: - with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", - headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, - ) - file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", filepath=file_object) - assert isinstance(file_path, BytesIO) - - def test_download_sanitizes_name(self) -> None: - filename = "Name,With,Commas.twbx" - disposition = f'name="tableau_workbook"; filename="{filename}"' - with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", - headers={"Content-Disposition": disposition}, - ) - file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") - assert os.path.basename(file_path) == "NameWithCommas.twbx" - assert os.path.exists(file_path) - os.remove(file_path) - - def test_download_extract_only(self) -> None: - # Pretend we're 2.5 for 'extract_only' - self.server.version = "2.5" - self.baseurl = self.server.workbooks.baseurl - +def test_download_object(server) -> None: + with BytesIO() as file_object: with requests_mock.mock() as m: m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content?includeExtract=False", + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, - complete_qs=True, - ) - # Technically this shouldn't download a twbx, but we are interested in the qs, not the file - file_path = self.server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", include_extract=False) - assert os.path.exists(file_path) - os.remove(file_path) - - def test_download_missing_id(self) -> None: - with pytest.raises(ValueError): - self.server.workbooks.download("") - - def test_populate_views(self) -> None: - response_xml = POPULATE_VIEWS_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views", text=response_xml) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_views(single_workbook) - - views_list = single_workbook.views - assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id - assert "GDP per capita" == views_list[0].name - assert "RESTAPISample/sheets/GDPpercapita" == views_list[0].content_url - - assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id - assert "Country ranks" == views_list[1].name - assert "RESTAPISample/sheets/Countryranks" == views_list[1].content_url - - assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id - assert "Interest rates" == views_list[2].name - assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url - - def test_populate_views_with_usage(self) -> None: - response_xml = POPULATE_VIEWS_USAGE_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views?includeUsageStatistics=true", - text=response_xml, ) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_views(single_workbook, usage=True) - - views_list = single_workbook.views - assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id - assert 2 == views_list[0].total_views - assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id - assert 37 == views_list[1].total_views - assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id - assert 0 == views_list[2].total_views - - def test_populate_views_missing_id(self) -> None: + file_path = server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", filepath=file_object) + assert isinstance(file_path, BytesIO) + +def test_download_sanitizes_name(server) -> None: + filename = "Name,With,Commas.twbx" + disposition = f'name="tableau_workbook"; filename="{filename}"' + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", + headers={"Content-Disposition": disposition}, + ) + file_path = server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2") + assert os.path.basename(file_path) == "NameWithCommas.twbx" + assert os.path.exists(file_path) + os.remove(file_path) + +def test_download_extract_only(server) -> None: + # Pretend we're 2.5 for 'extract_only' + server.version = "2.5" + server.workbooks.baseurl + + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content?includeExtract=False", + headers={"Content-Disposition": 'name="tableau_workbook"; filename="RESTAPISample.twbx"'}, + complete_qs=True, + ) + # Technically this shouldn't download a twbx, but we are interested in the qs, not the file + file_path = server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", include_extract=False) + assert os.path.exists(file_path) + os.remove(file_path) + +def test_download_missing_id(server) -> None: + with pytest.raises(ValueError): + server.workbooks.download("") + +def test_populate_views(server) -> None: + response_xml = POPULATE_VIEWS_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views", text=response_xml) single_workbook = TSC.WorkbookItem("test") - with pytest.raises(TSC.MissingRequiredFieldError): - self.server.workbooks.populate_views(single_workbook) - - def test_populate_connections(self) -> None: - response_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=response_xml) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_connections(single_workbook) - - assert "37ca6ced-58d7-4dcf-99dc-f0a85223cbef" == single_workbook.connections[0].id - assert "dataengine" == single_workbook.connections[0].connection_type - assert "4506225a-0d32-4ab1-82d3-c24e85f7afba" == single_workbook.connections[0].datasource_id - assert "World Indicators" == single_workbook.connections[0].datasource_name - - def test_populate_permissions(self) -> None: - response_xml = POPULATE_PERMISSIONS_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(self.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "21778de4-b7b9-44bc-a599-1506a2639ace" - - self.server.workbooks.populate_permissions(single_workbook) - permissions = single_workbook.permissions - - assert permissions[0].grantee.tag_name == "group" - assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" - assert permissions[0].capabilities == { - TSC.Permission.Capability.WebAuthoring: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.Read: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.Filter: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.AddComment: TSC.Permission.Mode.Allow, - } - - assert permissions[1].grantee.tag_name == "user" - assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" - assert permissions[1].capabilities == { - TSC.Permission.Capability.ExportImage: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.ShareView: TSC.Permission.Mode.Allow, - TSC.Permission.Capability.ExportData: TSC.Permission.Mode.Deny, - TSC.Permission.Capability.ViewComments: TSC.Permission.Mode.Deny, - } - - def test_add_permissions(self) -> None: - response_xml = UPDATE_PERMISSIONS.read_text(encoding="utf-8") - + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.populate_views(single_workbook) + + views_list = single_workbook.views + assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id + assert "GDP per capita" == views_list[0].name + assert "RESTAPISample/sheets/GDPpercapita" == views_list[0].content_url + + assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id + assert "Country ranks" == views_list[1].name + assert "RESTAPISample/sheets/Countryranks" == views_list[1].content_url + + assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id + assert "Interest rates" == views_list[2].name + assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url + +def test_populate_views_with_usage(server) -> None: + response_xml = POPULATE_VIEWS_USAGE_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views?includeUsageStatistics=true", + text=response_xml, + ) + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.populate_views(single_workbook, usage=True) + + views_list = single_workbook.views + assert "097dbe13-de89-445f-b2c3-02f28bd010c1" == views_list[0].id + assert 2 == views_list[0].total_views + assert "2c1ab9d7-8d64-4cc6-b495-52e40c60c330" == views_list[1].id + assert 37 == views_list[1].total_views + assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id + assert 0 == views_list[2].total_views + +def test_populate_views_missing_id(server) -> None: + single_workbook = TSC.WorkbookItem("test") + with pytest.raises(TSC.MissingRequiredFieldError): + server.workbooks.populate_views(single_workbook) + +def test_populate_connections(server) -> None: + response_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=response_xml) + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.populate_connections(single_workbook) + + assert "37ca6ced-58d7-4dcf-99dc-f0a85223cbef" == single_workbook.connections[0].id + assert "dataengine" == single_workbook.connections[0].connection_type + assert "4506225a-0d32-4ab1-82d3-c24e85f7afba" == single_workbook.connections[0].datasource_id + assert "World Indicators" == single_workbook.connections[0].datasource_name + +def test_populate_permissions(server) -> None: + response_xml = POPULATE_PERMISSIONS_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) single_workbook = TSC.WorkbookItem("test") single_workbook._id = "21778de4-b7b9-44bc-a599-1506a2639ace" - bob = UserItem.as_reference("7c37ee24-c4b1-42b6-a154-eaeab7ee330a") - group_of_people = GroupItem.as_reference("5e5e1978-71fa-11e4-87dd-7382f5c437af") - - new_permissions = [PermissionsRule(bob, {"Write": "Allow"}), PermissionsRule(group_of_people, {"Read": "Deny"})] - - with requests_mock.mock() as m: - m.put(self.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) - permissions = self.server.workbooks.update_permissions(single_workbook, new_permissions) + server.workbooks.populate_permissions(single_workbook) + permissions = single_workbook.permissions assert permissions[0].grantee.tag_name == "group" assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" - assert permissions[0].capabilities == {TSC.Permission.Capability.Read: TSC.Permission.Mode.Deny} + assert permissions[0].capabilities == { + TSC.Permission.Capability.WebAuthoring: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.Read: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.Filter: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.AddComment: TSC.Permission.Mode.Allow, + } + assert permissions[1].grantee.tag_name == "user" assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" - assert permissions[1].capabilities == {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow} - - def test_populate_connections_missing_id(self) -> None: + assert permissions[1].capabilities == { + TSC.Permission.Capability.ExportImage: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.ShareView: TSC.Permission.Mode.Allow, + TSC.Permission.Capability.ExportData: TSC.Permission.Mode.Deny, + TSC.Permission.Capability.ViewComments: TSC.Permission.Mode.Deny, + } + +def test_add_permissions(server) -> None: + response_xml = UPDATE_PERMISSIONS.read_text(encoding="utf-8") + + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "21778de4-b7b9-44bc-a599-1506a2639ace" + + bob = UserItem.as_reference("7c37ee24-c4b1-42b6-a154-eaeab7ee330a") + group_of_people = GroupItem.as_reference("5e5e1978-71fa-11e4-87dd-7382f5c437af") + + new_permissions = [PermissionsRule(bob, {"Write": "Allow"}), PermissionsRule(group_of_people, {"Read": "Deny"})] + + with requests_mock.mock() as m: + m.put(server.workbooks.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) + permissions = server.workbooks.update_permissions(single_workbook, new_permissions) + + assert permissions[0].grantee.tag_name == "group" + assert permissions[0].grantee.id == "5e5e1978-71fa-11e4-87dd-7382f5c437af" + assert permissions[0].capabilities == {TSC.Permission.Capability.Read: TSC.Permission.Mode.Deny} + assert permissions[1].grantee.tag_name == "user" + assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" + assert permissions[1].capabilities == {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow} + +def test_populate_connections_missing_id(server) -> None: + single_workbook = TSC.WorkbookItem("test") + with pytest.raises(TSC.MissingRequiredFieldError): + server.workbooks.populate_connections(single_workbook) + +def test_populate_pdf(server) -> None: + server.version = "3.4" + server.workbooks.baseurl + response = POPULATE_PDF.read_bytes() + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", + content=response, + ) single_workbook = TSC.WorkbookItem("test") - with pytest.raises(TSC.MissingRequiredFieldError): - self.server.workbooks.populate_connections(single_workbook) - - def test_populate_pdf(self) -> None: - self.server.version = "3.4" - self.baseurl = self.server.workbooks.baseurl - response = POPULATE_PDF.read_bytes() - with requests_mock.mock() as m: - m.get( - self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", - content=response, - ) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - - type = TSC.PDFRequestOptions.PageType.A5 - orientation = TSC.PDFRequestOptions.Orientation.Landscape - req_option = TSC.PDFRequestOptions(type, orientation) + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_pdf(single_workbook, req_option) - assert response == single_workbook.pdf + type = TSC.PDFRequestOptions.PageType.A5 + orientation = TSC.PDFRequestOptions.Orientation.Landscape + req_option = TSC.PDFRequestOptions(type, orientation) - def test_populate_pdf_unsupported(self) -> None: - self.server.version = "3.4" - self.baseurl = self.server.workbooks.baseurl - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", content=b"") - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - - type = TSC.PDFRequestOptions.PageType.A5 - orientation = TSC.PDFRequestOptions.Orientation.Landscape - req_option = TSC.PDFRequestOptions(type, orientation) - req_option.vf("Region", "West") - - with pytest.raises(UnsupportedAttributeError): - self.server.workbooks.populate_pdf(single_workbook, req_option) - - def test_populate_pdf_vf_dims(self) -> None: - self.server.version = "3.23" - self.baseurl = self.server.workbooks.baseurl - response = POPULATE_PDF.read_bytes() - with requests_mock.mock() as m: - m.get( - self.baseurl - + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape&vf_Region=West&vizWidth=1920&vizHeight=1080", - content=response, - ) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - - type = TSC.PDFRequestOptions.PageType.A5 - orientation = TSC.PDFRequestOptions.Orientation.Landscape - req_option = TSC.PDFRequestOptions(type, orientation) - req_option.vf("Region", "West") - req_option.viz_width = 1920 - req_option.viz_height = 1080 - - self.server.workbooks.populate_pdf(single_workbook, req_option) - assert response == single_workbook.pdf - - def test_populate_powerpoint(self) -> None: - self.server.version = "3.8" - self.baseurl = self.server.workbooks.baseurl - response = POPULATE_POWERPOINT.read_bytes() - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/powerpoint?maxAge=1", content=response) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - - ro = TSC.PPTXRequestOptions(maxage=1) - - self.server.workbooks.populate_powerpoint(single_workbook, ro) - assert response == single_workbook.powerpoint - - def test_populate_preview_image(self) -> None: - response = POPULATE_PREVIEW_IMAGE.read_bytes() - with requests_mock.mock() as m: - m.get(self.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/previewImage", content=response) - single_workbook = TSC.WorkbookItem("test") - single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - self.server.workbooks.populate_preview_image(single_workbook) - - assert response == single_workbook.preview_image + server.workbooks.populate_pdf(single_workbook, req_option) + assert response == single_workbook.pdf - def test_populate_preview_image_missing_id(self) -> None: +def test_populate_pdf_unsupported(server) -> None: + server.version = "3.4" + server.workbooks.baseurl + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", content=b"") single_workbook = TSC.WorkbookItem("test") - with pytest.raises(TSC.MissingRequiredFieldError): - self.server.workbooks.populate_preview_image(single_workbook) - - def test_publish(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) - - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + + type = TSC.PDFRequestOptions.PageType.A5 + orientation = TSC.PDFRequestOptions.Orientation.Landscape + req_option = TSC.PDFRequestOptions(type, orientation) + req_option.vf("Region", "West") + + with pytest.raises(UnsupportedAttributeError): + server.workbooks.populate_pdf(single_workbook, req_option) + +def test_populate_pdf_vf_dims(server) -> None: + server.version = "3.23" + server.workbooks.baseurl + response = POPULATE_PDF.read_bytes() + with requests_mock.mock() as m: + m.get( + server.workbooks.baseurl + + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape&vf_Region=West&vizWidth=1920&vizHeight=1080", + content=response, + ) + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + + type = TSC.PDFRequestOptions.PageType.A5 + orientation = TSC.PDFRequestOptions.Orientation.Landscape + req_option = TSC.PDFRequestOptions(type, orientation) + req_option.vf("Region", "West") + req_option.viz_width = 1920 + req_option.viz_height = 1080 + + server.workbooks.populate_pdf(single_workbook, req_option) + assert response == single_workbook.pdf + +def test_populate_powerpoint(server) -> None: + server.version = "3.8" + server.workbooks.baseurl + response = POPULATE_POWERPOINT.read_bytes() + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/powerpoint?maxAge=1", content=response) + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" - new_workbook.description = "REST API Testing" - - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew - - new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id - assert "RESTAPISample" == new_workbook.name - assert "RESTAPISample_0" == new_workbook.content_url - assert not new_workbook.show_tabs - assert 1 == new_workbook.size - assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) - assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id - assert "default" == new_workbook.project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id - assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id - assert "GDP per capita" == new_workbook.views[0].name - assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - assert "REST API Testing" == new_workbook.description - - def test_publish_a_packaged_file_object(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) + ro = TSC.PPTXRequestOptions(maxage=1) - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + server.workbooks.populate_powerpoint(single_workbook, ro) + assert response == single_workbook.powerpoint - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - - with open(sample_workbook, "rb") as fp: - publish_mode = self.server.PublishMode.CreateNew - - new_workbook = self.server.workbooks.publish(new_workbook, fp, publish_mode) - - assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id - assert "RESTAPISample" == new_workbook.name - assert "RESTAPISample_0" == new_workbook.content_url - assert not new_workbook.show_tabs - assert 1 == new_workbook.size - assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) - assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id - assert "default" == new_workbook.project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id - assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id - assert "GDP per capita" == new_workbook.views[0].name - assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - - def test_publish_non_packeged_file_object(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) +def test_populate_preview_image(server) -> None: + response = POPULATE_PREVIEW_IMAGE.read_bytes() + with requests_mock.mock() as m: + m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/previewImage", content=response) + single_workbook = TSC.WorkbookItem("test") + single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.populate_preview_image(single_workbook) - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + assert response == single_workbook.preview_image - sample_workbook = os.path.join(TEST_ASSET_DIR, "RESTAPISample.twb") - - with open(sample_workbook, "rb") as fp: - publish_mode = self.server.PublishMode.CreateNew - - new_workbook = self.server.workbooks.publish(new_workbook, fp, publish_mode) - - assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id - assert "RESTAPISample" == new_workbook.name - assert "RESTAPISample_0" == new_workbook.content_url - assert not new_workbook.show_tabs - assert 1 == new_workbook.size - assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) - assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id - assert "default" == new_workbook.project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id - assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id - assert "GDP per capita" == new_workbook.views[0].name - assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - - def test_publish_path_object(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) - - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) +def test_populate_preview_image_missing_id(server) -> None: + single_workbook = TSC.WorkbookItem("test") + with pytest.raises(TSC.MissingRequiredFieldError): + server.workbooks.populate_preview_image(single_workbook) - sample_workbook = Path(TEST_ASSET_DIR) / "SampleWB.twbx" - publish_mode = self.server.PublishMode.CreateNew - - new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - - assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id - assert "RESTAPISample" == new_workbook.name - assert "RESTAPISample_0" == new_workbook.content_url - assert not new_workbook.show_tabs - assert 1 == new_workbook.size - assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) - assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) - assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id - assert "default" == new_workbook.project_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id - assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id - assert "GDP per capita" == new_workbook.views[0].name - assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - - def test_publish_with_hidden_views_on_workbook(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) +def test_publish(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew + new_workbook.description = "REST API Testing" + + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew + + new_workbook = server.workbooks.publish(new_workbook, sample_workbook, publish_mode) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + assert "REST API Testing" == new_workbook.description + +def test_publish_a_packaged_file_object(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - new_workbook.hidden_views = ["GDP per capita"] - new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - request_body = m._adapter.request_history[0]._request.body - # order of attributes in xml is unspecified - assert re.search(b'<\\/views>', request_body) - assert re.search(b'<\\/views>', request_body) + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - def test_publish_with_thumbnails_user_id(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - new_workbook = TSC.WorkbookItem( - name="Sample", - show_tabs=False, - project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", - thumbnails_user_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20761", - ) + with open(sample_workbook, "rb") as fp: + publish_mode = server.PublishMode.CreateNew - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew - new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - request_body = m._adapter.request_history[0]._request.body - # order of attributes in xml is unspecified - assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) + new_workbook = server.workbooks.publish(new_workbook, fp, publish_mode) - def test_publish_with_thumbnails_group_id(self) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - new_workbook = TSC.WorkbookItem( - name="Sample", - show_tabs=False, - project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", - thumbnails_group_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20762", - ) +def test_publish_non_packeged_file_object(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew - new_workbook = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode) - request_body = m._adapter.request_history[0]._request.body - assert re.search(b'thumbnailsGroupId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20762\\"', request_body) + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - @pytest.mark.filterwarnings("ignore:'as_job' not available") - def test_publish_with_query_params(self) -> None: - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(self.baseurl, text=response_xml) + sample_workbook = os.path.join(TEST_ASSET_DIR, "RESTAPISample.twb") - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + with open(sample_workbook, "rb") as fp: + publish_mode = server.PublishMode.CreateNew - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew + new_workbook = server.workbooks.publish(new_workbook, fp, publish_mode) - self.server.workbooks.publish( - new_workbook, sample_workbook, publish_mode, as_job=True, skip_connection_check=True - ) + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url - request_query_params = m._adapter.request_history[0].qs - assert "asjob" in request_query_params - assert request_query_params["asjob"] - assert "skipconnectioncheck" in request_query_params - assert request_query_params["skipconnectioncheck"] +def test_publish_path_object(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - def test_publish_async(self) -> None: - self.server.version = "3.0" - baseurl = self.server.workbooks.baseurl - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post(baseurl, text=response_xml) + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + sample_workbook = Path(TEST_ASSET_DIR) / "SampleWB.twbx" + publish_mode = server.PublishMode.CreateNew + + new_workbook = server.workbooks.publish(new_workbook, sample_workbook, publish_mode) + + assert "a8076ca1-e9d8-495e-bae6-c684dbb55836" == new_workbook.id + assert "RESTAPISample" == new_workbook.name + assert "RESTAPISample_0" == new_workbook.content_url + assert not new_workbook.show_tabs + assert 1 == new_workbook.size + assert "2016-08-18T18:33:24Z" == format_datetime(new_workbook.created_at) + assert "2016-08-18T20:31:34Z" == format_datetime(new_workbook.updated_at) + assert "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" == new_workbook.project_id + assert "default" == new_workbook.project_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == new_workbook.owner_id + assert "fe0b4e89-73f4-435e-952d-3a263fbfa56c" == new_workbook.views[0].id + assert "GDP per capita" == new_workbook.views[0].name + assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + +def test_publish_with_hidden_views_on_workbook(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") - publish_mode = self.server.PublishMode.CreateNew + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - new_job = self.server.workbooks.publish(new_workbook, sample_workbook, publish_mode, as_job=True) + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew - assert "7c3d599e-949f-44c3-94a1-f30ba85757e4" == new_job.id - assert "PublishWorkbook" == new_job.type - assert "0" == new_job.progress - assert "2018-06-29T23:22:32Z" == format_datetime(new_job.created_at) - assert 1 == new_job.finish_code + new_workbook.hidden_views = ["GDP per capita"] + new_workbook = server.workbooks.publish(new_workbook, sample_workbook, publish_mode) + request_body = m._adapter.request_history[0]._request.body + # order of attributes in xml is unspecified + assert re.search(b'<\\/views>', request_body) + assert re.search(b'<\\/views>', request_body) - def test_publish_invalid_file(self) -> None: - new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") - with pytest.raises(IOError): - self.server.workbooks.publish(new_workbook, ".", self.server.PublishMode.CreateNew) +def test_publish_with_thumbnails_user_id(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - def test_publish_invalid_file_type(self) -> None: - new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") - with pytest.raises(ValueError): - self.server.workbooks.publish( - new_workbook, os.path.join(TEST_ASSET_DIR, "SampleDS.tds"), self.server.PublishMode.CreateNew - ) + new_workbook = TSC.WorkbookItem( + name="Sample", + show_tabs=False, + project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", + thumbnails_user_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20761", + ) - def test_publish_unnamed_file_object(self) -> None: - new_workbook = TSC.WorkbookItem("test") + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew + new_workbook = server.workbooks.publish(new_workbook, sample_workbook, publish_mode) + request_body = m._adapter.request_history[0]._request.body + # order of attributes in xml is unspecified + assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) - with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx"), "rb") as f: - with pytest.raises(ValueError): - self.server.workbooks.publish(new_workbook, f, self.server.PublishMode.CreateNew) +def test_publish_with_thumbnails_group_id(server) -> None: + response_xml = PUBLISH_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - def test_publish_non_bytes_file_object(self) -> None: - new_workbook = TSC.WorkbookItem("test") + new_workbook = TSC.WorkbookItem( + name="Sample", + show_tabs=False, + project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760", + thumbnails_group_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20762", + ) - with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx")) as f: - with pytest.raises(TypeError): - self.server.workbooks.publish(new_workbook, f, self.server.PublishMode.CreateNew) + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew + new_workbook = server.workbooks.publish(new_workbook, sample_workbook, publish_mode) + request_body = m._adapter.request_history[0]._request.body + assert re.search(b'thumbnailsGroupId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20762\\"', request_body) - def test_publish_file_object_of_unknown_type_raises_exception(self) -> None: - new_workbook = TSC.WorkbookItem("test") - with BytesIO() as file_object: - file_object.write(bytes.fromhex("89504E470D0A1A0A")) - file_object.seek(0) - with pytest.raises(ValueError): - self.server.workbooks.publish(new_workbook, file_object, self.server.PublishMode.CreateNew) +@pytest.mark.filterwarnings("ignore:'as_job' not available") +def test_publish_with_query_params(server) -> None: + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(server.workbooks.baseurl, text=response_xml) - def test_publish_multi_connection(self) -> None: - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) - connection1 = TSC.ConnectionItem() - connection1.server_address = "mysql.test.com" - connection1.connection_credentials = TSC.ConnectionCredentials("test", "secret", True) - connection2 = TSC.ConnectionItem() - connection2.server_address = "pgsql.test.com" - connection2.connection_credentials = TSC.ConnectionCredentials("test", "secret", True) - - response = RequestFactory.Workbook._generate_xml(new_workbook, connections=[connection1, connection2]) - # Can't use ConnectionItem parser due to xml namespace problems - connection_results = fromstring(response).findall(".//connection") - - assert connection_results[0].get("serverAddress", None) == "mysql.test.com" - assert connection_results[0].find("connectionCredentials").get("name", None) == "test" - assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" - assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" - - def test_publish_multi_connection_flat(self) -> None: new_workbook = TSC.WorkbookItem( name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" ) - connection1 = TSC.ConnectionItem() - connection1.server_address = "mysql.test.com" - connection1.username = "test" - connection1.password = "secret" - connection1.embed_password = True - connection2 = TSC.ConnectionItem() - connection2.server_address = "pgsql.test.com" - connection2.username = "test" - connection2.password = "secret" - connection2.embed_password = True - - response = RequestFactory.Workbook._generate_xml(new_workbook, connections=[connection1, connection2]) - # Can't use ConnectionItem parser due to xml namespace problems - connection_results = fromstring(response).findall(".//connection") - - assert connection_results[0].get("serverAddress", None) == "mysql.test.com" - assert connection_results[0].find("connectionCredentials").get("name", None) == "test" - assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" - assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" - - def test_synchronous_publish_timeout_error(self) -> None: - with requests_mock.mock() as m: - m.register_uri("POST", self.baseurl, status_code=504) - - new_workbook = TSC.WorkbookItem(project_id="") - publish_mode = self.server.PublishMode.CreateNew - - with pytest.raises(InternalServerError, match="Please use asynchronous publishing to avoid timeouts"): - self.server.workbooks.publish(new_workbook, asset("SampleWB.twbx"), publish_mode) - - def test_delete_extracts_all(self) -> None: - self.server.version = "3.10" - self.baseurl = self.server.workbooks.baseurl - - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post( - self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", status_code=200, text=response_xml - ) - self.server.workbooks.delete_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - - def test_create_extracts_all(self) -> None: - self.server.version = "3.10" - self.baseurl = self.server.workbooks.baseurl - - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post( - self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml - ) - self.server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - def test_create_extracts_one(self) -> None: - self.server.version = "3.10" - self.baseurl = self.server.workbooks.baseurl + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew - datasource = TSC.DatasourceItem("test") - datasource._id = "1f951daf-4061-451a-9df1-69a8062664f2" + server.workbooks.publish( + new_workbook, sample_workbook, publish_mode, as_job=True, skip_connection_check=True + ) - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.post( - self.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml - ) - self.server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42", False, datasource) + request_query_params = m._adapter.request_history[0].qs + assert "asjob" in request_query_params + assert request_query_params["asjob"] + assert "skipconnectioncheck" in request_query_params + assert request_query_params["skipconnectioncheck"] - def test_revisions(self) -> None: - self.baseurl = self.server.workbooks.baseurl - workbook = TSC.WorkbookItem("project", "test") - workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" +def test_publish_async(server) -> None: + server.version = "3.0" + baseurl = server.workbooks.baseurl + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post(baseurl, text=response_xml) - response_xml = REVISION_XML.read_text(encoding="utf-8") - with requests_mock.mock() as m: - m.get(f"{self.baseurl}/{workbook.id}/revisions", text=response_xml) - self.server.workbooks.populate_revisions(workbook) - revisions = workbook.revisions - - assert len(revisions) == 3 - assert "2016-07-26T20:34:56Z" == format_datetime(revisions[0].created_at) - assert "2016-07-27T20:34:56Z" == format_datetime(revisions[1].created_at) - assert "2016-07-28T20:34:56Z" == format_datetime(revisions[2].created_at) - - assert not revisions[0].deleted - assert not revisions[0].current - assert not revisions[1].deleted - assert not revisions[1].current - assert not revisions[2].deleted - assert revisions[2].current - - assert "Cassie" == revisions[0].user_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[0].user_id - assert revisions[1].user_name is None - assert revisions[1].user_id is None - assert "Cassie" == revisions[2].user_name - assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[2].user_id - - def test_delete_revision(self) -> None: - self.baseurl = self.server.workbooks.baseurl - workbook = TSC.WorkbookItem("project", "test") - workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) - with requests_mock.mock() as m: - m.delete(f"{self.baseurl}/{workbook.id}/revisions/3") - self.server.workbooks.delete_revision(workbook.id, "3") + sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") + publish_mode = server.PublishMode.CreateNew - def test_download_revision(self) -> None: - with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: - m.get( - self.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/revisions/3/content", - headers={"Content-Disposition": 'name="tableau_datasource"; filename="Sample datasource.tds"'}, - ) - file_path = self.server.workbooks.download_revision("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", "3", td) - assert os.path.exists(file_path) + new_job = server.workbooks.publish(new_workbook, sample_workbook, publish_mode, as_job=True) - def test_bad_download_response(self) -> None: - with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: - m.get( - self.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/content", - headers={"Content-Disposition": '''name="tableau_workbook"; filename*=UTF-8''"Sample workbook.twb"'''}, - ) - file_path = self.server.workbooks.download("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", td) - assert os.path.exists(file_path) - - def test_odata_connection(self) -> None: - self.baseurl = self.server.workbooks.baseurl - workbook = TSC.WorkbookItem("project", "test") - workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" - connection = TSC.ConnectionItem() - url = "https://odata.website.com/TestODataEndpoint" - connection.server_address = url - connection._connection_type = "odata" - connection._id = "17376070-64d1-4d17-acb4-a56e4b5b1768" - - creds = TSC.ConnectionCredentials("", "", True) - connection.connection_credentials = creds - response_xml = ODATA_XML.read_text(encoding="utf-8") + assert "7c3d599e-949f-44c3-94a1-f30ba85757e4" == new_job.id + assert "PublishWorkbook" == new_job.type + assert "0" == new_job.progress + assert "2018-06-29T23:22:32Z" == format_datetime(new_job.created_at) + assert 1 == new_job.finish_code - with requests_mock.mock() as m: - m.put(f"{self.baseurl}/{workbook.id}/connections/{connection.id}", text=response_xml) - self.server.workbooks.update_connection(workbook, connection) +def test_publish_invalid_file(server) -> None: + new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") + with pytest.raises(IOError): + server.workbooks.publish(new_workbook, ".", server.PublishMode.CreateNew) - history = m.request_history +def test_publish_invalid_file_type(server) -> None: + new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") + with pytest.raises(ValueError): + server.workbooks.publish( + new_workbook, os.path.join(TEST_ASSET_DIR, "SampleDS.tds"), server.PublishMode.CreateNew + ) - request = history[0] - xml = fromstring(request.body) - xml_connection = xml.find(".//connection") +def test_publish_unnamed_file_object(server) -> None: + new_workbook = TSC.WorkbookItem("test") - assert xml_connection is not None - assert xml_connection.get("serverAddress") == url + with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx"), "rb") as f: + with pytest.raises(ValueError): + server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) - def test_update_workbook_connections(self) -> None: - populate_xml, response_xml = read_xml_assets(POPULATE_CONNECTIONS_XML, UPDATE_CONNECTIONS_XML) +def test_publish_non_bytes_file_object(server) -> None: + new_workbook = TSC.WorkbookItem("test") - with requests_mock.Mocker() as m: - workbook_id = "1a2b3c4d-5e6f-7a8b-9c0d-112233445566" - connection_luids = ["abc12345-def6-7890-gh12-ijklmnopqrst", "1234abcd-5678-efgh-ijkl-0987654321mn"] + with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx")) as f: + with pytest.raises(TypeError): + server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) - workbook = TSC.WorkbookItem(workbook_id) - workbook._id = workbook_id - self.server.version = "3.26" - url = f"{self.server.baseurl}/{workbook_id}/connections" - m.get( - "http://test/api/3.26/sites/dad65087-b08b-4603-af4e-2887b8aafc67/workbooks/1a2b3c4d-5e6f-7a8b-9c0d-112233445566/connections", - text=populate_xml, - ) - m.put( - "http://test/api/3.26/sites/dad65087-b08b-4603-af4e-2887b8aafc67/workbooks/1a2b3c4d-5e6f-7a8b-9c0d-112233445566/connections", - text=response_xml, - ) +def test_publish_file_object_of_unknown_type_raises_exception(server) -> None: + new_workbook = TSC.WorkbookItem("test") + with BytesIO() as file_object: + file_object.write(bytes.fromhex("89504E470D0A1A0A")) + file_object.seek(0) + with pytest.raises(ValueError): + server.workbooks.publish(new_workbook, file_object, server.PublishMode.CreateNew) + +def test_publish_multi_connection(server) -> None: + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) + connection1 = TSC.ConnectionItem() + connection1.server_address = "mysql.test.com" + connection1.connection_credentials = TSC.ConnectionCredentials("test", "secret", True) + connection2 = TSC.ConnectionItem() + connection2.server_address = "pgsql.test.com" + connection2.connection_credentials = TSC.ConnectionCredentials("test", "secret", True) + + response = RequestFactory.Workbook._generate_xml(new_workbook, connections=[connection1, connection2]) + # Can't use ConnectionItem parser due to xml namespace problems + connection_results = fromstring(response).findall(".//connection") + + assert connection_results[0].get("serverAddress", None) == "mysql.test.com" + assert connection_results[0].find("connectionCredentials").get("name", None) == "test" + assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" + assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" + +def test_publish_multi_connection_flat(server) -> None: + new_workbook = TSC.WorkbookItem( + name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" + ) + connection1 = TSC.ConnectionItem() + connection1.server_address = "mysql.test.com" + connection1.username = "test" + connection1.password = "secret" + connection1.embed_password = True + connection2 = TSC.ConnectionItem() + connection2.server_address = "pgsql.test.com" + connection2.username = "test" + connection2.password = "secret" + connection2.embed_password = True + + response = RequestFactory.Workbook._generate_xml(new_workbook, connections=[connection1, connection2]) + # Can't use ConnectionItem parser due to xml namespace problems + connection_results = fromstring(response).findall(".//connection") + + assert connection_results[0].get("serverAddress", None) == "mysql.test.com" + assert connection_results[0].find("connectionCredentials").get("name", None) == "test" + assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" + assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" + +def test_synchronous_publish_timeout_error(server) -> None: + with requests_mock.mock() as m: + m.register_uri("POST", server.workbooks.baseurl, status_code=504) + + new_workbook = TSC.WorkbookItem(project_id="") + publish_mode = server.PublishMode.CreateNew + + with pytest.raises(InternalServerError, match="Please use asynchronous publishing to avoid timeouts"): + server.workbooks.publish(new_workbook, asset("SampleWB.twbx"), publish_mode) + +def test_delete_extracts_all(server) -> None: + server.version = "3.10" + server.workbooks.baseurl + + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post( + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", status_code=200, text=response_xml + ) + server.workbooks.delete_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - connection_items = self.server.workbooks.update_connections( - workbook_item=workbook, - connection_luids=connection_luids, - authentication_type="AD Service Principal", - username="svc-client", - password="secret-token", - embed_password=True, - ) - updated_ids = [conn.id for conn in connection_items] +def test_create_extracts_all(server) -> None: + server.version = "3.10" + server.workbooks.baseurl - assert updated_ids == connection_luids - assert "AD Service Principal" == connection_items[0].auth_type + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post( + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml + ) + server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") - def test_get_workbook_all_fields(self) -> None: - self.server.version = "3.21" - baseurl = self.server.workbooks.baseurl +def test_create_extracts_one(server) -> None: + server.version = "3.10" + server.workbooks.baseurl - response = GET_XML_ALL_FIELDS.read_text(encoding="utf-8") + datasource = TSC.DatasourceItem("test") + datasource._id = "1f951daf-4061-451a-9df1-69a8062664f2" - ro = TSC.RequestOptions() - ro.all_fields = True + response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.post( + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml + ) + server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42", False, datasource) + +def test_revisions(server) -> None: + server.workbooks.baseurl + workbook = TSC.WorkbookItem("project", "test") + workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" + + response_xml = REVISION_XML.read_text(encoding="utf-8") + with requests_mock.mock() as m: + m.get(f"{server.workbooks.baseurl}/{workbook.id}/revisions", text=response_xml) + server.workbooks.populate_revisions(workbook) + revisions = workbook.revisions + + assert len(revisions) == 3 + assert "2016-07-26T20:34:56Z" == format_datetime(revisions[0].created_at) + assert "2016-07-27T20:34:56Z" == format_datetime(revisions[1].created_at) + assert "2016-07-28T20:34:56Z" == format_datetime(revisions[2].created_at) + + assert not revisions[0].deleted + assert not revisions[0].current + assert not revisions[1].deleted + assert not revisions[1].current + assert not revisions[2].deleted + assert revisions[2].current + + assert "Cassie" == revisions[0].user_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[0].user_id + assert revisions[1].user_name is None + assert revisions[1].user_id is None + assert "Cassie" == revisions[2].user_name + assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[2].user_id + +def test_delete_revision(server) -> None: + server.workbooks.baseurl + workbook = TSC.WorkbookItem("project", "test") + workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" + + with requests_mock.mock() as m: + m.delete(f"{server.workbooks.baseurl}/{workbook.id}/revisions/3") + server.workbooks.delete_revision(workbook.id, "3") + +def test_download_revision(server) -> None: + with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: + m.get( + server.workbooks.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/revisions/3/content", + headers={"Content-Disposition": 'name="tableau_datasource"; filename="Sample datasource.tds"'}, + ) + file_path = server.workbooks.download_revision("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", "3", td) + assert os.path.exists(file_path) + +def test_bad_download_response(server) -> None: + with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: + m.get( + server.workbooks.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/content", + headers={"Content-Disposition": '''name="tableau_workbook"; filename*=UTF-8''"Sample workbook.twb"'''}, + ) + file_path = server.workbooks.download("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", td) + assert os.path.exists(file_path) + +def test_odata_connection(server) -> None: + server.workbooks.baseurl + workbook = TSC.WorkbookItem("project", "test") + workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" + connection = TSC.ConnectionItem() + url = "https://odata.website.com/TestODataEndpoint" + connection.server_address = url + connection._connection_type = "odata" + connection._id = "17376070-64d1-4d17-acb4-a56e4b5b1768" + + creds = TSC.ConnectionCredentials("", "", True) + connection.connection_credentials = creds + response_xml = ODATA_XML.read_text(encoding="utf-8") + + with requests_mock.mock() as m: + m.put(f"{server.workbooks.baseurl}/{workbook.id}/connections/{connection.id}", text=response_xml) + server.workbooks.update_connection(workbook, connection) + + history = m.request_history + + request = history[0] + xml = fromstring(request.body) + xml_connection = xml.find(".//connection") + + assert xml_connection is not None + assert xml_connection.get("serverAddress") == url + +def test_update_workbook_connections(server) -> None: + populate_xml, response_xml = read_xml_assets(POPULATE_CONNECTIONS_XML, UPDATE_CONNECTIONS_XML) + + with requests_mock.Mocker() as m: + workbook_id = "1a2b3c4d-5e6f-7a8b-9c0d-112233445566" + connection_luids = ["abc12345-def6-7890-gh12-ijklmnopqrst", "1234abcd-5678-efgh-ijkl-0987654321mn"] + + workbook = TSC.WorkbookItem(workbook_id) + workbook._id = workbook_id + server.version = "3.26" + url = f"{server.baseurl}/{workbook_id}/connections" + m.get( + "http://test/api/3.26/sites/dad65087-b08b-4603-af4e-2887b8aafc67/workbooks/1a2b3c4d-5e6f-7a8b-9c0d-112233445566/connections", + text=populate_xml, + ) + m.put( + "http://test/api/3.26/sites/dad65087-b08b-4603-af4e-2887b8aafc67/workbooks/1a2b3c4d-5e6f-7a8b-9c0d-112233445566/connections", + text=response_xml, + ) - with requests_mock.mock() as m: - m.get(f"{baseurl}?fields=_all_", text=response) - workbooks, _ = self.server.workbooks.get(req_options=ro) - - assert workbooks[0].id == "9df3e2d1-070e-497a-9578-8cc557ced9df" - assert workbooks[0].name == "Superstore" - assert workbooks[0].content_url == "Superstore" - assert workbooks[0].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265605" - assert workbooks[0].show_tabs - assert workbooks[0].size == 2 - assert workbooks[0].created_at == parse_datetime("2024-02-14T04:42:09Z") - assert workbooks[0].updated_at == parse_datetime("2024-02-14T04:42:10Z") - assert workbooks[0].sheet_count == 9 - assert not workbooks[0].has_extracts - assert not workbooks[0].encrypt_extracts - assert workbooks[0].default_view_id == "2bdcd787-dcc6-4a5d-bc61-2846f1ef4534" - assert workbooks[0].share_description == "Superstore" - assert workbooks[0].last_published_at == parse_datetime("2024-02-14T04:42:09Z") - assert isinstance(workbooks[0].project, TSC.ProjectItem) - assert workbooks[0].project.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" - assert workbooks[0].project.name == "Samples" - assert workbooks[0].project.description == "This project includes automatically uploaded samples." - assert isinstance(workbooks[0].location, TSC.LocationItem) - assert workbooks[0].location.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" - assert workbooks[0].location.type == "Project" - assert workbooks[0].location.name == "Samples" - assert isinstance(workbooks[0].owner, TSC.UserItem) - assert workbooks[0].owner.email == "bob@example.com" - assert workbooks[0].owner.fullname == "Bob Smith" - assert workbooks[0].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" - assert workbooks[0].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") - assert workbooks[0].owner.name == "bob@example.com" - assert workbooks[0].owner.site_role == "SiteAdministratorCreator" - assert workbooks[1].id == "6693cb26-9507-4174-ad3e-9de81a18c971" - assert workbooks[1].name == "World Indicators" - assert workbooks[1].content_url == "WorldIndicators" - assert workbooks[1].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265606" - assert workbooks[1].show_tabs - assert workbooks[1].size == 1 - assert workbooks[1].created_at == parse_datetime("2024-02-14T04:42:11Z") - assert workbooks[1].updated_at == parse_datetime("2024-02-14T04:42:12Z") - assert workbooks[1].sheet_count == 8 - assert not workbooks[1].has_extracts - assert not workbooks[1].encrypt_extracts - assert workbooks[1].default_view_id == "3d10dbcf-a206-47c7-91ba-ebab3ab33d7c" - assert workbooks[1].share_description == "World Indicators" - assert workbooks[1].last_published_at == parse_datetime("2024-02-14T04:42:11Z") - assert isinstance(workbooks[1].project, TSC.ProjectItem) - assert workbooks[1].project.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" - assert workbooks[1].project.name == "Samples" - assert workbooks[1].project.description == "This project includes automatically uploaded samples." - assert isinstance(workbooks[1].location, TSC.LocationItem) - assert workbooks[1].location.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" - assert workbooks[1].location.type == "Project" - assert workbooks[1].location.name == "Samples" - assert isinstance(workbooks[1].owner, TSC.UserItem) - assert workbooks[1].owner.email == "bob@example.com" - assert workbooks[1].owner.fullname == "Bob Smith" - assert workbooks[1].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" - assert workbooks[1].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") - assert workbooks[1].owner.name == "bob@example.com" - assert workbooks[1].owner.site_role == "SiteAdministratorCreator" - assert workbooks[2].id == "dbc0f162-909f-4edf-8392-0d12a80af955" - assert workbooks[2].name == "Superstore" - assert workbooks[2].description == "This is a superstore workbook" - assert workbooks[2].content_url == "Superstore_17078880698360" - assert workbooks[2].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265621" - assert not workbooks[2].show_tabs - assert workbooks[2].size == 1 - assert workbooks[2].created_at == parse_datetime("2024-02-14T05:21:09Z") - assert workbooks[2].updated_at == parse_datetime("2024-07-02T02:19:59Z") - assert workbooks[2].sheet_count == 7 - assert workbooks[2].has_extracts - assert not workbooks[2].encrypt_extracts - assert workbooks[2].default_view_id == "8c4b1d3e-3f31-4d2a-8b9f-492b92f27987" - assert workbooks[2].share_description == "Superstore" - assert workbooks[2].last_published_at == parse_datetime("2024-07-02T02:19:58Z") - assert isinstance(workbooks[2].project, TSC.ProjectItem) - assert workbooks[2].project.id == "9836791c-9468-40f0-b7f3-d10b9562a046" - assert workbooks[2].project.name == "default" - assert workbooks[2].project.description == "The default project that was automatically created by Tableau." - assert isinstance(workbooks[2].location, TSC.LocationItem) - assert workbooks[2].location.id == "9836791c-9468-40f0-b7f3-d10b9562a046" - assert workbooks[2].location.type == "Project" - assert workbooks[2].location.name == "default" - assert isinstance(workbooks[2].owner, TSC.UserItem) - assert workbooks[2].owner.email == "bob@example.com" - assert workbooks[2].owner.fullname == "Bob Smith" - assert workbooks[2].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" - assert workbooks[2].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") - assert workbooks[2].owner.name == "bob@example.com" - assert workbooks[2].owner.site_role == "SiteAdministratorCreator" + connection_items = server.workbooks.update_connections( + workbook_item=workbook, + connection_luids=connection_luids, + authentication_type="AD Service Principal", + username="svc-client", + password="secret-token", + embed_password=True, + ) + updated_ids = [conn.id for conn in connection_items] + + assert updated_ids == connection_luids + assert "AD Service Principal" == connection_items[0].auth_type + +def test_get_workbook_all_fields(server) -> None: + server.version = "3.21" + baseurl = server.workbooks.baseurl + + response = GET_XML_ALL_FIELDS.read_text(encoding="utf-8") + + ro = TSC.RequestOptions() + ro.all_fields = True + + with requests_mock.mock() as m: + m.get(f"{baseurl}?fields=_all_", text=response) + workbooks, _ = server.workbooks.get(req_options=ro) + + assert workbooks[0].id == "9df3e2d1-070e-497a-9578-8cc557ced9df" + assert workbooks[0].name == "Superstore" + assert workbooks[0].content_url == "Superstore" + assert workbooks[0].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265605" + assert workbooks[0].show_tabs + assert workbooks[0].size == 2 + assert workbooks[0].created_at == parse_datetime("2024-02-14T04:42:09Z") + assert workbooks[0].updated_at == parse_datetime("2024-02-14T04:42:10Z") + assert workbooks[0].sheet_count == 9 + assert not workbooks[0].has_extracts + assert not workbooks[0].encrypt_extracts + assert workbooks[0].default_view_id == "2bdcd787-dcc6-4a5d-bc61-2846f1ef4534" + assert workbooks[0].share_description == "Superstore" + assert workbooks[0].last_published_at == parse_datetime("2024-02-14T04:42:09Z") + assert isinstance(workbooks[0].project, TSC.ProjectItem) + assert workbooks[0].project.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" + assert workbooks[0].project.name == "Samples" + assert workbooks[0].project.description == "This project includes automatically uploaded samples." + assert isinstance(workbooks[0].location, TSC.LocationItem) + assert workbooks[0].location.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" + assert workbooks[0].location.type == "Project" + assert workbooks[0].location.name == "Samples" + assert isinstance(workbooks[0].owner, TSC.UserItem) + assert workbooks[0].owner.email == "bob@example.com" + assert workbooks[0].owner.fullname == "Bob Smith" + assert workbooks[0].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" + assert workbooks[0].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") + assert workbooks[0].owner.name == "bob@example.com" + assert workbooks[0].owner.site_role == "SiteAdministratorCreator" + assert workbooks[1].id == "6693cb26-9507-4174-ad3e-9de81a18c971" + assert workbooks[1].name == "World Indicators" + assert workbooks[1].content_url == "WorldIndicators" + assert workbooks[1].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265606" + assert workbooks[1].show_tabs + assert workbooks[1].size == 1 + assert workbooks[1].created_at == parse_datetime("2024-02-14T04:42:11Z") + assert workbooks[1].updated_at == parse_datetime("2024-02-14T04:42:12Z") + assert workbooks[1].sheet_count == 8 + assert not workbooks[1].has_extracts + assert not workbooks[1].encrypt_extracts + assert workbooks[1].default_view_id == "3d10dbcf-a206-47c7-91ba-ebab3ab33d7c" + assert workbooks[1].share_description == "World Indicators" + assert workbooks[1].last_published_at == parse_datetime("2024-02-14T04:42:11Z") + assert isinstance(workbooks[1].project, TSC.ProjectItem) + assert workbooks[1].project.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" + assert workbooks[1].project.name == "Samples" + assert workbooks[1].project.description == "This project includes automatically uploaded samples." + assert isinstance(workbooks[1].location, TSC.LocationItem) + assert workbooks[1].location.id == "669ca36b-492e-4ccf-bca1-3614fe6a9d7a" + assert workbooks[1].location.type == "Project" + assert workbooks[1].location.name == "Samples" + assert isinstance(workbooks[1].owner, TSC.UserItem) + assert workbooks[1].owner.email == "bob@example.com" + assert workbooks[1].owner.fullname == "Bob Smith" + assert workbooks[1].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" + assert workbooks[1].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") + assert workbooks[1].owner.name == "bob@example.com" + assert workbooks[1].owner.site_role == "SiteAdministratorCreator" + assert workbooks[2].id == "dbc0f162-909f-4edf-8392-0d12a80af955" + assert workbooks[2].name == "Superstore" + assert workbooks[2].description == "This is a superstore workbook" + assert workbooks[2].content_url == "Superstore_17078880698360" + assert workbooks[2].webpage_url == "https://10ax.online.tableau.com/#/site/exampledev/workbooks/265621" + assert not workbooks[2].show_tabs + assert workbooks[2].size == 1 + assert workbooks[2].created_at == parse_datetime("2024-02-14T05:21:09Z") + assert workbooks[2].updated_at == parse_datetime("2024-07-02T02:19:59Z") + assert workbooks[2].sheet_count == 7 + assert workbooks[2].has_extracts + assert not workbooks[2].encrypt_extracts + assert workbooks[2].default_view_id == "8c4b1d3e-3f31-4d2a-8b9f-492b92f27987" + assert workbooks[2].share_description == "Superstore" + assert workbooks[2].last_published_at == parse_datetime("2024-07-02T02:19:58Z") + assert isinstance(workbooks[2].project, TSC.ProjectItem) + assert workbooks[2].project.id == "9836791c-9468-40f0-b7f3-d10b9562a046" + assert workbooks[2].project.name == "default" + assert workbooks[2].project.description == "The default project that was automatically created by Tableau." + assert isinstance(workbooks[2].location, TSC.LocationItem) + assert workbooks[2].location.id == "9836791c-9468-40f0-b7f3-d10b9562a046" + assert workbooks[2].location.type == "Project" + assert workbooks[2].location.name == "default" + assert isinstance(workbooks[2].owner, TSC.UserItem) + assert workbooks[2].owner.email == "bob@example.com" + assert workbooks[2].owner.fullname == "Bob Smith" + assert workbooks[2].owner.id == "ee8bc9ca-77fe-4ae0-8093-cf77f0ee67a9" + assert workbooks[2].owner.last_login == parse_datetime("2025-02-04T06:39:20Z") + assert workbooks[2].owner.name == "bob@example.com" + assert workbooks[2].owner.site_role == "SiteAdministratorCreator" From 0ab3cbc8cdcc90d1e402a4ac50037b6318ef17c5 Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Wed, 20 Aug 2025 20:30:15 -0500 Subject: [PATCH 4/7] style: black --- .../server/endpoint/workbooks_endpoint.py | 11 +- test/test_workbook.py | 104 +++++++++++++++--- 2 files changed, 95 insertions(+), 20 deletions(-) diff --git a/tableauserverclient/server/endpoint/workbooks_endpoint.py b/tableauserverclient/server/endpoint/workbooks_endpoint.py index 19bceb9b..a9331719 100644 --- a/tableauserverclient/server/endpoint/workbooks_endpoint.py +++ b/tableauserverclient/server/endpoint/workbooks_endpoint.py @@ -387,6 +387,7 @@ def update_connections( return connection_items T = TypeVar("T", bound=FileObjectW) + @overload def download( self, @@ -762,7 +763,8 @@ def delete_permission(self, item: WorkbookItem, capability_item: PermissionsRule return self._permissions.delete(item, capability_item) @overload - def publish(self, + def publish( + self, workbook_item: WorkbookItem, file: PathOrFileR, mode: str, @@ -770,10 +772,11 @@ def publish(self, as_job: Literal[False], skip_connection_check: bool, parameters=None, - ) -> WorkbookItem: ... + ) -> WorkbookItem: ... @overload - def publish(self, + def publish( + self, workbook_item: WorkbookItem, file: PathOrFileR, mode: str, @@ -781,7 +784,7 @@ def publish(self, as_job: Literal[True], skip_connection_check: bool, parameters=None, - ) -> JobItem: ... + ) -> JobItem: ... @api(version="2.0") @parameter_added_in(as_job="3.0") diff --git a/test/test_workbook.py b/test/test_workbook.py index 24e6729d..5e569dae 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -40,6 +40,7 @@ UPDATE_PERMISSIONS = TEST_ASSET_DIR / "workbook_update_permissions.xml" UPDATE_CONNECTIONS_XML = TEST_ASSET_DIR / "workbook_update_connections.xml" + @pytest.fixture(scope="function") def server(): server = TSC.Server("http://test", False) @@ -49,7 +50,8 @@ def server(): server._auth_token = "j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM" return server - + + def test_get(server) -> None: response_xml = GET_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -84,6 +86,7 @@ def test_get(server) -> None: assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == all_workbooks[1].owner_id assert {"Safari", "Sample"} == all_workbooks[1].tags + def test_get_ignore_invalid_date(server) -> None: response_xml = GET_INVALID_DATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -92,11 +95,13 @@ def test_get_ignore_invalid_date(server) -> None: assert format_datetime(all_workbooks[0].created_at) is None assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) + def test_get_before_signin(server) -> None: server._auth_token = None with pytest.raises(TSC.NotSignedInError): server.workbooks.get() + def test_get_empty(server) -> None: response_xml = GET_EMPTY_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -106,6 +111,7 @@ def test_get_empty(server) -> None: assert 0 == pagination_item.total_available assert [] == all_workbooks + def test_get_by_id(server) -> None: response_xml = GET_BY_ID_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -129,6 +135,7 @@ def test_get_by_id(server) -> None: assert "ENDANGERED SAFARI" == single_workbook.views[0].name assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url + def test_get_by_id_personal(server) -> None: # workbooks in personal space don't have project_id or project_name response_xml = GET_BY_ID_XML_PERSONAL.read_text(encoding="utf-8") @@ -153,18 +160,25 @@ def test_get_by_id_personal(server) -> None: assert "ENDANGERED SAFARI" == single_workbook.views[0].name assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url + def test_get_by_id_missing_id(server) -> None: with pytest.raises(ValueError): server.workbooks.get_by_id("") + def test_refresh_id(server) -> None: server.version = "2.8" server.workbooks.baseurl response_xml = REFRESH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: - m.post(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) + m.post( + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", + status_code=202, + text=response_xml, + ) server.workbooks.refresh("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + def test_refresh_object(server) -> None: server.version = "2.8" server.workbooks.baseurl @@ -172,18 +186,25 @@ def test_refresh_object(server) -> None: workbook._id = "3cc6cd06-89ce-4fdc-b935-5294135d6d42" response_xml = REFRESH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: - m.post(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", status_code=202, text=response_xml) + m.post( + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", + status_code=202, + text=response_xml, + ) server.workbooks.refresh(workbook) + def test_delete(server) -> None: with requests_mock.mock() as m: m.delete(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", status_code=204) server.workbooks.delete("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + def test_delete_missing_id(server) -> None: with pytest.raises(ValueError): server.workbooks.delete("") + def test_update(server) -> None: response_xml = UPDATE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -208,11 +229,13 @@ def test_update(server) -> None: assert single_workbook.data_acceleration_config["acceleration_enabled"] assert not single_workbook.data_acceleration_config["accelerate_now"] + def test_update_missing_id(server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.update(single_workbook) + def test_update_copy_fields(server) -> None: connection_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") update_xml = UPDATE_XML.read_text(encoding="utf-8") @@ -230,6 +253,7 @@ def test_update_copy_fields(server) -> None: assert single_workbook._initial_tags == updated_workbook._initial_tags assert single_workbook._preview_image == updated_workbook._preview_image + def test_update_tags(server) -> None: add_tags_xml = ADD_TAGS_XML.read_text(encoding="utf-8") update_xml = UPDATE_XML.read_text(encoding="utf-8") @@ -247,6 +271,7 @@ def test_update_tags(server) -> None: assert single_workbook.tags == updated_workbook.tags assert single_workbook._initial_tags == updated_workbook._initial_tags + def test_download(server) -> None: with requests_mock.mock() as m: m.get( @@ -257,6 +282,7 @@ def test_download(server) -> None: assert os.path.exists(file_path) os.remove(file_path) + def test_download_object(server) -> None: with BytesIO() as file_object: with requests_mock.mock() as m: @@ -267,6 +293,7 @@ def test_download_object(server) -> None: file_path = server.workbooks.download("1f951daf-4061-451a-9df1-69a8062664f2", filepath=file_object) assert isinstance(file_path, BytesIO) + def test_download_sanitizes_name(server) -> None: filename = "Name,With,Commas.twbx" disposition = f'name="tableau_workbook"; filename="{filename}"' @@ -280,6 +307,7 @@ def test_download_sanitizes_name(server) -> None: assert os.path.exists(file_path) os.remove(file_path) + def test_download_extract_only(server) -> None: # Pretend we're 2.5 for 'extract_only' server.version = "2.5" @@ -296,10 +324,12 @@ def test_download_extract_only(server) -> None: assert os.path.exists(file_path) os.remove(file_path) + def test_download_missing_id(server) -> None: with pytest.raises(ValueError): server.workbooks.download("") + def test_populate_views(server) -> None: response_xml = POPULATE_VIEWS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -321,6 +351,7 @@ def test_populate_views(server) -> None: assert "Interest rates" == views_list[2].name assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url + def test_populate_views_with_usage(server) -> None: response_xml = POPULATE_VIEWS_USAGE_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -340,11 +371,13 @@ def test_populate_views_with_usage(server) -> None: assert "0599c28c-6d82-457e-a453-e52c1bdb00f5" == views_list[2].id assert 0 == views_list[2].total_views + def test_populate_views_missing_id(server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_views(single_workbook) + def test_populate_connections(server) -> None: response_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -358,6 +391,7 @@ def test_populate_connections(server) -> None: assert "4506225a-0d32-4ab1-82d3-c24e85f7afba" == single_workbook.connections[0].datasource_id assert "World Indicators" == single_workbook.connections[0].datasource_name + def test_populate_permissions(server) -> None: response_xml = POPULATE_PERMISSIONS_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -386,6 +420,7 @@ def test_populate_permissions(server) -> None: TSC.Permission.Capability.ViewComments: TSC.Permission.Mode.Deny, } + def test_add_permissions(server) -> None: response_xml = UPDATE_PERMISSIONS.read_text(encoding="utf-8") @@ -408,11 +443,13 @@ def test_add_permissions(server) -> None: assert permissions[1].grantee.id == "7c37ee24-c4b1-42b6-a154-eaeab7ee330a" assert permissions[1].capabilities == {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow} + def test_populate_connections_missing_id(server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_connections(single_workbook) + def test_populate_pdf(server) -> None: server.version = "3.4" server.workbooks.baseurl @@ -432,11 +469,15 @@ def test_populate_pdf(server) -> None: server.workbooks.populate_pdf(single_workbook, req_option) assert response == single_workbook.pdf + def test_populate_pdf_unsupported(server) -> None: server.version = "3.4" server.workbooks.baseurl with requests_mock.mock() as m: - m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", content=b"") + m.get( + server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/pdf?type=a5&orientation=landscape", + content=b"", + ) single_workbook = TSC.WorkbookItem("test") single_workbook._id = "1f951daf-4061-451a-9df1-69a8062664f2" @@ -448,6 +489,7 @@ def test_populate_pdf_unsupported(server) -> None: with pytest.raises(UnsupportedAttributeError): server.workbooks.populate_pdf(single_workbook, req_option) + def test_populate_pdf_vf_dims(server) -> None: server.version = "3.23" server.workbooks.baseurl @@ -471,6 +513,7 @@ def test_populate_pdf_vf_dims(server) -> None: server.workbooks.populate_pdf(single_workbook, req_option) assert response == single_workbook.pdf + def test_populate_powerpoint(server) -> None: server.version = "3.8" server.workbooks.baseurl @@ -485,6 +528,7 @@ def test_populate_powerpoint(server) -> None: server.workbooks.populate_powerpoint(single_workbook, ro) assert response == single_workbook.powerpoint + def test_populate_preview_image(server) -> None: response = POPULATE_PREVIEW_IMAGE.read_bytes() with requests_mock.mock() as m: @@ -495,11 +539,13 @@ def test_populate_preview_image(server) -> None: assert response == single_workbook.preview_image + def test_populate_preview_image_missing_id(server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_preview_image(single_workbook) + def test_publish(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -530,6 +576,7 @@ def test_publish(server) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url assert "REST API Testing" == new_workbook.description + def test_publish_a_packaged_file_object(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -560,6 +607,7 @@ def test_publish_a_packaged_file_object(server) -> None: assert "GDP per capita" == new_workbook.views[0].name assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + def test_publish_non_packeged_file_object(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -590,6 +638,7 @@ def test_publish_non_packeged_file_object(server) -> None: assert "GDP per capita" == new_workbook.views[0].name assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + def test_publish_path_object(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -618,6 +667,7 @@ def test_publish_path_object(server) -> None: assert "GDP per capita" == new_workbook.views[0].name assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url + def test_publish_with_hidden_views_on_workbook(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -637,6 +687,7 @@ def test_publish_with_hidden_views_on_workbook(server) -> None: assert re.search(b'<\\/views>', request_body) assert re.search(b'<\\/views>', request_body) + def test_publish_with_thumbnails_user_id(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -656,6 +707,7 @@ def test_publish_with_thumbnails_user_id(server) -> None: # order of attributes in xml is unspecified assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) + def test_publish_with_thumbnails_group_id(server) -> None: response_xml = PUBLISH_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: @@ -674,6 +726,7 @@ def test_publish_with_thumbnails_group_id(server) -> None: request_body = m._adapter.request_history[0]._request.body assert re.search(b'thumbnailsGroupId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20762\\"', request_body) + @pytest.mark.filterwarnings("ignore:'as_job' not available") def test_publish_with_query_params(server) -> None: response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") @@ -687,9 +740,7 @@ def test_publish_with_query_params(server) -> None: sample_workbook = os.path.join(TEST_ASSET_DIR, "SampleWB.twbx") publish_mode = server.PublishMode.CreateNew - server.workbooks.publish( - new_workbook, sample_workbook, publish_mode, as_job=True, skip_connection_check=True - ) + server.workbooks.publish(new_workbook, sample_workbook, publish_mode, as_job=True, skip_connection_check=True) request_query_params = m._adapter.request_history[0].qs assert "asjob" in request_query_params @@ -697,6 +748,7 @@ def test_publish_with_query_params(server) -> None: assert "skipconnectioncheck" in request_query_params assert request_query_params["skipconnectioncheck"] + def test_publish_async(server) -> None: server.version = "3.0" baseurl = server.workbooks.baseurl @@ -719,11 +771,13 @@ def test_publish_async(server) -> None: assert "2018-06-29T23:22:32Z" == format_datetime(new_job.created_at) assert 1 == new_job.finish_code + def test_publish_invalid_file(server) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") with pytest.raises(IOError): server.workbooks.publish(new_workbook, ".", server.PublishMode.CreateNew) + def test_publish_invalid_file_type(server) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") with pytest.raises(ValueError): @@ -731,6 +785,7 @@ def test_publish_invalid_file_type(server) -> None: new_workbook, os.path.join(TEST_ASSET_DIR, "SampleDS.tds"), server.PublishMode.CreateNew ) + def test_publish_unnamed_file_object(server) -> None: new_workbook = TSC.WorkbookItem("test") @@ -738,6 +793,7 @@ def test_publish_unnamed_file_object(server) -> None: with pytest.raises(ValueError): server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) + def test_publish_non_bytes_file_object(server) -> None: new_workbook = TSC.WorkbookItem("test") @@ -745,6 +801,7 @@ def test_publish_non_bytes_file_object(server) -> None: with pytest.raises(TypeError): server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) + def test_publish_file_object_of_unknown_type_raises_exception(server) -> None: new_workbook = TSC.WorkbookItem("test") with BytesIO() as file_object: @@ -753,10 +810,9 @@ def test_publish_file_object_of_unknown_type_raises_exception(server) -> None: with pytest.raises(ValueError): server.workbooks.publish(new_workbook, file_object, server.PublishMode.CreateNew) + def test_publish_multi_connection(server) -> None: - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + new_workbook = TSC.WorkbookItem(name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") connection1 = TSC.ConnectionItem() connection1.server_address = "mysql.test.com" connection1.connection_credentials = TSC.ConnectionCredentials("test", "secret", True) @@ -773,10 +829,9 @@ def test_publish_multi_connection(server) -> None: assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" + def test_publish_multi_connection_flat(server) -> None: - new_workbook = TSC.WorkbookItem( - name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760" - ) + new_workbook = TSC.WorkbookItem(name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") connection1 = TSC.ConnectionItem() connection1.server_address = "mysql.test.com" connection1.username = "test" @@ -797,6 +852,7 @@ def test_publish_multi_connection_flat(server) -> None: assert connection_results[1].get("serverAddress", None) == "pgsql.test.com" assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" + def test_synchronous_publish_timeout_error(server) -> None: with requests_mock.mock() as m: m.register_uri("POST", server.workbooks.baseurl, status_code=504) @@ -807,6 +863,7 @@ def test_synchronous_publish_timeout_error(server) -> None: with pytest.raises(InternalServerError, match="Please use asynchronous publishing to avoid timeouts"): server.workbooks.publish(new_workbook, asset("SampleWB.twbx"), publish_mode) + def test_delete_extracts_all(server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -814,10 +871,13 @@ def test_delete_extracts_all(server) -> None: response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( - server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", status_code=200, text=response_xml + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", + status_code=200, + text=response_xml, ) server.workbooks.delete_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + def test_create_extracts_all(server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -825,10 +885,13 @@ def test_create_extracts_all(server) -> None: response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( - server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", + status_code=200, + text=response_xml, ) server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") + def test_create_extracts_one(server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -839,10 +902,13 @@ def test_create_extracts_one(server) -> None: response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") with requests_mock.mock() as m: m.post( - server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", status_code=200, text=response_xml + server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", + status_code=200, + text=response_xml, ) server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42", False, datasource) + def test_revisions(server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") @@ -873,6 +939,7 @@ def test_revisions(server) -> None: assert "Cassie" == revisions[2].user_name assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[2].user_id + def test_delete_revision(server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") @@ -882,6 +949,7 @@ def test_delete_revision(server) -> None: m.delete(f"{server.workbooks.baseurl}/{workbook.id}/revisions/3") server.workbooks.delete_revision(workbook.id, "3") + def test_download_revision(server) -> None: with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: m.get( @@ -891,6 +959,7 @@ def test_download_revision(server) -> None: file_path = server.workbooks.download_revision("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", "3", td) assert os.path.exists(file_path) + def test_bad_download_response(server) -> None: with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: m.get( @@ -900,6 +969,7 @@ def test_bad_download_response(server) -> None: file_path = server.workbooks.download("9dbd2263-16b5-46e1-9c43-a76bb8ab65fb", td) assert os.path.exists(file_path) + def test_odata_connection(server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") @@ -927,6 +997,7 @@ def test_odata_connection(server) -> None: assert xml_connection is not None assert xml_connection.get("serverAddress") == url + def test_update_workbook_connections(server) -> None: populate_xml, response_xml = read_xml_assets(POPULATE_CONNECTIONS_XML, UPDATE_CONNECTIONS_XML) @@ -960,6 +1031,7 @@ def test_update_workbook_connections(server) -> None: assert updated_ids == connection_luids assert "AD Service Principal" == connection_items[0].auth_type + def test_get_workbook_all_fields(server) -> None: server.version = "3.21" baseurl = server.workbooks.baseurl From 8c584ad8ffb587032b68ea7900ed1bfc87b4a1e8 Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Fri, 22 Aug 2025 18:13:51 -0500 Subject: [PATCH 5/7] chore: remove asset and read_assets references --- test/test_workbook.py | 70 +++++++++++++++++++++---------------------- 1 file changed, 35 insertions(+), 35 deletions(-) diff --git a/test/test_workbook.py b/test/test_workbook.py index 5e569dae..459bbaaf 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -13,7 +13,6 @@ from tableauserverclient.models import UserItem, GroupItem, PermissionsRule from tableauserverclient.server.endpoint.exceptions import InternalServerError, UnsupportedAttributeError from tableauserverclient.server.request_factory import RequestFactory -from ._utils import read_xml_assets, asset TEST_ASSET_DIR = Path(__file__).parent / "assets" @@ -53,7 +52,7 @@ def server(): def test_get(server) -> None: - response_xml = GET_XML.read_text(encoding="utf-8") + response_xml = GET_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) all_workbooks, pagination_item = server.workbooks.get() @@ -88,7 +87,7 @@ def test_get(server) -> None: def test_get_ignore_invalid_date(server) -> None: - response_xml = GET_INVALID_DATE_XML.read_text(encoding="utf-8") + response_xml = GET_INVALID_DATE_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) all_workbooks, pagination_item = server.workbooks.get() @@ -103,7 +102,7 @@ def test_get_before_signin(server) -> None: def test_get_empty(server) -> None: - response_xml = GET_EMPTY_XML.read_text(encoding="utf-8") + response_xml = GET_EMPTY_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) all_workbooks, pagination_item = server.workbooks.get() @@ -113,7 +112,7 @@ def test_get_empty(server) -> None: def test_get_by_id(server) -> None: - response_xml = GET_BY_ID_XML.read_text(encoding="utf-8") + response_xml = GET_BY_ID_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) single_workbook = server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d42") @@ -138,7 +137,7 @@ def test_get_by_id(server) -> None: def test_get_by_id_personal(server) -> None: # workbooks in personal space don't have project_id or project_name - response_xml = GET_BY_ID_XML_PERSONAL.read_text(encoding="utf-8") + response_xml = GET_BY_ID_XML_PERSONAL.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d43", text=response_xml) single_workbook = server.workbooks.get_by_id("3cc6cd06-89ce-4fdc-b935-5294135d6d43") @@ -169,7 +168,7 @@ def test_get_by_id_missing_id(server) -> None: def test_refresh_id(server) -> None: server.version = "2.8" server.workbooks.baseurl - response_xml = REFRESH_XML.read_text(encoding="utf-8") + response_xml = REFRESH_XML.read_text() with requests_mock.mock() as m: m.post( server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", @@ -184,7 +183,7 @@ def test_refresh_object(server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("") workbook._id = "3cc6cd06-89ce-4fdc-b935-5294135d6d42" - response_xml = REFRESH_XML.read_text(encoding="utf-8") + response_xml = REFRESH_XML.read_text() with requests_mock.mock() as m: m.post( server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/refresh", @@ -206,7 +205,7 @@ def test_delete_missing_id(server) -> None: def test_update(server) -> None: - response_xml = UPDATE_XML.read_text(encoding="utf-8") + response_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=response_xml) single_workbook = TSC.WorkbookItem("1d0304cd-3796-429f-b815-7258370b9b74", show_tabs=True) @@ -237,8 +236,8 @@ def test_update_missing_id(server) -> None: def test_update_copy_fields(server) -> None: - connection_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") - update_xml = UPDATE_XML.read_text(encoding="utf-8") + connection_xml = POPULATE_CONNECTIONS_XML.read_text() + update_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=connection_xml) m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=update_xml) @@ -255,8 +254,8 @@ def test_update_copy_fields(server) -> None: def test_update_tags(server) -> None: - add_tags_xml = ADD_TAGS_XML.read_text(encoding="utf-8") - update_xml = UPDATE_XML.read_text(encoding="utf-8") + add_tags_xml = ADD_TAGS_XML.read_text() + update_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags", text=add_tags_xml) m.delete(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/tags/b", status_code=204) @@ -331,7 +330,7 @@ def test_download_missing_id(server) -> None: def test_populate_views(server) -> None: - response_xml = POPULATE_VIEWS_XML.read_text(encoding="utf-8") + response_xml = POPULATE_VIEWS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -353,7 +352,7 @@ def test_populate_views(server) -> None: def test_populate_views_with_usage(server) -> None: - response_xml = POPULATE_VIEWS_USAGE_XML.read_text(encoding="utf-8") + response_xml = POPULATE_VIEWS_USAGE_XML.read_text() with requests_mock.mock() as m: m.get( server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views?includeUsageStatistics=true", @@ -379,7 +378,7 @@ def test_populate_views_missing_id(server) -> None: def test_populate_connections(server) -> None: - response_xml = POPULATE_CONNECTIONS_XML.read_text(encoding="utf-8") + response_xml = POPULATE_CONNECTIONS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -393,7 +392,7 @@ def test_populate_connections(server) -> None: def test_populate_permissions(server) -> None: - response_xml = POPULATE_PERMISSIONS_XML.read_text(encoding="utf-8") + response_xml = POPULATE_PERMISSIONS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) single_workbook = TSC.WorkbookItem("test") @@ -422,7 +421,7 @@ def test_populate_permissions(server) -> None: def test_add_permissions(server) -> None: - response_xml = UPDATE_PERMISSIONS.read_text(encoding="utf-8") + response_xml = UPDATE_PERMISSIONS.read_text() single_workbook = TSC.WorkbookItem("test") single_workbook._id = "21778de4-b7b9-44bc-a599-1506a2639ace" @@ -547,7 +546,7 @@ def test_populate_preview_image_missing_id(server) -> None: def test_publish(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -578,7 +577,7 @@ def test_publish(server) -> None: def test_publish_a_packaged_file_object(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -609,7 +608,7 @@ def test_publish_a_packaged_file_object(server) -> None: def test_publish_non_packeged_file_object(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -640,7 +639,7 @@ def test_publish_non_packeged_file_object(server) -> None: def test_publish_path_object(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -669,7 +668,7 @@ def test_publish_path_object(server) -> None: def test_publish_with_hidden_views_on_workbook(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -689,7 +688,7 @@ def test_publish_with_hidden_views_on_workbook(server) -> None: def test_publish_with_thumbnails_user_id(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -709,7 +708,7 @@ def test_publish_with_thumbnails_user_id(server) -> None: def test_publish_with_thumbnails_group_id(server) -> None: - response_xml = PUBLISH_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -729,7 +728,7 @@ def test_publish_with_thumbnails_group_id(server) -> None: @pytest.mark.filterwarnings("ignore:'as_job' not available") def test_publish_with_query_params(server) -> None: - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -752,7 +751,7 @@ def test_publish_with_query_params(server) -> None: def test_publish_async(server) -> None: server.version = "3.0" baseurl = server.workbooks.baseurl - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post(baseurl, text=response_xml) @@ -861,14 +860,14 @@ def test_synchronous_publish_timeout_error(server) -> None: publish_mode = server.PublishMode.CreateNew with pytest.raises(InternalServerError, match="Please use asynchronous publishing to avoid timeouts"): - server.workbooks.publish(new_workbook, asset("SampleWB.twbx"), publish_mode) + server.workbooks.publish(new_workbook, TEST_ASSET_DIR / "SampleWB.twbx", publish_mode) def test_delete_extracts_all(server) -> None: server.version = "3.10" server.workbooks.baseurl - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post( server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/deleteExtract", @@ -882,7 +881,7 @@ def test_create_extracts_all(server) -> None: server.version = "3.10" server.workbooks.baseurl - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post( server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", @@ -899,7 +898,7 @@ def test_create_extracts_one(server) -> None: datasource = TSC.DatasourceItem("test") datasource._id = "1f951daf-4061-451a-9df1-69a8062664f2" - response_xml = PUBLISH_ASYNC_XML.read_text(encoding="utf-8") + response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post( server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42/createExtract", @@ -914,7 +913,7 @@ def test_revisions(server) -> None: workbook = TSC.WorkbookItem("project", "test") workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" - response_xml = REVISION_XML.read_text(encoding="utf-8") + response_xml = REVISION_XML.read_text() with requests_mock.mock() as m: m.get(f"{server.workbooks.baseurl}/{workbook.id}/revisions", text=response_xml) server.workbooks.populate_revisions(workbook) @@ -982,7 +981,7 @@ def test_odata_connection(server) -> None: creds = TSC.ConnectionCredentials("", "", True) connection.connection_credentials = creds - response_xml = ODATA_XML.read_text(encoding="utf-8") + response_xml = ODATA_XML.read_text() with requests_mock.mock() as m: m.put(f"{server.workbooks.baseurl}/{workbook.id}/connections/{connection.id}", text=response_xml) @@ -999,7 +998,8 @@ def test_odata_connection(server) -> None: def test_update_workbook_connections(server) -> None: - populate_xml, response_xml = read_xml_assets(POPULATE_CONNECTIONS_XML, UPDATE_CONNECTIONS_XML) + populate_xml = POPULATE_CONNECTIONS_XML.read_text() + response_xml = UPDATE_CONNECTIONS_XML.read_text() with requests_mock.Mocker() as m: workbook_id = "1a2b3c4d-5e6f-7a8b-9c0d-112233445566" @@ -1036,7 +1036,7 @@ def test_get_workbook_all_fields(server) -> None: server.version = "3.21" baseurl = server.workbooks.baseurl - response = GET_XML_ALL_FIELDS.read_text(encoding="utf-8") + response = GET_XML_ALL_FIELDS.read_text() ro = TSC.RequestOptions() ro.all_fields = True From 10b20a8b0602230f34cee3abbb44eb0e7edf70f4 Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Thu, 28 Aug 2025 21:10:13 -0500 Subject: [PATCH 6/7] chore: narrow download_revision return type --- tableauserverclient/server/endpoint/workbooks_endpoint.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/tableauserverclient/server/endpoint/workbooks_endpoint.py b/tableauserverclient/server/endpoint/workbooks_endpoint.py index a9331719..5f969582 100644 --- a/tableauserverclient/server/endpoint/workbooks_endpoint.py +++ b/tableauserverclient/server/endpoint/workbooks_endpoint.py @@ -1022,10 +1022,12 @@ def _get_workbook_revisions( revisions = RevisionItem.from_response(server_response.content, self.parent_srv.namespace, workbook_item) return revisions + T = TypeVar("T", bound=FileObjectW) + @overload def download_revision( - self, workbook_id: str, revision_number: Optional[str], filepath: FileObjectW, include_extract: bool - ) -> FileObjectW: ... + self, workbook_id: str, revision_number: Optional[str], filepath: T, include_extract: bool + ) -> T: ... @overload def download_revision( From 5b0f6f3fc4615129677ca10a47e9e3585c720ac7 Mon Sep 17 00:00:00 2001 From: Jordan Woods <13803242+jorwoods@users.noreply.github.com> Date: Sat, 30 Aug 2025 09:05:17 -0500 Subject: [PATCH 7/7] chore: add type hints to fixture --- test/test_workbook.py | 122 +++++++++++++++++++++--------------------- 1 file changed, 61 insertions(+), 61 deletions(-) diff --git a/test/test_workbook.py b/test/test_workbook.py index 459bbaaf..e6e807f8 100644 --- a/test/test_workbook.py +++ b/test/test_workbook.py @@ -41,7 +41,7 @@ @pytest.fixture(scope="function") -def server(): +def server() -> TSC.Server: server = TSC.Server("http://test", False) # Fake sign in @@ -51,7 +51,7 @@ def server(): return server -def test_get(server) -> None: +def test_get(server: TSC.Server) -> None: response_xml = GET_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) @@ -86,7 +86,7 @@ def test_get(server) -> None: assert {"Safari", "Sample"} == all_workbooks[1].tags -def test_get_ignore_invalid_date(server) -> None: +def test_get_ignore_invalid_date(server: TSC.Server) -> None: response_xml = GET_INVALID_DATE_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) @@ -95,13 +95,13 @@ def test_get_ignore_invalid_date(server) -> None: assert "2016-08-04T17:56:41Z" == format_datetime(all_workbooks[0].updated_at) -def test_get_before_signin(server) -> None: +def test_get_before_signin(server: TSC.Server) -> None: server._auth_token = None with pytest.raises(TSC.NotSignedInError): server.workbooks.get() -def test_get_empty(server) -> None: +def test_get_empty(server: TSC.Server) -> None: response_xml = GET_EMPTY_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl, text=response_xml) @@ -111,7 +111,7 @@ def test_get_empty(server) -> None: assert [] == all_workbooks -def test_get_by_id(server) -> None: +def test_get_by_id(server: TSC.Server) -> None: response_xml = GET_BY_ID_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", text=response_xml) @@ -135,7 +135,7 @@ def test_get_by_id(server) -> None: assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url -def test_get_by_id_personal(server) -> None: +def test_get_by_id_personal(server: TSC.Server) -> None: # workbooks in personal space don't have project_id or project_name response_xml = GET_BY_ID_XML_PERSONAL.read_text() with requests_mock.mock() as m: @@ -160,12 +160,12 @@ def test_get_by_id_personal(server) -> None: assert "SafariSample/sheets/ENDANGEREDSAFARI" == single_workbook.views[0].content_url -def test_get_by_id_missing_id(server) -> None: +def test_get_by_id_missing_id(server: TSC.Server) -> None: with pytest.raises(ValueError): server.workbooks.get_by_id("") -def test_refresh_id(server) -> None: +def test_refresh_id(server: TSC.Server) -> None: server.version = "2.8" server.workbooks.baseurl response_xml = REFRESH_XML.read_text() @@ -178,7 +178,7 @@ def test_refresh_id(server) -> None: server.workbooks.refresh("3cc6cd06-89ce-4fdc-b935-5294135d6d42") -def test_refresh_object(server) -> None: +def test_refresh_object(server: TSC.Server) -> None: server.version = "2.8" server.workbooks.baseurl workbook = TSC.WorkbookItem("") @@ -193,18 +193,18 @@ def test_refresh_object(server) -> None: server.workbooks.refresh(workbook) -def test_delete(server) -> None: +def test_delete(server: TSC.Server) -> None: with requests_mock.mock() as m: m.delete(server.workbooks.baseurl + "/3cc6cd06-89ce-4fdc-b935-5294135d6d42", status_code=204) server.workbooks.delete("3cc6cd06-89ce-4fdc-b935-5294135d6d42") -def test_delete_missing_id(server) -> None: +def test_delete_missing_id(server: TSC.Server) -> None: with pytest.raises(ValueError): server.workbooks.delete("") -def test_update(server) -> None: +def test_update(server: TSC.Server) -> None: response_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: m.put(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2", text=response_xml) @@ -229,13 +229,13 @@ def test_update(server) -> None: assert not single_workbook.data_acceleration_config["accelerate_now"] -def test_update_missing_id(server) -> None: +def test_update_missing_id(server: TSC.Server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.update(single_workbook) -def test_update_copy_fields(server) -> None: +def test_update_copy_fields(server: TSC.Server) -> None: connection_xml = POPULATE_CONNECTIONS_XML.read_text() update_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: @@ -253,7 +253,7 @@ def test_update_copy_fields(server) -> None: assert single_workbook._preview_image == updated_workbook._preview_image -def test_update_tags(server) -> None: +def test_update_tags(server: TSC.Server) -> None: add_tags_xml = ADD_TAGS_XML.read_text() update_xml = UPDATE_XML.read_text() with requests_mock.mock() as m: @@ -271,7 +271,7 @@ def test_update_tags(server) -> None: assert single_workbook._initial_tags == updated_workbook._initial_tags -def test_download(server) -> None: +def test_download(server: TSC.Server) -> None: with requests_mock.mock() as m: m.get( server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/content", @@ -282,7 +282,7 @@ def test_download(server) -> None: os.remove(file_path) -def test_download_object(server) -> None: +def test_download_object(server: TSC.Server) -> None: with BytesIO() as file_object: with requests_mock.mock() as m: m.get( @@ -293,7 +293,7 @@ def test_download_object(server) -> None: assert isinstance(file_path, BytesIO) -def test_download_sanitizes_name(server) -> None: +def test_download_sanitizes_name(server: TSC.Server) -> None: filename = "Name,With,Commas.twbx" disposition = f'name="tableau_workbook"; filename="{filename}"' with requests_mock.mock() as m: @@ -307,7 +307,7 @@ def test_download_sanitizes_name(server) -> None: os.remove(file_path) -def test_download_extract_only(server) -> None: +def test_download_extract_only(server: TSC.Server) -> None: # Pretend we're 2.5 for 'extract_only' server.version = "2.5" server.workbooks.baseurl @@ -324,12 +324,12 @@ def test_download_extract_only(server) -> None: os.remove(file_path) -def test_download_missing_id(server) -> None: +def test_download_missing_id(server: TSC.Server) -> None: with pytest.raises(ValueError): server.workbooks.download("") -def test_populate_views(server) -> None: +def test_populate_views(server: TSC.Server) -> None: response_xml = POPULATE_VIEWS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/views", text=response_xml) @@ -351,7 +351,7 @@ def test_populate_views(server) -> None: assert "RESTAPISample/sheets/Interestrates" == views_list[2].content_url -def test_populate_views_with_usage(server) -> None: +def test_populate_views_with_usage(server: TSC.Server) -> None: response_xml = POPULATE_VIEWS_USAGE_XML.read_text() with requests_mock.mock() as m: m.get( @@ -371,13 +371,13 @@ def test_populate_views_with_usage(server) -> None: assert 0 == views_list[2].total_views -def test_populate_views_missing_id(server) -> None: +def test_populate_views_missing_id(server: TSC.Server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_views(single_workbook) -def test_populate_connections(server) -> None: +def test_populate_connections(server: TSC.Server) -> None: response_xml = POPULATE_CONNECTIONS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/connections", text=response_xml) @@ -391,7 +391,7 @@ def test_populate_connections(server) -> None: assert "World Indicators" == single_workbook.connections[0].datasource_name -def test_populate_permissions(server) -> None: +def test_populate_permissions(server: TSC.Server) -> None: response_xml = POPULATE_PERMISSIONS_XML.read_text() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/21778de4-b7b9-44bc-a599-1506a2639ace/permissions", text=response_xml) @@ -420,7 +420,7 @@ def test_populate_permissions(server) -> None: } -def test_add_permissions(server) -> None: +def test_add_permissions(server: TSC.Server) -> None: response_xml = UPDATE_PERMISSIONS.read_text() single_workbook = TSC.WorkbookItem("test") @@ -443,13 +443,13 @@ def test_add_permissions(server) -> None: assert permissions[1].capabilities == {TSC.Permission.Capability.Write: TSC.Permission.Mode.Allow} -def test_populate_connections_missing_id(server) -> None: +def test_populate_connections_missing_id(server: TSC.Server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_connections(single_workbook) -def test_populate_pdf(server) -> None: +def test_populate_pdf(server: TSC.Server) -> None: server.version = "3.4" server.workbooks.baseurl response = POPULATE_PDF.read_bytes() @@ -469,7 +469,7 @@ def test_populate_pdf(server) -> None: assert response == single_workbook.pdf -def test_populate_pdf_unsupported(server) -> None: +def test_populate_pdf_unsupported(server: TSC.Server) -> None: server.version = "3.4" server.workbooks.baseurl with requests_mock.mock() as m: @@ -489,7 +489,7 @@ def test_populate_pdf_unsupported(server) -> None: server.workbooks.populate_pdf(single_workbook, req_option) -def test_populate_pdf_vf_dims(server) -> None: +def test_populate_pdf_vf_dims(server: TSC.Server) -> None: server.version = "3.23" server.workbooks.baseurl response = POPULATE_PDF.read_bytes() @@ -513,7 +513,7 @@ def test_populate_pdf_vf_dims(server) -> None: assert response == single_workbook.pdf -def test_populate_powerpoint(server) -> None: +def test_populate_powerpoint(server: TSC.Server) -> None: server.version = "3.8" server.workbooks.baseurl response = POPULATE_POWERPOINT.read_bytes() @@ -528,7 +528,7 @@ def test_populate_powerpoint(server) -> None: assert response == single_workbook.powerpoint -def test_populate_preview_image(server) -> None: +def test_populate_preview_image(server: TSC.Server) -> None: response = POPULATE_PREVIEW_IMAGE.read_bytes() with requests_mock.mock() as m: m.get(server.workbooks.baseurl + "/1f951daf-4061-451a-9df1-69a8062664f2/previewImage", content=response) @@ -539,13 +539,13 @@ def test_populate_preview_image(server) -> None: assert response == single_workbook.preview_image -def test_populate_preview_image_missing_id(server) -> None: +def test_populate_preview_image_missing_id(server: TSC.Server) -> None: single_workbook = TSC.WorkbookItem("test") with pytest.raises(TSC.MissingRequiredFieldError): server.workbooks.populate_preview_image(single_workbook) -def test_publish(server) -> None: +def test_publish(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -576,7 +576,7 @@ def test_publish(server) -> None: assert "REST API Testing" == new_workbook.description -def test_publish_a_packaged_file_object(server) -> None: +def test_publish_a_packaged_file_object(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -607,7 +607,7 @@ def test_publish_a_packaged_file_object(server) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url -def test_publish_non_packeged_file_object(server) -> None: +def test_publish_non_packeged_file_object(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -638,7 +638,7 @@ def test_publish_non_packeged_file_object(server) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url -def test_publish_path_object(server) -> None: +def test_publish_path_object(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -667,7 +667,7 @@ def test_publish_path_object(server) -> None: assert "RESTAPISample_0/sheets/GDPpercapita" == new_workbook.views[0].content_url -def test_publish_with_hidden_views_on_workbook(server) -> None: +def test_publish_with_hidden_views_on_workbook(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -687,7 +687,7 @@ def test_publish_with_hidden_views_on_workbook(server) -> None: assert re.search(b'<\\/views>', request_body) -def test_publish_with_thumbnails_user_id(server) -> None: +def test_publish_with_thumbnails_user_id(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -707,7 +707,7 @@ def test_publish_with_thumbnails_user_id(server) -> None: assert re.search(b'thumbnailsUserId=\\"ee8c6e70-43b6-11e6-af4f-f7b0d8e20761\\"', request_body) -def test_publish_with_thumbnails_group_id(server) -> None: +def test_publish_with_thumbnails_group_id(server: TSC.Server) -> None: response_xml = PUBLISH_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -727,7 +727,7 @@ def test_publish_with_thumbnails_group_id(server) -> None: @pytest.mark.filterwarnings("ignore:'as_job' not available") -def test_publish_with_query_params(server) -> None: +def test_publish_with_query_params(server: TSC.Server) -> None: response_xml = PUBLISH_ASYNC_XML.read_text() with requests_mock.mock() as m: m.post(server.workbooks.baseurl, text=response_xml) @@ -748,7 +748,7 @@ def test_publish_with_query_params(server) -> None: assert request_query_params["skipconnectioncheck"] -def test_publish_async(server) -> None: +def test_publish_async(server: TSC.Server) -> None: server.version = "3.0" baseurl = server.workbooks.baseurl response_xml = PUBLISH_ASYNC_XML.read_text() @@ -771,13 +771,13 @@ def test_publish_async(server) -> None: assert 1 == new_job.finish_code -def test_publish_invalid_file(server) -> None: +def test_publish_invalid_file(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") with pytest.raises(IOError): server.workbooks.publish(new_workbook, ".", server.PublishMode.CreateNew) -def test_publish_invalid_file_type(server) -> None: +def test_publish_invalid_file_type(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem("test", "ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") with pytest.raises(ValueError): server.workbooks.publish( @@ -785,7 +785,7 @@ def test_publish_invalid_file_type(server) -> None: ) -def test_publish_unnamed_file_object(server) -> None: +def test_publish_unnamed_file_object(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem("test") with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx"), "rb") as f: @@ -793,7 +793,7 @@ def test_publish_unnamed_file_object(server) -> None: server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) -def test_publish_non_bytes_file_object(server) -> None: +def test_publish_non_bytes_file_object(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem("test") with open(os.path.join(TEST_ASSET_DIR, "SampleWB.twbx")) as f: @@ -801,7 +801,7 @@ def test_publish_non_bytes_file_object(server) -> None: server.workbooks.publish(new_workbook, f, server.PublishMode.CreateNew) -def test_publish_file_object_of_unknown_type_raises_exception(server) -> None: +def test_publish_file_object_of_unknown_type_raises_exception(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem("test") with BytesIO() as file_object: file_object.write(bytes.fromhex("89504E470D0A1A0A")) @@ -810,7 +810,7 @@ def test_publish_file_object_of_unknown_type_raises_exception(server) -> None: server.workbooks.publish(new_workbook, file_object, server.PublishMode.CreateNew) -def test_publish_multi_connection(server) -> None: +def test_publish_multi_connection(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem(name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") connection1 = TSC.ConnectionItem() connection1.server_address = "mysql.test.com" @@ -829,7 +829,7 @@ def test_publish_multi_connection(server) -> None: assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" -def test_publish_multi_connection_flat(server) -> None: +def test_publish_multi_connection_flat(server: TSC.Server) -> None: new_workbook = TSC.WorkbookItem(name="Sample", show_tabs=False, project_id="ee8c6e70-43b6-11e6-af4f-f7b0d8e20760") connection1 = TSC.ConnectionItem() connection1.server_address = "mysql.test.com" @@ -852,7 +852,7 @@ def test_publish_multi_connection_flat(server) -> None: assert connection_results[1].find("connectionCredentials").get("password", None) == "secret" -def test_synchronous_publish_timeout_error(server) -> None: +def test_synchronous_publish_timeout_error(server: TSC.Server) -> None: with requests_mock.mock() as m: m.register_uri("POST", server.workbooks.baseurl, status_code=504) @@ -863,7 +863,7 @@ def test_synchronous_publish_timeout_error(server) -> None: server.workbooks.publish(new_workbook, TEST_ASSET_DIR / "SampleWB.twbx", publish_mode) -def test_delete_extracts_all(server) -> None: +def test_delete_extracts_all(server: TSC.Server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -877,7 +877,7 @@ def test_delete_extracts_all(server) -> None: server.workbooks.delete_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") -def test_create_extracts_all(server) -> None: +def test_create_extracts_all(server: TSC.Server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -891,7 +891,7 @@ def test_create_extracts_all(server) -> None: server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42") -def test_create_extracts_one(server) -> None: +def test_create_extracts_one(server: TSC.Server) -> None: server.version = "3.10" server.workbooks.baseurl @@ -908,7 +908,7 @@ def test_create_extracts_one(server) -> None: server.workbooks.create_extract("3cc6cd06-89ce-4fdc-b935-5294135d6d42", False, datasource) -def test_revisions(server) -> None: +def test_revisions(server: TSC.Server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" @@ -939,7 +939,7 @@ def test_revisions(server) -> None: assert "5de011f8-5aa9-4d5b-b991-f462c8dd6bb7" == revisions[2].user_id -def test_delete_revision(server) -> None: +def test_delete_revision(server: TSC.Server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" @@ -949,7 +949,7 @@ def test_delete_revision(server) -> None: server.workbooks.delete_revision(workbook.id, "3") -def test_download_revision(server) -> None: +def test_download_revision(server: TSC.Server) -> None: with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: m.get( server.workbooks.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/revisions/3/content", @@ -959,7 +959,7 @@ def test_download_revision(server) -> None: assert os.path.exists(file_path) -def test_bad_download_response(server) -> None: +def test_bad_download_response(server: TSC.Server) -> None: with requests_mock.mock() as m, tempfile.TemporaryDirectory() as td: m.get( server.workbooks.baseurl + "/9dbd2263-16b5-46e1-9c43-a76bb8ab65fb/content", @@ -969,7 +969,7 @@ def test_bad_download_response(server) -> None: assert os.path.exists(file_path) -def test_odata_connection(server) -> None: +def test_odata_connection(server: TSC.Server) -> None: server.workbooks.baseurl workbook = TSC.WorkbookItem("project", "test") workbook._id = "06b944d2-959d-4604-9305-12323c95e70e" @@ -997,7 +997,7 @@ def test_odata_connection(server) -> None: assert xml_connection.get("serverAddress") == url -def test_update_workbook_connections(server) -> None: +def test_update_workbook_connections(server: TSC.Server) -> None: populate_xml = POPULATE_CONNECTIONS_XML.read_text() response_xml = UPDATE_CONNECTIONS_XML.read_text() @@ -1032,7 +1032,7 @@ def test_update_workbook_connections(server) -> None: assert "AD Service Principal" == connection_items[0].auth_type -def test_get_workbook_all_fields(server) -> None: +def test_get_workbook_all_fields(server: TSC.Server) -> None: server.version = "3.21" baseurl = server.workbooks.baseurl