Wie kann ich gespeicherte Prozeduren von SQL Server mit sqlAlchemy aufrufen?gespeicherte Prozeduren mit sqlAlchemy
Antwort
Engines und Verbindungen haben eine execute()
Methode, die Sie für beliebige SQL-Anweisungen verwenden können, und so auch Sessions. Zum Beispiel:
results = sess.execute('myproc ?, ?', [param1, param2])
können Sie outparam()
verwenden, um Ausgabeparameter zu erstellen, wenn Sie müssen (oder binden Parameter bindparam()
mit der isoutparam=True
Option)
Gerade Prozedur Objekt ausführen mit func
erstellt:
from sqlalchemy import create_engine, func
from sqlalchemy.orm import sessionmaker
engine = create_engine('sqlite://', echo=True)
print engine.execute(func.upper('abc')).scalar() # Using engine
session = sessionmaker(bind=engine)()
print session.execute(func.upper('abc')).scalar() # Using session
Dies funktioniert nicht mit MySQL, 'Funktion existiert nicht. " – Profpatsch
Arbeitete für mich, elegante und einfache Art, gespeicherte Prozeduren aufzurufen. Offizielle Notizen _The: Daten:' .func' Konstrukt hat nur begrenzte Unterstützung für den Aufruf Standalone "gespeicherten Prozeduren", vor allem diejenigen mit speziellen Bedenken . Finden Sie im Abschnitt: ref: 'stored_procedures' für Details zur Verwendung die' 'Callproc()' 'Methode der DBAPI-Ebene für vollständig traditionellen gespeicherten procedures._ Code für Leute wie mich:' session.execute (Funk.your_proc_name (param1, param2)) ' – Niyojan
Angenommen, Sie haben bereits eine Sitzung mit sessionmaker() erstellt, können Sie folgende Funktion verwenden:
def exec_procedure(session, proc_name, params):
sql_params = ",".join(["@{0}={1}".format(name, value) for name, value in params.items()])
sql_string = """
DECLARE @return_value int;
EXEC @return_value = [dbo].[{proc_name}] {params};
SELECT 'Return Value' = @return_value;
""".format(proc_name=proc_name, params=sql_params)
return session.execute(sql_string).fetchall()
Jetzt können Sie Ihre gespeicherte Prozedur ‚MyProc‘ mit Parametern ausführen einfach so:
params = {
'Foo': foo_value,
'Bar': bar_value
}
exec_procedure(session, 'MyProc', params)
Dies scheint anfällig für SQL-Injektion. –
Das ist in der Tat anfällig. Es ist besser, benannte Argumente mit 'execute (sql_string, params = ...) 'zu übergeben, damit die Engine die Argumentwerte ausschließen kann. Die Antwort von @Profpatsch macht das schon. –
Wie würde ich damit einen Ausgangsparameter sammeln? dh meine Aussage lautet: 'EXEC dbo.next_rowid 'dbo', 'workorder_feature', @id OUTPUT;' wie bekomme ich die ID? – roemhildtg
Von einer verzweifelten Notwendigkeit für ein Projekt von mir, ich eine Funktion geschrieben, die Prozedur Griffe gespeicherten Anrufe.
Hier gehen Sie:
import sqlalchemy as sql
def execute_db_store_procedure(database, types, sql_store_procedure, *sp_args):
""" Execute the store procedure and return the response table.
Attention: No injection checking!!!
Does work with the CALL syntax as of yet (TODO: other databases).
Attributes:
database -- the database
types -- tuple of strings of SQLAlchemy type names.
Each type describes the type of the argument
with the same number.
List: http://docs.sqlalchemy.org/en/rel_0_7/core/types.html
sql_store_procudure -- string of the stored procedure to be executed
sp_args -- arguments passed to the stored procedure
"""
if not len(types) == len(sp_args):
raise ValueError("types tuple must be the length of the sp args.")
# Construch the type list for the given types
# See
# http://docs.sqlalchemy.org/en/latest/core/sqlelement.html?highlight=expression.text#sqlalchemy.sql.expression.text
# sp_args (and their types) are numbered from 0 to len(sp_args)-1
type_list = [sql.sql.expression.bindparam(
str(no), type_=getattr(sql.types, typ)())
for no, typ in zip(range(len(types)), types)]
try:
# Adapts to the number of arguments given to the function
sp_call = sql.text("CALL `%s`(%s)" % (
sql_store_procedure,
", ".join([":%s" % n for n in range(len(sp_args))])),
bindparams=type_list
)
#raise ValueError("%s\n%s" % (sp_call, type_list))
with database.engine.begin() as connection:
return connection.execute(
sp_call,
# Don't do this at home, kids...
**dict((str(no), arg)
for (no, arg) in zip(range(len(sp_args)), sp_args)))
except sql.exc.DatabaseError:
raise
Es arbeitet mit der CALL-Syntax, so MySQL sollte wie erwartet funktionieren. MSSQL verwendet EXEC anstelle von Aufruf und etwas unterschiedlicher Syntax, denke ich. Es serverunabhängig zu machen, liegt an Ihnen, sollte aber nicht zu schwer sein.
Der einfachste Weg, um eine gespeicherte Prozedur in MySQL mit SQLAlchemy aufzurufen, ist die Methode von Engine.raw_connection()
. call_proc
erfordert den Prozedurnamen und die Parameter, die für den Aufruf der gespeicherten Prozedur erforderlich sind.
def call_procedure(function_name, params):
connection = cloudsql.Engine.raw_connection()
try:
cursor = connection.cursor()
cursor.callproc(function_name, params)
results = list(cursor.fetchall())
cursor.close()
connection.commit()
return results
finally:
connection.close()
- 1. Gespeicherte Prozeduren mit SQLAlchemy erstellen
- 2. gespeicherte SQL-Prozeduren
- 3. Gespeicherte Prozeduren und Funktionen
- 4. Gespeicherte Prozeduren PHP
- 5. Gespeicherte Prozeduren im Entitätsframework
- 6. Gespeicherte Prozeduren in Hive
- 7. Muster für gespeicherte Prozeduren?
- 8. Gespeicherte Prozeduren oder OR-Mapper?
- 9. MySQL: Ansichten vs gespeicherte Prozeduren
- 10. clr gespeicherte Prozeduren mit zwei in Parametern
- 11. Gespeicherte MySQL-Prozeduren mit Javascript-Objekten verwenden
- 12. Gespeicherte Prozeduren in Rails verwenden
- 13. EF4-Vererbung und gespeicherte Prozeduren
- 14. Spring Data und gespeicherte Prozeduren
- 15. ASP.NET MVC Aufruf gespeicherte Prozeduren
- 16. Gespeicherte Prozeduren in .SQL-Dateien
- 17. Gespeicherte Prozeduren für komplexe Abfragen
- 18. Gute Ressource für gespeicherte Prozeduren
- 19. SubSonic - Nicht-Crud Gespeicherte Prozeduren
- 20. Hilfe, gespeicherte Prozeduren und Cursor
- 21. Gespeicherte Prozeduren an SVN-Repository übergeben
- 22. Entity Framework + Sql Anywhere 11 + Gespeicherte Prozeduren
- 23. So sichern Sie gespeicherte Prozeduren in MySQL
- 24. Verschiedene gespeicherte Prozeduren parallel in EF6 ausführen
- 25. Regressionstests für gespeicherte T-SQL-Prozeduren
- 26. SQL Server - Suche durch gespeicherte Prozeduren?
- 27. Gespeicherte Prozeduren von Entity Framework und POCO
- 28. Synchronisierte gespeicherte Prozeduren zwischen zwei Datenbanken?
- 29. ADO.Net und Ausgabeparameter für gespeicherte Prozeduren
- 30. Ist LINQ langsamer als gespeicherte Prozeduren aufrufen?
Dies ist nicht datenbankunabhängig. Verwenden Sie stattdessen 'sqlalchemy.sql.text'. – Profpatsch
BTW müssen Sie 'sess.execute ('SET NOCOUNT ON')', wenn Sie auf die Zeilen zugreifen möchten von der gespeicherten Prozedur in MS SQL Server zurückgegeben. Das können Sie in einem Aufruf ausführen: 'results = sess.execute ('NOCOUNT EINSTELLEN; EXEC myproc?,?; NOCOUNT AUSSTELLEN', [param1, param2])'. –
Dies ist ein alter Thread, vielleicht ist dies etwas, das in neueren Versionen von sqlalchemy geändert wurde, aber ich musste ein Wörterbuch anstelle einer Liste für die Parameter verwenden und ": param_name" im rohen sql anstelle von "?" . So wird das obige Beispiel: 'sess.execute ('myproc: p1,: p2', {'p1': 'Wert1', 'p2': 'Wert2'})' – ThatAintWorking