Skip to content

Commit

Permalink
Initial implementation to address tableau#102 and provide datetime ob…
Browse files Browse the repository at this point in the history
…jects
  • Loading branch information
Russell Hay authored and t8y8 committed Jun 28, 2017
1 parent 53d6aac commit 0f9cc2a
Show file tree
Hide file tree
Showing 5 changed files with 65 additions and 9 deletions.
7 changes: 6 additions & 1 deletion tableauserverclient/models/datasource_item.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import xml.etree.ElementTree as ET
from .exceptions import UnpopulatedPropertyError
from .property_decorators import property_not_nullable
from .property_decorators import property_not_nullable, property_is_datetime
from .tag_item import TagItem
from .. import NAMESPACE
from ..datetime_helpers import parse_datetime
Expand Down Expand Up @@ -35,6 +35,11 @@ def content_url(self):
def created_at(self):
return self._created_at

@created_at.setter
@property_is_datetime
def created_at(self, value):
self._created_at = value

@property
def id(self):
return self._id
Expand Down
12 changes: 11 additions & 1 deletion tableauserverclient/models/schedule_item.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
from datetime import datetime

from .interval_item import IntervalItem, HourlyInterval, DailyInterval, WeeklyInterval, MonthlyInterval
from .property_decorators import property_is_enum, property_not_nullable, property_is_int
from .property_decorators import property_is_enum, property_not_nullable, property_is_int, property_is_datetime
from .. import NAMESPACE
from ..datetime_helpers import parse_datetime

Expand Down Expand Up @@ -37,6 +37,11 @@ def __init__(self, name, priority, schedule_type, execution_order, interval_item
def created_at(self):
return self._created_at

@created_at.setter
@property_is_datetime
def created_at(self, value):
self._created_at = value

@property
def end_schedule_at(self):
return self._end_schedule_at
Expand Down Expand Up @@ -99,6 +104,11 @@ def state(self, value):
def updated_at(self):
return self._updated_at

@updated_at.setter
@property_is_datetime
def updated_at(self, value):
self._updated_at = value

def _parse_common_tags(self, schedule_xml):
if not isinstance(schedule_xml, ET.Element):
schedule_xml = ET.fromstring(schedule_xml).find('.//t:schedule', namespaces=NAMESPACE)
Expand Down
12 changes: 11 additions & 1 deletion tableauserverclient/models/workbook_item.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import xml.etree.ElementTree as ET
from .exceptions import UnpopulatedPropertyError
from .property_decorators import property_not_nullable, property_is_boolean
from .property_decorators import property_not_nullable, property_is_boolean, property_is_datetime
from .tag_item import TagItem
from .view_item import ViewItem
from .. import NAMESPACE
Expand Down Expand Up @@ -41,6 +41,11 @@ def content_url(self):
def created_at(self):
return self._created_at

@created_at.setter
@property_is_datetime
def created_at(self, value):
self._created_at = value

@property
def id(self):
return self._id
Expand Down Expand Up @@ -82,6 +87,11 @@ def size(self):
def updated_at(self):
return self._updated_at

@updated_at.setter
@property_is_datetime
def updated_at(self, value):
self._updated_at = value

@property
def views(self):
if self._views is None:
Expand Down
31 changes: 31 additions & 0 deletions test/test_datasource_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,34 @@ def test_invalid_project_id(self):
datasource = TSC.DatasourceItem("10")
with self.assertRaises(ValueError):
datasource.project_id = None

def test_datetime_conversion(self):
datasource = TSC.DatasourceItem("10")
datasource.created_at = "2016-08-18T19:25:36Z"
actual = datasource.created_at
self.assertIsInstance(actual, datetime.datetime)
self.assertEquals(actual.year, 2016)
self.assertEquals(actual.month, 8)
self.assertEquals(actual.day, 18)
self.assertEquals(actual.hour, 19)
self.assertEquals(actual.minute, 25)
self.assertEquals(actual.second, 36)

def test_datetime_conversion_allows_datetime_passthrough(self):
datasource = TSC.DatasourceItem("10")
now = datetime.datetime.utcnow()
datasource.created_at = now
self.assertEquals(datasource.created_at, now)

def test_datetime_conversion_is_timezone_aware(self):
datasource = TSC.DatasourceItem("10")
datasource.created_at = "2016-08-18T19:25:36Z"
actual = datasource.created_at
self.assertEquals(actual.utcoffset().seconds, 0)

def test_datetime_conversion_rejects_things_that_cannot_be_converted(self):
datasource = TSC.DatasourceItem("10")
with self.assertRaises(ValueError):
datasource.created_at = object()
with self.assertRaises(ValueError):
datasource.created_at = "This is so not a datetime"
12 changes: 6 additions & 6 deletions test/test_requests.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@ def test_make_get_request(self):
auth_token='j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM',
content_type='text/xml')

self.assertEquals(resp.request.query, 'pagenumber=13&pagesize=13')
self.assertEquals(resp.request.headers['x-tableau-auth'], 'j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM')
self.assertEquals(resp.request.headers['content-type'], 'text/xml')
self.assertEqual(resp.request.query, 'pagenumber=13&pagesize=13')
self.assertEqual(resp.request.headers['x-tableau-auth'], 'j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM')
self.assertEqual(resp.request.headers['content-type'], 'text/xml')

def test_make_post_request(self):
with requests_mock.mock() as m:
Expand All @@ -42,6 +42,6 @@ def test_make_post_request(self):
request_object=None,
auth_token='j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM',
content_type='multipart/mixed')
self.assertEquals(resp.request.headers['x-tableau-auth'], 'j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM')
self.assertEquals(resp.request.headers['content-type'], 'multipart/mixed')
self.assertEquals(resp.request.body, b'1337')
self.assertEqual(resp.request.headers['x-tableau-auth'], 'j80k54ll2lfMZ0tv97mlPvvSCRyD0DOM')
self.assertEqual(resp.request.headers['content-type'], 'multipart/mixed')
self.assertEqual(resp.request.body, b'1337')

0 comments on commit 0f9cc2a

Please sign in to comment.