Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Automate test runs #70

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 32 additions & 0 deletions .github/workflows/integration_test.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
name: Integration Test

on:
push:
branches: master
tags:
- "*"
schedule:
# 4 AM Central Daylight Time
- cron: '0 9 * * *'

jobs:
flake8_py3:
runs-on: ubuntu-latest
steps:
- name: Checkout Code
uses: actions/checkout@v2
- name: Setup Python
uses: actions/setup-python@v2
with:
python-version: 3.8.0
architecture: x64
- name: Install Dependencies
run: |
python -m pip install --upgrade pip
pip install -r requirements.txt
- name: Run Integration Tests
env:
IRACING_USERNAME: ${{ secrets.IRACING_USERNAME }}
IRACING_PASSWORD: ${{ secrets.IRACING_PASSWORD }}
run: |
python -m unittest discover integration_tests/ -p "*_test.py"
27 changes: 25 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,32 @@ The goal of this project is to provide access to iRacing stats in a manner that
The contributors of this project use Discord as the primary means of communication; The [iRacing Open Wheel server](https://discord.gg/UwnhM7w) was created by the author of this project and hosts the channels for discussion there. When joining, please ask Jacob Anderson for the role to see the appropriate channels.

# Documentation & Discussion

All documentation for this project is available through the [Github Pages project site](https://esterni.github.io/pyracing/).

# Dependencies

* [httpx](https://www.python-httpx.org/) = 0.13.x

# Running Tests

Before running tests, you have to prepare the environment variables.
This is different for windows and linux.

**Windows**
```
set "[email protected]"
set "IRACING_PASSWORD=hunter2"
```

**Linux**
```
set IRACING_USERNAME="[email protected]"
set IRACING_PASSWORD="hunter2"
```

Running the tests is the same on both systems:

# Dependancies
[httpx](https://www.python-httpx.org/) = 0.13.x
```
python -m unitttest discover integration_tests/ -p "*_test.py"
```
86 changes: 86 additions & 0 deletions integration_tests/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
import asyncio
import logging
import os
import sys
import unittest

from pyracing.client import Client


__all__ = [
"IRacingIntegrationTest",
"async_test",
]

logging.basicConfig(
stream=sys.stdout,
level=logging.INFO,
datefmt="%Y-%m-%dT%H:%M:%S%Z",
format="%(asctime)s [%(levelname)s] -- %(message)s"
)


def get_required_env(key: str) -> str:
"""
Get an environment variable's value, raising an exception if it isn't set.
"""
value = os.getenv(key)
if value is None:
raise EnvironmentError(
f"Must set {key} environment variable to to run integration tests."
)
return value


IRACING_USERNAME = get_required_env("IRACING_USERNAME")
IRACING_PASSWORD = get_required_env("IRACING_PASSWORD")

# We create a singleton client that we use for all tests to avoid constantly
# re-authenticating. iRacing may see constant re-authentication as suspicious
# activity, we see the disadvantages of 1) using a singleton and 2) sharing
# state between tests are outweighed by being good citizens to the iRacing
# platform.
client = Client(
username=IRACING_USERNAME,
password=IRACING_PASSWORD,
)


def async_test(f):
"""
Function that can be used as a decorator for tests of async functions.

For example,

class MyTest(unittests.TestCase):
@async_test
async def test_example(self):
self.assertTrue(True)

:param f: the function to wrap
:return: the wrapped function

>>> class MyTest(unittest.TestCase):
... @async_test
... async def test_example(self):
... self.assertTrue(True)
"""
def wrapper(*args, **kwargs):
coro = asyncio.coroutine(f)
future = coro(*args, **kwargs)
loop = asyncio.get_event_loop()
loop.run_until_complete(future)

return wrapper


class IRacingIntegrationTest(unittest.TestCase):
"""
Test service that runs against iRacing's server.
"""

def setUp(self) -> None:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need the client we instantiate above if we re-instantiate here? Should we be using the singleton we created as you mentioned in the comment so we don't auth multiple times when we run more suites?

self.client = Client(
username=IRACING_USERNAME,
password=IRACING_PASSWORD,
)
Loading