Groovy

Groovy ist eine Skriptsprache, die sehr nah an Java angelehnt ist. Die Syntax ist nahezu identisch zu der Syntax von Java, mit einigen Erweiterungen. So ist es in Groovy möglich, eine typenlose Deklaration von Variablen vorzunehmen, wenn man das möchte. Intrexx verwendet Groovy hauptsächlich zur Steuerung von Prozessen, zur Durchführung von komplexen Berechnungen sowie ebenso komplexen Abfragen. Durch die Nähe zu Java ist es in den meisten Fällen möglich, Skripte aus der vielfältigen Java-Welt zu kopieren und in Groovy wiederzuverwenden. Auch hier lassen sich außerdem eigene Java Klassen einbinden. Die API bietet eine Reihe von Zugriffsmethoden auf wichtige Intrexx-Funktionalitäten und Objekte.

Allgemeine Informationen zum Thema "Scripting" finden Sie hier.

Intrexx-Standardbibliothek

Im Groovy-Skripteditor haben Sie im Bereich "Bibliotheken" Zugriff auf die Intrexx-Standardbibliothek. Wenn Sie einen Eintrag in der Bibliothek markiert haben, finden Sie unten rechts die folgenden Schaltflächen:

Beschreibung anzeigen

Hier finden Sie eine Beschreibung der aktuell ausgewählten Funktion mit Beispiel-Skript.

Link öffnen

Verlinkt auf entsprechende Seiten mit weiterführenden Informationen. Dabei wird jeweils genau die Seite mit den Klassen, Interfaces, Methoden oder Properties geöffnet, die Sie für die aktuell markierte Funktion verwenden können.

Im Folgenden finden Sie die Beschreibung der enthaltenen Funktionen.

Applikationsstruktur

Applikations-Property aus Datensatz-Objekt

Liest Applikationseigenschaften aus dem Datensatz-Objekt. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

def appInfoValue = g_record.applicationInfo.getGuid()

Liefert die GUID der Applikation, zu der der Datensatz gehört.

Snippet

def appInfoValue = g_record.applicationInfo.myMethod()

Class AbstractGroovyRecord

Datengruppen-Property aus Datensatz-Objekt

Liest Datengruppen-Eigenschaften aus dem Datensatz-Objekt. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

def dgInfoValue = g_record.dataGroupInfo.getGuid()

Liefert die GUID der Datengruppe, zu der der Datensatz gehört.

Snippet

def dgInfoValue = g_record.dataGroupInfo.myMethod()

Class AbstractGroovyRecord

Interface DataGroupInfo

Applikationsinfo

Liefert Informationen zur Applikation mit der übergebenen GUID. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

def appPropValue = app?.getGuid()

Liefert die GUID der Applikation.

Snippet

def app = g_rtCache.applications["<application GUID>"]
def appPropValue = app?.myMethod()

Interface ApplicationInfo

Kontrollen-Info

Liefert Informationen zur Kontrolle mit der übergebenen GUID. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

def ctrlInfo = ctrl?.getPageGuid()

Liefert die GUID der Seite, auf der sich die Kontrolle befindet.

Snippet

def ctrl = g_rtCache.controls["<control GUID>"]
def ctrlInfo = ctrl?.myMethod()

Interface ControlInfo

Datengruppen-Info

Liefert Informationen zur Datengruppe mit der übergebenen GUID. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

liefert die GUID der Datengruppe:

def dgInfo = dg?.getGuid()

Snippet

def dg = g_rtCache.dataGroups["<data group GUID>"]
def dgInfo = dg?.myMethod()

Interface DataGroupInfo

Datenfeld-Info

Liefert Informationen zum Datenfeld mit der übergebenen GUID. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

Liefert die GUID des Datenfeldes:

def fldInfo = fld?.getGuid()

Snippet

def fld = g_rtCache.fields["<data field GUID>"]
def fldInfo = fld?.myMethod()

Interface FieldInfo

Referenz-Info

Liefert Informationen zur Referenz mit der übergebenen GUID. Ersetzen Sie im Beispiel-Skript "myMethod()" mit der gewünschten Methode.

Beispiel

Liefert die GUID der Referenz:

def refInfo = ref?.getGuid()

Snippet

def ref = g_rtCache.references["<reference GUID>"]
def refInfo = ref?.myMethod()

Interface ReferenceInfo

Application-API

JSON-Antwort (für Groovy-Endpoints)

Das folgende Snippet kann in Groovy-Endpoints verwendet werden. Es unterscheidet sich von dem vorhandenen Beispiel durch das Fehlen des json()-Aufrufs und vor allem der Fehlerbehandlung. Letztere funktioniert im Application-API nicht, weil sie vom Framework übernommen wird.

Snippet

// write a JSON object that is defined in Groovy
// using maps, lists, strings, numbers, ...
writeJSON("person": [
	givenName: "Donald",
	lastName: "Duck",
	age: 87,
	nephews: ["Huey", "Dewey", "Louie"]
])

JSON-Body aus Request parsen (Groovy-Endpoints)

Mit dem folgenden Codeschnipsel kann JSON-Content, der im Body eines HTTP-Requests übertragen wurde, geparst werden.

Snippet

def json = g_json.parse(request)

Zugriff auf Pfadvariablen

Mit dem folgenden Codeschnipsel kann auf Pfadvariablen von Groovy-Endpoints zugegriffen werden. Die Werte haben den in der Konfiguration des Endpoints definierten Datentyp.

"g_pathVariables" steht auch in Groovy-Skripten von Prozessen zur Verfügung. Der Wert kann allerdings null sein, falls der Prozess nicht durch einen Aufruf des Application-APIs getriggert wurde.

Beispiel:

Prüfen, ob Pfadvariablen vorhanden sind

if (g_pathVariables) {
        // do something
}

Snippet

def pathValue = g_pathVariables?.nameOfThePathVariable

Zugriff auf Query-Variablen

Mit dem folgenden Codeschnipsel kann auf Query-Variablen von Groovy-Endpoints zugegriffen werden. Die Werte haben den in der Konfiguration des Endpoints definierten Datentyp. "g_queryParameters" steht auch in Groovy-Skripten von Prozessen zur Verfügung. Der Wert kann allerdings null sein, falls der Prozess nicht durch einen Aufruf des Application-APIs getriggert wurde.

Beispiel:

Prüfen, ob Query-Variablen vorhanden sind

if (g_queryParameters) {
        // do something
}

Snippet

def queryValue = g_queryParameters?.nameOfTheQueryParameter

Setzen von HTTP-Status-Code bei Exception

Snippet

try
{
	writeJSON("person": [
		givenName: "Donald",
		lastName: "Duck",
		age: 87,
		nephews: ["Huey", "Dewey", "Louie"]
	])

	throw new Exception("Let's test catching an exception.")
}
catch (e)
{
	g_syslog.error("Exception has been caught.", e)

	response.reset()
	response.setStatus(406)
}

Class GroovyHttpServletResponse

Setzen von HTTP-Status-Code durch Exception

Snippet

import de.uplanet.net.http.HttpBadRequestException

throw new HttpBadRequestException("Set HTTP status code by exception")

writeJSON("success": true)

Class HttpErrorException

Sprachkonstanten

Alle im Intrexx-Standard verwendeten Textelemente sind in den globalen Sprachkonstanten definiert. Allgemeine Informationen zu diesem Thema finden Sie hier.

Zugriff auf globale Sprachkonstante

Liefert den Wert, den die globale Sprachkonstante in der Portal-Standardsprache hat. Ersetzen Sie im Beispiel-Skript "PORTAL_CONST_NAME" mit dem Namen der gewünschten Sprachkonstante.

Beispiel

def strValue = g_i18n.BUTTON_NEXT

Liefert "Weiter" (Beschriftung der "Weiter"-Schaltfläche, die Sie in vielen Dialogen finden, in deutsch, der Standardsprache des Beispielportals).

Snippet

def strValue = g_i18n.PORTAL_CONST_NAME

Class GroovyLanguageConstants

Zugriff auf globale Sprachkonstante in einer bestimmten Sprache

Liefert den Wert, den die globale Sprachkonstante in einer bestimmten Portalsprache hat. Ersetzen Sie im Beispiel-Skript "PORTAL_CONST_NAME" mit dem Namen der gewünschten Sprachkonstante.

Beispiel

liefert den Wert, den die globale Sprachkonstante in der englischen Spracheinstellung hat.

def lang = g_i18n.language("en")

Snippet

def lang = g_i18n.language("language code")
def strValue = lang.PORTAL_CONST_NAME

Class GroovyLanguageConstants

Zugriff auf Sprachkonstante einer Applikation

Liefert den Wert, den die Applikations-Sprachkonstante in der Portal-Standardsprache hat. Ersetzen Sie im Beispiel-Skript "APP_CONST_NAME" mit dem Namen der gewünschten Sprachkonstante.

Snippet

def app = g_i18n.application("<application GUID>")
def strValue = app.APP_CONST_NAME

Class GroovyLanguageConstants

Zugriff auf Sprachkonstante einer Applikation in einer bestimmten Sprache

Liefert den Wert, den die Applikations-Sprachkonstante in einer bestimmten Portalsprache hat. Ersetzen Sie im Beispiel-Skript "APP_CONST_NAME" mit dem Namen der gewünschten Sprachkonstante. Als Sprachcode setzen Sie z.B. "en" für englisch ein.

Snippet

def app = g_i18n.application("<application GUID>")
def strLang  = app.language("<language code>")
def strValue = strLang.APP_CONST_NAME

Class GroovyLanguageConstants

Imports

Intrexx AccessController

Klasse, mit der geprüft werden kann, ob die durch Zugriffsanfragen basierend auf der aktuell gültigen Sicherheitsrichtlinie zugelassen oder abgelehnt werden sollen.

Snippet

import de.uplanet.lucy.server.security.IxAccessController

Class IxAccessController

IFilter

Snippet

import de.uplanet.util.filter.IFilter

Interface IFilter

WorkflowException

Fehlerbehandlung von Prozessen.

Snippet

import de.uplanet.lucy.server.workflow.WorkflowException

Class WorkflowException

Objekte im Groovy-Kontext

PageActionHandler und PageRenderingHandler

g_appGuid

g_handlerGuid

g_page

g_action

g_binding

Zugriff auf alle Bindings, die zum Zeitpunkt des Zugriffs zur Verfügung stehen.

Snippet

g_binding

Class GroovyBinding

g_context

Der aktuelle Verarbeitungskontext.

Snippet

g_context

Interface IProcessingContext

g_ctx

BPEE Verarbeitungskontext - nur verfügbar im Webservicekontext.

Snippet

g_ctx

g_dataCollection

Die Seite, die als Portlet dient bzw. die DataCollection, die dann geladen wird.

Beispiel 1

Zugriff auf Tabelle:

g_dataCollection.getDataRange("<GUID TABLERECORDS>").getNumberOfRecords() > 0

Beispiel 2

Zugriff auf einen Datensatz:

g_dataCollection.getValueHolder(String p_guid)

Snippet

g_dataCollection

Class GroovyDataCollection

g_dbConnections

Zugriff auf verfügbare Datenbankverbindungen.

Snippet

//System connection 
def conn = g_dbConnections.systemConnection

//External data connection
def connForeign = g_dbConnections["CONNECTION_NAME"]

Class GroovyContextConnections

g_dbQuery

Objekt zur Generierung und Ausführung von Datenbankabfragen. An Stelle von "executeAndGetScalarValue" wird die Verwendung der typisierten Methoden (z.B. executeAndGetScalarValueIntValue, executeAndGetScalarStringValue) empfohlen.

Snippet

//Build a prepared statement
def stmt = g_dbQuery.prepare(conn, "SELECT * FROM MYTABLE WHERE LID = ?")
stmt.setInt(1, iLid)
stmt.executeQuery()
stmt.close()

//Query of a single value
def iMax = g_dbQuery.executeAndGetScalarValue(conn, "SELECT MAX(LID) FROM MYTABLE", 0)

Class DbQuery

g_defaultLanguage

Dieser String enthält die Sprache des Portals, die in den Portaleigenschaften / Ländereinstellungen / Sprachen als Standardsprache ausgewählt ist.

Mit println(g_defaultLanguage) kann z.B. der entsprechende Sprachcode in der Prozess-Logdatei ausgegeben werden (z.B. "de" oder "en").

Beispiel:

assert g_defaultLanguage == 'en' : 'This script requires default language en.'

Snippet

g_defaultLanguage

g_defaultLocaleId

Dieser String enthält das standortabhängige Format des Portals, das in den Portaleigenschaften / Ländereinstellungen / Format als Standardeinstellung ausgewählt ist.

Mit println(g_defaultLocaleId) kann z.B. der entsprechende Sprachcode in der Prozess-Logdatei ausgegeben werden (z.B. "de" oder "en").

Snippet

g_defaultLocaleId

g_dgFile

Der Groovy-Handler ist in Grooy-Workflow-Actions verwendbar und in Groovy-Handlern der Application API. Er kann über "g_dgFile" aufgerufen werden.

Kopieren von Dateien

Beispiele:

g_dgFile.copy(guid: "DF GUID", id: "recordID", file: "/tmp/test.txt")
g_dgFile.copy(guid: "DF GUID", id: "recordID", files: ["/tmp/test.txt", "tmp/test1.txt"])
g_dgFile.copy(guid: "DF GUID", id: "recordID", file: [ file: "tmp/test.txt", name: "name.txt", contentType: "application/json", mode: "appendFirst"])
g_dgFile.copy(guid: "DF GUID", id: "recordID", files: [ file: "tmp/test.txt", name: "name.txt", contentType: "application/json", mode: "appendFirst"], [ file: "tmp/test1.txt", name: "name1.txt", contentType: "application/json", mode: "append"])
g_dgFile.copy(guid: "DF GUID", id: "recordID", file: "tmp/test.txt", name: "name2.txt", replaceName: "name.txt", contentType: "application/json", mode: "replace")
g_dgFile.copy(guid: "DF GUID", id: "recordID", file: "tmp/test.txt", name: "name2.txt", pos: 1, contentType: "application/json", mode: "replace")
g_dgFile.copy(guid: "DF GUID", id: "recordID", file: "tmp/test.txt", name: "name2.txt", fileId: 1, contentType: "application/json", mode: "replace")
g_dgFile.copy(guid: "DF GUID", id: "recordID", files: [[file: "tmp/test.txt", name: "name2.txt", replaceName: "name.txt", contentType: "application/json", mode: "replace"], [file: "tmp/test1.txt", name: "name3.txt", contentType: "application/json", mode: "append"], [name: "file.txt", mode: "delete"])

Parameter:

guid: Datenfeld-GUID des Dateifeldes

id: Record Id, (für zusammengesetze PKs Intrexx-Serialisierungsformat (id= 1, lang= de) oder separat für jeden PK)

id_%feldname%: Wert für Primary-Key-Feld mit Namen

replaceMode: true/false (default: false) Wenn "true" werden alle vorhandenen Dateien ersetzt

triggerWorkflow: true/false (default: false) Wenn "true" wird bei Änderung der Workflow getriggert

file: Kann Typ "String", "File", "Path", "FileMap" oder ein FileInformation-Objekt sein

mode: append(default), appendFirst, replace, delete

file: Die Quelldatei, Type "String", "Path", "File", FileInformation (mode != delete)

Für mode: append/appendFirst

name: Der Name der Datei (muss eindeutig sein, neu mit der API)

Für mode "replace" entweder fileId, replaceName, oder pos mitgeben - s. folgende:

fileId: Die Datei mit der entsprechenden id soll ersetzt werden

replaceName: Die Datei mit dem entsprechenden Namen soll ersetzen werden

pos: Die Datei an der entsprechenden Position soll ersetzt werden (erste Datei hat Position 0)

Wenn mode "delete" einer von entweder fileId, name, oder pos mitgeben - s. folgende:

fileId: Die Datei mit der entsprechenden id soll ersetzt werden

name: Die Datei mit dem entsprechenden Namen soll ersetzen werden

pos: Die Datei an der entsprechenden Position soll ersetzt werden (Erste Datei ist position 0)

files: Array of file, Strings (Pfad zu Datei), java.io.File, java.io.Path, FileInformation

Verschieben von Dateien (wie Kopieren von Dateien)

g_dgFile.move(guid: "DF GUID", id: "recordID", file: "/tmp/test.txt", deleteAlways: true)
g_dgFile.move(guid: "DF GUID", id: "recordID", files: ["/tmp/test.txt", "tmp/test1.txt"])
g_dgFile.move(guid: "DF GUID", id: "recordID", file: "tmp/test.txt", name: "name.txt", contentType: "application/json", mode: "appendFirst")
g_dgFile.move(guid: "DF GUID", id: "recordID", files: [[file: "tmp/test.txt", name: "name.txt", contentType: "application/json", mode: "appendFirst"], [file: "tmp/test1.txt", name: "name1.txt", contentType: "application/json", mode: "append"], [ pos: 2, mode: "delete"]])
g_dgFile.move(guid: "DF GUID", id: "recordID", file: "tmp/test.txt", name: "name2.txt", replaceName: "name.txt", contentType: "application/json", mode: "replace")
g_dgFile.move(guid: "DF GUID", id: "recordID", files: [[file: "tmp/test.txt", name: "name2.txt", replaceName: "name.txt", contentType: "application/json", mode: "replace"], [file: "tmp/test2.txt", name: "name3.txt",  contentType: "application/json", mode: "append"]])

Hat zusätzlichen Parameter "deleteAlways" (default: "false")

Wenn deleteAlways=true wird die Quelldatei auch gelöscht, wenn ein Fehler beim Verschieben auftritt.

Bei "move" ist FileInformation als Quelldatei nicht zulässig.

Löschen von Dateien

g_dgFile.delete(guid: "DF GUID", id: "recordID")
g_dgFile.delete(guid: "DF GUID", id: "recordID", fileId: 1)
g_dgFile.delete(guid: "DF GUID", id: "recordID", name: "test.txt")
g_dgFile.delete(guid: "DF GUID", id: "recordID", pos: 1)

Parameter:

guid: Datenfeld GUID des Dateifeldes

id: Record Id, (Für zusammengesetze PK's Intrexx serialisierungs Format (id= 1, lang= de) oder separat für jeden PK

id_%feldname%: Wert für Primary Key feld mit namen.

Ohne fileId, name oder pos werden alle Dateien gelöscht

fileId: Id der zu löschenden Datei.

name: Name der zu löschenden Datei

pos: Position der zu löschenden Datei (0 = Erstedatei)

Dateien holen

g_dgFile.getFile(guid: "DF GUID", id: "recordID", fileId: 1) => Path
g_dgFile.getFile(guid: "DF GUID", id: "recordID", pos: 1) => Path
g_dgFile.getFile(guid: "DF GUID", id: "recordID", name: "test.txt") => Path
g_dgFile.getFileInformation(guid: "DF GUID", id: "recordID", fileName: "test.txt") => de.uplanet.lucy.server.businesslogic.util.FileInformation
g_dgFile.getFiles(guid: "DF GUID", id: "recordID", count: 3) => List<Path> (maximum number 3)
g_dgFile.getFilesInformation(guid: "DF GUID", id: "recordID", count: 3) => List<de.uplanet.lucy.server.businesslogic.util.FileDefinition>

Beispiel für das Kopieren von Dateien mit Mehrfach-PK

def sourceFile = g_dgFile.getFile(guid:"D6A9628243660FDB691B70E02CD64E860F98A82F", id_STRID: strArticleId, id_STR_LANG: g_language, pos: 0)
     if(sourceFile != null)
     {
         g_dgFile.copy(guid: "AC4DFDF9C27F23E721EAED68C276831962885FC3", id: strNewGuid, file: sourceFile, mode: "appendFirst")
     }

Anmerkung zu de.uplanet.lucy.server.businesslogic.util.FileDefinition und den Methoden "getFileInformation" bzw. "getFilesInformation"

Für Kopieren kann das FileInformation Object als Quelldatei-Parameter verwendet werden. Damit können Dateien von einem anderen Datensatz kopiert werden.

Beispiel:

def src = g_dgFile.getFileInformation(guid: "GUID1", id: "1", pos: 0)
g_dgFile.copy(guid: "GUID1", id: 2, file: src, mode: "appendFirst") // Copies first file of record with id 1 to first position of record with id 2.
def src = g_dgFile.getFilesInformation(guid: "GUID1", id: "1")
g_dgFile.copy(guid: "GUID1", id: 2, replaceMode: true, files: src) // Copies all files from record with id 1 and replaces the files from record with id 2.

Class GroovyDGFileHelper

g_dirWorkflow

Nur in Prozessen verfügbar - liefert das Verzeichnis des aktuellen Prozesses. Auf dieses Verzeichnis sollte ausschließlich lesend zugegriffen werden.

Snippet

g_dirWorkflow

Class File

g_dirWorkflowTmp

Zugriff auf das temporäre Arbeitsverzeichnis des Prozesses auf dem Server. Das Verzeichnis ist für alle nachfolgenden Prozess-Elemente verfügbar, bis der Prozess beendet ist.

Snippet

g_dirWorkflowTmp

Class File

g_event

Nur in Prozessen verfügbar - beinhaltet das Ereignis, das den aktuellen Prozess auslöste. Zu beachten ist, dass Vergleiche auf das aktuelle Event (s. Skript-Beispiel) immer auf die Interfaces und nie auf die konkreten Klassen auszuführen sind.

Snippet

import de.uplanet.lucy.server.workflow.event.*

if (g_event instanceof IGlobalTimerWorkflowEvent)
//Insert script that responds to a timerevent here.

Interface IWorkflowEvent

g_exception

Enthält die Exception, die aufgefangen wurde. Diese muss untersucht und dann entschieden werden, ob sich der ErrorHandler sich dafür zuständig erklärt. Häufige Kriterien hierfür sind:

  • Die Exception wurde von einer Exception eines bestimmten Typs ausgelöst.

  • Die Exception wurde von einer Exception eines bestimmten Typs ausgelöst und die Fehlermeldung hat einen bestimmten Inhalt (beginnt z.B. mit "my-custom-prefix:").

Vgl. auch readme.txt und handler_50_xxx.groovy.example im Portalverzeichnis internal/system/vm/html/errorhandler/custom.

Snippet

g_exception

Class ExceptionUtil

g_fileScript

Pfad zum aktuellen Skript als java.io.File. Dieses Objekt steht im Webservice-Umfeld nicht zur Verfügung.

Beispiel

println("Executing " + g_fileScript.path)

Snippet

g_fileScript

Class File

g_guidSelf

Enthält die GUID des aktuellen Prozess-Objekts (Aktion, Bedingung oder Ereignisbehandler). Diese Variable ist nur in Prozessen definiert.

Snippet

g_guidSelf

g_guidWf

Enthält die GUID des aktuellen Prozesses. Diese Variable ist nur in Prozessen definiert.

Snippet

g_guidWf

g_i18n

Zugriff auf Sprachkonstanten.

Snippet

g_i18n

Class GroovyLanguageConstants

g_json

Das Objekt g_json implementiert ein paar einfache Anwendungsfälle im Zusammenhang mit JSON:

  • Parsen von JSON-Text

  • Serialisieren von Objekten als JSON-Text

  • Erzeugen von JSON-Objekten

  • Senden von GET-Requests und parsen der Response als JSON

Beispiel für das Parsen von JSON

def strJson = '''{"person": {
	"givenName": "Donald",
	"lastName": "Duck",
	"age": 87,
	"nephews": ["Huey", "Dewey", "Louie"]
}}'''

def parsed = g_json.parse(strJson)

println(parsed.person.lastName)
println(parsed.person.givenName)

Snippet

g_json

Class GroovyJSON

g_language

Dieser String enthält die Sprache des aktuellen Benutzers, die in seinem Konto in der Benutzerverwaltung unter "Organisation" festgelegt ist.

Mit println(g_language) kann z.B. der entsprechende Sprachcode in der Prozess-Logdatei ausgegeben werden (z.B. "de" oder "en").

Snippet

g_language

g_localeId

Dieser String enthält das Format des aktuellen Benutzers, das in seinem Konto in der Benutzerverwaltung unter "Organisation" festgelegt ist.

Mit println(g_localeId) kann z.B. der entsprechende Sprachcode in der Prozess-Logdatei ausgegeben werden (z.B. "de" oder "en").

Snippet

g_localeId

g_log

Schreibt einen Eintrag in die zum Ausführungskontext des Skripts gehörige Logdatei.

Snippet

g_log.info("Process finished without errors.")
g_log.error("An error has occurred.")

Logging

g_om

Objekt für den Zugriff auf die Benutzerverwaltung.

Snippet

g_om

Intrexx bietet eine Vielzahl an erweiterten Möglichkeiten der prozessgesteuerten Benutzerverwaltung. Mit Zugriffsobjekten und –methoden in Groovy-Aktionen können u.a. neue Benutzer angelegt und verwaltet werden. Als Einstiegspunkt für die Organisationsstruktur eines Portals in Prozessen dient das global verfügbare und bereits initialisierte Objekt g_om. Damit können grundlegende UseCases wie z.B. das Suchen eines Benutzers oder das Generieren eines neuen Passworts umgesetzt werden. Diese Methoden sind wie "normale" Methodenaufrufe zu verwenden. Hier finden Sie alle zur Verfügung stehenden Methoden in unseren JavaDocs:

Class GroovyOrgBuilder

Class GroovyOrgBuilder

Class GroovyOrgStructureWrapper

Beispiele

//Change password of the passed user
g_om.changePassword(g_session.user, "SECRET")
//Generate and send a new password to the passed user
g_om.generateAndSendPassword(g_session.user)
//Search a user by means of a GUID
def user = g_om.getUser("C10579449052F85D9C3FF3C2824348FCE020A22E")
//Classify a list of GUIDs
//A list of GUIDs or a text can be passed, e.g. the content of a data field of a multiple selection element
def guids = ["AE39A904172F5867DA23DE289D1D6B7967420DC0", "6AA80844C3C99EF93BF4536EB18605BF86FDD3C5", g_session.user.guid]
			 
def classified = g_om.classifyGuids(guids) //guids = Collection or String

//Results in a map with categorized GUIDs, e.g. {containers=[], users=[7312F993D0DA4CECCA9AE5A9D865BE142DE413EA], 
//      unclassified=[AE39A904172F5867DA23DE289D1D6B7967420DC0], 
//      sets=[6AA80844C3C99EF93BF4536EB18605BF86FDD3C5]}
println(classified)

//filter on object types
println(classified.users)
println(classified.containers)
println(classified.sets)
println(classified.unclassified)

//number of non anonymous sessions
g_om.getNonAnonymousActiveSessionCount()

Darüber hinaus verfügt das Objekt g_om noch über einige Methoden, die in Verbindung mit einer Closure aufgerufen werden, um weiterführende Aktionen zu realisieren. Zu erkennen sind diese Methoden an dem in den JavaDocs angegebenen Parameter vom Typ groovy.lang.Closure, z.B. GroovyOrgBuilder.createUser(groovy.lang.Closure p_closure). Innerhalb einer solchen Closure können Methoden jener Klasse aufgerufen werden, die in den jeweiligen hinterlegten Links dokumentiert sind. Folgende Methoden sind mit einer Closure aufrufbar:

g_om.createUser(groovy.lang.Closure p_closure)

Damit kann ein neuer Intrexx-Benutzer angelegt werden. Dabei können innerhalb der Closure die folgend aufgelisteten Propertys gesetzt werden, wobei die Propertys name und loginName erforderlich, die restlichen optional sind.

Property

Datatype

birthday

Date

city

String

container

Object

country

String

defaultLanguage

String

defaultLayout

String

deletable

boolean

deleted

boolean

description

String

disabled

boolean

dn

String

emailBiz

String

emailHome

String

employeeNo

String

enterDate

Date

externalLogin1

String

externalLogin2

String

externalLogin3

String

externalPassword1

String

externalPassword2

String

externalPassword3

String

externalPrimaryGroupId

int

female

boolean

firstName

String

fullName

String

gender

int

guid

String

id

int

internalUsn

int

lastName

String

loginDomain

String

loginDomainLwr

String

loginName

String

loginNameLwr

String

male

boolean

memberOf

Collection<?>

middleName

String

name

String

password

String

passwordChangedDate

Date

passwordExpires

boolean

passwordHash

String

phoneBiz

String

phoneFax

String

phoneHome

String

phoneMobileBiz

String

phoneMobileHome

String

phonePager

String

poBox

String

postalCode

String

priority

int

rplGuid

String

salt

String

showUser

boolean

state

String

street

String

timeZone

TimeZone

title

String

userImageContentType

String

userImageFile

File

userImageMetaInfo

String

Bei den Propertys "container" und "memberOf" können wahlweise die GUIDs, die eindeutigen Namen der Container, Rollen, Sets oder Gruppen und Pfade in der Organisationsstruktur angegeben werden.

Beispiel

g_om.createUser 
{
    name      	= "g_om"
    loginName 	= "g_om"
    birthday  	= now()
    container 	= "0F8233A39555B28F6B32CFFE666A5151E1F41AD3"
    memberOf 	= ["8FBF199EE826D16742F0F131E0AB4CF0E6BA6CA3", "Benutzer"]
    emailBiz  	= "g_om@example.org"
    guid      	= newGuid()
    male      	= true
}
g_om.getLoggedOnUsers(boolean p_bIncludeAnonymous, groovy.lang.Closure p_closure)

Gibt alle aktuell eingeloggten Benutzer aus. Über p_bIncludeAnonymous kann angegeben werden, ob anonyme Sessions in das Ergebnis mitaufgenommen werden sollen. Über die Groovy-Closure können weitere Filterungen vorgenommen werden.

Beispiel

def userOnline = g_om.getLoggedOnUsers(false) {
    it.containerGuid == "9DABA9EE4F9F6F771704F75C79A1C3A124FF399C"
}
g_om.getLoggedOnUsersDistinct(groovy.lang.Closure p_closure)

Gibt alle aktuell eingeloggten, nicht-anonymen Benutzer ohne doppelte Vorkommen aus. Über die Groovy-Closure können analog zu g_om.getLoggedOnUsers(boolean p_bIncludeAnonymous, groovy.lang.Closure p_closure) weitere Filterungen vorgenommen werden.

g_om.withOrgStructure(groovy.lang.Closure p_closure)

Erlaubt das Arbeiten auf der Organisationsstruktur eines Portals.

Beispiel

g_om.withOrgStructure {
    println("9DABA9EE4F9F6F771704F75C79A1C3A124FF399C".isUser())
}

Folgende Methoden sind innerhalb der OrgStructure-Closure aufrufbar:

  • isUser()

  • isSet()

  • isGroup()

  • isDistList()

  • isContainer()

  • isOrganization()

  • isOrgUnit()

g_om.getMembers(java.lang.Object,boolean)

Erzeugt eine Liste der GUIDs aller Benutzer, die zu einer bestimmten oder mehreren Gruppen gehören.

Beispiel

def userGuids = g_om.getMembers(["00A303288634E154D755732E478F2BE0D9AD36F7"], false)*.guid

"00A303288634E154D755732E478F2BE0D9AD36F7" ist die aus dem Modul "Benutzer" kopierte GUID der Gruppe. Mehrere Gruppen-GUIDs bzw. Set-GUIDs sind möglich.

Class GroovyOrgBuilder

g_parameter

Objekt für den Zugriff auf Parameter.

Beispiel

def customerid = g_parameter.get("customerid")

Snippet

g_parameter

Class GroovyParameter

Seiten-Eigenschaften - Reiter "Parameter"

g_permissions

Diese Klasse dient der Prüfung und Abfrage von Berechtigungen. Die Verwendung wird in der Vorlage "JSON-Antwort" für den dortigen Anwendungsfall gezeigt. checkPermission(Permission) und check(Closure) prüfen, ob die gewünschten Berechtigungen gewährt werden. Andernfalls wird eine java.security.AccessControlException geworfen. hasPermission(Permission) und has(Closure) funktionieren analog, liefern jedoch einen boolean-Wert, der angibt, ob die angeforderten Berechtigungen gewährt werden oder nicht. Die Closure-Methoden delegieren an das o.g. GroovyIxAccessControllerDelegate-Objekt und verlangen eine Map, die den Objektnamen Aktionen zuweist. Beispiel: Prüfe Zugriffsberechtigung an der Applikation <application GUID>, Leseberechtigungen an der Datengruppe <data group GUID> sowie Schreibberechtigungen an der Datengruppe <another data group GUID>.

Beispiel

g_permissions.check {
    application("<application GUID>": "access")
    dataGroup("<data group GUID>": "read", "<another data group GUID>": "write,create")
}

Snippet

g_permissions

Class GroovyIxAccessController

Class GroovyIxAccessController.GroovyIxAccessControllerDelegate

Klassen aus de.uplanet.lucy.security.permission

g_portal

Objekt für den Zugriff auf Portaleigenschaften wie Name oder Base-URL.

Beispiel

def strUrl = g_portal.baseUrl

Snippet

g_portal

Class GroovyPortalInfo

g_portlet

Zugriff auf das jeweilige Portlet, das gefiltert werden soll (im Portlet-Pool oder beim Rendern des Portlets).

Snippet

g_portlet

Class GroovyPortlet

g_portletPool

Zugriff auf den Portlet-Pool, der gefiltert werden soll (Collection von Portlets), zum einen wirklich im Portlet-Pool und zum anderen beim Rendern der Portlets.

Snippet

g_portletPool

Class GroovyPortlet

g_record

Zugriff auf den aktuellen Datensatz.

Beispiel

def iLid = g_record["0D8F13B2B43B128DB23C0C1CC8C5DC1143C9D826"].value // datafield (PK) (S) ID

Snippet

g_record

Class ReadOnlyGroovyRecord

g_rwRecord

Lesender und schreibender Zugriff auf den aktuellen Datensatz. Nur verfügbar innerhalb von Groovy-PageActionHandlern.

Beispiel

def iLid = g_rwRecord["0D8F13B2B43B128DB23C0C1CC8C5DC1143C9D826"].value // datafield (PK) (S) ID

Snippet

g_rwRecord

Class ReadWriteGroovyRecord

g_request

Zugriff auf den aktuellen Request, z.B. Auslesen von Requestvariablen im Prozess. Diese Variable ist nur definiert, wenn das Skript von einem Web-Request aufgerufen wurde.

Snippet

g_request

Class GroovyServerBridgeRequest

g_rtCache

RtCache - Zugriff auf Datengruppen, Applikationen, Felder etc.

Beispiel

//Find all data groups of the application with the GUID 68C97BF4D89E8466BDE08AF03A4EF95F5B23AF72
def datagroups = g_rtCache.dataGroups.findAll {it.appGuid == "68C97BF4D89E8466BDE08AF03A4EF95F5B23AF72"}

Snippet

g_rtCache

Class GroovyRtCache

g_session

Die aktuelle Session.

Beispiel

//Name of the currently logged-in user
def strUserName = g_session?.user?.name

Snippet

g_session

Class GroovySession

g_sharedState

Shared State, in den Variablen und Werte geschrieben und wieder ausgelesen werden können.

Beispiel

//write variable to shared state
g_sharedState.meineVariable = "my value"
//read variable from shared state
def strValue = g_sharedState.myVariable

Snippet

g_sharedState

Class SharedState

g_sourcePage

Liefert z.B. GUID, Applikations-GUID oder RecID der Seite, die Parameter sendet.

Beispiel

def strMyPage = g_sourcePage.getPageGuid()
g_log.info(strMyPage)

Snippet

g_sourcePage

Class GroovySourcePage

g_springApplicationContext

Spring Anwendungskontext

Snippet

g_springApplicationContext

Interface ApplicationContext

g_store

Das folgende Skript zeigt, wie g_store.ephemeral verwendet werden kann, um ein systemweit abrufbares, flüchtiges Name-Value-Paar zu setzen und an anderer Stelle wieder zu konsumieren.

Snippet

//------------------------------ supplier side ------------------------------
// initially no value exists for myUniqueKey
assert g_store.ephemeral.contains('myUniqueKey') == false

// insert an ephemeral value (does not survive portal service restart)
g_store.ephemeral.put('myUniqueKey', 'foo')

// now the value exists
assert g_store.ephemeral.contains('myUniqueKey') == true


//------------------------------ consumer side side ------------------------------
assert g_store.ephemeral.contains('myUniqueKey') == true

// get the ephemeral value
def val = g_store.ephemeral.remove('myUniqueKey')
assert val == 'foo'

// no the value does not exist anymore
assert g_store.ephemeral.contains('myUniqueKey') == false

Class GroovyInternalStore

g_sysDg

Mit diesem Objekt können Werte aus einer Systemdatengruppe ausgelesen werden.

Beispiel

//Specify the Guid of the system data field as GUID
def strValue            = g_sysDg['C1BFDD165EBFD0713D306D3E2B124E80021E613F']
def strValueByFieldGuid = g_sysDg.getValueByFieldGuid('C1BFDD165EBFD0713D306D3E2B124E80021E613F')
def vhByFieldGuid       = g_sysDg.getValueHolderByFieldGuid('C1BFDD165EBFD0713D306D3E2B124E80021E613F')

Snippet

g_sysDg

Class GroovySystemDataGroup

g_syslog

Loggingobjekt zur Ausgabe in die Log-Datei des Portals (portal.log).

Snippet

g_syslog.info("my message in portal log.")

g_ws

Objekt zum expliziten Aufruf eines Webservices. Nur verfügbar bei Skripts, die bei einem Webservice hinterlegt sind.

Snippet

g_ws.invoke()

Closures

Die vordefinierten Closures können wie Funktionen aufgerufen werden.

checkInterrupted()

Prüft, ob entweder

  • der Thread, der den Prozess ausführt, von einem anderen Thread eine Unterbrechungsanforderung erhalten hat oder

  • der für den Prozess eingestellte Timeout überschritten wurde.

Verwenden sie diesen Aufruf in Skripts, die sich in solchen Fällen kooperativ verhalten sollen.

Snippet

checkInterrupted()

Class CheckInterruptedClosure

createTemporaryDirectory()

Erzeugt ein temporäres Arbeitsverzeichnis, dass bis zum Ende der Abarbeitung des Prozesses verfügbar ist.

Snippet

createTemporaryDirectory()

Class CreateTemporaryDirectoryClosure

currentTimestamp()

Diese Closure liefert den Zeitstempel der aktuellen Transaktion. Dieser Wert bleibt bis zum Verarbeitungsende dieser Transaktion unverändert.

Beispiel

def dtNow = currentTimestamp()

Snippet

currentTimestamp()

Class CurrentTimestampClosure

getStackTraceString()

Liefert den vollständigen StackTrace eines aufgetretenen Fehlers als String zurück. Die Closure "getStackTraceString()" benötigt einen Parameter vom Typ java.lang.Throwable, also eine Exception.

Snippet

try
{
    trySomething()

}
catch (e)
{
    def strStackTrace = getStackTraceString(e)

    doSomethingWithStackTrace(strStackTrace)
}

Class CreateStackTraceStringClosure

newGuid()

Erzeugt eine neue GUID.

Snippet

newGuid()

Class NewGuidClosure

now()

Erzeugt ein neues Datum (Jetzt) als Timestamp oder als ValueHolder.

Snippet

now()

Class NowClosure

parseGuids(strText)

Parst GUIDs aus dem übergebenen String (z.B. eine Pipe-getrennte Liste) und liefert ein TreeSet mit den gefundenen GUIDs zurück.

Snippet

def strText = "18CC231E0A71F6F27091855C4C0FD0D6F2F26038||D0CACC8058DC36A9A499AB2DD3B993F427AB9200"
def guids   = parseGuids(strText)
guids.each {println it}

Class ParseGuidsClosure

vh()

Erzeugt einen neuen ValueHolder aus dem übergebenen Objekt.

Snippet

def vhTest = vh("Hello world!")
def vhInt  = vh(1000)

Class CreateValueHolderClosure

Datenbanken

Datengruppen

Datengruppe per GUID finden

Hier finden Sie ein Beispiel, mit dem der Name einer Datengruppe ermittelt werden kann:
def strName = g_rtCache.dataGroups["C399FB1F398D76E91BC7DC679E1E4DDB9F5CEB9C"].name

Snippet

def strName = g_rtCache.dataGroups["<data group GUID"].name

Interface DataGroupInfo

Datengruppe in SQL über GUID referenzieren

Mit Hilfe dieser Clientfunktion kann eine Datengruppe über ihre GUID statt über ihren Namen referenziert werden. Damit muss in SQL-Statements nicht der Name der Datengruppe fest hinterlegt werden, womit Probleme beim Import oder bei Änderungen an der Datengruppe vermieden werden. Nur verfügbar über das Intrexx Datenbank-API.

Beispiel

g_dbQuery.executeAndGetScalarValue(conn, "SELECT COUNT(LID) FROM DATAGROUP('DAF7CECF66481FCABE50E529828116EAFE906962')")

An Stelle von "executeAndGetScalarValue" wird die Verwendung der typisierten Methoden (z.B. executeAndGetScalarValueIntValue, executeAndGetScalarStringValue) empfohlen.

Snippet

def strName = g_rtCache.dataGroups["<data group GUID>"].name

Interface DataGroupInfo

Spaltennamen einer Datengruppe

Liefert eine Liste mit den Namen aller Spalten der Datengruppe mit der übergebenen GUID.

Snippet

def fieldNames = g_rtCache.fields.findAll{it.dataGroupGuid == "DG-GUID"}*.columnName

Interface FieldInfo

Intrexx Datenbank-API

Vorbereitete Anweisung mit SELECT

Führt eine vorbereitete Anweisung mit einem SELECT-Statement aus. Anschließend kann über die Ergebnisse im Resultset iteriert werden.

Beispiel

stmt = g_dbQuery.prepare(conn, "SELECT * FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') WHERE ID = ?")
stmt.setInt(1, 1)
stmt.executeQuery()
stmt = Safely.close(stmt)

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null
def rs   = null

try
{
        stmt = g_dbQuery.prepare(conn, "SELECT <COLUMNS> FROM DATAGROUP('<DATAGROUP_GUID>') WHERE <CONDITION>")
	
        //stmt.setInt(1, 1)
	
        rs = stmt.executeQuery()
	
        while (rs.next())
        {
            // do something
            // rs.getIntValue(1)
            // rs.getStringValue(2)
            // rs.getBooleanValue(3)
            // rs.getTimestampValue(4)
        }
	
        rs   = Safely.close(rs)
        stmt = Safely.close(stmt)
}
finally
{
        rs   = Safely.close(rs)
        stmt = Safely.close(stmt)
}

Class DbPreparedStatement

Vorbereitete Anweisung mit INSERT

Führt eine vorbereitete Anweisung mit einem INSERT-Statement aus.

Beispiel

stmt = g_dbQuery.prepare(conn, "INSERT INTO DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') (ID, STRTEXT, DTDATE, BBOOLEAN) VALUES (?,?,?,?)")
stmt.setInt(1, 1)
stmt.setString(2, "Example text")
stmt.setTimestamp(3, now().withoutFractionalSeconds)
stmt.setBoolean(4, true)

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = g_dbQuery.prepare(conn, "INSERT INTO DATAGROUP('<DATAGROUP_GUID>') (<COLUMNS>) VALUES ()")
	
	//stmt.setInt(1, 1)
	//stmt.setString(2, "Example text")
	//stmt.setTimestamp(3, now().withoutFractionalSeconds)
	//stmt.setBoolean(4, true)
	
	stmt.executeUpdate()

	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}

Class DbPreparedStatement

Vorbereitete Anweisung mit INSERT (mit Closure)

Führt eine vorbereitete Anweisung mit einem INSERT-Statement mit Closure aus.

Beispiel

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "INSERT INTO DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') (LID, STRTEXT, DATE) VALUES (?,?,?)") {
	setInt(1, 1)
	setString(2, "Example text")
	setTimestamp(3, now().withoutFractionalSeconds)
}

Bitte beachten: Soll das Statement wiederverwendet werden, z.B. innerhalb einer Schleife, ist die Variante als Prepared Statement ohne Closure effizienter.

Snippet

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "INSERT INTO DATAGROUP('<DATAGROUP_GUID>') (<COLUMNS>) VALUES ()") {
	//setString(1, "Example text")
	//setTimestamp(2, now().withoutFractionalSeconds)
	//setBoolean(3, true)
}

Class DbQuery

Vorbereitete Anweisung mit UPDATE

Führt eine vorbereitete Anweisung mit einem UPDATE-Statement aus.

Beispiel

try
{				
	stmt = g_dbQuery.prepare(conn, "UPDATE DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') SET STRTEXT = ?, DTDATE = ?, BBOOLEAN = ? WHERE ID = ?")
	
	stmt.setString(1, "Example text")
	stmt.setTimestamp(2, now().withoutFractionalSeconds)
	stmt.setBoolean(3, true)
	stmt.setInt(4, 1)
	
	stmt.executeUpdate()
	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}			

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = g_dbQuery.prepare(conn, "UPDATE DATAGROUP('<DATAGROUP_GUID>') SET <COLUMNS> = ? WHERE <CONDITION>")
	
	//stmt.setInt(1, 1)
	//stmt.setString(2, "Example text")
	//stmt.setTimestamp(3, now().withoutFractionalSeconds)
	//stmt.setBoolean(4, true)
	
	stmt.executeUpdate()

	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}

Class DbPreparedStatement

Vorbereitete Anweisung mit UPDATE (mit Closure)

Führt eine vorbereitete Anweisung mit einem UPDATE-Statement mit Closure aus.

Beispiel

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "UPDATE DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') SET STRTEXT = ? WHERE DATE < ?") {
	setString(1, "Example text")
	setTimestamp(2, now().withoutFractionalSeconds)
}

Bitte beachten: Soll das Statement wiederverwendet werden, z.B. innerhalb einer Schleife, ist die Variante als Prepared Statement ohne Closure effizienter.

Snippet

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "UPDATE DATAGROUP('<DATAGROUP_GUID>') SET <COLUMNS> = ? WHERE <CONDITION>") {
	//setString(1, "Example text")
	//setTimestamp(2, now().withoutFractionalSeconds)
	//setBoolean(3, true)
}

Class DbQuery

Vorbereitete Anweisung mit DELETE

Führt eine vorbereitete Anweisung mit einem DELETE-Statement aus.

Beispiel

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = g_dbQuery.prepare(conn, "DELETE FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') WHERE ID > ?")

	stmt.setInt(1, 5)
	stmt.executeUpdate()
	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = g_dbQuery.prepare(conn, "DELETE FROM DATAGROUP('<DATAGROUP_GUID>') WHERE <CONDITION>")
	
	//stmt.setInt(1, 1)
	//stmt.setString(2, "Example text")
	//stmt.setTimestamp(3, now().withoutFractionalSeconds)
	//stmt.setBoolean(4, true)
	
	stmt.executeUpdate()
	
	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}

Class DbPreparedStatement

Vorbereitete Anweisung mit DELETE (mit Closure)

Führt eine vorbereitete Anweisung mit einem DELETE-Statement mit Closure aus.

Beispiel

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "DELETE FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') WHERE ID > ?"){

	setInt(1, 5)
}

Bitte beachten: Soll das Statement wiederverwendet werden, z.B. innerhalb einer Schleife, ist die Variante als Prepared Statement ohne Closure effizienter.

Snippet

def conn = g_dbConnections.systemConnection

g_dbQuery.executeUpdate(conn, "DELETE FROM DATAGROUP('<DATAGROUP_GUID>') WHERE <CONDITION>"){

	//setInt(1, 1)
	//setString(2, "Example text")
	//setTimestamp(3, now().withoutFractionalSeconds)
	//setBoolean(4, true)

Class DbPreparedStatement

Einzelner Wert aus Datenbankabfrage

Liest einen einzelnen Wert aus einer Datenbankabfrage aus. Ist die Ergebnismenge leer oder null, wird der mit fallbackValue definierte Wert zurückgegeben. Soll der Datentyp der Rückgabe genauer spezifiziert werden, können typisierte Methodenaufrufe wie z.B. executeAndGetScalarBooleanValue(...) erfolgen.

Beispiel

def value = g_dbQuery.executeAndGetScalarValue(conn, "SELECT MAX(ID) FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F')", 0)

oder mit vorbereiteter Anweisung

def value = g_dbQuery.executeAndGetScalarValue(conn, "SELECT MAX(ID) FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F') WHERE DTEDIT < ?", 0) {
setTimestamp(1, now().withoutFractionalSeconds)

An Stelle von "executeAndGetScalarValue" wird die Verwendung der typisierten Methoden (z.B. executeAndGetScalarValueIntValue, executeAndGetScalarStringValue) empfohlen.

Snippet

def conn = g_dbConnections.systemConnection

def value = g_dbQuery.executeAndGetScalarValue(conn, "SELECT <COLUMNS> FROM DATAGROUP('<DATAGROUP_GUID>') WHERE <CONDITION>", <FALLBACK_VALUE>) {
	//setString(1, "Example text.")
}

Class DbQuery

Einzelner Wert aus vorbereiteter Datenbankabfrage

Liest einen einzelnen Wert aus einer Datenbankabfrage aus. Ist die Ergebnismenge leer oder null, wird der mit fallbackValue definierte Wert zurückgegeben. Soll der Datentyp der Rückgabe genauer spezifiziert werden, können typisierte Methodenaufrufe wie z.B. executeAndGetScalarBooleanValue(...) erfolgen.

Beispiel

def stmt = g_dbQuery.prepare(conn, "SELECT MAX(LID) FROM DATAGROUP('7AFAF7CB5DE281D35F05D96FCD96CE27692C110F')")

def value = stmt.executeAndGetScalarValue(0)

stmt = Safely.close(stmt)

An Stelle von "executeAndGetScalarValue" wird die Verwendung der typisierten Methoden (z.B. executeAndGetScalarValueIntValue, executeAndGetScalarStringValue) empfohlen.

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn  = g_dbConnections.systemConnection
def stmt  = null
def value

try
{
	stmt = g_dbQuery.prepare(conn, "SELECT <COLUMN> FROM DATAGROUP('<DATAGROUP_GUID>') WHERE <CONDITION>")

	//stmt.setInt(1, 1)
	//stmt.setString(2 , "Example text")
	//stmt.setTimestamp(3, now().withoutFractionalSeconds)
	//stmt.setBoolean(4, false)

	value = stmt.executeAndGetScalarValue(<FALLBACK_VALUE>)

	stmt = Safely.close(stmt)
}
finally
{
	stmt = Safely.close(stmt)
}

Class DbPreparedStatement

JDBC

Vorbereitete Anweisung mit SELECT

Führt eine vorbereitete Anweisung mit einem SELECT-Statement aus. Anschließend kann über die Ergebnisse iteriert werden.

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null
def rs   = null

try
{
	stmt = conn.prepareStatement("SELECT <COLUMNS> FROM <DATAGROUP_NAME> WHERE <CONDITION>")

	//stmt.setInt(1, 42)
	//stmt.setString(2, "Example text")
	//stmt.setTimestamp(3, now().withoutFractionalSeconds)
	//stmt.setBoolean(4, false)

	rs = stmt.executeQuery()

	while (rs.next())
	{
		// do something
		// rs.getInt(1)
		// rs.getString(2)
		// rs.getTimestamp(3)
	}
}
finally
{
	rs   = Safely.close(rs)
	stmt = Safely.close(stmt)
}

Interface PreparedStatement

Vorbereitete Anweisung mit INSERT

Führt eine vorbereitete Anweisung mit einem INSERT-Statement aus.

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = conn.prepareStatement("INSERT INTO <DATAGROUP_NAME> (<COLUMNS>) VALUES ()")

	// stmt.setInt(1, 1234)
	// stmt.setString(2, "Example text")
	// stmt.setBoolean(3, true)
	// stmt.setTimestamp(4, now().withoutFractionalSeconds)

	stmt.executeUpdate()
}
finally
{
	stmt = Safely.close(stmt)
}

Interface PreparedStatement

Vorbereitete Anweisung mit UPDATE

Führt eine vorbereitete Anweisung mit einem UPDATE-Statement aus.

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
stmt = conn.prepareStatement("UPDATE <DATAGROUP_NAME> SET <COLUMNS> = ? WHERE <CONDITION>")

			// stmt.setInt(1, 1234)
			// stmt.setString(2, "Example text")
			// stmt.setBoolean(3, true)
			// stmt.setTimestamp(4, now().withoutFractionalSeconds)

			stmt.executeUpdate()
			}
			finally
			{
			stmt = Safely.close(stmt)
			}

Interface PreparedStatement

Vorbereitete Anweisung mit DELETE

Führt eine vorbereitete Anweisung mit einem DELETE-Statement aus.

Snippet

import de.uplanet.scripting.groovy.util.Safely

def conn = g_dbConnections.systemConnection
def stmt = null

try
{
	stmt = conn.prepareStatement("DELETE FROM <DATAGROUP_NAME> WHERE <CONDITION>")

	// stmt.setInt(1, 1234)
	// stmt.setString(2, "Example text")
	// stmt.setBoolean(3, true)
	// stmt.setTimestamp(4, now().withoutFractionalSeconds)

	stmt.executeUpdate()
}
finally
{
	stmt = Safely.close(stmt)
}

Interface PreparedStatement

Systemdatenquelle

System-Datenbankverbindung

Beispiel

def conn = g_dbConnections.systemConnection

Snippet

g_dbConnections.systemConnection

Class GroovyContextConnections

Fremddatenquelle

Verbindung zu einer Fremddatenquelle. Anzugeben ist der im Modul Integration vergebene Name für die Fremddatenverbindung.

Beispiel

def conn = g_dbConnections["ForeignData"]

Snippet

g_dbConnections["<CONNECTION_NAME>"]

Class GroovyContextConnections

Datenbanktyp unterscheiden

Ermittelt den Datenbanktyp.

Snippet

def conn = g_dbConnections.systemConnection

switch (conn.descriptor.databaseType)
{
	case "Db2":
		// DB2
		break

	case "Derby":
		// Derby/Java DB
		break

	case "Firebird":
		// Firebird
		break

	case "HSQLDB":
		// HSQLDB
		break

	case "Ingres":
		// Ingres
		break

	case "Oracle8":
		// Oracle 8
		break

	case "Oracle9":
		// Oracle 9
		break

	case "Oracle10":
		// Oracle 10
		break

	case "PostgreSQL":
		// PostgreSQL
		break

	case "MaxDB":
		// MaxDB
		break

	case "MsSqlServer":
		// Microsoft SQL Server
		break

	case "Standard":
		// unspecified
		break

	default:
		assert false : "Unexpected database type."
		break
}

Class GroovyContextConnections

Webservices

Webservice-Aufruf ausführen

Ruft den zu Grunde liegenden Webservice auf. Gilt nur für Skripts, die innerhalb eines Webservices definiert sind.

Snippet

g_ws.invoke()

Webservice-Eingabewerte auslesen

Auslesen von Werten, die einem Webservice als Eingabeparameter übergeben werden. Als Variablenname ist der Name der Kontrolle anzugeben, die den Wert enthält.

Beispiel

g_ctx.requestVars.textcontrolD72A9620

Snippet

g_ctx.requestVars.

Webservice-Rückgabewerte auslesen

Auslesen von Werten, die einem Webservice als Rückgabeparameter übergeben werden. Als Variablenname ist der Name der Kontrolle anzugeben, in die der Rückgabewert geschrieben wird.

Beispiel

g_ctx.bpeeVars.textvcontrol72EF4A0B.value

Snippet

g_ctx.bpeeVars..value

Fallunterscheidung

switch-Anweisung für Groovy-Bedingung

Anwendbar in Prozessen. Die Rückgabewerte entsprechen den ausgehenden Verbindungen (Verbindungs-ID) der Groovy-Bedingung.

Snippet

switch (g_record[""].value)
{
	case "expected value 1":
		return connectionId1
	case "expected value 2":
		return connectionId2
	default:
		return connectionId3
}

switch / case

switch-Anweisung für Datengruppenereignisse

Anwendbar in Prozessen.

Snippet

import de.uplanet.lucy.server.workflow.event.IAfterCreateDataGroupWorkflowEvent
import de.uplanet.lucy.server.workflow.event.IAfterUpdateDataGroupWorkflowEvent
import de.uplanet.lucy.server.workflow.event.IBeforeDeleteDataGroupWorkflowEvent
import de.uplanet.lucy.server.workflow.event.INotifyDataGroupWorkflowEvent

switch (g_event)
{
	case IAfterCreateDataGroupWorkflowEvent:
		g_log.info("A new record was inserted.")
		break

	case IAfterUpdateDataGroupWorkflowEvent:
		g_log.info("A record was updated.")
		break

	case IBeforeDeleteDataGroupWorkflowEvent:
		g_log.info("A record will be deleted.")
		break

	case INotifyDataGroupWorkflowEvent:
		g_log.info("A timer resubmitted a record.")
		break

	default:
		g_log.warn("Unhandled event ${g_event}.")
		break
}

Interface IWorkflowEvent

Datensätze bei globalen Datengruppen-Timern

Unterscheidung zwischen dem erstem und den nachfolgenden Datensätzen bei globalen Datengruppen-Timern.

Snippet

if (g_sharedState["wasHere${g_guidSelf}"])
{
	// we were here before
}
else
{
	// we are here for the first time
	g_sharedState["wasHere${g_guidSelf}"] = true
}

Mathematische Berechnungen

Kaufmännisches Runden

Kaufmännisches Runden mit optionaler Angabe der Nachkommastellen.

Beispiel

 13,3749 ->  13,37
-13,3749 -> -13,37
 13,3750 ->  13,38
-13,3750 -> -13,38

Snippet

import de.uplanet.util.math.RoundingUtil
RoundingUtil.roundHalfAwayFromZero(, 2)

Class Math

Mathematisches Runden

Mathematisches Runden mit optionaler Angabe der Nachkommastellen.

Beispiel

2.2499 -> 2.2
2.2501 -> 2.3
2.2500 -> 2.2
2.3500 -> 2.4

Snippet

import de.uplanet.util.math.RoundingUtil
RoundingUtil.roundHalfEven(, 2)

Class Math

Datum / Uhrzeit

Datumswerte formatieren

Hier finden Sie Skript für die Formatierung von Datumswerten.

Snippet

import java.text.SimpleDateFormat

// specify the time zone
def tz = g_session.user.timeZone
//def tz = de.uplanet.lucy.server.DefaultTimeZone.get()
//def tz = TimeZone.getTimeZone("Europe/Berlin")

assert tz != null

// the date/time to be formatted
def dt = new Date()

// the date format
// https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/text/SimpleDateFormat.html
def fmt = new SimpleDateFormat("yyyy-MM-dd")
fmt.setTimeZone(tz)

println(fmt.format(dt))

SimpleDateFormat

Dauer in Tagen berechnen

Ein Datensatz beinhaltet Daten für ein Start- und ein Enddatum. Berechnet wird die Zeitspanne zwischen diesen beiden Datumswerten. Bitte beachten Sie, dass hier keine Zeitzonen berücksichtigt werden.

Snippet

def conn    = g_dbConnections.systemConnection
def dtStart = g_record["GUID"].value // datafield startDate
def dtEnd   = g_record["GUID"].value // datafield endDate
def iID     = g_record["GUID"].value // datafield (PK) (S) ID

use (groovy.time.TimeCategory)
{
	def duration = dtEnd - dtStart

	def stmt = g_dbQuery.prepare(conn, "UPDATE DATAGROUP('<DATAGROUP_GUID>') SET <COLUMN_DURATION> = ? WHERE LID = ?")

	stmt.setInt(1, duration.days)
	stmt.setInt(2, iID)
	stmt.executeUpdate()
	stmt.close()
}

ISO-Datumsstring parsen

Parst eine Zeichenkette im ISO-Format in ein java.util.Date-Objekt.

Beispiel

def strDate        = "2013-01-01T12:00:01Z"
def strDateMillis = "2013-01-01T15:00:01.000Z"

def dtDate1 = ISODateTimeUtil.parseISODateTime(strDate)
def dtDate2 = ISODateTimeUtil.parseISODateTimeMillis(strDateMillis)
def dtDate3 = ISODateTimeUtil.parseISODateTimeOptionalMillis(strDate)
def dtDate4 = ISODateTimeUtil.parseISODateTimeOptionalMillis(strDateMillis)

Snippet

import de.uplanet.util.ISODateTimeUtil

def dtDate  = ISODateTimeUtil.parseISODateTimeOptionalMillis("<DATE_ISO_STRING>")

Class ISODateTimeUtil

Datum als ISO-String formatieren

Formatiert ein Datumsobjekt als ISO-String.

Beispiel

println ISODateTimeUtil.formatISODateTime(currentTimestamp())
println ISODateTimeUtil.formatISODateTimeMillis(currentTimestamp())

Snippet

import de.uplanet.util.ISODateTimeUtil

ISODateTimeUtil.formatISODateTime(currentTimestamp())

Class ISODateTimeUtil

Jetzt als Timestamp

Snippet

now().withoutFractionalSeconds

Class ChimeraDate

Zeitstempel für Systemwerte

Diese Closure liefert den Zeitstempel der aktuellen Transaktion. Dieser Wert bleibt bis zum Verarbeitungsende dieser Transaktion unverändert.

Snippet

currentTimestamp()

Class CurrentTimestampClosure

E-Mail

Groovy E-Mail (einfach)

Eine einfache Text-E-Mail erzeugen.

Snippet

import de.uplanet.lucy.server.mail.GroovyMailBuilder
	def mail = new GroovyMailBuilder().composeMail {
	from    = "sender@example.org"
	to      = "recipient@example.org"
	subject = "Insert the subject here"

	body << "Hello world"
}

mail.drop()

Class GroovyMailBuilder

Groovy E-Mail

Eine HTML-E-Mail mit Bildern und Dateianhang erzeugen.

Snippet

import de.uplanet.lucy.server.mail.GroovyMailBuilder

def fileImg        = new File(g_dirWorkflow, "theImage.png")
def fileAttachment = new File(g_dirWorkflow, "document.pdf")

def mail = new GroovyMailBuilder().composeMail {
	headers = [
		"Importance": "High",
		"X-Priority": "1"
		]

	from        = "sender@example.org"
	to          = ["recipient-1@example.org", "recipient-2@example.org"]
	subject     = "Insert the subject here"
	contentType = "text/html; charset=UTF-8"

	body << """<html>
	<body>
		<h1>Hello World</h1>
		<p>
			Look at this image
			<br>
			<img src="${srcInlineImage(fileImg)}">
			<br>
			Nice.
		</p>
	</body>
	</html>"""

	// note: name is an optional parameter
	attachFile(file: fileAttachment, name: "nameOfTheAttachment.pdf", contentType: "application/pdf")
}

mail.drop()

Class GroovyMailBuilder

E-Mail per Ant verschicken

Bitte beachten Sie: Das Versenden der E-Mail ist nicht Teil der Transaktion, sondern wird sofort und unabhängig vom Erfolg der Transaktion ausgeführt.

Snippet

def strFromAddr = g_session?.user?.emailBiz
def strFromName = g_session?.user?.name
def strToAddr   = "" // insert the recipient here

new AntBuilder().mail(mailhost:"localhost", messagemimetype:"text/plain", subject:"Hello World") {
	from(address:"${strFromName} <${strFromAddr}>")
	to(address:addrTo)
	message("""Here goes the message text.

With kind regards
${strFromName}
""")
}

Dateien und Verzeichnisse

Festplattenplatz ermitteln

Ermittelt die freie und gesamte Festplattenkapazität.

Snippet

// the partition where the Intrexx portal resides
File partition = new File(".")

long totalSpace = partition.totalSpace
long freeSpace = partition.freeSpace

Class File

Verzeichnis des aktuellen Prozesses

Liefert das Verzeichnis des aktuellen Prozesses. Auf dieses Verzeichnis sollte ausschließlich lesend zugegriffen werden.

Snippet

g_dirWorkflow

Class File

Temporäres Prozess-Verzeichnis

Zugriff auf ein temporäres Prozess-Verzeichnis. Das Verzeichnis ist auch für nachfolgende Prozess-Objekte sichtbar. Es wird gelöscht, sobald der Prozess vollständig abgearbeitet wurde.

Snippet

g_dirWorkflowTmp

Class File

In temporärem Verzeichnis arbeiten

Verwendet ein temporäres Verzeichnis für die Bearbeitung.

Snippet

import de.uplanet.io.IOHelper 

File dirTemp = createTemporaryDirectory()

try
{
	
}
finally
{
	IOHelper.deleteFileRecursively(dirTemp)
}	

Class File

Datei zu Datensatz hinzufügen

Bitte beachten Sie: wir empfehlen statt "FileUCHelper" die Verwendung von g_dgFile.

Fügt eine Datei zu einem bestehenden Datensatz hinzu. Mit copyFileToIntrexx(...) wird die Quelldatei kopiert und bleibt an ihrem Speicherort erhalten. Ein analoger Aufruf ist mit moveFileToIntrexx(...). Hierbei wird die Quelldatei nach Intrexx verschoben.

Parameter:
p_ctx - Der aktuelle Verarbeitungskontext (g_context)
p_fileSrc - Datei, die hinzugefügt werden soll
p_strFieldGUID - GUID des Dateidatenfeldes
p_recId - ID des Datensatzes, zu dem die Datei hinzugefügt werden soll
p_bTriggerWorkflow - Soll ein Workflow getriggert werden, der auf Datensatzänderungen reagiert?

Der Parameter "p_bTriggerWorkflow" der Klasse "FileUCHelper" ist nicht implementiert und hat deshalb immer den Wert "false".

Beispiel

FileUCHelper.copyFileToIntrexx(g_context, fileInput, "0B5CFF839F946923DBB0D92F39BB5D79BEC8D94C", g_record.recId,  false)

Snippet

import de.uplanet.lucy.server.businesslogic.util.FileUCHelper
FileUCHelper.copyFileToIntrexx(g_context, p_fileSrc, p_strFieldGuid, p_recId, p_bTriggerWorkflow) 
		

Class FileUCHelper

Datei aus Datensatz löschen

Bitte beachten Sie: wir empfehlen statt "FileUCHelper" die Verwendung von g_dgFile.

Löscht eine Datei aus einem Datensatz.

Parameter:
p_ctx - Der aktuelle Verarbeitungskontext (g_context)
p_strFieldGUID - GUID des Dateidatenfeldes
p_recId - ID des Datensatzes, von dem die Datei gelöscht werden soll

Beispiel

FileUCHelper.deleteFileFromIntrexx(g_context, "0B5CFF839F946923DBB0D92F39BB5D79BEC8D94C", g_record.recId)

Snippet

import de.uplanet.lucy.server.businesslogic.util.FileUCHelper
FileUCHelper.deleteFileFromIntrexx(g_context, p_strFieldGuid, p_recId) 
		

Class FileUCHelper

Textdatei einlesen

Liest den Inhalt einer Texdatei mit dem definierten Encoding. Nicht bei großen Datenmengen einsetzen.

Snippet

def fileIn     = new File("<FILE_NAME>")
def strContent = fileIn.getText("UTF-8")

Class File

Textdatei zeilenweise einlesen

Liest zeilenweise den Inhalt einer Texdatei mit dem definierten Encoding.

Snippet

def fileIn     = new File("_in.txt")
fileIn.eachLine("UTF-8") {line ->
	//process line
}

Class File

In Textdatei schreiben

Schreibt eine Textausgabe in eine Textdatei mit dem definierten Encoding.

Beispiel

def fileOut  = new File("out.txt")
def strOutput = "This is my output text.\n"

fileOut.withWriter("UTF-8") 
{
		out -> out << strOutput
		out.write(strOutput)
		out.append(strOutput)
}

Snippet

def fileOut = new File("out.txt")

fileOut.withWriter("UTF-8") 
{
out ->	
//write output to  file
}

Class File

Session / Benutzer

Name des aktuellen Benutzers

Snippet

g_session?.user?.name

Interface IUser

E-Mail-Adresse des aktuellen Benutzers

Snippet

g_session?.user?.emailBiz

Interface IUser

Anonyme Session oder nicht?

Snippet

g_session?.anonymous

Class GroovySession

Zugriff auf die Organisationsstruktur

Snippet

g_om.getOrgStructure()

g_om

Angemeldete Benutzer

Liste aller angemeldeten, nicht anonymen Benutzer.

Snippet

de.uplanet.lucy.server.portalserver.LoggedOnUsers.getLoggedOnUsersDistinct()

Neues Passwort für Benutzer setzen

Setzt ein neues Passwort für den angegebenen Benutzer.

Snippet

g_om.changePassword(user, password)

Class GroovyOrgBuilder

Benutzerverwaltung

Benutzer anlegen (einfach)

Snippet

g_om.createUser {
	container     = "System"
	name          = "user-${now().withoutFractionalSeconds}" 
	loginName     = "UserU-${now().withoutFractionalSeconds}"
	password      = "secret"
	emailBiz      = "user@example.org"
	description   = "User created with Groovy at ${now().withoutFractionalSeconds}"
}

Benutzer anlegen

Snippet

// provide the copy of an user image (optional)
def fileTemplImage = new File(g_dirWorkflow, "user.jpg")
def fileUserImage  = new File(g_dirWorkflowTmp, "user.jpg")

de.uplanet.io.IOHelper.copyFile(fileUserImage, fileTemplImage)

def user	= g_om.createUser {
container	= "System"
name		= "user-${now().withoutFractionalSeconds}" 
loginName	= "UserU-${now().withoutFractionalSeconds}"
password	= "secret"
emailBiz	= "user@example.org"
description	= "User created with Groovy at ${now().withoutFractionalSeconds}"
nickname	= "dodo"  // this is a custom user field
userImageFile 	= fileUserImage

// provide a list of sets (group, role, dist list, ...) the user should be member of
// allowed are GUIDs, unique names, paths, or org structure set nodes
memberOf 	= ["importantRole", "36B3BFD54A57BE5D1EE51288D920CDA9B20A67A4"]
}

// create a new password and send it to the user's emailBiz address (optional)
g_om.generateAndSendPassword(user, g_defaultLanguage)

Bestehende Benutzer bearbeiten

Snippet

def user = g_om.getUser("LOGINNAME", "DOMAIN")

if (user != null)
{
	// provide the copy of a user image (optional)
	def fileTemplImage = new File(g_dirWorkflow, "user.jpg")
	def fileUserImage  = new File(g_dirWorkflowTmp, "user.jpg")
	de.uplanet.io.IOHelper.copyFile(fileUserImage, fileTemplImage)

    // get the GUID list of sets (group, role, dist list, ...) the user is member of
    def membership = user.getDirectMemberSets()
    
    membership.remove("EF16F15EDA8562E19D7CD56BF2E43001F119193C")
    membership.add("36B3BFD54A57BE5D1EE51288D920CDA9B20A67A4")
    
    user.containerGuid = "4B87C2470868AAB57BFB31958D1F73583FB3778E"
    user.name          = "user-${now().withoutFractionalSeconds}"
    user.emailBiz      = "user@example.org"
    user.description   = "User created with Groovy at ${now().withoutFractionalSeconds}"
    user.nickName      = "dodo"  // this is a custom user field
    user.userImageFile = fileUserImage
    
    user.save()
}

GUIDs klassifizieren

Klassifizieren von GUIDs nach

  • Benutzer

  • Container (Organization, Organizational Unit, ...)

  • Set (Gruppe, Rolle, DistList, ...)

  • nicht klassifizierbare GUID

Snippet

def classified = g_om.classifyGuids(/* a list of GUIDs or text that contains GUIDs */)

// do something with the classified GUIDs
classified.users
classified.containers
classified.sets
classified.unclassified

Kategorien

Datum / Uhrzeit

Snippet

use (groovy.time.TimeCategory)
{
	
}

IValueHolder

Snippet

use (de.uplanet.lucy.server.scripting.groovy.GroovyIntrexxValueHolderCategory)
{
	
}

Class GroovyIntrexxValueHolderCategory

Info

Systeminformation

Snippet

def osmbean = java.lang.management.ManagementFactory.operatingSystemMXBean
def sysInfo = """
name                        ${osmbean.name}
version                     ${osmbean.version}
arch                        ${osmbean.arch}
availableProcessors         ${osmbean.availableProcessors}
processCpuTime              ${osmbean.processCpuTime}
systemLoadAverage           ${osmbean.systemLoadAverage}
committedVirtualMemorySize  ${osmbean.committedVirtualMemorySize} bytes
totalPhysicalMemorySize     ${osmbean.totalPhysicalMemorySize} bytes
freePhysicalMemorySize      ${osmbean.freePhysicalMemorySize} bytes
totalSwapSpaceSize          ${osmbean.totalSwapSpaceSize} bytes
freeSwapSpaceSize           ${osmbean.freeSwapSpaceSize} bytes"""

g_log.info(sysInfo)

Intrexx-Version

Liefert die Version der Intrexx-Installation.

Snippet

de.uplanet.lucy.VERSION.CURRENT.toFormattedString()

Class Version

Fehlerbehandlung und Fehlersuche

Stacktrace als String

Snippet

getStackTraceString()

Groovy-Kontext

Snippet

def dumpBinding = {
	def sbuf = new StringBuilder()

	sbuf << "Dump the Groovy binding:\n"

	binding.variables.each { k, v ->
		if (v && v.metaClass && v.metaClass.respondsTo(v, "dump"))
			sbuf << "${k} = ${v.dump()}\n"
		else
			sbuf << "${k} = ${v?.toString()}\n"
	}

	sbuf.toString()
}

g_log.info(dumpBinding())

Fehlerbehandler für Skript definieren

Einsetzbar in

  • Groovy-Seiten

  • Action- und Rendering-Handlern

Snippet

onError = { exception, err ->	
	err.title = ""
	err.description = "Insert your description here. ${exception.message}"
}

Groovy Server Skripts

JSON-Antwort

Bitte beachten Sie, dass vor allen Aktionen, die von Benutzern ausgelöst werden können, eine Rechteprüfung (IxAccessController) erforderlich ist.

Snippet

response.json()

// define an error handler
response.onError = 
{
e, err ->	
    //err.type = "default"
    // either title/description, ...
    err.title = "my error"
    err.description = e.message
    err.showEmbedded = true
    // ... or a redirect
    // err.redirectUrl = "https://www.example.org/"
    err.redirectDelay = 1500 // milliseconds
}

// check permissions
g_permissions.check 
{
    // application("${application.guid}": "access")
    // dataGroup("<data group GUID>": "read", "<another data group GUID>": "write,create")
}

// create some JSON content
writeJSON("person": [
    givenName: "Donald",
    lastName: "Duck",
    age: 78,
    nephews: ["Huey", "Dewey", "Louie"]
])
		

Mögliche Varianten des oben angegebenen Skripts

Closure ohne oder mit genau einem Parameter

Falls die Closure einen Parameter deklariert, wird im ersten Parameter (e) die aufgetretene Exception an die Closure übergeben.

Snippet

// define an error handler
response.onError = {e ->
	writeJSON("error": "Something bad happened.")
}

Closure mit zwei Parametern

Im ersten Parameter (e) wird die aufgetretene Exception und im zweiten Parameter (err) ein ErrorResponseData-Objekt an die Closure übergeben. In der Closure kann das ErrorResponseData-Objekt gemäß den jeweiligen Bedürfnissen konfiguriert werden.

Snippet

// define an error handler
response.onError = {e, err ->
	//err.type = "default"
	// either title/description, ...
	err.title = "my error"
	err.description = e.message
	err.showEmbedded = true
	// ... or a redirect
	// err.redirectUrl = "https://www.example.org/"
	// err.redirectDelay = 1500 // milliseconds
}

Mit String

Der angegebene String wird im Response-Body zum Client gesendet.

Snippet

response.onError = '{"error": "Something bad happened."}'

Zuweisung eines anderen Objekts

Im Falle einer JSON-Antwort wird versucht, aus dem Objekt JSON zu erzeugen. Falls die Antwort nicht vom Typ JSON ist, wird versucht, das Objekt in geeigneter Weise als Text auszugegeben.

Snippet

response.onError = [
	"error": "Something bad happened.",
	"solace": "But things could be worse."
]

Velocity

Text aus Velocity-Template erzeugen

Snippet

import de.uplanet.lucy.server.scripting.velocity.VelocityContextUtil
import org.apache.velocity.app.Velocity

def fileVm = new File(g_dirWorkflow, "") // the Velocity input file
def vc     = VelocityContextUtil.createDefaultContext(g_context)

// add additional variables to the Velocity context
// vc.put("PreparedQuery", g_dbQuery)
// vc.put("variableName", variableValue)

def template = Velocity.getTemplate(fileVm.path)
def writer   = new StringWriter(4096) // 4 KiB initial buffer

template.merge(vc, writer)

g_log.info(writer.toString())

Datei aus Velocity-Template erzeugen

Aus Sicherheitsgründen können Velocity-Dateien nur ausgeführt werden, wenn sie sich in einem der folgenden Unterverzeichnisse befinden:

  • internal/system/vm

  • internal/layout/vm

  • internal/application/vm

  • internal/application/resource

  • internal/workflow/<GUID>/velocity

Request-Variable

g_request.get(...)

Snippet

g_request.get("")

Class GroovyServerBridgeRequest

rq_Lang

Liefert die aktuell verwendete Sprache des angemeldeten Benutzers.

Snippet

rq_Lang

REMOTE_ADDR

IP-Adresse des Client-Computers.

Snippet

REMOTE_ADDR

SERVER_PORT

Snippet

SERVER_PORT

HTTP_HOST

Snippet

HTTP_HOST

HTTP_REFERER

Snippet

HTTP_REFERER

Snippet

HTTP_COOKIE

HTTP_USER_AGENT

Snippet

HTTP_USER_AGENT

SCHEME

HTTP oder HTTPS

Snippet

SCHEME

Bilder

Bild skalieren

Unterstützte Formate sind PNG, JPEG (JPG) und BMP.

Snippet

import de.uplanet.lucy.server.scripting.groovy.ImageHelper

// Parameters: inputFile, outputFile, format?, width?, height?, maxWidth?, 
// maxHeight?, scaleX?, scaleY?, shrinkOnly?, rotate?, crop?
ImageHelper.scaleImage(inputFile: , outputFile: <OUTPUT_FILE>)

Class ImageHelper

Bildgröße ermitteln

Als Parameter kann ein File-Objekt oder ein Pfad als Zeichenfolge übergeben werden.

Snippet

import de.uplanet.lucy.server.scripting.groovy.ImageHelper

def (x, y) = ImageHelper.getImageSize()
		

Class ImageHelper

Iterieren über Bild-Metadaten

Hier finden Sie ein Beispiel, das die Verwendung der Metadaten-Extraktion in Groovy zeigt.

Snippet

import de.uplanet.lucy.server.scripting.groovy.ImageHelper

def file = ImageHelper.getImageMetaData(file).each { 
    tag, value ->	println("$tag -> $value")
}
		

Class ImageHelper

Logging

Info in Portal-Logdatei schreiben

Schreibt einen INFO-Eintrag in die portal.log-Datei. Diese Methode kann verwendet werden, wenn die zum Ausführungskontext des Skripts gehörige Logdatei nicht die portal.log ist, die Ausgabe aber dennoch in die portal.log erfolgen soll.

Snippet

g_syslog.info("")

Class GroovyLogger

Info in Logdatei schreiben

Schreibt einen INFO-Eintrag in die zum Ausführungskontext des Scripts gehörige Logdatei.

Snippet

g_log.info("")

Class GroovyLogger

Warnung in Portal-Logdatei schreiben

Schreibt einen WARN-Eintrag in die portal.log-Datei. Diese Methode kann verwendet werden, wenn die zum Ausführungskontext des Scripts gehörige Logdatei nicht die portal.log ist, die Ausgabe aber aber dennoch in die portal.log erfolgen soll.

Snippet

g_syslog.warn("")

Class GroovyLogger

Warnung in Logdatei schreiben

Schreibt einen WARN-Eintrag in die zum Ausführungskontext des Scripts gehörige Logdatei.

Snippet

g_log.warn("")

Class GroovyLogger

Fehler in Portal-Logdatei schreiben

Schreibt einen ERROR-Eintrag in die portal.log-Datei. Diese Methode kann verwendet werden, wenn die zum Ausführungskontext des Scripts gehörige Logdatei nicht die portal.log ist, die Ausgabe aber aber dennoch in die portal.log erfolgen soll.

Snippet

g_syslog.error("")

Class GroovyLogger

Fehler in Logdatei schreiben

Schreibt einen ERROR-Eintrag in die zum Ausführungskontext des Scripts gehörige Logdatei.

Snippet

g_log.error("")

Class GroovyLogger

Statistik-Logs lesen

Snippet

import de.uplanet.lucy.server.monitor.log.GroovyLogReader

// flush queued log entries to disk
GroovyLogReader.flushLogQueue()

// collect the log files
def logFiles = []

new File("internal/statistics").eachFile {
	if (!it.name.startsWith(".")) // TODO check additional criteria
		logFiles << it
}

// read the selected log files
logFiles.each { file ->
	GroovyLogReader.readLog(file) { entry ->
		// TODO do something with the entry
		println("Time in millis = ${entry.time}, targetGuid = ${entry.targetGuid}")
	}
}

Connector für Microsoft Exchange

Aktuelle Exchange-Verbindung

Liefert die aktuelle Verbindung zu Microsoft Exchange.

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)

Class ExchangeConnectionUtil

Mailboxname des aktuellen Exchangebenutzers

Liefert den Namen der Mailbox der aktuellen Exchangeverbindung.

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def mailboxUtil = ExchangeUtils.getMailboxUtil(connEx)

def strMailboxName = mailboxUtil.getImpersonateUserAccount(g_context.impersonateUserGuid).exchangeMailbox

Class ExchangeUserMailboxInfo

E-Mail lokal als EML abspeichern

Speichert eine E-Mail lokal im EML-Format ab. Alternativ kann auch saveMessageAsMSG(..) verwendet werden, um die E-Mail im Format MSG abzuspeichern.

Parameter:

  • strMessageId - Die ID der abzuspeichernden E-Mail

  • fileMail - Fileobjekt, mit dem die Mail gespeichert wird

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def messageUtil = ExchangeUtils.getMessageUtil(connEx)

messageUtil.saveMessageAsEML(strMessageId, fileMail)

Interface IExchangeMessageUtil

Anhänge einer E-Mail abspeichern

Speichert die Anhänge der durch strMessageId definierten E-Mail.

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def itemUtil    = ExchangeUtils.getItemUtil(connEx)
def attachments = itemUtil.getAttachments(strMessageId)

attachments.each{ item ->
	def attachment = new File(g_dirWorkflowTmp, item.displayName)
	itemUtil.saveAttachment(item, attachment)
}

Interface IExchangeItemUtil

Abwesenheitsnachricht setzen

Schreibt den Text der Abwesenheitsnachricht und setzt den Status auf aktiv. Achtung: Der Text wird sowohl als interne als auch als externe Nachricht gesetzt.

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def mailboxUtil = ExchangeUtils.getMailboxUtil(connEx)

mailboxUtil.setOutOfOfficeMessage("Out of office till 2010/31/12")
mailboxUtil.setOutOfOffice(true)

Interface IExchangeMailboxUtil

Ordnerinformationen abrufen

Ruft Informationen zu einem Ordner des Exchangekontos ab.

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def mailboxUtil = ExchangeUtils.getMailboxUtil(connEx)
def folderInfo  = mailboxUtil.getFolderInfoByHref(mailboxUtil.getInboxFolderHref())

Interface IFolderInfo

Ordner erstellen

Erstellt einen Exchange-Ordner (in diesem Beispiel unterhalb des Posteingangs).

Parameter:

  • Name des übergeordneten Ordners

  • Name des neuen Ordners

  • Exchange content-class

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil

def connEx         = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def mailboxUtil    = ExchangeUtils.getMailboxUtil(connEx)
def strInboxFolder = mailboxUtil.getInboxFolderHref()

mailboxUtil.createFolder(strInboxFolder, "myFolder", "urn:content-classes:mailfolder")

Interface IExchangeMailboxUtil

Anhang einem Element hinzufügen

Fügt einem bereits existieren Element (z.B. einem Termin) einen Anhang hinzu.

Parameter:

  • strItemId - ID des Elements, an das der Anhang hinzugefügt werden soll

  • fileAttach - Anhang, der hinzugefügt werden soll

  • strFileName - Name des Anhangs

  • strMimeType - Mime Type des Anhangs. Falls null, wird application/octet-stream verwendet

  • bIsContactPhoto - True, wenn eine Bilddatei einem Kontakt hinzugefügt werden soll

  • bDeleteAfter - True, wenn die Originaldatei nach dem Anhängen gelöscht werden soll

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def itemUtil    = ExchangeUtils.getItemUtil(connEx)
def strFileName = "myAttachment.txt"
def strMimeType = "text/plain"
def fileAttach  = new File(strFileName)

itemUtil.addAttachmentToItem(strItemId, fileAttach, strFileName, strMimeType, bIsContactPhoto, bDeleteAfter)

Interface IExchangeItemUtil

Exchange-Termin anlegen

Legt für den aktuellen Exchange-Benutzer einen neuen Termin an.

Parameter:

  • dtStartDate - Startdatum des Termins

  • dtEndDate - Enddatum des Termins

  • strSubject - Titel des Termins

  • strBody - Beschreibung des Termins

Werden nach dem Erstellen des Termins weitere Eigenschaften über set()-Methoden definiert, müssen abschließend mit appointment.save() der Termin erneut gespeichert werden, um die Änderungen zu übernehmen.

Beispiel

def appointment = aptUtil.createNewAppointment(dtStartDate, dtEndDate, strSubject, strBody)

appointment.setLocation("Konferenzraum")
appointment.save()

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx  = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def aptUtil = ExchangeUtils.getAppointmentUtil(connEx)

def appointment = aptUtil.createNewAppointment(dtStartDate, dtEndDate, strSubject, strBody)

Interface IExchangeAppointmentUtil

Exchange-Kontakt anlegen

Legt für den aktuellen Exchange-Benutzer einen neuen Kontakt an.

Parameter:

  • strLastName - Nachname des Kontakts

  • strFirstName - Vorname des Kontakts

  • strMail - E-Mail-Adresse des Kontakts

  • strMailbox - Mailbox des Benutzers, zu dem der Kontakt angelegt werden soll. Wird null angegeben, wird die Mailbox des aktuellen Benutzers verwendet.

Werden nach dem Erstellen des Kontakts weitere Eigenschaften über set()-Methoden definiert, muss der Termin abschließend mit contact.save() erneut gespeichert werden, um die Änderungen zu übernehmen.

Beispiel

def contact = contactUtil.createNewContact("Doe", "John", "john.doe@example.org", null)

contact.setJobTitle("Developer")
contact.save()

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx      = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def contactUtil = ExchangeUtils.getContactUtil(connEx)

def contact = contactUtil.createNewContact(strLastName, strFirstName, strMail, strMailbox)

Interface IExchangeContactUtil

Exchange-E-Mail generieren und versenden

Generiert eine neue E-Mail für den aktuellen Exchange-Benutzer.

Parameter:

  • strFrom - Absenderadresse

  • strTo - Empfängeradresse

  • strSubject - Betreff

  • strBody - Nachrichtentext

Werden nach dem Erstellen der E-Mail weitere Eigenschaften über set()-Methoden definiert, muss der Entwurf abschließend mit message.save() erneut gespeichert werden, um die Änderungen zu übernehmen.

Beispiel

def message = msgUtil.createNewDraft("sender@example.org", "recipient@example.org", "Example subject", "Example text")


message.setCc("cc_recipient@example.org")
message.save()
message.send()

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx  = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def msgUtil = ExchangeUtils.getMessageUtil(connEx)

def message = msgUtil.createNewDraft(strSender, strRecipient, strSubject, strBody)

Interface IExchangeMessageUtil

Exchange-Notiz anlegen

Legt für den aktuellen Exchange-Benutzer eine neue Notiz an.

Parameter:

  • strText - Text der Notiz

  • strMailBox - Name der Mailbox, in der die Notiz angelegt werden soll. Wird null angegeben, wird die Mailbox des aktuellen Benutzers verwendet.

Beispiel

def noteUtil = ExchangeUtils.getNoteUtil(connEx)
def note = noteUtil.createNewNote("My note", null)

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx   = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def noteUtil = ExchangeUtils.getNoteUtil(connEx)

def note = noteUtil.createNewNote(strText, strMailBox)

Interface IExchangeNoteUtil

Exchange-Aufgabe anlegen

Legt für den aktuellen Exchange-Benutzer eine neue Aufgabe an.

Parameter:

  • dtStart - Startdatum der Aufgabe

  • dtDue - Fälligkeitsdatum der Aufgabe

  • strSubject - Titel der Aufgabe

  • strMailBox - Name der Mailbox, in der die Aufgabe angelegt werden soll. Wird null angegeben, wird die Mailbox des aktuellen Benutzers verwendet.

Beispiel

def taskUtil = ExchangeUtils.getTaskUtil(connEx)

def dtStart, dtDue, reminder

use (groovy.time.TimeCategory)
{
	dtStart   = new Date() + 1.day
	dtStart   = dtStart.clearTime()
	dtDue    = dtStart + 5.days
	reminder = dtDue - 12.hours
}

def task = taskUtil.createNewTask(dtStart, dtDue, "Task subject", null)

task.setPercentComplete(25.0)
task.setUserDefinedFieldValue("ReminderTime", VH.getValueHolder(reminder))
task.setUserDefinedFieldValue("ReminderSet",  VH.getValueHolder(true))

task.save()

Snippet

import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeConnectionUtil
import de.uplanet.lucy.server.businesslogic.exchange.util.ExchangeUtils

def connEx   = ExchangeConnectionUtil.getConnectionForWorkflowAction(g_context)
def taskUtil = ExchangeUtils.getTaskUtil(connEx)

def task = taskUtil.createNewTask(dtStart, dtDue, "Task subject", null)

Interface IExchangeTaskUtil

Portlets

Portlet nur anzeigen, wenn Datensätze in Tabelle enthalten sind

Mit dem folgenden Skript wird das Portlet nur angezeigt, wenn die darin enthaltene Tabelle Datensätze enthält und die Einstellung "Anzeige des Portlets im Web durch Groovy-Skript einschränken" gesetzt ist. Das Skript kann genauso für die Einstellung "Auswahl des Portlets im Web durch Groovy-Skript einschränken" verwendet werden - dann ist das Portlet nicht mehr in den Portlet-Einstellungen unter "Portlets aus Applikationen" aufgeführt und kann damit nicht auf der Portalseite eingebunden werden.

Snippet

g_dataCollection.getDataRange("768A3C783F2BC9FD7EF20B1979FD3B27498779E2").getNumberOfRecords() > 0

Tipps & Tricks - Portlets mit Groovy filtern

Einschränkung von Portlets im Portletcontainer

Um Portlets im Portletcontainer einzuschränken, muss als Rückgabewert eine Liste mit Portlet-Objekten zurückgegeben werden. Mit "g_portletPool" können alle verfügbaren Portlet-Objekte abgerufen werden. In diesem Beispiel würde nur das Portlet mit der GUID zur Verfügung stehen, die anstatt dem Platzhalter eingetragen wird.

Snippet

def portletsAus = []

for(portlet in g_portletPool){
	if(portlet.getPageGuid() == "<GUID>)"{
			portletsAus.add(portlet) 
	}
}
return portletsAus 

Class GroovyPortlet

Steuerung der Anzeige mit booleschem Wert

Mit der Rückgabe eines booleschen Wertes kann z.B. in den Portleteigenschaften gesteuert werden, ob ein Portlet angezeigt wird oder nicht:

Snippet

def isok = "<check if a portlet shall be displayed>"
if( isok)
	return true
else
	return false

Class GroovyPortlet

WebSockets

Versenden einer Text-Nachricht

Beispiel

import de.uplanet.lucy.server.websocket.groovy.GroovyWebSocketTopic
GroovyWebSocketTopic.sendTextMessage("D00F000000000000000000000000000000000000", "Hello world!")

Snippet

import de.uplanet.lucy.server.websocket.groovy.GroovyWebSocketTopic
GroovyWebSocketTopic.sendTextMessage("<topicGUID>", "<string>")

Class GroovyWebSocketTopic

Versenden einer JSON-Nachricht

Beispiel

import de.uplanet.lucy.server.websocket.groovy.GroovyWebSocketTopic

def msg = [
    seq: 1,
    greet: "Hello world!"
]

GroovyWebSocketTopic.sendJsonMessage("D00F000000000000000000000000000000000000", msg)

Snippet

import de.uplanet.lucy.server.websocket.groovy.GroovyWebSocketTopic

def msg = [
	seq: 1,
	greet: "<string>"
]

GroovyWebSocketTopic.sendJsonMessage(${cursor}"<topicGUID>", msg)

Class GroovyWebSocketTopic

Auf eine Unterbrechungsanforderung prüfen

checkInterrupted()

Prüft ob entweder

  • der Thread, der den Prozess ausführt, von einem anderen Thread eine Unterbrechungsanforderung erhalten hat oder

  • der für den Prozess eingestellte Timeout überschritten wurde.

Verwenden sie diesen Aufruf in Skripts, die sich in solchen Fällen kooperativ verhalten sollen.

Snippet

checkInterrupted()

Class CheckInterruptedClosure

Automatischer Logout implizit generierter Sessions

Wird ein Groovy-Endpoint aufgerufen, ohne dass der Client eine gültige Session-ID mitschickt, so wird auf dem Server implizit eine anonyme Session erzeugt. Mit dem folgenden Skript kann verhindert werden, dass diese Sessions bis zum Timeout der anonymen Session auf dem Server bestehen bleiben. Dabei ist das Kriterium für den automatischen Logout, dass der Client kein co_SId-Session-Cookie gesendet hat.

Snippet

import de.uplanet.server.transaction.TransactionManager

// if the client did not send a session cookie we logout
// the session after the current transaction has finished
if (!g_request.get('co_SId'))
	TransactionManager.addAfterCommitAction {g_session.logout()}

Scheduler-Job starten

Eingabeparameter: ID bzw. GUID des Jobs. Die Parameter "testParam" und "greeting" aus dem folgenden Snippet stehen im SharedState im gestarteten Timer-Prozess zu Verfügung.

Snippet

import de.uplanet.lucy.server.scheduler.JobStarter
JobStarter.startJob("B39F3AA1C06E56FD06538F92F46C075333F97F68", [testParam: true, greeting: ' Hello world!'])

Tipps & Tricks - Prozesse starten

Externes Programm ausführen

Führt ein externes Programm aus. Weitere Informationen finden Sie hier.

Snippet

def pOut = new StringBuffer()
def pErr = new StringBuffer()
def proc = [""].execute()

proc.consumeProcessOutput(pOut, pErr)
proc.waitForOrKill(10000) // 10 seconds

if (proc.exitValue() == 0)
{
	// success
	// ...
}
else
{
	// an error occurred
	g_log.error(pErr.toString())
}

Class Process

Neue GUID erzeugen

Erzeugt eine neue GUID.

Snippet

newGuid()

Class NewGuidClosure

GUID prüfen

Prüft, ob ein gegebener String eine GUID im Sinne von Intrexx ist. Im Falle, dass der übergebene Wert null ist, liefert die Methode false zurück.

Beispiel:

def valueToCheck = 'DAF7CECF66481FCABE50E529828116EAFE906962'
if (Guid.isStringRepresentation(valueToCheck))
{
    //valid GUID
}

Snippet

Guid.isStringRepresentation('<GUID>')

Class Guid

ValueHolder erzeugen

Erzeugt einen ValueHolder für einen einfachen Datentyp. Wird null übergeben, so wird ein NullValueHolder erzeugt. Dessen Wert null ist; hasValue() gibt false zurück.

Snippet

vh()

GUIDs parsen

GUIDs aus textuellen Eingaben parsen. Es sind mehrere Parameter möglich.

Snippet

parseGuids()

Zeitzone des Portals ermitteln

Hier finden Sie Skript für die Ermittlung der Default-Zeitzone, die in den Portaleigenschaften in den Ländereinstellungen festgelegt ist.

Snippet

import  de.uplanet.lucy.server.DefaultTimeZone
def tz = DefaultTimeZone.get()

Class DefaultTimeZone

Startzeit und Uptime des Portals ermitteln

Snippet

g_portal.getStartTime()
g_portal.getUptimeMillis()

Class GroovyPortalInfo

Vorlage - Groovy-API für Shortlinks.

Kriterien für das Matchen von Shortlinks mit konfigurierter Shortlink-Regel:

Kriterien für den Match

1.) gleiches statisches Pfad-Präfix

2.) gleiche Anzahl Pfadkomponenten bzw. Pfadkomponenten + Variablen und gleiche Anzahl Slashes

3.) Pfadkomponenten, die nicht Variablen sind, müssen gleich sein

Für Pfadkomponenten, die Variablen sind, bekommen die Variablen die Werte der entsprechenden Pfadkomponenten.

Erzeugung der Ziel-URLs

Ziel-URLs können absolut oder relativ zum Wurzelverzeichnis der Website sein. Im ersten Fall können beliebige Ziele angegeben werden. Im zweiten Fall wird als Ziel die Website angenommen, die im Browser des Benutzers aufgerufen wurde.

Die beim Matchen belegten Variablen können im Ziel-URL sowohl als Pfadbestandteil als auch im Querystring verwendet werden. Querystring-Parameter, die in der Eingabe-URL, nicht aber in der konfigurierten Ziel-URL vorkommen, werden in die Ausgabe-URL übernommen.

Beispiele


import de.uplanet.lucy.server.urlredirect.scripting.groovy.GroovyRedirectRules

//----------------------------------
// create a new empty configuration
//----------------------------------

def rules = GroovyRedirectRules.createNew()
assert rules.isEmpty() // no rules
assert rules.size() == 0 // no rules


//---------------------------------------
// create and append some redirect rules
//---------------------------------------

def rule1 = rules.createNewRule('/from/path/1', '/to/path1')
rules << rule1 // append it
	assert rules.size() == 1

	def rule2 = rules.createNewRule('/from/path/2', '/to/path2')
	rules << rule2
	assert rules.size() == 2

	def rule3 = rules.createNewRule(
		fromUrl: '/search/${term}',
		toUrl:   'https://www.google.de/search?q=intrexx+${term}')
	rules << rule3
	assert rules.size() == 3

	def rule4 = rules.createNewRule(
		fromUrl: '/customer/${custNo}',
		toUrl:   '/foo/?customer=${custNo}',
		appGuid: 'DEADBEEFDEADBEEFDEADBEEFDEADBEEFDEADBEEF')
	rules << rule4
	assert rules.size() == 4

	def rule5 = rules.createNewRule(
		fromUrl: '/invoice/${invoiceNo}',
		toUrl:   '/bar/?invoice=${invoiceNo}',
		appGuid: 'DEADBEEFDEADBEEFDEADBEEFDEADBEEFDEADBEEF')
	rules << rule5
	assert rules.size() == 5

	// check if a rule is in the rules list
	assert rules.contains(rule1) == true
	assert rules[1] == rule2

	// save the newly created redirect rules; this overwites internal/cfg/urlredirect.cfg
	// and thus deletes all existing rules defined therein
	rules.save()

	rules = null // no reference to the rules anymore


	//-------------------------------------------------------
	// load existing rules from internal/cfg/urlredirect.cfg
	//-------------------------------------------------------

	rules = GroovyRedirectRules.load()
	assert rules.size() == 5

	// list the from URLs
	def froms = rules*.fromUrl
	assert froms == [
		'/from/path/1',
		'/from/path/2',
		'/search/${term}',
		'/customer/${custNo}',
		'/invoice/${invoiceNo}']

	// find a certain rule
	def rule = rules.find {it.fromUrl == '/customer/${custNo}'}
	assert rules.indexOf(rule) == 3
	assert rule.fromUrl == '/customer/${custNo}'
	assert rule.toUrl   == '/foo/?customer=${custNo}'

	// modify the rule
	rule.toUrl = '/bar/?customer=${custNo}'
	assert rule.toUrl   == '/bar/?customer=${custNo}'

	// find all rules that belong to application with
	// GUID DEADBEEFDEADBEEFDEADBEEFDEADBEEFDEADBEEF
	def appRules = rules.findAll {it.appGuid == 'DEADBEEFDEADBEEFDEADBEEFDEADBEEFDEADBEEF'}
	assert appRules.size() == 2

	// remove these rules
	rules.removeAll(appRules)
	assert rules.size() == 3

Snippet

import de.uplanet.lucy.server.urlredirect.scripting.groovy.GroovyRedirectRules
def rules = GroovyRedirectRules.load()
// do something with the redirect rules
rules.save()

Class GroovyRedirectRules