KSQL-Treiber
Eigene Treiber für den KSQL-Port (TDS 7.4 mit dem KSQL-Profil) in acht Sprachen, je nach dem Vorbild des Microsoft-Treibers: dieselbe Schnittstelle, dieselben Schlüssel der Verbindungszeichenfolge, dieselbe Abbildung der Typen und Fehler — und dazu, was KSQL über SQL Server hinaus kann. Jeder arbeitet auch an SQL Server. Jeder Treiber spielt denselben sprachneutralen Prüfkatalog ab (KuonenSQL/tools/ksql-konformitaet/faelle.json, D36.1), einmal gegen den KSQL-Port und einmal gegen SQL Server 2025.
Vorbild: mssql-python bzw. DB-API 2.0 (PEP 249) · Paket ksql, Paketname kuonen-ksql (pyproject.toml) · Python 3.10+, nur Standardbibliothek (TLS über ssl) · Quelle: Data/src/Kuonen.Data.Ksql.Python
· Roadmap D36.7 ✅
Herunterladen und einbinden
- kuonen_ksql-2.0.0-py3-none-any.whl · 39 KB
SHA-256
e0cc4191c20572d34be42939e8bb8365059eb85a71b6bfd468965811dc6441fe
pip install kuonen_ksql-2.0.0-py3-none-any.whl
# dann im Code: import ksqlReines Python ohne Abhängigkeiten, ab Python 3.10. Das Paket geht nicht auf PyPI.
Aus dem Quellcode bauen
cd Data/src/Kuonen.Data.Ksql.Python
python -m unittest discover -s tests # Robustheit gegen verfälschte Antworten, EinheitenDas Paket ksql liegt im Ordner ksql/ und wird über pyproject.toml gebaut (Paketname kuonen-ksql), ohne Fremdabhängigkeiten. Es trägt „Private :: Do Not Upload“ und geht nicht auf PyPI.
Verbindungszeichenfolge
Server=localhost,1333;UID=sa;PWD=<Ihr-Kennwort>;Encrypt=yes;TrustServerCertificate=yesOhne Port gilt 1333 (der KSQL-Port).
| Schlüssel | Bedeutung |
|---|---|
Server | host,port (Vorgabeport 1333) |
Database, UID, PWD | Anmeldung |
Encrypt | yes, no, strict |
TrustServerCertificate, HostNameInCertificate | Prüfung des Zertifikats |
Connect Timeout, APP, WSID, Packet Size, ApplicationIntent | wie bei ODBC Driver 18 |
connect(…, autocommit=False, timeout=0) | Autocommit und Befehlsfrist |
Beispiel: verbinden, abfragen, Parameter, Transaktion
import ksql
conn = ksql.connect("Server=localhost,1333;UID=sa;PWD=…;Encrypt=yes;TrustServerCertificate=yes", autocommit=True)
cur = conn.cursor()
cur.execute("SELECT name FROM sys.tables WHERE name LIKE ?", ("kk_%",))
print(cur.fetchall())
conn.begin() # Transaction-Manager-Anfrage
cur.execute("UPDATE konto SET saldo = saldo - ? WHERE id = ?", (1, 7))
conn.commit()
try:
cur.execute("SELECT 1 / 0")
except ksql.DataError as e: # e.number 8134, e.sqlstate "22012"
print(e.number, e.sqlstate)Typen
| SQL- bzw. KSQL-Typ | im Treiber |
|---|---|
| Typen von SQL Server | wie PEP 249 und mssql-python; Parameter mit ksql.Param(value, sqltype, direction, name), etwa decimal(9,2) oder nvarchar(max) |
| BOOLEAN | bool |
| DECFLOAT | decimal.Decimal |
| INTERVAL, ROW, ARRAY, MULTISET | die Textklassen ksql.Interval, ksql.Row, ksql.Array, ksql.Multiset |
| time(7), datetime2(7) | ksql.Zeit, ksql.Zeitpunkt: die siebte Stelle steht in nanosecond |
| Cursor.column_types | die SQL-Typen der Spalten, KSQL-Typen mit ihrem Namen auf der Leitung |
Fehler und SQLSTATE
| Fall | Angaben |
|---|---|
| Ausnahmen nach PEP 249 | DataError (SQLSTATE-Klasse 22), IntegrityError, ProgrammingError, OperationalError … |
| Felder | number, severity, state, message, sqlstate und server_sqlstate |
| sqlstate am KSQL-Port | der Zustand der Norm vom Meldungsende |
| sqlstate an SQL Server | aus der Nummer wie die ODBC-Treiber von Microsoft; server_sqlstate ist dort None |
| cancel(), timeout | OperationalError mit HY008 bzw. HYT00 |
Unterschiede zu mssql-python bzw. DB-API 2.0 (PEP 249)
- paramstyle qmark (?); dazu @name mit einer Zuordnung oder ksql.Param(name=…).
- Cursor.callproc mit Rückgabestatus in return_value, Cursor.bulkcopy für die Massenkopie, Cursor.cancel() per ATTENTION auch aus einem anderen Faden.
- Connection.begin(), .savepoint(name), .rollback(savepoint=…) über die Transaction-Manager-Anfrage.
- Vorgabeport 1333.
Was fehlt
- Benannte Instanzen (SQL Browser), Windows- und Entra-Anmeldung, MARS, Umleitung (ENVCHANGE 20).
- Always Encrypted, Tabellenwertparameter.
- Verteilung über PyPI erst nach Entscheid von Marc (Code bleibt geschlossen).
| Restzeile | Beschreibung | Stand |
|---|---|---|
D36.7f Rest aus D36.7e | (1) `docker run` startete am 21.10. keinen Container; `pruefstand.ps1` und ein Test wie `DockerPruefstandTests` für Python und Go sind noch nicht durchgelaufen (die Läufe gingen als Bauschritte). (2) Beide: keine Windows- oder Entra-Anmeldung, kein Always Encrypted; Go: `TVP` nicht als `sql.Out`; der SQL Browser nur gegen einen nachgebauten, nicht gegen einen echten SQL-Server-Browser; die Umleitung nur gegen einen falschen Server (der KSQL-Port leitet nur bei Lesezugriff auf eine Kopie um). (3) Python liest Codepages über `codecs`: undefinierte Byte werden zum Ersatzzeichen bzw. zum Byte gleicher Nummer, SQL Server nennt dafür teils Zeichen der privaten Zone (Messung in D36.7e). (4) Verteilung: das Python-Paket trägt „Private :: Do Not Upload“, das Go-Modul `kuonen.org/ksql` braucht einen Ort, der den Importpfad ausliefert - beides erst nach Entscheid von Marc (Code bleibt geschlossen). (5) `tools/roadmap.py` braucht Python 3.10+, lokal gibt es 3.9: Status von Hand gesetzt, `nachziehen` nicht gelaufen. **Erledigt 21.10.2026:** (1) `PythonGoPruefstandTests` (Bauschritt wie `OdbcPruefstandTests`, `KUONENSQL_DOCKER_ABNAHME=1`): Python (`python:3.12-slim`, 23 Tests im Bau) und Go (`golang:1.23`, gofmt, vet, Tests im Bau) bestehen den Katalog am KSQL-Port (0 abweichend, 0 übersprungen) und an SQL Server 2025 (nur die Fälle „nur ksql“ übersprungen) - 4 von 4 grün. Dafür liegen die Go-Quellen mit LF im Arbeitsbaum (`.gitattributes` des Treibers; unter Windows scheiterte `gofmt -l` an CRLF) und beide Abbilder haben ein `Dockerfile.dockerignore`. (3) Am Orakel gemessen (je eine Datenbank in der Sortierung, alle Byte 0x80-0xFF von 12 Einzelbyte-Codepages): abweichend von den Codecs nur 874 (DB-DE, FC-FF → U+F8C1-F8C8), 1253 (AA, D2, FF → U+F8F9-F8FB), 1255 (CA → U+05BA, D9-DF, FB, FC, FF → U+F88D-F896) und 1257 (A1, A5 → U+F8FC, F8FD); der Python-Treiber liest sie so und schreibt sie zurück zu ihrem Byte (je Codepage ein Fehlerbehandler `ksql-roh-<cp>`, Test `test_undefinierte_byte_der_codepages_wie_sql_server`, vorher rot; Sabotage ohne die Tabelle rot). (5) `tools/roadmap.py` läuft mit Python 3.14: `pruefen` bestätigt die von Hand gesetzten Stände der Meilensteine (nur Datum und Fassung der Kopfzeilen wären nachzuziehen). Python lokal (3.14) 24 Tests, 3 übersprungen. Rest in D36.7h. | ✅ |
D36.7h Rest aus D36.7f | (1) Beide: keine Windows- oder Entra-Anmeldung, kein Always Encrypted; Go: `TVP` nicht als `sql.Out`; der SQL Browser nur gegen einen nachgebauten, nicht gegen einen echten SQL-Server-Browser; die Umleitung nur gegen einen falschen Server (der KSQL-Port leitet nur bei Lesezugriff auf eine Kopie um). (2) Mehrbyte-Codepages (932, 936, 949, 950): wie in D36.7e gemessen; die Byte ohne Zeichen in den Einzelbyte-Codepages 437, 850 und 1250-1258 ausser den gemessenen sind Zeichen gleicher Nummer. (3) **Entscheid von Marc:** Verteilung - das Python-Paket trägt „Private :: Do Not Upload“, das Go-Modul `kuonen.org/ksql` braucht einen Ort, der den Importpfad ausliefert (Code bleibt geschlossen). | ⬜ |
Herkunft und Lizenz
Eigenbau: übernommen sind nur die Schnittstelle des Microsoft-Treibers und das am Orakel (SQL Server 2025) gemessene Verhalten, kein Code – auch nicht aus MIT- oder BSD-lizenzierten Quellen –, damit der Treiber uneingeschränkt KuonenSQL gehört. Der Code bleibt geschlossen; eine Veröffentlichung gibt es nur als eigenständigen Fork, den Marc Kuonen selbst anlegt.
Kein Code von mssql-python; nur Standardbibliothek. Das Paket trägt „Private :: Do Not Upload“.