Prompt file imported from microsoft/mssql-python (
.github/prompts/build-ddbc.prompt.md). Copyright stays with the author.
Build DDBC Extensions Prompt for microsoft/mssql-python
You are a development assistant helping rebuild the DDBC C++ pybind11 extensions for the mssql-python driver.
PREREQUISITES
⚠️ This prompt assumes your development environment is already set up. If you haven't set up your environment yet, use
#setup-dev-envfirst.
Quick sanity check:
# Verify venv is active
if [ -z "$VIRTUAL_ENV" ]; then
echo "❌ No virtual environment active. Run: source myvenv/bin/activate"
exit 1
fi
# Verify pybind11 is installed
python -c "import pybind11; print('✅ Ready to build with Python', __import__('sys').version.split()[0])"
Important: The C++ extension will be built for the active Python version. Make sure you're using the same venv and Python version you'll use to run the code.
TASK
Help the developer rebuild the DDBC bindings after making C++ code changes. Follow this process sequentially.
STEP 0: Understand What You're Building
What Are DDBC Bindings?
The ddbc_bindings module is a C++ pybind11 extension that provides:
- Low-level ODBC connectivity to SQL Server
- High-performance database operations
- Platform-specific optimizations
When to Rebuild
- ✅ After modifying any
.cppor.hfiles inmssql_python/pybind/ - ✅ After changing
CMakeLists.txt - ✅ After upgrading Python version
- ✅ After pulling changes that include C++ modifications
- ❌ After Python-only changes (no rebuild needed)
Key Files
mssql_python/pybind/
├── ddbc_bindings.cpp # Main bindings implementation
├── ddbc_bindings.h # Header file
├── logger_bridge.cpp # Python logging bridge
├── logger_bridge.hpp # Logger header
├── connection/ # Connection implementation
│ ├── connection.cpp
│ ├── connection.h
│ ├── connection_pool.cpp
│ └── connection_pool.h
├── CMakeLists.txt # CMake build configuration
├── build.sh # macOS/Linux build script
└── build.bat # Windows build script
STEP 1: Build the Extension
1.1 Run Build Script
Important: The commands below will automatically return to the repository root after building.
macOS / Linux
# Standard build
cd mssql_python/pybind && ./build.sh && cd ../..
# Build with code coverage instrumentation (Linux only)
cd mssql_python/pybind && ./build.sh codecov && cd ../..
Windows (in Developer Command Prompt)
cd mssql_python\pybind && build.bat && cd ..\..
1.2 What the Build Does
- Cleans existing
build/directory - Detects Python version and architecture
- Configures CMake with correct paths
- Compiles C++ code to platform-specific extension
- Copies the built extension to
mssql_python/directory - Signs the extension (macOS only - for SIP compliance)
- Returns to repository root directory
Output files by platform:
| Platform | Output File |
|---|---|
| macOS | ddbc_bindings.cp{version}-universal2.so |
| Linux | ddbc_bindings.cp{version}-{arch}.so |
| Windows | ddbc_bindings.cp{version}-{arch}.pyd |
STEP 2: Verify the Build
These commands assume you're at the repository root (which you should be after Step 1).
2.1 Check Output File Exists
# macOS/Linux
ls -la mssql_python/ddbc_bindings.*.so
# Windows
dir mssql_python\ddbc_bindings.*.pyd
2.2 Verify Import Works
python -c "from mssql_python import connect; print('✅ Import successful')"
STEP 3: Clean Build (If Needed)
If you need a completely fresh build:
# From repository root
rm -rf mssql_python/pybind/build/
rm -f mssql_python/ddbc_bindings.*.so
rm -f mssql_python/ddbc_bindings.*.pyd
# Rebuild
cd mssql_python/pybind
./build.sh # or build.bat on Windows
Troubleshooting
❌ "CMake configuration failed"
Cause: CMake can't find Python or pybind11 paths
Fix:
# Verify Python include directory exists
python -c "import sysconfig; print(sysconfig.get_path('include'))"
ls $(python -c "import sysconfig; print(sysconfig.get_path('include'))")
# Verify pybind11 include directory exists
python -c "import pybind11; print(pybind11.get_include())"
ls $(python -c "import pybind11; print(pybind11.get_include())")
If pybind11 path doesn't exist, run: pip install pybind11
❌ "pybind11 not found" during build
Cause: pybind11 not installed in active venv
Fix:
# Ensure venv is active
source myvenv/bin/activate # adjust path if needed
# Install pybind11
pip install pybind11
# Verify
python -c "import pybind11; print(pybind11.get_include())"
❌ "sql.h not found" (macOS)
Cause: ODBC development headers not installed
Fix:
# Install Microsoft ODBC Driver (provides headers)
brew tap microsoft/mssql-release https://github.com/Microsoft/homebrew-mssql-release
ACCEPT_EULA=Y brew install msodbcsql18
# Or specify custom path
export ODBC_INCLUDE_DIR=/path/to/odbc/headers
./build.sh
❌ "undefined symbol" errors at runtime
Cause: Built with different Python than you're running
Fix:
# Check which Python was used to build (look at output filename)
ls mssql_python/ddbc_bindings.*.so
# e.g., ddbc_bindings.cp313-universal2.so means Python 3.13
# Check current Python
python --version
# If mismatch, rebuild with correct Python
rm -rf mssql_python/pybind/build/
cd mssql_python/pybind
./build.sh
❌ "cmake is not recognized" (Windows)
Cause: Not using Developer Command Prompt
Fix:
- Close current terminal
- Open Start Menu → search "Developer Command Prompt for VS 2022"
- Navigate to project:
cd C:\path\to\mssql-python\mssql_python\pybind - Run:
build.bat
❌ "codesign failed" (macOS)
Cause: macOS SIP (System Integrity Protection) issues
Fix: The build script handles this automatically. If issues persist:
codesign -s - -f mssql_python/ddbc_bindings.*.so
❌ Build succeeds but import fails
Cause: Usually path issues or old cached files
Fix:
# Clear Python cache
find . -type d -name __pycache__ -exec rm -rf {} + 2>/dev/null
# Clear any .pyc files
find . -name "*.pyc" -delete
# Reinstall in dev mode
pip install -e .
# Try import again
python -c "from mssql_python import connect; print('✅ OK')"
❌ "Permission denied" running build.sh
Fix:
chmod +x mssql_python/pybind/build.sh
./build.sh
❌ Build takes too long / seems stuck
Cause: Universal binary build on macOS compiles for both architectures
Info: This is normal. macOS builds for both arm64 and x86_64. First build takes longer, subsequent builds use cache.
If truly stuck (>10 minutes):
# Cancel with Ctrl+C, then clean and retry
rm -rf build/
./build.sh
Quick Reference
One-Liner Build Commands
# macOS/Linux - Full rebuild from repo root
cd mssql_python/pybind && rm -rf build && ./build.sh && cd ../.. && python -c "from mssql_python import connect; print('✅ Build successful')"
Build Output Naming Convention
| Platform | Python | Architecture | Output File |
|---|---|---|---|
| macOS | 3.13 | Universal | ddbc_bindings.cp313-universal2.so |
| Linux | 3.12 | x86_64 | ddbc_bindings.cp312-x86_64.so |
| Linux | 3.11 | ARM64 | ddbc_bindings.cp311-arm64.so |
| Windows | 3.13 | x64 | ddbc_bindings.cp313-amd64.pyd |
| Windows | 3.12 | ARM64 | ddbc_bindings.cp312-arm64.pyd |
After Building
Once the build succeeds:
- Run tests → Use
#run-tests - Test manually with a connection to SQL Server
- Create a PR with your C++ changes → Use
#create-pr