README: remove windows known issue warning - issue has been fixed #52
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: CI | |
| on: | |
| push: | |
| branches: [master] | |
| pull_request: | |
| branches: [master] | |
| jobs: | |
| lint: | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Set up Python | |
| uses: actions/setup-python@v6 | |
| with: | |
| python-version: "3.14" | |
| - name: Install linters | |
| run: pip install ruff 'black<26' | |
| - name: Run ruff check | |
| run: ruff check plugins/ tests/ utils/ | |
| - name: Run black check | |
| run: black --check plugins/ tests/ utils/ | |
| build: | |
| needs: lint | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| os: [ubuntu-latest, macos-latest, windows-latest] | |
| python-version: ["3.12", "3.14"] | |
| exclude: | |
| # ubuntu-latest is 24.04 with system Python 3.12; | |
| # GStreamer gi bindings are built for 3.12 only | |
| - os: ubuntu-latest | |
| python-version: "3.14" | |
| include: | |
| - os: ubuntu-latest | |
| gst-install: | | |
| sudo apt-get update | |
| sudo apt-get install -y \ | |
| gstreamer1.0-tools \ | |
| gstreamer1.0-plugins-base \ | |
| gstreamer1.0-plugins-good \ | |
| gstreamer1.0-plugins-bad \ | |
| gir1.2-gstreamer-1.0 \ | |
| gir1.2-gst-plugins-base-1.0 \ | |
| gir1.2-gst-plugins-bad-1.0 \ | |
| libgstreamer-plugins-bad1.0-dev \ | |
| python3-gi \ | |
| python3-gi-cairo \ | |
| python3-gst-1.0 \ | |
| gstreamer1.0-python3-plugin-loader \ | |
| libcairo2 \ | |
| libcairo2-dev \ | |
| pkg-config \ | |
| libgirepository-2.0-dev \ | |
| libglib2.0-dev \ | |
| python3-dev | |
| pip install numpy opencv-python-headless ultralytics onnxruntime | |
| - os: macos-latest | |
| gst-install: | | |
| brew install gstreamer cairo pkg-config pygobject3 gobject-introspection | |
| echo "DYLD_LIBRARY_PATH=$(brew --prefix)/lib:$DYLD_LIBRARY_PATH" >> $GITHUB_ENV | |
| echo "GI_TYPELIB_PATH=$(brew --prefix)/lib/girepository-1.0" >> $GITHUB_ENV | |
| - os: windows-latest | |
| gst-install: | | |
| choco install gstreamer gstreamer-devel --yes | |
| "C:\gstreamer\1.0\msvc_x86_64\bin" >> $env:GITHUB_PATH | |
| "GST_PLUGIN_PATH=C:\gstreamer\1.0\msvc_x86_64\lib\gstreamer-1.0" >> $env:GITHUB_ENV | |
| "PKG_CONFIG_PATH=C:\gstreamer\1.0\msvc_x86_64\lib\pkgconfig" >> $env:GITHUB_ENV | |
| runs-on: ${{ matrix.os }} | |
| steps: | |
| - uses: actions/checkout@v6 | |
| - name: Set up Python | |
| uses: actions/setup-python@v6 | |
| with: | |
| python-version: ${{ matrix.python-version }} | |
| - name: Install GStreamer | |
| run: ${{ matrix.gst-install }} | |
| - name: Create venv and install CPU dependencies | |
| shell: bash | |
| run: | | |
| python -m venv --system-site-packages .venv | |
| if [[ "$RUNNER_OS" == "Windows" ]]; then | |
| source .venv/Scripts/activate | |
| else | |
| source .venv/bin/activate | |
| fi | |
| pip install --no-deps -e . | |
| pip install numpy opencv-python-headless ultralytics | |
| # pygobject/pycairo from pip need C build deps; install only where available | |
| pip install pygobject pycairo || echo "pygobject/pycairo pip install failed (using system packages)" | |
| - name: Verify core imports | |
| shell: bash | |
| continue-on-error: true | |
| run: | | |
| if [[ "$RUNNER_OS" == "Windows" ]]; then | |
| source .venv/Scripts/activate | |
| else | |
| source .venv/bin/activate | |
| fi | |
| python -c " | |
| import gi | |
| gi.require_version('Gst', '1.0') | |
| gi.require_version('GstBase', '1.0') | |
| from gi.repository import Gst | |
| Gst.init(None) | |
| import importlib, sys | |
| modules = [ | |
| 'plugins.python.streammux', | |
| 'plugins.python.streamdemux', | |
| 'plugins.python.overlay', | |
| 'plugins.python.engine.ml_engine', | |
| 'plugins.python.engine.engine_factory', | |
| ] | |
| failed = [] | |
| for m in modules: | |
| try: | |
| importlib.import_module(m) | |
| print(f' OK {m}') | |
| except Exception as e: | |
| print(f' FAIL {m}: {e}') | |
| failed.append(m) | |
| if failed: | |
| print(f'\n{len(failed)} import(s) failed') | |
| sys.exit(1) | |
| print('\nAll imports OK') | |
| " | |
| - name: Check GStreamer plugin discovery (Linux) | |
| if: runner.os == 'Linux' | |
| run: | | |
| source .venv/bin/activate | |
| VENV_SITE=$(python -c "import site; print(site.getsitepackages()[0])") | |
| # libgstpython.so uses system Python which needs: | |
| # - /usr/lib/python3/dist-packages for gi (python3-gi apt package) | |
| # - venv site-packages for pip-installed ML packages | |
| # - plugins/python for our GStreamer element modules | |
| export PYTHONPATH="/usr/lib/python3/dist-packages:${VENV_SITE}:${{ github.workspace }}/plugins/python" | |
| export GST_PLUGIN_PATH=${{ github.workspace }}/plugins | |
| # Prevent hostedtoolcache libpython from shadowing system libpython | |
| unset LD_LIBRARY_PATH | |
| rm -rf ~/.cache/gstreamer-1.0 | |
| gst-inspect-1.0 python | |
| gst-inspect-1.0 pyml_objectdetector | |
| - name: ONNX pipeline smoke test (Linux) | |
| if: runner.os == 'Linux' | |
| run: | | |
| source .venv/bin/activate | |
| pip install onnxruntime | |
| VENV_SITE=$(python -c "import site; print(site.getsitepackages()[0])") | |
| export PYTHONPATH="/usr/lib/python3/dist-packages:${VENV_SITE}:${{ github.workspace }}/plugins/python" | |
| export GST_PLUGIN_PATH=${{ github.workspace }}/plugins | |
| unset LD_LIBRARY_PATH | |
| rm -rf ~/.cache/gstreamer-1.0 | |
| # Export YOLO model to ONNX | |
| python -c "from ultralytics import YOLO; YOLO('yolo11n.pt').export(format='onnx')" | |
| # Run 2-frame smoke test with synthetic source (avoids codec deps) | |
| gst-launch-1.0 videotestsrc num-buffers=2 \ | |
| ! "video/x-raw,format=RGB,width=640,height=640" \ | |
| ! pyml_objectdetector engine-name=onnx model-name=yolo11n.onnx device=cpu input-format=nchw post-process=anchor_free \ | |
| ! fakesink | |
| - name: ONNX pipeline smoke test (macOS) | |
| if: runner.os == 'macOS' | |
| run: | | |
| # brew's libgstpython.dylib embeds brew's Python (not actions/setup-python). | |
| # Install ML packages into brew's Python so libgstpython can find them. | |
| BREW_PREFIX=$(brew --prefix) | |
| BREW_PIP="${BREW_PREFIX}/bin/pip3" | |
| BREW_PYTHON="${BREW_PREFIX}/bin/python3" | |
| ${BREW_PIP} install --break-system-packages ultralytics onnxruntime onnx numpy opencv-python-headless | |
| export GST_PLUGIN_PATH=${{ github.workspace }}/plugins | |
| export PYTHONPATH=${{ github.workspace }}/plugins/python | |
| # Export YOLO model to ONNX | |
| ${BREW_PYTHON} -c "from ultralytics import YOLO; YOLO('yolo11n.pt').export(format='onnx')" | |
| # Run 2-frame smoke test with synthetic source (avoids codec deps) | |
| gst-launch-1.0 videotestsrc num-buffers=2 \ | |
| ! "video/x-raw,format=RGB,width=640,height=640" \ | |
| ! pyml_objectdetector engine-name=onnx model-name=yolo11n.onnx device=cpu input-format=nchw post-process=anchor_free \ | |
| ! fakesink | |
| - name: ONNX pipeline smoke test (Windows) | |
| if: runner.os == 'Windows' | |
| continue-on-error: true | |
| shell: bash | |
| run: | | |
| source .venv/Scripts/activate | |
| pip install onnxruntime | |
| SITE_PKGS=$(python -c "import site; print(site.getsitepackages()[0])") | |
| # Find GStreamer install location | |
| GST_BIN=$(find /c/gstreamer -name "gst-launch-1.0.exe" 2>/dev/null | head -1 | xargs dirname) | |
| if [[ -z "$GST_BIN" ]]; then | |
| echo "ERROR: gst-launch-1.0.exe not found under /c/gstreamer" | |
| find /c/gstreamer -type f -name "gst-*" 2>/dev/null || echo "No gst binaries found" | |
| ls /c/gstreamer/ 2>/dev/null || echo "/c/gstreamer does not exist" | |
| exit 1 | |
| fi | |
| echo "Found GStreamer at: $GST_BIN" | |
| export PATH="${GST_BIN}:$PATH" | |
| GST_LIB=$(dirname "$GST_BIN")/lib/gstreamer-1.0 | |
| export GST_PLUGIN_PATH="${{ github.workspace }}/plugins;${GST_LIB}" | |
| export PYTHONPATH="${SITE_PKGS};${{ github.workspace }}/plugins/python;$PYTHONPATH" | |
| # Export YOLO model to ONNX | |
| python -c "from ultralytics import YOLO; YOLO('yolo11n.pt').export(format='onnx')" | |
| # Run 2-frame smoke test with synthetic source (avoids codec deps) | |
| gst-launch-1.0.exe videotestsrc num-buffers=2 \ | |
| ! "video/x-raw,format=RGB,width=640,height=640" \ | |
| ! pyml_objectdetector engine-name=onnx model-name=yolo11n.onnx device=cpu input-format=nchw post-process=anchor_free \ | |
| ! fakesink |