|
4 | 4 | import sys |
5 | 5 | import os |
6 | 6 | import unittest |
| 7 | +import atexit |
7 | 8 |
|
| 9 | +from ..python.socket import find_available_port |
| 10 | + |
| 11 | +from .. import installation |
| 12 | +from .. import cluster as pg_cluster |
8 | 13 | from .. import exceptions as pg_exc |
9 | | -from .. import unittest as pg_unittest |
10 | 14 |
|
11 | 15 | from ..driver import dbapi20 as dbapi20 |
12 | 16 | from .. import driver as pg_driver |
13 | 17 | from .. import open as pg_open |
14 | 18 |
|
15 | 19 | msw = sys.platform in ('win32', 'win64') |
16 | 20 |
|
17 | | -class test_connect(pg_unittest.TestCaseWithCluster): |
| 21 | +class TestCaseWithCluster(unittest.TestCase): |
| 22 | + """ |
| 23 | + postgresql.driver *interface* tests. |
| 24 | + """ |
| 25 | + def __init__(self, *args, **kw): |
| 26 | + super().__init__(*args, **kw) |
| 27 | + self.installation = installation.default() |
| 28 | + self.cluster_path = \ |
| 29 | + 'py_unittest_pg_cluster_' \ |
| 30 | + + str(os.getpid()) + getattr(self, 'cluster_path_suffix', '') |
| 31 | + |
| 32 | + if self.installation is None: |
| 33 | + sys.stderr.write("ERROR: cannot find 'default' pg_config\n") |
| 34 | + sys.stderr.write( |
| 35 | + "HINT: set the PGINSTALLATION environment variable to the `pg_config` path\n" |
| 36 | + ) |
| 37 | + sys.exit(1) |
| 38 | + |
| 39 | + self.cluster = pg_cluster.Cluster( |
| 40 | + self.installation, |
| 41 | + self.cluster_path, |
| 42 | + ) |
| 43 | + if self.cluster.initialized(): |
| 44 | + self.cluster.drop() |
| 45 | + |
| 46 | + def configure_cluster(self): |
| 47 | + self.cluster_port = find_available_port() |
| 48 | + if self.cluster_port is None: |
| 49 | + pg_exc.ClusterError( |
| 50 | + 'failed to find a port for the test cluster on localhost', |
| 51 | + creator = self.cluster |
| 52 | + ).raise_exception() |
| 53 | + self.cluster.settings.update(dict( |
| 54 | + port = str(self.cluster_port), |
| 55 | + max_connections = '6', |
| 56 | + shared_buffers = '24', |
| 57 | + listen_addresses = 'localhost', |
| 58 | + log_destination = 'stderr', |
| 59 | + log_min_messages = 'FATAL', |
| 60 | + silent_mode = 'off', |
| 61 | + )) |
| 62 | + # 8.4 turns prepared transactions off by default. |
| 63 | + if self.cluster.installation.version_info >= (8,1): |
| 64 | + self.cluster.settings.update(dict( |
| 65 | + max_prepared_transactions = '3', |
| 66 | + )) |
| 67 | + |
| 68 | + def initialize_database(self): |
| 69 | + c = self.cluster.connection( |
| 70 | + user = 'test', |
| 71 | + database = 'template1', |
| 72 | + ) |
| 73 | + with c: |
| 74 | + if c.prepare( |
| 75 | + "select true from pg_catalog.pg_database " \ |
| 76 | + "where datname = 'test'" |
| 77 | + ).first() is None: |
| 78 | + c.execute('create database test') |
| 79 | + |
| 80 | + def connection(self, *args, **kw): |
| 81 | + return self.cluster.connection(*args, user = 'test', **kw) |
| 82 | + |
| 83 | + def run(self, *args, **kw): |
| 84 | + if not self.cluster.initialized(): |
| 85 | + self.cluster.encoding = 'utf-8' |
| 86 | + self.cluster.init( |
| 87 | + user = 'test', |
| 88 | + encoding = self.cluster.encoding, |
| 89 | + logfile = None, |
| 90 | + ) |
| 91 | + sys.stderr.write('*') |
| 92 | + try: |
| 93 | + atexit.register(self.cluster.drop) |
| 94 | + self.configure_cluster() |
| 95 | + self.cluster.start(logfile = sys.stdout) |
| 96 | + self.cluster.wait_until_started() |
| 97 | + self.initialize_database() |
| 98 | + except Exception: |
| 99 | + self.cluster.drop() |
| 100 | + atexit.unregister(self.cluster.drop) |
| 101 | + raise |
| 102 | + if not self.cluster.running(): |
| 103 | + self.cluster.start() |
| 104 | + self.cluster.wait_until_started() |
| 105 | + |
| 106 | + db = self.connection() |
| 107 | + with db: |
| 108 | + self.db = db |
| 109 | + return super().run(*args, **kw) |
| 110 | + self.db = None |
| 111 | + |
| 112 | +class test_connect(TestCaseWithCluster): |
18 | 113 | """ |
19 | 114 | postgresql.driver connectivity tests |
20 | 115 | """ |
|
0 commit comments