Quick Tip: Validate current user by enforcing him to enter his password

Category: Quick-Tipp, AdminCamp, Entwicklung, IBM Notes, LotusScript, Sicherheit, C-API

Quick-TippIBM Notes
I had a "small" request from a customer last week: He'd be interested in the extended commercial version of our assono Password-Safe. But his internal audit team had the requirement that a user should have to re-enter his Notes client password when opening a document or copying it directly to the clipboard from a view.

There is a @Command for this: ToolsUserLogoff. It just logs the user off, thus you have to combine it with some kind of server access to get the password input dialog to appear, like described here: Forcing user re-entry of passwords for electronic signatures in script.

This approach has three drawbacks:
1. It doesn't work offline, i.e. on a local replica, because it depends on the server contact for the  password input dialog to be opened.
2. I need it to protect the opening of existing documents. When the user just cancels the password input dialog, the document continues to be opened.
3. The formula code must be placed in the QueryOpen event of the form. But I really need to put some LotusScript there.

Thus I had to search further for a solution working in LotusScript. And I found one by Eknori from 2004: @Command(ToolsUserLogoff) in Lotus Script.
It had to be adopted for the current versions of Notes, because the log out key had been changed from F5 to Ctrl-F5.

I still wasn't convinced this would be the best possible solution. Its strictly Windows only and the user keeps logged out, when he cancels the dialog, I don't know, it would work locally etc.

I looked further and found a great idea: Use the Notes C api to access privat portions of the user's ID file, namely the REGGetIDInfoString function with REGIDGetPrivateKey as infoType.
  • This would bring up the password input dialog, but doesn't log off the user.
  • It would work locally without any server contact.
  • I even could determine, if the user cancelled the dialog box, and react, if necessary.
Thank you, Davy Vanherbergen, for your OpenNTF Code Bin post (from 2003!): Call notes password prompt from lotusscript 

I took the idea and implemented it "my way", using my C api helper functions and letting the user choose another ID file, if the configured ID file is not his own.

Function ValidateCurrentUser As Boolean
        ' * validates current user by letting him enter his password
        ' *
        ' * @return  True, if user has successfully entered his password
        ' *
        ' * @author  Thomas Bahn/assono <tbahn@assono.de>
        ' * @version 2014-09-30
        ' */

        Const MAXOUTBUFRLEN% = 4096
        Dim idFileName As String
        Dim returnCode As Integer
        Dim userNameBuffer As String*MAXUSERNAME
        Dim actualLen As Long
        Dim currentUserName As String                
        Dim outBufrLen As String*MAXOUTBUFRLEN
        If Not IsDebugMode() Then On Error GoTo errorHandler
        ValidateCurrentUser = False
        idFileName = session.GetEnvironmentString("KeyFileName", True)
        returnCode = REGGetIDInfoString(idFileName, REGIDGetName, _
                userNameBuffer, MAXUSERNAME, actualLen)
        Call ShowCAPIErrorIfAnyAndEnd(returnCode, "REGGetIDInfo", _
        currentUserName = Left(userNameBuffer, actualLen - 1)        
        Do While session.UserName <> currentUserName
                ' ID file configured in notes.ini is not the ID file of the
                ' current user
                idFileName = uiws.OpenFileDialog(False, _
                        "Choose your ID file:", "*.ID|", _
                        GetNotesDataDirectory(), idFileName)(0)

                returnCode = REGGetIDInfoString(idFileName, REGIDGetName, _
                        userNameBuffer, MAXUSERNAME, actualLen)
                Call ShowCAPIErrorIfAnyAndEnd(returnCode, "REGGetIDInfo", _
                currentUserName = Left(userNameBuffer, actualLen - 1)
        returnCode = REGGetIDInfoString(idFileName, REGIDGetPrivateKey, _
                        outBufrLen, MAXOUTBUFRLEN, actualLen)
        If returnCode = -32355 Then
                Exit Function ' user cancelled dialog
                Call ShowCAPIErrorIfAnyAndEnd(returnCode, "REGGetIDInfo", _
        End If

        ' when we get here, the user must have entered his password
        ' successfully
        ValidateCurrentUser = True
        Exit Function
        If HandleError() = RESUME_NEXT_LINE Then Resume Next
        Exit Function
End Function

GetNotesDataDirectory() is a helper function to get the name of the Notes data directory. Replace it by your own function or a String constant.
And adopt the error handling code (IsDebugMode() and HandleError()) to your standard.

Read More


AdminCamp 2014: Weil sicher sicher sicher ist - Sicherheit in IBM Domino

Category: AdminCamp, Administration, IBM Domino, IBM Notes, Konferenzen

Der zweite Tag des diesjährigen AdminCamps nähert sich langsam dem Ende. Ich warte noch gespannt auf die Fragestunde nach dem Abendessen. Auf meine Frage gestern habe ich ganz viele wertvolle Antworten bekommen, so dass ich letzte Nacht gleich eine Lösung bauen konnte. Dazu gleich mehr in einem weiteren Blog-Eintrag.

Hier schon mal die Präsentation zu meinem heutigen Vortrag in Track 2, Session 3: Weil sicher sicher sicher ist - Sicherheit in IBM Domino:


IBM Notes Traveler IF7 und 9.0.1 IF6 erschienen

Category: Administration, IBM Notes Traveler

Lotus Notes Traveler
In aller Kürze: IBM hat die Interim Fixes IF7 und 9.0.1 IF6 für IBM Notes Traveler heraus gebracht. Beide Fixes bieten bereits Support für iOS 8.

Für mehr Informationen zum Interim Fix Pack 6 für Traveler 9.0.1:

Für mehr Informationen zum Interim Fix Pack 7 für Traveler

Die Liste der Änderungen gibt es wie immer im IBM Domino-Wiki.


Quick-Tip: Script library prevents execution of agent

Category: Entwicklung, IBM Notes, Quick-Tipp

Quick-TippIBM Notes
Today I solved a mysterious problem, a customer of mine had with an scheduled LotusScript agent: It just didn't ran!

It was executed by the agent manager, e.g. via tell amgr run "some-db.nsf" 'Test':
AMgr: Start executing agent 'Test' in 'some-db.nsf'
AMgr: Agent 'Test' in 'some-db.nsf' completed execution
But event a Print "TEST" as the first line of its Initialize sub didn't work - not to speak of its original "payload".

We checked everything (really), including, but not limited to server security, application properties ("don't execute backend agents"), ACL, agent properties, ...

Then I built another agent copying Use statements and other code - step by step - and tested and retested: it just worked as expected.

Finally I deleted the "corrupt" agent and renamed the new one - and it stoped working! Renamed to its original name - it worked - renamed to the name of the deleted agent - worked not.

I fired up the Domino Administrator and switched on the "God mode" (aka Full-access administration) and searched in the Designer for another "hidden" agent with the same name. Nope, nothing.

But I found a script library with the exact same name. Renamed it ... and ... the ... agent .. worked!!!

Lesson learned: Script libraries with the same name as an agent prevent the execution of this agent.


Fix Pack 2 für IBM Notes und Domino 9.0.1 erschienen

Category: Administration, IBM Domino, IBM Notes

IBM NotesIBM Domino
IBM hat kürzlich das 2. Fix Pack für IBM Notes und Domino 9.0.1 heraus gebracht. Aus meiner Sicht nichts Spektakuläres (nicht zu erwarten), aber es werden neuere Versionen in der "Umgebung" offiziell unterstützt, z. B. Microsoft Internet Explorer 11 für XPages und Citrix XenApp 7.5 für den Client, und einige Fehler korrigiert.

Weitere Informationen:
IBM Notes/Domino 9.0.1 Fix Pack 2 Release Notice
Download Options for Notes & Domino 9.0.1 Fix Packs


Auch mit Firefox 31 nun keine selbstsignierten SSL Zertifikate mehr unterstützt (Update 06.08.)

Category: Administration, IBM Domino, IBM Notes Traveler, Quick-Tipp

Quick-Tipp Lotus Notes Traveler IBM Domino
Die Luft für Nutzer selbstsignierter SSL Zertifikate wird immer dünner.
Schon vor einiger Zeit berichteten wir darüber, dass Windows Phone keine selbst signierten Zertifikate unterstützt. Diese Problem ist nun bei einem anderen Kunden wieder aufgetaucht, der nun auch mit einem Nokia Lumia experimentieren wollte. Erschwerend war hier nun aber, dass auch der Zugriff auf die Traveler-Weboberfläche mit Firefox plötzlich nicht mehr möglich war. Statt der erwarteten Anmeldemaske erschien eine Fehlermeldung, die einem mitteilte, dass das Zertifikat ungültig sei. Keine Möglichkeit mehr, die Meldung zu ignorieren bzw. eine Ausnahme hinzuzufügen.

Dazu gibt es seit gestern eine Technote bei IBM.
Es gibt offenbar mit Firefox 31 einen neuen Validierungsalgorithmus für SSL-Zertifikate, der das neue Verhalten zeigt. Diesen kann man über die Konfiguration (about:config) deaktivieren, um das alte Verhalten zurück zu bekommen. Das ist natürlich aus mehreren Gründen keine langfristige Lösung:
  • Der alte Algorithmus wird mit der Zeit aus Firefox ausgebaut werden (laut Mozilla Wiki), so dass man sich dem Problem mittelfristig wieder wird stellen müssen.
  • Es ist zu viel Aufwand, wenn man das nicht zentral steuern kann - was vermutlich nicht bei allen Unternehmen der Fall ist
  • Es bedeutet einen vermutlich sichereren Algorithmus mutwillig zu deaktivieren, weil man...
  • ...nicht das ohnehin sicherere, aber kostenpflichtige/-günstige, vertrauenswürdige Zertifikat kaufen möchte.
-> Also besser gleich ein Zertifikat einer vertrauenswürdigen CA ausstellen lassen.

BTW: Die von IBM vorgeschlagene "Lösung" funktioniert .

Update vom 06.08.

...zumindest manchmal.
In dem Fall, in dem es funktionierte, hatte ich vorher noch nie mit diesem Browser auf den fraglichen Server zugegriffen.
Jetzt habe ich mit meinem lokalen Testserver noch ein paar Dinge ausprobiert und stellte dabei fest, dass die "Lösung" von IBM eben nicht immer zuverlässig funktioniert.
Erst habe ich noch versucht, die Zertifikate-Datenbank (cert8.db) im Firefox-Profil zu löschen, aber das brachte keine Erleichterung. Erst die Zurücksetzung über about:support hat das Problem gelöst - auf Kosten meiner Einstellungen und Addons. Dabei wird aber auch selbstverständlich die oben beschriebene Einstellung ebenfalls zurückgesetzt und es funktioniert nachher dennoch. Hier muss also offensichtlich noch einiges klargestellt werden.

Offenbar speichert Firefox die temporären Zertifikate besuchter Webseiten noch anderswo als nur in der cert8.db und beim Wechsel des Algorithmus wird die entsprechende Datenbank anscheinend "korrumpiert".

Wenn hier jemand noch weitere Hinweise geben kann. Willkommen


Die 30-Tage-iFixes für IBM Connections 5

Category: IBM Connections, Administration

IBM Connections
Kaum wird IBM Connections 5 einen Monat alt, schon gibt es die ersten "required" iFixes: "All IBM Connections 5.0 environments must apply iFixes LO80688 and LO80990." Eine weitere wichtige Voraussetzung ist der WebSphere Application Server iFix PM91417 (Partial application updates will not update JARs in non-active Java EE locations).

Die IBM Technote Update strategy for IBM Connections 5.0 enthält auch relevante Informationen für IBM Connections-Installationen auf einer Oracle-DB und für Leute, die ihr Connections von 4.5 auf 5 aktualisieren wollen.


IBM Notes-Kunden dürfen jetzt auch Version 5 von IBM Connections nutzen

Category: IBM Connections, IBM Domino, IBM Notes

IBM ConnectionsIBM Notes
Seit knapp 2 Jahren dürfen IBM Notes-Kunden zwei Module von IBM Connections nutzen: IBM Connections Files und IBM Connections Profiles. Vor einem Monat ist IBM Connections 5 heraus gekommen und es war nur eine Frage der Zeit, wann die Berechtigung für Notes-Kunden aktualisiert werden würde.

Ehrlich gesagt, habe ich es etwas verpasst: Bereits am 1. Juli hat IBM diese Änderung verkündet: IBM Notes and Domino V9.0.1 adds new social software capabilities


Quick-Tipp: 'Verbergen-Formeln von Aktionen bei jedem Dok'wechsel prüfen' funktioniert nicht

Category: Quick-Tipp, IBM Notes, Entwicklung

Quick-TippIBM Notes
Es gibt immer mal wieder Tage, wo einem das Offensichtliche nicht ins Gesicht springt und man sucht und sucht und sucht...

Man kann bei einer Ansicht eine Eigenschaft einstellen, dass die Verbergen-Wenn-Formeln (hide when) jedes mal neu berechnet werden, wenn man auf ein anderes Dokument in der Ansicht geht bzw. darauf klickt.
A picture named M2

Das braucht man, wenn man z. B. Ansicht-Aktionen abhängig von Status des Dokuments anzeigen möchte, also die Aktion "Antrag genehmigen" in der Ansicht nur anzeigen möchte, wenn der aktuell ausgewählte Antrag auf "zu genehmigen" steht.

Ich wollte eine Aktion zum Kopieren des Feldinhalts in die Zwischenablage nur dann anzeigen, wenn das Feld "Passwort" ausgefüllt ist:
A picture named M3

So einfach funktioniert das - normalerweise. Und die gleiche Aktion in der Maske funktionierte auch, nur eben nicht in der Ansicht.

Nach längerer Suche und viel Ausprobieren bin ich dann auf die Lösung gekommen. Kern des Problems war, dass das Feld "Passwort" verschlüsselt gespeichert wird:
A picture named M4

Verschlüsselte Felder werden nicht "normal" im Dokument gespeichert, sondern in $SealData-Items.
A picture named M5

Sie können dann weder in Spalten angezeigt, noch in Spalten- oder Aktionsformeln benutzt werden.

Als Lösung habe ich ein neues Feld "PasswortEingegeben" in der Maske hinzugefügt, dass nur die Information speichert, ob das Passwort-Feld gefüllt ist. Im geöffneten Dokument kann man ja noch einfach auf die verschlüsselten Felder zugreifen.
A picture named M6

Danach habe ich das neue Feld in der Verbergen-Wenn-Formel der Aktion benutzt:
A picture named M7

Und es funktioniert!


Quick Tip: Get rid of those Scheduler messages each time the Domino server starts

Category: Administration, Entwicklung, IBM Domino, Quick-Tipp, C-API

Quick-TippIBM Domino
Chris Miller  is one of the best Domino administrators alive. He regularly writes for the SocialBiz user group and answers difficult questions about  Domino administration, like last week's From the SocialBiz Mailbox: Excluding Calendars from Mail-in Databases  

You all probably know those unnecessary "errors" the Scheduler writes each time, when it encounters a mail database, where it cannot find the database's owner in the Domino directory anymore.
SchedMgr: Error processing calendar profile document (NoteID: NT....) in database...:
Can't find $BusyName field on profile

SchedMgr: Error processing calendar profile document (NoteID: NT...) in database ...:
Cannot find user in Domino Directory

Perhaps, the user has left the company, doesn't use this mail database anymore or the database simply is a mail-in database.

The Scheduler task is important to validate and update freetime information about current users, but in the above cases, the mail database doesn't include important calendar information anymore. Thus it would be great to just tell the Schedule: "Please, ignore this database".

And Chris knows a solution: There is a small program "NoCal" to do this magic little trick.

But it has some limitations:
  • It's really, really old: Release: R5, Platform: Windows 95/98/NT, Date Posted: 04.05.2001
  • it has to be run from the command line and
  • it just can switch off the "Has Calendar" database option.
I felt this itching again: Can't I do better than this?  
  • Something small and transportable like an agent, you can easily put in your mail(-in) database template or any database, you want,
  • it should be easy to switch on and off this option and
  • it can be run comfortably in the Notes client.
 And I did it with through investigations, lot of tries (and failures) and some C API calls:

The basic agent looks like this:

Sub Initialize
        ' * gets current database's options, prints "Has Calendar" option,
        ' * toggles it and prints new status
        ' *
        ' * @author        Thomas Bahn/assono <tbahn@assono.de>
        ' * @version        2014-07-17
        ' */                

        Dim session As NotesSession
        Dim returnCode As Integer
        Dim hDB As Long
        Dim retDbOptions As Long
        On Error GoTo miniErrorHandler

        Set session = New NotesSession
        ' open the current database
        returnCode = NSFDbOpen(session.CurrentDatabase.FilePath, hDB)
        Call ShowCAPIErrorIfAnyAndEnd(returnCode, "NSFDbOpen", hDB)

        ' get current options
        returnCode = NSFDbGetOptions(hDB, retDbOptions)
        Call ShowCAPIErrorIfAnyAndEnd(returnCode, "NSFDbGetOptions", hDB)
        ' print current status
        If retDbOptions And  DBOPTION_HAS_CALENDAR Then
                Print "Database has calendar"
                Print "Database doesn't have calendar"
        End If
        ' toggle option
        returnCode = NSFDbSetOptions(hDB, _
                        retDbOptions Xor DBOPTION_HAS_CALENDAR, _
        Call ShowCAPIErrorIfAnyAndEnd(returnCode, "NSFDbSetOptions", hDB)
        ' get current options
        returnCode = NSFDbGetOptions(hDB, retDbOptions)
        Call ShowCAPIErrorIfAnyAndEnd(returnCode, "NSFDbGetOptions", hDB)
        ' print new status
        If retDbOptions And  DBOPTION_HAS_CALENDAR Then
                Print "Database now has calendar"
                Print "Database now doesn't have calendar"
        End If
        ' close the database
        returnCode = NSFDbClose(hDB)
        Exit Sub
        MessageBox "Error #" & Err & " occurred in line " & Erl & Chr$(10) &_
                "Error message: " & Chr$(10) & Error$, 48, "Error"
        If hDB <> 0 Then ' if there is a valid handle, try to close database
                returnCode = NSFDbClose(hDB)
        End If
End Sub

Read More

Kalender (Calendar)


Deutsche RSS-Feeds (German)

Custom Button Custom Button

English RSS feeds

Custom Button Custom Button