1"""Prepare py.test."""
2import json
3import os
4import socket
5import sys
6import time
7from base64 import b64encode
8from sys import platform
9
10import betamax
11import pytest
12from betamax_serializers import pretty_json
13
14# pylint: disable=import-error,no-name-in-module
15if sys.version_info.major == 2:
16    from urllib import quote_plus  # NOQA
17else:
18    from urllib.parse import quote_plus  # NOQA
19
20
21# Prevent calls to sleep
22def _sleep(*args):
23    raise Exception("Call to sleep")
24
25
26time.sleep = _sleep
27
28
29def b64_string(input_string):
30    """Return a base64 encoded string (not bytes) from input_string."""
31    return b64encode(input_string.encode("utf-8")).decode("utf-8")
32
33
34def env_default(key):
35    """Return environment variable or placeholder string."""
36    return os.environ.get(
37        "prawtest_{}".format(key), "placeholder_{}".format(key)
38    )
39
40
41def filter_access_token(interaction, current_cassette):
42    """Add Betamax placeholder to filter access token."""
43    request_uri = interaction.data["request"]["uri"]
44    response = interaction.data["response"]
45    if (
46        "api/v1/access_token" not in request_uri
47        or response["status"]["code"] != 200
48    ):
49        return
50    body = response["body"]["string"]
51    try:
52        token = json.loads(body)["access_token"]
53    except (KeyError, TypeError, ValueError):
54        return
55    current_cassette.placeholders.append(
56        betamax.cassette.cassette.Placeholder(
57            placeholder="<ACCESS_TOKEN>", replace=token
58        )
59    )
60
61
62os.environ["praw_check_for_updates"] = "False"
63
64
65placeholders = {
66    x: env_default(x)
67    for x in (
68        "auth_code client_id client_secret password redirect_uri "
69        "test_subreddit user_agent username"
70    ).split()
71}
72placeholders["basic_auth"] = b64_string(
73    "{}:{}".format(placeholders["client_id"], placeholders["client_secret"])
74)
75
76
77betamax.Betamax.register_serializer(pretty_json.PrettyJSONSerializer)
78with betamax.Betamax.configure() as config:
79    config.cassette_library_dir = "tests/integration/cassettes"
80    config.default_cassette_options["serialize_with"] = "prettyjson"
81    config.before_record(callback=filter_access_token)
82    for key, value in placeholders.items():
83        if key == "password":
84            value = quote_plus(value)
85        config.define_cassette_placeholder("<{}>".format(key.upper()), value)
86
87
88class Placeholders(object):
89    def __init__(self, _dict):
90        self.__dict__ = _dict
91
92
93def pytest_configure():
94    pytest.placeholders = Placeholders(placeholders)
95
96
97if platform == "darwin":  # Work around issue with betamax on OS X
98    socket.gethostbyname = lambda x: "127.0.0.1"
99