Database-Klasse
Die Klassen Database und QueryBuilder sowie Table und TableRow sind veraltet und sollten nicht mehr verwendet werden.
In diesem Artikel wird nur die Klasse Database behandelt. Die Klasse QueryBuilder wird in einem separaten Artikel behandelt.
Database-Klasse
Die Database-Klasse wurde verwendet um Datenbankabfragen auszuführen. Sie bestand aus zwei wesentlichen Funktionen: executeQuery und executeStatement. Die Funktion executeQuery führte eine SELECT-Datenbankabfrage mit Hilfe der QueryBuilder-Klasse aus und lieferte eine Instanz von Table zurück. Die Funktion executeStatement führte eine DELETE, INSERT oder UPDATE Datenbankabfrage aus und lieferte ein boolischen Rückgabewerte.
executeQuery
executeQuery - Bisherige Logik
Nach der alten Logik wurde zuerst eine QueryBuilder Instanz erzeugt, gefolgt von einer Database Instanz. Die Datenbankabfrage wurde mit der Funktion executeQuery ausgeführt, die eine Instanz der Table-Klasse zurückgab.
// #import "ou.sp.Library"
const query = new QueryBuilder();
query.select(["costcenter", "costcenterName"], false);
query.from("costcenter", false);
const dbUser = util.getEnvironment("OUSP_DATABASE_USER");
const dbPassword = util.getEnvironment("OUSP_DATABASE_PASSWORD");
const db = new DBConnection("odbc", "ousp", dbUser, dbPassword);
const database = new Database(db);
const table = database.executeQuery(query);
// ODER
const table = database.executeQuery(query, (column, value) => value);
const rows = table.rows.map((row) => {
// @ts-ignore
delete row.data;
return row;
});
database.close();
Da die Table-Klasse eine Update-Logik besaß, wurden die Daten in der Table-Instanz doppelt gespeichert. Dies führte zu einer unnötigen Speicherbelegung. Daher musste man die Daten aus der Table-Instanz in ein neues Array kopieren (.map()) und über den delete-Operator die data-Eigenschaft löschen.
executeQuery - Neue Logik
In der neuen Logik wird die Datenbankabfrage über die Funktion execute der Klasse SelectBuilder ausgeführt. Es findet nun keine doppelte Speicherbelegung mehr statt. Im Umkehrschluss entfällt jedoch auch die Aktualisierungsmöglichkeit. Wird eine Aktualisierung benötigt, so muss die Datenbankabfrage über die Funktion executeStatement in Kombination mit dem UpdateBuilder ausgeführt werden.
context.enableModules();
const { SelectBuilder } = require("ou.sp.SelectBuilder");
const dbUser = util.getEnvironment("OUSP_DATABASE_USER");
const dbPassword = util.getEnvironment("OUSP_DATABASE_PASSWORD");
const db = new DBConnection("odbc", "ousp", dbUser, dbPassword);
try {
const rows = SelectBuilder
.from("costcenter", db)
.select("costcenter", "string")
.select("costcenterName", "string")
.execute();
context.returnValue = JSON.stringify(rows);
} catch (error) {
context.errorMessage = error.message;
context.returnValue = -1;
} finally {
db?.close();
}
Bei Verwendung der SelectBuilder-Klasse ist es nun wichtig, den Datentyp der Spalten anzugeben.
Wird bei der select-Funktion des SelectBuilders "string" als Datentyp angegeben, so wird auch
wirklich nur der Wert, wie er in der Datenbank steht, als String zurückgegeben.
D.h. folgende Transformationen finden nicht mehr automatisch statt:
null-Werte werden nicht mehr in leere Strings umgewandelt.- Strings im
Date-Format werden nicht mehr inDate-Objekte umgewandelt. - String im
Number-Format werden nicht mehr inNumber-Objekte umgewandelt.
Diese Transformationen müssen nun explizit selbst an den zurückgegebenen Werten vorgenommen werden.
Durch die Verwendung der Datentypen in der SelectBuilder-Klasse wird nun auch das Intellisense in VSCode unterstützt. Die ausgewählten Spalten inklusive dem Datentyp werden in der Autovervollständigung angezeigt (siehe hier).
executeStatement
executeStatement - Bisherige Logik
In der alten Logik wurde die Funktion executeStatement verwendet, um eine DELETE, INSERT oder UPDATE Datenbankabfrage auszuführen. Die Funktion lieferte ein boolischen Rückgabewerte.
// #import "ou.sp.Library"
const dbUser = util.getEnvironment("OUSP_DATABASE_USER");
const dbPassword = util.getEnvironment("OUSP_DATABASE_PASSWORD");
const db = new DBConnection("odbc", "ousp", dbUser, dbPassword);
const database = new Database(db);
var insertStatement = InsertBuilder.into("costcenter")
.addRange([
["id", "1000"],
["recipient", "R0100"],
["costcenter", "K30101"],
["costcenterName", "GmbH Entwicklung Testlab"],
])
.toSQL();
const result = database.executeStatement(insertBuilder.toSQL());
executeStatement - Neue Logik
In der neuen Logik muss lediglich die Funktion executeStatement der Klasse DBConnection ausgeführt werden. Die Database-Klasse wird nicht mehr benötigt.
const { InsertBuilder } = require("ou.sp.InsertBuilder");
const dbUser = util.getEnvironment("OUSP_DATABASE_USER");
const dbPassword = util.getEnvironment("OUSP_DATABASE_PASSWORD");
const db = new DBConnection("odbc", "ousp", dbUser, dbPassword);
try {
if (!db) {
throw new Error("DBConnection is null");
}
if (db.getLastError()) {
throw new Error("DBConnection error: " + db.getLastError());
}
const insertStatement = InsertBuilder.into("costcenter")
.addRange([
["id", "1000"],
["recipient", "R0100"],
["costcenter", "K30101"],
["costcenterName", "GmbH Entwicklung Testlab"],
])
.toSQL();
const result = db.executeStatement(insertStatement);
if (!result && db.getLastError()) {
throw new Error("DBConnection error: " + db.getLastError());
}
} catch (error) {
context.errorMessage = error.message;
context.returnValue = -1;
} finally {
if (db) {
db.close();
}
}