Skip to content

Commit c35c355

Browse files
author
jason.hsu
committed
feat: add dependency file and cicd
1 parent 1fb02f4 commit c35c355

File tree

4 files changed

+131
-23
lines changed

4 files changed

+131
-23
lines changed

.github/workflows/ci.yml

Lines changed: 63 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,48 @@ on:
1414
- 'releases/*'
1515

1616
jobs:
17+
# ============================================
18+
# DEPENDENCY CHECK JOB
19+
# Ensures all imports are satisfied by requirements.txt
20+
# ============================================
21+
dependency-check:
22+
name: Dependency Check
23+
runs-on: ubuntu-latest
24+
steps:
25+
- uses: actions/checkout@v4
26+
27+
- name: Set up Python
28+
uses: actions/setup-python@v5
29+
with:
30+
python-version: "3.11"
31+
32+
- name: Install only from requirements.txt (clean environment)
33+
run: |
34+
python -m pip install --upgrade pip
35+
pip install -r requirements.txt
36+
37+
- name: Verify all production imports work
38+
run: |
39+
# This catches missing dependencies in requirements.txt
40+
python -c "
41+
import okx
42+
from okx import Account, Trade, Funding, MarketData, PublicData
43+
from okx import SubAccount, Convert, BlockTrading, CopyTrading
44+
from okx import SpreadTrading, Grid, TradingData, Status
45+
from okx.websocket import WsPublicAsync, WsPrivateAsync
46+
print('✅ All imports successful')
47+
print(f' okx version: {okx.__version__}')
48+
"
49+
50+
- name: Install dev dependencies and verify test imports
51+
run: |
52+
pip install -r requirements-dev.txt
53+
python -c "
54+
import pytest
55+
import unittest
56+
print('✅ Dev imports successful')
57+
"
58+
1759
# ============================================
1860
# LINT JOB
1961
# ============================================
@@ -31,11 +73,11 @@ jobs:
3173
- name: Install linting tools
3274
run: |
3375
python -m pip install --upgrade pip
34-
pip install flake8
76+
pip install ruff
3577
36-
- name: Run flake8
78+
- name: Run ruff
3779
run: |
38-
flake8 okx/ --max-line-length=120 --ignore=E501,W503,E203 --count --show-source --statistics
80+
ruff check okx/ --ignore=E501
3981
continue-on-error: true # Set to false once codebase is cleaned up
4082

4183
# ============================================
@@ -44,10 +86,12 @@ jobs:
4486
test:
4587
name: Test (Python ${{ matrix.python-version }})
4688
runs-on: ubuntu-latest
89+
needs: [dependency-check] # Only run tests if dependencies are valid
4790
strategy:
48-
fail-fast: false
91+
fail-fast: true
92+
max-parallel: 1
4993
matrix:
50-
python-version: ["3.9", "3.10", "3.11", "3.12"]
94+
python-version: ["3.9", "3.12"]
5195

5296
steps:
5397
- uses: actions/checkout@v4
@@ -61,23 +105,23 @@ jobs:
61105
uses: actions/cache@v4
62106
with:
63107
path: ~/.cache/pip
64-
key: ${{ runner.os }}-pip-${{ matrix.python-version }}-${{ hashFiles('setup.py') }}
108+
key: ${{ runner.os }}-pip-${{ matrix.python-version }}-${{ hashFiles('requirements*.txt') }}
65109
restore-keys: |
66110
${{ runner.os }}-pip-${{ matrix.python-version }}-
67111
${{ runner.os }}-pip-
68112
69113
- name: Install dependencies
70114
run: |
71115
python -m pip install --upgrade pip
116+
pip install -r requirements-dev.txt
72117
pip install -e .
73-
pip install pytest pytest-cov pytest-asyncio websockets certifi
74118
75119
- name: Run tests
76120
run: |
77121
python -m pytest test/unit/ -v --cov=okx --cov-report=term-missing --cov-report=xml
78122
79123
- name: Upload coverage to Codecov
80-
if: matrix.python-version == '3.11'
124+
if: matrix.python-version == '3.12'
81125
uses: codecov/codecov-action@v4
82126
with:
83127
file: ./coverage.xml
@@ -110,10 +154,20 @@ jobs:
110154
- name: Check package
111155
run: twine check dist/*
112156

157+
- name: Test install from wheel (clean environment)
158+
run: |
159+
# Create a fresh venv and install the built wheel
160+
python -m venv /tmp/test-install
161+
/tmp/test-install/bin/pip install dist/*.whl
162+
/tmp/test-install/bin/python -c "
163+
import okx
164+
from okx import Account, Trade, Funding
165+
print(f'✅ Package installs correctly: okx {okx.__version__}')
166+
"
167+
113168
- name: Upload build artifacts
114169
uses: actions/upload-artifact@v4
115170
with:
116171
name: dist
117172
path: dist/
118173
retention-days: 7
119-

requirements-dev.txt

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
# Development dependencies
2+
-r requirements.txt
3+
4+
# Testing
5+
pytest>=7.0.0
6+
pytest-asyncio>=0.21.0
7+
pytest-cov>=4.0.0
8+
9+
# Linting & Formatting
10+
ruff>=0.1.0
11+
mypy>=1.0.0
12+
13+
# Environment
14+
python-dotenv>=1.0.0
15+
16+
# Build tools
17+
build>=1.0.0
18+
twine>=4.0.0
19+

requirements.txt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
# Core dependencies for python-okx
2+
httpx[http2]>=0.24.0
3+
requests>=2.25.0
4+
websockets>=10.0
5+
certifi>=2021.0.0
6+
loguru>=0.7.0
7+

setup.py

Lines changed: 42 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,36 @@
11
import setuptools
2+
from pathlib import Path
3+
4+
# Read version from package
25
import okx
3-
with open("README.md", "r",encoding="utf-8") as fh:
6+
7+
# Read README
8+
with open("README.md", "r", encoding="utf-8") as fh:
49
long_description = fh.read()
510

11+
12+
def parse_requirements(filename): # type: (str) -> list
13+
"""Parse requirements from a requirements file."""
14+
requirements_path = Path(__file__).parent / filename
15+
requirements = []
16+
17+
if not requirements_path.exists():
18+
return requirements
19+
20+
with open(requirements_path, "r", encoding="utf-8") as f:
21+
for line in f:
22+
line = line.strip()
23+
# Skip empty lines, comments, and -r includes
24+
if not line or line.startswith("#") or line.startswith("-r"):
25+
continue
26+
# Handle inline comments
27+
if "#" in line:
28+
line = line.split("#")[0].strip()
29+
requirements.append(line)
30+
31+
return requirements
32+
33+
634
setuptools.setup(
735
name="python-okx",
836
version=okx.__version__,
@@ -12,21 +40,21 @@
1240
long_description=long_description,
1341
long_description_content_type="text/markdown",
1442
url="https://okx.com/docs-v5/",
15-
packages=setuptools.find_packages(),
43+
packages=setuptools.find_packages(exclude=["test", "test.*", "example"]),
44+
python_requires=">=3.7",
1645
classifiers=[
1746
"Programming Language :: Python :: 3",
47+
"Programming Language :: Python :: 3.7",
48+
"Programming Language :: Python :: 3.8",
49+
"Programming Language :: Python :: 3.9",
50+
"Programming Language :: Python :: 3.10",
51+
"Programming Language :: Python :: 3.11",
52+
"Programming Language :: Python :: 3.12",
1853
"License :: OSI Approved :: MIT License",
1954
"Operating System :: OS Independent",
2055
],
21-
install_requires=[
22-
"importlib-metadata",
23-
"httpx[http2]",
24-
"keyring",
25-
"loguru",
26-
"requests",
27-
"Twisted",
28-
"pyOpenSSL",
29-
"websockets",
30-
"certifi"
31-
]
32-
)
56+
install_requires=parse_requirements("requirements.txt"),
57+
extras_require={
58+
"dev": parse_requirements("requirements-dev.txt"),
59+
},
60+
)

0 commit comments

Comments
 (0)