From b1a4845afc2122a510f90dc41d4e12d32d31b456 Mon Sep 17 00:00:00 2001 From: C'tri Goudie <43475390+Ctri-The-Third@users.noreply.github.com> Date: Fri, 2 Jun 2023 21:35:51 +0100 Subject: [PATCH 1/4] Gmail refactor (#24) * rudimentary changes to Zendesk feed to allow the getting of a Zendesk form's details. * add workflows for testing later versions of python * updated zendesk test to reflect test users' changed details * Update pytest 3.10.yml * surface ticket form ID field * GMail refactor add tests, exclude interactive from workflows * refactor token methods token methods now outside of class build service now its own method called during constructur added "InvalidCredentialsException" to help inform failures. * rework pytest workflows * add refresh function * add extract method * update env vars --- .github/workflows/pytest 3.10.yml | 53 -------- .github/workflows/pytest 3.8.yml | 53 -------- .github/workflows/pytest 3.9.yml | 53 -------- .github/workflows/pytest-all-supported.yml | 103 +++++++++++++++ .gitignore | 1 + serviceHelpers/gmail.py | 142 +++++++++++++++------ setup.py | 2 +- tests/test_gmail.py | 30 +++++ tests/test_gmail_tokens.py | 47 +++++++ tests/test_slack.py | 3 +- tests/test_zendesk.py | 2 +- 11 files changed, 291 insertions(+), 198 deletions(-) delete mode 100644 .github/workflows/pytest 3.10.yml delete mode 100644 .github/workflows/pytest 3.8.yml delete mode 100644 .github/workflows/pytest 3.9.yml create mode 100644 .github/workflows/pytest-all-supported.yml create mode 100644 tests/test_gmail.py create mode 100644 tests/test_gmail_tokens.py diff --git a/.github/workflows/pytest 3.10.yml b/.github/workflows/pytest 3.10.yml deleted file mode 100644 index 72a4135..0000000 --- a/.github/workflows/pytest 3.10.yml +++ /dev/null @@ -1,53 +0,0 @@ -# This is a basic workflow to help you get started with Actions - -name: PyTest 3.10 - -env: - ZENDESK_KEY: ${{ secrets.ZENDESK_KEY}} - ZENDESK_HOST: ${{ secrets.ZENDESK_HOST}} - FRESHDESK_KEY: ${{ secrets.FRESHDESK_KEY}} - FRESHDESK_HOST: ${{ secrets.FRESHDESK_HOST}} - TEST_EMAIL: ${{ secrets.TEST_EMAIL}} - JIRA_HOST_1: ${{secrets.JIRA_HOST_1}} - JIRA_KEY_1: ${{secrets.JIRA_KEY_1}} - SLACK_TOKEN: ${{secrets.SLACK_TOKEN}} - TRELLO_KEY: ${{secrets.TRELLO_KEY}} - TRELLO_TOKEN: ${{secrets.TRELLO_TOKEN}} -# Controls when the workflow will run -on: - # Triggers the workflow on push or pull request events but only for the main branch - push: - branches: [ main ] - pull_request: - branches: [ main ] - - # Allows you to run this workflow manually from the Actions tab - workflow_dispatch: - -# A workflow run is made up of one or more jobs that can run sequentially or in parallel -jobs: - # This workflow contains a single job called "build" - build: - # The type of runner that the job will run on - runs-on: ubuntu-latest - - # Steps represent a sequence of tasks that will be executed as part of the job - steps: - # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it - - uses: actions/checkout@v3 - - # Runs a single command using the runners shell - - name: Set up Python 3.10 - uses: actions/setup-python@v1 - with: - python-version: 3.10.10 - - name: Install dependencies - run: | - python -m pip install --upgrade pip - pip install flake8 pytest - pip install -r requirements.txt - # Runs a set of commands using the runners shell - - name: Test with pytest - run: pytest -vv - - diff --git a/.github/workflows/pytest 3.8.yml b/.github/workflows/pytest 3.8.yml deleted file mode 100644 index 512b9ae..0000000 --- a/.github/workflows/pytest 3.8.yml +++ /dev/null @@ -1,53 +0,0 @@ -# This is a basic workflow to help you get started with Actions - -name: PyTest 3.8 - -env: - ZENDESK_KEY: ${{ secrets.ZENDESK_KEY}} - ZENDESK_HOST: ${{ secrets.ZENDESK_HOST}} - FRESHDESK_KEY: ${{ secrets.FRESHDESK_KEY}} - FRESHDESK_HOST: ${{ secrets.FRESHDESK_HOST}} - TEST_EMAIL: ${{ secrets.TEST_EMAIL}} - JIRA_HOST_1: ${{secrets.JIRA_HOST_1}} - JIRA_KEY_1: ${{secrets.JIRA_KEY_1}} - SLACK_TOKEN: ${{secrets.SLACK_TOKEN}} - TRELLO_KEY: ${{secrets.TRELLO_KEY}} - TRELLO_TOKEN: ${{secrets.TRELLO_TOKEN}} -# Controls when the workflow will run -on: - # Triggers the workflow on push or pull request events but only for the main branch - push: - branches: [ main ] - pull_request: - branches: [ main ] - - # Allows you to run this workflow manually from the Actions tab - workflow_dispatch: - -# A workflow run is made up of one or more jobs that can run sequentially or in parallel -jobs: - # This workflow contains a single job called "build" - build: - # The type of runner that the job will run on - runs-on: ubuntu-latest - - # Steps represent a sequence of tasks that will be executed as part of the job - steps: - # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it - - uses: actions/checkout@v3 - - # Runs a single command using the runners shell - - name: Set up Python 3.8 - uses: actions/setup-python@v1 - with: - python-version: 3.8 - - name: Install dependencies - run: | - python -m pip install --upgrade pip - pip install flake8 pytest - pip install -r requirements.txt - # Runs a set of commands using the runners shell - - name: Test with pytest - run: pytest -vv - - diff --git a/.github/workflows/pytest 3.9.yml b/.github/workflows/pytest 3.9.yml deleted file mode 100644 index de6caff..0000000 --- a/.github/workflows/pytest 3.9.yml +++ /dev/null @@ -1,53 +0,0 @@ -# This is a basic workflow to help you get started with Actions - -name: PyTest 3.9 - -env: - ZENDESK_KEY: ${{ secrets.ZENDESK_KEY}} - ZENDESK_HOST: ${{ secrets.ZENDESK_HOST}} - FRESHDESK_KEY: ${{ secrets.FRESHDESK_KEY}} - FRESHDESK_HOST: ${{ secrets.FRESHDESK_HOST}} - TEST_EMAIL: ${{ secrets.TEST_EMAIL}} - JIRA_HOST_1: ${{secrets.JIRA_HOST_1}} - JIRA_KEY_1: ${{secrets.JIRA_KEY_1}} - SLACK_TOKEN: ${{secrets.SLACK_TOKEN}} - TRELLO_KEY: ${{secrets.TRELLO_KEY}} - TRELLO_TOKEN: ${{secrets.TRELLO_TOKEN}} -# Controls when the workflow will run -on: - # Triggers the workflow on push or pull request events but only for the main branch - push: - branches: [ main ] - pull_request: - branches: [ main ] - - # Allows you to run this workflow manually from the Actions tab - workflow_dispatch: - -# A workflow run is made up of one or more jobs that can run sequentially or in parallel -jobs: - # This workflow contains a single job called "build" - build: - # The type of runner that the job will run on - runs-on: ubuntu-latest - - # Steps represent a sequence of tasks that will be executed as part of the job - steps: - # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it - - uses: actions/checkout@v3 - - # Runs a single command using the runners shell - - name: Set up Python 3.9 - uses: actions/setup-python@v1 - with: - python-version: 3.9 - - name: Install dependencies - run: | - python -m pip install --upgrade pip - pip install flake8 pytest - pip install -r requirements.txt - # Runs a set of commands using the runners shell - - name: Test with pytest - run: pytest -vv - - diff --git a/.github/workflows/pytest-all-supported.yml b/.github/workflows/pytest-all-supported.yml new file mode 100644 index 0000000..87b2834 --- /dev/null +++ b/.github/workflows/pytest-all-supported.yml @@ -0,0 +1,103 @@ +# This is a basic workflow to help you get started with Actions + +name: PyTest all supported builds + +env: + ZENDESK_KEY: ${{ secrets.ZENDESK_KEY}} + ZENDESK_HOST: ${{ secrets.ZENDESK_HOST}} + FRESHDESK_KEY: ${{ secrets.FRESHDESK_KEY}} + FRESHDESK_HOST: ${{ secrets.FRESHDESK_HOST}} + TEST_EMAIL: ${{ secrets.TEST_EMAIL}} + JIRA_HOST_1: ${{secrets.JIRA_HOST_1}} + JIRA_KEY_1: ${{secrets.JIRA_KEY_1}} + SLACK_TOKEN: ${{secrets.SLACK_TOKEN}} + SLACK_TOKEN_TEST: ${{secrets.SLACK_TOKEN_TEST}} + TRELLO_KEY: ${{secrets.TRELLO_KEY}} + TRELLO_TOKEN: ${{secrets.TRELLO_TOKEN}} + GMAIL_REFRESH_TOKEN: ${{secrets.GMAIL_REFRESH_TOKEN_TEST}} + GMAIL_SECRET_JSON: ${{secrets.GMAIL_SECRET_JSON}} +# Controls when the workflow will run +on: + # Triggers the workflow on push or pull request events but only for the main branch + push: + branches: [ main ] + pull_request: + branches: [ main ] + + # Allows you to run this workflow manually from the Actions tab + workflow_dispatch: + +# A workflow run is made up of one or more jobs that can run sequentially or in parallel +jobs: + # This workflow contains a single job called "build" + pytest3-10: + # The type of runner that the job will run on + runs-on: ubuntu-latest + + # Steps represent a sequence of tasks that will be executed as part of the job + steps: + # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it + - uses: actions/checkout@v3 + + # Runs a single command using the runners shell + - name: Set up Python 3.10 + uses: actions/setup-python@v1 + with: + python-version: 3.10 + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install flake8 pytest + pip install -r requirements.txt + # Runs a set of commands using the runners shell + - name: Test with pytest + run: pytest -vv -m "not interactive" + + pytest3-8: + # The type of runner that the job will run on + runs-on: ubuntu-latest + + # Steps represent a sequence of tasks that will be executed as part of the job + steps: + # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it + - uses: actions/checkout@v3 + + # Runs a single command using the runners shell + - name: Set up Python 3.8 + uses: actions/setup-python@v1 + with: + python-version: 3.8 + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install flake8 pytest + pip install -r requirements.txt + # Runs a set of commands using the runners shell + - name: Test with pytest + run: pytest -vv -m "not interactive" + + pytest3-9: + # The type of runner that the job will run on + runs-on: ubuntu-latest + + # Steps represent a sequence of tasks that will be executed as part of the job + steps: + # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it + - uses: actions/checkout@v3 + + # Runs a single command using the runners shell + - name: Set up Python 3.9 + uses: actions/setup-python@v1 + with: + python-version: 3.9 + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install flake8 pytest + pip install -r requirements.txt + # Runs a set of commands using the runners shell + - name: Test with pytest + run: pytest -vv -m "not interactive" + + + \ No newline at end of file diff --git a/.gitignore b/.gitignore index e7fb84f..497ecfd 100644 --- a/.gitignore +++ b/.gitignore @@ -135,3 +135,4 @@ tests/zendesk_settings.json install.bat install2.bat setup.bat +*.secret diff --git a/serviceHelpers/gmail.py b/serviceHelpers/gmail.py index 74513cf..cb3fd20 100644 --- a/serviceHelpers/gmail.py +++ b/serviceHelpers/gmail.py @@ -7,6 +7,7 @@ from googleapiclient.discovery import build from google_auth_oauthlib.flow import InstalledAppFlow from google.auth.transport.requests import Request +from google.oauth2.credentials import Credentials import logging @@ -16,19 +17,40 @@ lo = logging.getLogger("GMailMapper") class Gmail(): - def __init__(self, user_email,friendly_name) -> None: + """Class to handle GMail API interactions, including fetching of and threads. + + Args: + `user_email` (str): The email address of the user to fetch emails for + `friendly_name` (str): A friendly name for the user + `token` (google.oauth2.credentials.Credentials): A valid token object + `token_file_path` (str): The path to the token file to load. If not provided, the token object must be provided.""" + def __init__(self, user_email,friendly_name, token:Credentials = None, token_file_path=None) -> None: logging.getLogger('googleapicliet.discovery_cache').setLevel(logging.WARNING) - self.token = self._getToken(friendly_name) + if token_file_path is not None: + self.token = load_token(token_file_path) + self.token = token self.friendly_name = friendly_name self.user_email = user_email + self.service = self.build_service() pass - def list_threads_matching_query(self,service, user_id, query='label:UNREAD label:INBOX'): + def list_threads_matching_query(self, query='label:UNREAD label:INBOX'): + + + """List all Threads of the user's mailbox matching the query. The query should be formatted the same as you would use in the GMail search box. + For more info on query formatting see https://support.google.com/mail/answer/7190?hl=en + Args: + `service` (googleapiclient.discovery.Resource): The gmail service object + `user_id` (str): The email address of the user to fetch emails for + `query` (str): The query to use to filter the emails. Defaults to 'label:UNREAD label:INBOX' + """ + service = self.service + user_id = "me" try: response = service.users().threads().list(userId=user_id, q=query).execute() threads = [] @@ -45,38 +67,86 @@ def list_threads_matching_query(self,service, user_id, query='label:UNREAD label except Exception as error: print ('An error occurred: %s' % error) - def _getToken(self,tokenName): - creds = None - # The file token.pickle stores the user's access and refresh tokens, and is - # created automatically when the authorization flow completes for the first - # time. - filename = "resources/GMailAuthTokens/%s.pickle" % (tokenName) - #print(os.getcwd()+filename) - if os.path.exists(filename): - with open(filename, 'rb') as token: - creds = pickle.load(token) - # If there are no (valid) credentials available, let the user log in. - if not creds or not creds.valid: - lo.warning ("Needing authorisation for the %s inbox!" % (tokenName)) - if creds and creds.expired and creds.refresh_token: - creds.refresh(Request()) - else: - lo.warning ("Needing authorisation for the %s inbox!" % (tokenName)) - flow = InstalledAppFlow.from_client_secrets_file( - 'resources/GMailCredentials.json', SCOPES) - creds = flow.run_local_server(port=0) - # Save the credentials for the next run - with open(filename, 'wb') as token: - pickle.dump(creds, token) - return creds - - - def fetch_gmail_items(self): - """ - Lists the user's emails that are in the inbox. - """ - service = build('gmail', 'v1', credentials=self.token) - threads = self.list_threads_matching_query(service,"me") - return threads + def build_service(self): + """Builds the service object for the gmail API. This is used to make calls to the API. + + Returns: + `googleapiclient.discovery.Resource`: The gmail service object""" + self.service = build('gmail', 'v1', credentials=self.token) + return self.service + + +def load_token( file_path = None) -> Credentials: + "Gets valid user credentials from pickled storage." + creds = None + # The file token.pickle stores the user's access and refresh tokens, and is + # created automatically when the authorization flow completes for the first + # time. + #print(os.getcwd()+filename) + if os.path.exists(file_path): + with open(file_path, 'rb') as token: + creds = pickle.load(token) + + else: + raise FileNotFoundError(f"No token file found at {file_path}") + + # If there are no (valid) credentials available flag the error so the user can re-auth + if not creds or not creds.valid: + lo.warning ("Saved token no longer valid - need to re-auth") + raise InvalidCredentialsException(f"Valid credentials could not be found at {file_path}") + return creds + +def make_new_token(client_secrets_file:str, redirect_url = "https://127.0.0.1/") -> Credentials: + "builds new token and dumps it to file, then returns" + + flow = InstalledAppFlow.from_client_secrets_file( + client_secrets_file, SCOPES, redirect_uri=redirect_url) + + creds = flow.run_local_server( open_browser=True, host="localhost",port=8080) + + return creds + +def make_new_token_from_refresh_bits(refresh_token:str, client_id:str, client_secret:str, token_uri:str = "https://oauth2.googleapis.com/token") -> Credentials: + "builds new token and dumps it to file, then returns" + + creds = Credentials("token",refresh_token, token_uri=token_uri, client_id=client_id, client_secret=client_secret) + creds.refresh(Request()) + return creds + + +def save_token(token: Credentials, file_path:str): + "Saves the token to file" + with open(file_path, 'wb') as token_file: + pickle.dump(token, token_file) + + +def extract_clientid_clientsecret_from_secretjson(secret_json:str) -> tuple: + """Extracts the client id and secret from the secret json file + + Args: + `secret_json` (str): The contents of the secret json file (as a string) + + Returns: + `tuple(str,str)`: A tuple containing the client id and secret" + + """ + + data = json.loads(secret_json) + return (data["installed"]["client_id"], data["installed"]["client_secret"]) + +class InvalidCredentialsException(BaseException): + "Exception raised when credentials are invalid/ expired" + + +if __name__ == "__main__": + f_name = "oauth_token.secret" + credentials_filename = "serviceHelpers-testing-desktop.json" + try: + token = load_token(f_name) + except (InvalidCredentialsException, FileNotFoundError) as err: + token = make_new_token(credentials_filename) + with open(f_name, "wb") as f: + pickle.dump(token, f) + \ No newline at end of file diff --git a/setup.py b/setup.py index 1d810bb..548ef82 100644 --- a/setup.py +++ b/setup.py @@ -10,7 +10,7 @@ setup( name="hex-helpers", - version="2.10.0", + version="3.0.0", description="A series of light helpers for `freshdesk`,`gmail`,`habitica`,`hue lights`,`jira`,`slack`,`trello`", long_description=README, long_description_content_type="text/markdown", diff --git a/tests/test_gmail.py b/tests/test_gmail.py new file mode 100644 index 0000000..05e8174 --- /dev/null +++ b/tests/test_gmail.py @@ -0,0 +1,30 @@ + +import os + +import pytest +from serviceHelpers.gmail import make_new_token_from_refresh_bits, load_token, save_token +from serviceHelpers.gmail import extract_clientid_clientsecret_from_secretjson, InvalidCredentialsException, Gmail + +TEST_REFRESH_TOKEN = os.environ.get("GMAIL_REFRESH_TOKEN_TEST",None) +TEST_GMAIL_SECRET_JSON = os.environ.get("GMAIL_SECRET_JSON",None) +TEST_EMAIL_ADDRESS = "github-tests@ctri.co.uk" +@pytest.fixture + + +def test_env_vars(): + assert TEST_REFRESH_TOKEN is not None + assert TEST_GMAIL_SECRET_JSON is not None + +def gmail_service(): + secret_bits = extract_clientid_clientsecret_from_secretjson(TEST_GMAIL_SECRET_JSON) + token = make_new_token_from_refresh_bits(TEST_REFRESH_TOKEN, secret_bits[0], secret_bits[1]) + gmail = Gmail(TEST_EMAIL_ADDRESS,"test_gmail_service",token) + return gmail + +def test_gmail_fetch_gmail_items(gmail_service:Gmail): + items = gmail_service.list_threads_matching_query( query="label:UNREAD label:INBOX") + + assert items is not None + + + diff --git a/tests/test_gmail_tokens.py b/tests/test_gmail_tokens.py new file mode 100644 index 0000000..6f067cd --- /dev/null +++ b/tests/test_gmail_tokens.py @@ -0,0 +1,47 @@ +import pytest +from serviceHelpers.gmail import make_new_token,make_new_token_from_refresh_bits, load_token, save_token,InvalidCredentialsException +import os +import json + + +TEST_REFRESH_TOKEN = os.environ.get("GMAIL_REFRESH_TOKEN",None) +TEST_GMAIL_SECRET_JSON = os.environ.get("GMAIL_SECRET_JSON",None) + +def save_secret_json_to_file(): + with open("gcloud_secrets.secret", "w") as f: + f.write(TEST_GMAIL_SECRET_JSON) + + +def test_env_vars(): + assert TEST_REFRESH_TOKEN is not None + assert TEST_GMAIL_SECRET_JSON is not None + +@pytest.mark.interactive +def test_make_new_token(): + token = make_new_token("gcloud_secrets.secret") + + assert token is not None + +def test_save_token(): + token = test_make_new_token_from_refresh_bits() + save_token(token, "oauth_token.secret") + assert os.path.exists("oauth_token.secret") + +def test_load_token(): + save_secret_json_to_file() + try: + token = load_token("oauth_token.secret") + except (InvalidCredentialsException, FileNotFoundError) as err: + assert False + assert token is not None + + + +def test_make_new_token_from_refresh_bits(): + secret = json.loads(TEST_GMAIL_SECRET_JSON) + client_id = secret["installed"]["client_id"] + client_secret = secret["installed"]["client_secret"] + token = make_new_token_from_refresh_bits(TEST_REFRESH_TOKEN, client_id, client_secret) + assert token is not None + assert token.valid is True + return token \ No newline at end of file diff --git a/tests/test_slack.py b/tests/test_slack.py index 6a4e41f..6d86112 100644 --- a/tests/test_slack.py +++ b/tests/test_slack.py @@ -14,7 +14,7 @@ ### Initialise Slack Helper ### SLACK_WEBHOOK = os.environ.get("SLACK_WEBHOOK") -SLACK_TOKEN = os.environ.get("SLACK_TOKEN") +SLACK_TOKEN = os.environ.get("SLACK_TOKEN_TEST") def test_environment_key(): @@ -143,6 +143,7 @@ def test_fetch_user_profile(caplog): good_profile_id = "U0214H4VCAX" profile = helper.fetch_user_profile(good_profile_id) + assert isinstance(profile["email"], str) assert isinstance(profile["display_name_normalized"], str) assert isinstance(profile["email"], str) diff --git a/tests/test_zendesk.py b/tests/test_zendesk.py index bc0c6dc..c5463fd 100644 --- a/tests/test_zendesk.py +++ b/tests/test_zendesk.py @@ -82,7 +82,7 @@ def test_get_user(caplog): assert entry.levelno < logging.ERROR assert isinstance(user, ZendeskUser) - assert user.name == "test test" + assert user.name == "test fg" assert user.email == "test@test.com" assert user.user_id == 417316391 assert user.organisationID is None From b5acf1d0261f6142f0bf8f8312622c87d80447a1 Mon Sep 17 00:00:00 2001 From: C'tri Goudie Date: Fri, 2 Jun 2023 21:37:58 +0100 Subject: [PATCH 2/4] Update pytest-all-supported.yml --- .github/workflows/pytest-all-supported.yml | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/.github/workflows/pytest-all-supported.yml b/.github/workflows/pytest-all-supported.yml index 87b2834..581635a 100644 --- a/.github/workflows/pytest-all-supported.yml +++ b/.github/workflows/pytest-all-supported.yml @@ -30,6 +30,28 @@ on: # A workflow run is made up of one or more jobs that can run sequentially or in parallel jobs: # This workflow contains a single job called "build" + pytest3-11: + # The type of runner that the job will run on + runs-on: ubuntu-latest + + # Steps represent a sequence of tasks that will be executed as part of the job + steps: + # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it + - uses: actions/checkout@v3 + + # Runs a single command using the runners shell + - name: Set up Python 3.10 + uses: actions/setup-python@v1 + with: + python-version: 3.11.3 + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install flake8 pytest + pip install -r requirements.txt + # Runs a set of commands using the runners shell + - name: Test with pytest + run: pytest -vv -m "not interactive" pytest3-10: # The type of runner that the job will run on runs-on: ubuntu-latest From a02ccac16ef942ac9cb942d77d5666eea4adba1b Mon Sep 17 00:00:00 2001 From: C'tri Goudie Date: Fri, 2 Jun 2023 21:39:47 +0100 Subject: [PATCH 3/4] test tweaks --- .github/workflows/pytest-all-supported.yml | 2 +- tests/test_gmail.py | 7 ++++--- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/.github/workflows/pytest-all-supported.yml b/.github/workflows/pytest-all-supported.yml index 581635a..64c9b64 100644 --- a/.github/workflows/pytest-all-supported.yml +++ b/.github/workflows/pytest-all-supported.yml @@ -40,7 +40,7 @@ jobs: - uses: actions/checkout@v3 # Runs a single command using the runners shell - - name: Set up Python 3.10 + - name: Set up Python 3.11 uses: actions/setup-python@v1 with: python-version: 3.11.3 diff --git a/tests/test_gmail.py b/tests/test_gmail.py index 05e8174..078cdb3 100644 --- a/tests/test_gmail.py +++ b/tests/test_gmail.py @@ -5,16 +5,17 @@ from serviceHelpers.gmail import make_new_token_from_refresh_bits, load_token, save_token from serviceHelpers.gmail import extract_clientid_clientsecret_from_secretjson, InvalidCredentialsException, Gmail -TEST_REFRESH_TOKEN = os.environ.get("GMAIL_REFRESH_TOKEN_TEST",None) +TEST_REFRESH_TOKEN = os.environ.get("GMAIL_REFRESH_TOKEN",None) TEST_GMAIL_SECRET_JSON = os.environ.get("GMAIL_SECRET_JSON",None) TEST_EMAIL_ADDRESS = "github-tests@ctri.co.uk" -@pytest.fixture def test_env_vars(): assert TEST_REFRESH_TOKEN is not None assert TEST_GMAIL_SECRET_JSON is not None - + + +@pytest.fixture def gmail_service(): secret_bits = extract_clientid_clientsecret_from_secretjson(TEST_GMAIL_SECRET_JSON) token = make_new_token_from_refresh_bits(TEST_REFRESH_TOKEN, secret_bits[0], secret_bits[1]) From e4fd2655d1845d07deaf697683465ab6b650075f Mon Sep 17 00:00:00 2001 From: C'tri Goudie Date: Fri, 2 Jun 2023 21:41:16 +0100 Subject: [PATCH 4/4] Update pytest-all-supported.yml --- .github/workflows/pytest-all-supported.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/pytest-all-supported.yml b/.github/workflows/pytest-all-supported.yml index 64c9b64..c07119a 100644 --- a/.github/workflows/pytest-all-supported.yml +++ b/.github/workflows/pytest-all-supported.yml @@ -65,7 +65,7 @@ jobs: - name: Set up Python 3.10 uses: actions/setup-python@v1 with: - python-version: 3.10 + python-version: 3.10.11 - name: Install dependencies run: | python -m pip install --upgrade pip