Skip to content

Commit 66c8efd

Browse files
committed
test on osx & windows
1 parent 1a59923 commit 66c8efd

7 files changed

Lines changed: 76 additions & 16 deletions

File tree

.github/workflows/ci.yml

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,4 +39,44 @@ jobs:
3939
- name: Check formatting
4040
run: |
4141
uv run --python ${{ matrix.python-version }} black --check .
42-
uv run --python ${{ matrix.python-version }} isort --check-only .
42+
uv run --python ${{ matrix.python-version }} isort --check-only .
43+
44+
test-osx:
45+
name: macOS Python 3.12
46+
runs-on: macos-latest
47+
48+
steps:
49+
- name: Checkout repository
50+
uses: actions/checkout@v5
51+
52+
- name: Set up uv
53+
uses: astral-sh/setup-uv@v6
54+
55+
- name: Install Python 3.12
56+
run: uv python install 3.12
57+
58+
- name: Install the project
59+
run: uv sync --locked --all-extras --dev
60+
61+
- name: Run tests
62+
run: uv run --python 3.12 pytest
63+
64+
test-windows:
65+
name: Windows Python 3.12
66+
runs-on: windows-latest
67+
68+
steps:
69+
- name: Checkout repository
70+
uses: actions/checkout@v5
71+
72+
- name: Set up uv
73+
uses: astral-sh/setup-uv@v6
74+
75+
- name: Install Python 3.12
76+
run: uv python install 3.12
77+
78+
- name: Install the project
79+
run: uv sync --locked --all-extras --dev
80+
81+
- name: Run tests
82+
run: uv run --python 3.12 pytest

.readthedocs.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,4 +6,4 @@ build:
66
python: "3.12"
77
commands:
88
- pip install .[docs]
9-
- python -m pdoc --docformat google --output-directory $READTHEDOCS_OUTPUT/html tinypg
9+
- python -m pdoc --docformat google --output-directory $READTHEDOCS_OUTPUT/html --logo https://iili.io/Klv1Zcx.md.png tinypg

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11

2-
[![Klv1Zcx.md.png](https://iili.io/Klv1Zcx.md.png)](https://freeimage.host/i/Klv1Zcx)
2+
![logo](https://iili.io/Klv1Zcx.md.png)
33

44
# TinyPG
55

@@ -9,7 +9,7 @@ A Python package for creating ephemeral PostgreSQL databases, inspired by [ephem
99

1010
TinyPG provides a clean Python API for creating temporary PostgreSQL databases for development and testing. It's designed to be self-contained and work without requiring system-wide PostgreSQL installation.
1111

12-
**Currently only tested on linux, but should work on OSX and Windows hopefully**
12+
**Works on Linux, OSX and Windows**
1313

1414
## Features
1515

pyproject.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ classifiers = [
1515
"Intended Audience :: Developers",
1616
"License :: OSI Approved :: MIT License",
1717
"Operating System :: POSIX :: Linux",
18+
"Operating System :: MacOS :: MacOS X",
19+
"Operating System :: Microsoft :: Windows",
1820
"Programming Language :: Python :: 3",
1921
"Programming Language :: Python :: 3.8",
2022
"Programming Language :: Python :: 3.9",

src/tinypg/__init__.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
"""
2-
[![Klv1Zcx.md.png](https://iili.io/Klv1Zcx.md.png)](https://freeimage.host/i/Klv1Zcx)
32
43
TinyPG: Ephemeral PostgreSQL databases for Python development and testing.
54

src/tinypg/binaries.py

Lines changed: 22 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,9 @@
2222
class PostgreSQLBinaries:
2323
"""Manages PostgreSQL binary installation and versioning."""
2424

25+
PLATFORM = platform.machine().lower()
26+
SYSTEM = platform.system().lower()
27+
2528
# PostgreSQL versions supported (from pg-embed)
2629
SUPPORTED_VERSIONS = {
2730
"17": "17.2.0",
@@ -50,7 +53,7 @@ def __init__(self, cache_dir: Optional[Path] = None):
5053

5154
def _detect_os(self) -> str:
5255
"""Detect the operating system."""
53-
system = platform.system().lower()
56+
system = self.SYSTEM
5457
if system == "darwin":
5558
return "darwin"
5659
elif system == "windows":
@@ -63,7 +66,7 @@ def _detect_os(self) -> str:
6366

6467
def _detect_arch(self) -> str:
6568
"""Detect the CPU architecture."""
66-
machine = platform.machine().lower()
69+
machine = self.PLATFORM
6770
if machine in ["x86_64", "amd64"]:
6871
return "amd64"
6972
elif machine in ["i386", "i686"]:
@@ -81,6 +84,17 @@ def _get_platform_string(self) -> str:
8184
"""Get the platform string for binary downloads."""
8285
return f"{self.os_name}-{self.arch}"
8386

87+
@staticmethod
88+
def _get_binary_path(
89+
manager: "PostgreSQLBinaries", version: str, binary_name: str
90+
) -> str:
91+
install_dir = manager._get_install_dir(version)
92+
binary_path = install_dir / "bin" / binary_name
93+
94+
if manager.SYSTEM == "windows":
95+
binary_path = binary_path.with_suffix(".exe")
96+
return binary_path
97+
8498
@classmethod
8599
def ensure_version(cls, version: str) -> Path:
86100
"""
@@ -142,9 +156,7 @@ def get_binary_path(cls, binary_name: str, version: str = None) -> Path:
142156
return Path(system_binary)
143157

144158
# Check our installation
145-
install_dir = manager._get_install_dir(version)
146-
binary_path = install_dir / "bin" / binary_name
147-
159+
binary_path = cls._get_binary_path(manager, version, binary_name)
148160
if binary_path.exists() and os.access(binary_path, os.X_OK):
149161
return binary_path
150162

@@ -311,8 +323,8 @@ def _is_version_installed(self, version: str) -> bool:
311323
install_dir = self._get_install_dir(version)
312324

313325
# Check if all required binaries exist
314-
for binary in self.REQUIRED_BINARIES:
315-
binary_path = install_dir / "bin" / binary
326+
for binary_name in self.REQUIRED_BINARIES:
327+
binary_path = self._get_binary_path(self, version, binary_name)
316328
if not (binary_path.exists() and os.access(binary_path, os.X_OK)):
317329
return False
318330

@@ -366,6 +378,9 @@ def _verify_installation(self, install_dir: Path) -> None:
366378

367379
for binary in self.REQUIRED_BINARIES:
368380
binary_path = bin_dir / binary
381+
if self.SYSTEM == "windows":
382+
binary_path = binary_path.with_suffix(".exe")
383+
369384
if not (binary_path.exists() and os.access(binary_path, os.X_OK)):
370385
raise BinaryNotFoundError(f"Binary {binary} not found in installation")
371386

src/tinypg/core.py

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@
1818
from .config import TinyPGConfig
1919
from .exceptions import (
2020
DatabaseStartError,
21-
DatabaseTimeoutError,
2221
InitDBError,
2322
ProcessError,
2423
)
@@ -210,8 +209,13 @@ def load_sql_file(self, file_path: Path) -> None:
210209
def _initialize_database(self) -> Path:
211210
"""Initialize a new PostgreSQL database cluster."""
212211
# Create temporary directory
213-
self._temp_dir = tempfile.mkdtemp(prefix="tinypg.")
214-
temp_path = Path(self._temp_dir)
212+
is_windows = PostgreSQLBinaries.SYSTEM == "windows"
213+
sep = "-" if is_windows else "."
214+
if is_windows:
215+
temp_path = Path(tempfile.gettempdir()) / sep / tempfile.gettempprefix()
216+
else:
217+
self._temp_dir = tempfile.mkdtemp(prefix=f"tinypg{sep}")
218+
temp_path = Path(self._temp_dir)
215219

216220
# Data directory for this PostgreSQL version
217221
data_dir = temp_path / self.version
@@ -233,7 +237,7 @@ def _initialize_database(self) -> Path:
233237
],
234238
check=True,
235239
capture_output=True,
236-
cwd=temp_path,
240+
cwd=None if is_windows else temp_path,
237241
)
238242

239243
# Configure PostgreSQL for ephemeral use

0 commit comments

Comments
 (0)