Skip to content

Commit 9a16b95

Browse files
authored
Support bulk get endpoints (#142)
* support for new bulk endpoints * Need to update mock tests but merging due to breaking API changes.
1 parent fa34aed commit 9a16b95

File tree

3 files changed

+39
-28
lines changed

3 files changed

+39
-28
lines changed

.travis.yml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,10 @@ os:
44
- linux
55
python:
66
- '2.7'
7-
- '3.4'
8-
- '3.5'
97
- '3.6'
8+
- '3.7'
9+
- '3.8'
10+
- '3.9'
1011
install:
1112
- pip install -U pip
1213
- pip install -U tox-travis

setup.py

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,12 @@
1515
setup(
1616
name='testrail',
1717
packages=['testrail'],
18-
version='0.3.13',
18+
version='0.3.14',
1919
description='Python library for interacting with TestRail via REST APIs.',
2020
author='Travis Pavek',
2121
author_email='[email protected]',
2222
url='https://github.com/travispavek/testrail-python',
23-
download_url='https://github.com/travispavek/testrail-python/tarball/0.3.13',
23+
download_url='https://github.com/travispavek/testrail-python/tarball/0.3.14',
2424
keywords=['testrail', 'api', 'client', 'library', 'rest'],
2525
install_requires=install_requires,
2626
classifiers=[
@@ -37,8 +37,9 @@
3737
'Programming Language :: Python :: 2',
3838
'Programming Language :: Python :: 2.7',
3939
'Programming Language :: Python :: 3',
40-
'Programming Language :: Python :: 3.4',
41-
'Programming Language :: Python :: 3.5',
4240
'Programming Language :: Python :: 3.6',
41+
'Programming Language :: Python :: 3.7',
42+
'Programming Language :: Python :: 3.8',
43+
'Programming Language :: Python :: 3.9',
4344
],
4445
)

testrail/api.py

Lines changed: 31 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,17 @@ def _conf(self):
164164

165165
return {'email': _email, 'key': _key, 'url': _url, 'verify_ssl': verify_ssl}
166166

167+
def _paginate_request(self, end_point, params, field):
168+
params["offset"] = 0
169+
params["limit"] = 250
170+
values = []
171+
while True:
172+
items = self._get(end_point, params=params)
173+
if items["size"] == 0:
174+
return values
175+
values.extend(items[field])
176+
params["offset"] += params["limit"]
177+
167178
@staticmethod
168179
def _raise_on_429_or_503_status(resp):
169180
""" 429 is TestRail's status for too many API requests
@@ -234,7 +245,7 @@ def user_with_email(self, user_email):
234245
def projects(self):
235246
if self._refresh(self._projects['ts']):
236247
# get new value, if request is good update value with new ts.
237-
self._projects['value'] = self._get('get_projects')
248+
self._projects['value'] = self._paginate_request("get_projects", {}, "projects")
238249
self._projects['ts'] = datetime.now()
239250
return self._projects['value']
240251

@@ -270,13 +281,13 @@ def add_suite(self, suite):
270281
return self._post('add_suite/%s' % project_id, payload)
271282

272283
# Case Requests
273-
def cases(self, project_id=None, suite_id=10):
284+
def cases(self, project_id=None, suite_id=-1):
274285
project_id = project_id or self._project_id
275286
if self._refresh(self._cases[project_id][suite_id]['ts']):
276287
# get new value, if request is good update value with new ts.
277-
params = {'suite_id': suite_id} if suite_id != -1 else None
278-
_cases = self._get('get_cases/%s' % project_id, params=params)
279-
self._cases[project_id][suite_id]['value'] = _cases
288+
endpoint = 'get_cases/%s' % project_id
289+
params = {'suite_id': suite_id} if suite_id != -1 else {}
290+
self._cases[project_id][suite_id]["value"] = self._paginate_request(endpoint, params, "cases")
280291
self._cases[project_id][suite_id]['ts'] = datetime.now()
281292
return self._cases[project_id][suite_id]['value']
282293

@@ -326,8 +337,8 @@ def case_type_with_id(self, case_type_id):
326337
def milestones(self, project_id):
327338
if self._refresh(self._milestones[project_id]['ts']):
328339
# get new value, if request is good update value with new ts.
329-
_milestones = self._get('get_milestones/%s' % project_id)
330-
self._milestones[project_id]['value'] = _milestones
340+
endpoint = 'get_milestones/%s' % project_id
341+
self._milestones[project_id]['value'] = self._paginate_request(endpoint, {}, "milestones")
331342
self._milestones[project_id]['ts'] = datetime.now()
332343
return self._milestones[project_id]['value']
333344

@@ -384,9 +395,8 @@ def sections(self, project_id=None, suite_id=-1):
384395
project_id = project_id or self._project_id
385396
if self._refresh(self._sections[project_id][suite_id]['ts']):
386397
params = {'suite_id': suite_id} if suite_id != -1 else None
387-
_sections = self._get(
388-
'get_sections/%s' % project_id, params=params)
389-
self._sections[project_id][suite_id]['value'] = _sections
398+
endpoint = 'get_sections/%s' % project_id
399+
self._sections[project_id][suite_id]['value'] = self._paginate_request(endpoint, params, "sections")
390400
self._sections[project_id][suite_id]['ts'] = datetime.now()
391401
return self._sections[project_id][suite_id]['value']
392402

@@ -414,8 +424,8 @@ def plans(self, project_id=None):
414424
project_id = project_id or self._project_id
415425
if self._refresh(self._plans[project_id]['ts']):
416426
# get new value, if request is good update value with new ts.
417-
_plans = self._get('get_plans/%s' % project_id)
418-
self._plans[project_id]['value'] = _plans
427+
endpoint = 'get_plans/%s' % project_id
428+
self._plans[project_id]['value'] = self._paginate_request(endpoint, {}, "plans")
419429
self._plans[project_id]['ts'] = datetime.now()
420430
return self._plans[project_id]['value']
421431

@@ -452,11 +462,10 @@ def runs(self, project_id=None, completed=None):
452462
project_id = project_id or self._project_id
453463
if self._refresh(self._runs[project_id]['ts']):
454464
# get new value, if request is good update value with new ts.
455-
end_point = 'get_runs/%s' % project_id
465+
endpoint = 'get_runs/%s' % project_id
456466
if completed is not None:
457-
end_point += '&is_completed=%s' % str(int(completed))
458-
_runs = self._get(end_point)
459-
self._runs[project_id]['value'] = _runs
467+
endpoint += '&is_completed=%s' % str(int(completed))
468+
self._runs[project_id]['value'] = self._paginate_request(endpoint, {}, "runs")
460469
self._runs[project_id]['ts'] = datetime.now()
461470
return self._runs[project_id]['value']
462471

@@ -521,8 +530,8 @@ def delete_plan(self, plan_id):
521530
# Test Requests
522531
def tests(self, run_id):
523532
if self._refresh(self._tests[run_id]['ts']):
524-
_tests = self._get('get_tests/%s' % run_id)
525-
self._tests[run_id]['value'] = _tests
533+
endpoint = 'get_tests/%s' % run_id
534+
self._tests[run_id]['value'] = self._paginate_request(endpoint, {}, "tests")
526535
self._tests[run_id]['ts'] = datetime.now()
527536
return self._tests[run_id]['value']
528537

@@ -541,15 +550,15 @@ def test_with_id(self, test_id, run_id=None):
541550
# Result Requests
542551
def results_by_run(self, run_id):
543552
if self._refresh(self._results[run_id]['ts']):
544-
_results = self._get('get_results_for_run/%s' % run_id)
545-
self._results[run_id]['value'] = _results
553+
endpoint = 'get_results_for_run/%s' % run_id
554+
self._results[run_id]['value'] = self._paginate_request(endpoint, {}, "results")
546555
self._results[run_id]['ts'] = datetime.now()
547556
return self._results[run_id]['value']
548557

549558
def results_by_test(self, test_id):
550559
if self._refresh(self._results[test_id]['ts']):
551-
_results = self._get('get_results/%s' % test_id)
552-
self._results[test_id]['value'] = _results
560+
endpoint = 'get_results/%s' % test_id
561+
self._results[test_id]['value'] = self._paginate_request(endpoint, {}, "results")
553562
self._results[test_id]['ts'] = datetime.now()
554563
return self._results[test_id]['value']
555564

0 commit comments

Comments
 (0)