Skip to content

Commit 27d1144

Browse files
committed
ADD: Initial project files
0 parents  commit 27d1144

File tree

8 files changed

+337
-0
lines changed

8 files changed

+337
-0
lines changed

Diff for: .gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
.pytest_cache/

Diff for: Pipfile

+14
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
[[source]]
2+
name = "pypi"
3+
url = "https://pypi.org/simple"
4+
verify_ssl = true
5+
6+
[dev-packages]
7+
pytest = "*"
8+
pylint = "*"
9+
10+
[packages]
11+
requests = "*"
12+
13+
[requires]
14+
python_version = "3.8"

Diff for: Pipfile.lock

+183
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Diff for: heroku/__init__.py

Whitespace-only changes.

Diff for: heroku/heroku.py

+51
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
import json, os
2+
import requests
3+
4+
class Heroku:
5+
6+
def __init__(self, api_key=None, headers={}):
7+
if api_key:
8+
self.api_key = api_key
9+
else:
10+
self.api_key = os.getenv('HEROKU_API_KEY')
11+
12+
self.session = requests.Session()
13+
14+
self.session.headers.update({
15+
'Accept': 'application/vnd.heroku+json; version=3',
16+
'Authorization': f'Bearer {self.api_key}',
17+
'Content-Type': 'application/json'
18+
})
19+
20+
self.session.headers.update(headers)
21+
22+
def delete(self, endpoint):
23+
"""Return the result of making a DELETE
24+
request to the Heroku Platform API"""
25+
26+
return self.session.delete(endpoint)
27+
28+
def get(self, endpoint, *args, **kwargs):
29+
"""Return the result of making a GET
30+
request to the Heroku Platform API"""
31+
32+
return self.session.get(endpoint, *args, **kwargs)
33+
34+
def patch(self, endpoint, *args, **kwargs):
35+
"""Return the result of making a PATCH
36+
request to the Heroku Platform API"""
37+
38+
return self.session.patch(endpoint, *args, **kwargs)
39+
40+
def put(self, endpoint, *args, **kwargs):
41+
"""Return the result of making a PUT
42+
request to the Heroku Platform API"""
43+
44+
return self.session.put(endpoint, *args, **kwargs)
45+
46+
def post(self, endpoint, *args, **kwargs):
47+
"""Return the result of making a POST
48+
request to the Heroku Platform API"""
49+
50+
return self.session.post(endpoint, *args, **kwargs)
51+

Diff for: readme.md

+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
# Heroku Platform Client
2+
3+
A Python client for the Heroku Platfrom API.
4+
5+
## Features
6+
- Reads `HEROKU_API_KEY` for zero-config use
7+
- Returns JSON-decoded Heroku API responses
8+
- Exposes response headers (necessary for some API functionality)
9+
10+
## Requirements
11+
- Python "3.8"
12+
- Requests
13+
**Dev packages**
14+
- Pytest
15+
- Pylint

Diff for: tests/__init__.py

Whitespace-only changes.

Diff for: tests/test_heroku.py

+73
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
import os
2+
import pytest
3+
from unittest.mock import MagicMock
4+
from heroku.heroku import Heroku
5+
6+
class TestHerokuClient:
7+
8+
def test_api_key_is_taken_from_environment_variable(self):
9+
os.environ['HEROKU_API_KEY'] = '123-123-123'
10+
heroku = Heroku()
11+
assert heroku.api_key == '123-123-123'
12+
13+
def test_api_key_can_be_explicitly_set(self):
14+
heroku = Heroku(api_key='ABC-ABC')
15+
assert heroku.api_key == 'ABC-ABC'
16+
17+
def test_default_headers_are_set(self):
18+
os.environ['HEROKU_API_KEY'] = '999-999-999'
19+
heroku = Heroku()
20+
expected = {
21+
'Accept': 'application/vnd.heroku+json; version=3',
22+
'Authorization': 'Bearer 999-999-999',
23+
'Content-Type': 'application/json'
24+
}
25+
assert set(expected.items()).issubset(
26+
set(heroku.session.headers.items())
27+
)
28+
29+
def test_default_headers_are_set_with_passed_API_key(self):
30+
heroku = Heroku(api_key='ABC-ABC-ABC')
31+
expected = {
32+
'Accept': 'application/vnd.heroku+json; version=3',
33+
'Authorization': 'Bearer ABC-ABC-ABC',
34+
'Content-Type': 'application/json'
35+
}
36+
assert set(expected.items()).issubset(
37+
set(heroku.session.headers.items())
38+
)
39+
40+
def test_calling_the_get_method_calls_requests_get_method(self):
41+
heroku = Heroku()
42+
heroku.session.get = MagicMock(return_value={})
43+
heroku.get('endpoint/foo', params={})
44+
45+
heroku.session.get.assert_called_with('endpoint/foo', params={})
46+
47+
def test_calling_the_post_method_calls_requests_post_method(self):
48+
heroku = Heroku()
49+
heroku.session.post = MagicMock(return_value={})
50+
heroku.post('endpoint/foo', data={})
51+
52+
heroku.session.post.assert_called_with('endpoint/foo', data={})
53+
54+
def test_calling_the_patch_method_calls_requests_patch_method(self):
55+
heroku = Heroku()
56+
heroku.session.patch = MagicMock(return_value={})
57+
heroku.patch('endpoint/foo', data={})
58+
59+
heroku.session.patch.assert_called_with('endpoint/foo', data={})
60+
61+
def test_calling_the_put_method_calls_requests_put_method(self):
62+
heroku = Heroku()
63+
heroku.session.put = MagicMock(return_value={})
64+
heroku.put('endpoint/foo', data={})
65+
66+
heroku.session.put.assert_called_with('endpoint/foo', data={})
67+
68+
def test_calling_the_delete_method_calls_requests_delete_method(self):
69+
heroku = Heroku()
70+
heroku.session.delete = MagicMock(return_value={})
71+
heroku.delete('endpoint/foo')
72+
73+
heroku.session.delete.assert_called_with('endpoint/foo')

0 commit comments

Comments
 (0)