Gulp: JavaScript-Buildsystem

Nachdem ich ja im letzten Post beschrieben habe, wie man mit Hilfe von node und bower sich JavaScript Bibliotheken für seine Anwendung einbinden kann, will ich nun noch etwas mehr zeigen, was einem Node so zu bieten hat.

Typische Aufgabe während der Entwicklung ist ja, dass die HTML und JavaScript-Dateien vom lokalen Rechner auf einen Web-Server kopiert werden müssen. Dazu müssen zunächst alle Dateien, die auf den Server kopiert werden müssen identifiziert und dann kopiert werden.

In reinen .Net Projekten würde ich für das Deployment vielleicht zu MSBuild greifen – das hilft mir aber in meinem Fall nicht so wirklich weiter.

Mit gulp gibt es ein Buildsystem als Node-Module in JavaScript.

npm install gulp -g

installiert gulp und stellt es global zur Verfügung. Nun kann ich in meinem Projekt ein gulpfile.js erstellen.

Ein einfaches Buildfile kann z.B. so aussehen:

var gulp = require('gulp');
gulp.task('copy', function(){
    return gulp.src('app/*.html')
        .pipe(gulp.dest('dist/'));
})

Dabei werden alle *.html Dateien aus dem Verzeichnis app in das Verzeichnis dist kopiert. Existiert das Verzeichnis dist noch nicht, wird es zuvor erstellt. Dieses Beispiel ist natürlich sehr einfach. Mittels gulp copy kann nun die neue copy-Task von einer Konsole ausgeführt werden:

D:\projects\html_app>gulp copy
[14:25:01] Using gulpfile D:\projects\html_app\gulpfile.js
[14:25:01] Starting 'copy'...
[14:25:01] Finished 'copy' after 17 ms

Ein etwas fortgeschritteneres Buildfile könnte wie folgt aussehen:

var gulp = require('gulp'),
    uglify = require('gulp-uglify');

gulp.task('html', function () {
    return gulp.src('app/*.html')
        .pipe(gulp.dest('dist'));
})

gulp.task('js', function () {
    return gulp.src('app/*.js')
        .pipe(uglify())
        .pipe(gulp.dest('dist'));
})

gulp.task('default', ['html', 'js'], function () {
})

Die Task default wird dabei automatisch aufgerufen, wenn man gulp von der Kommandozeile startet. Als zweiter Parameter der Task werden die abhängigen Tasks angegeben. Diese werden also automatisch zuvor ausgeführt.

D:\projects\html_app>gulp
[14:26:15] Using gulpfile D:\projects\html_app\gulpfile.js
[14:26:15] Starting 'html'...
[14:26:15] Starting 'js'...
[14:26:15] Finished 'js' after 39 ms
[14:26:15] Finished 'html' after 49 ms
[14:26:15] Starting 'default'...
[14:26:15] Finished 'default' after 12 μs

In diesem Fall werden alle *.js Datei aus dem Verzeichnis app mit dem uglify-Package minimiert und dann nach dist geschrieben. Somit kann man also in dem app-Verzeichnis die Anwendung entwickeln und in dist erhält man immer alle Dateien, die man auf den Server kopieren muss.

Frontend-Entwicklung mit Node und bower

Immer häufiger greife ich für Anpassungen nicht mehr zu Visual Studio, sondern zu „einfachen“ Editoren, mit denen ich „mal eben“ ein paar Anpassungen in JavaScript machen – oder doch die eine oder Anwendung komplett in HTML & JavaScript schreibe.

Auch wenn man alles nur mit Notepad machen kann, so ist das doch irgendwie auf die Dauer etwas lästig. Immer wieder man man JavaScript Dateien auf den Server kopieren oder man muss Coffee-Script Dateien auf der Kommandozeile durch den entsprechenden Compiler jagen und dann mit den anderen Scripten zum Server kopieren.

Mit Notepad++ kann man das schon etwas verbessern, indem man Plugins wie NppExec verwendet. Wie man mit NppExec Dateien deployen kann, habe ich ja in einem früheren Post schon mal beschrieben. Aber irgendwann hat man auch dort Grenzen erreicht.

Lange habe ich mich gefragt, ob ich Node wirklich brauche. Ich finde JavaScript toll, aber muss ich das mit Node auch auf dem Server ausführen? Inzwischen habe ich erkannt: Node ist doch irgendwie total cool, gerade um HTML & JavaScript basierte Lösungen zu erstellen.

Im Folgenden will ich einmal einen Eindruck geben, wie so ein Projekt exemplarisch aussehen kann.

Zunächst muss man natürlich Node installiert haben. Das geht am besten via Chocolatey. Hat man Chocolatey installiert kann man mit choco install nodejs Node installieren.

Für unsere neues Projekt muss als erstes ein Arbeitsverzeichnis erstellt werden und das für die Arbeit mit Node vorbereitet werden

mkdir html_app
cd html_app
git init & npm init

Als Ergebnis erhält man eine package.json Datei.

{ 
    "name": "html_app", 
    "version": "1.0.0", 
    "description": "", 
    "main": "index.html", 
    "author": "Henning Eiben", 
} 

Diese Datei beschreibt das aktuelle Projekt/Paket und dient auch dazu um alle verwendeten Pakete zu speichern. Nun kann man mit npm sich Node Pakete installieren. Als erstes installiere ich bower. Das ist ein Paket um JavaScript-Bibliotheken für Anwendungen zu verwalten. Da ich Bower häufiger gebrauche installiere ich das gleich global.

npm install -g bower 

Nun kann ich mir mit Bower ein paar Bibliotheken für meine JavaScript-Anwendung laden. In diesem Fall will ich Bootstrap und Knockout verwenden. Zuvor initialisiere ich mit bower init noch eine bower.json. Sie dient ähnlich wie die packages.json dazu um alle verwendeten Pakate zu speichern. Mit

bower install bootstrap knockout --save 

Kann ich nun die beiden Bibliiotheken installieren. Durch das --save werden die Bibliotheken in der bower.json als Abhängigkeit gespeichert. Die bower.json sieht dann so aus:

{ 
    "name": "html_app", 
    "version": "0.0.0", 
    "authors": [ 
        "Henning Eiben <eiben@busitec.de>" 
    ], 
    "ignore": [ 
        "**/.*", 
        "node_modules", 
        "bower_components", 
        "test", 
        "tests" 
    ], 
    "dependencies": { 
        "bootstrap": "~3.3.5", 
        "knockout": "~3.3.0" 
    } 
} 

Dabei wurde neben bootstrap und knockout auch jquery in der Version 2.1.4 installiert, weil das von Bootstrap benötigt wird – ohne dass ich mich darum kümmern musste.

D:\projects\html_app>bower install bootstrap knockout --save 
bower cached git://github.com/twbs/bootstrap.git#3.3.5 
bower validate 3.3.5 against git://github.com/twbs/bootstrap.git#* 
bower cached git://github.com/SteveSanderson/knockout.git#3.3.0 
bower validate 3.3.0 against git://github.com/SteveSanderson/knockout.git#* 
bower cached git://github.com/jquery/jquery.git#2.1.4 
bower validate 2.1.4 against git://github.com/jquery/jquery.git#>= 1.9.1 
bower install knockout#3.3.0 
bower install bootstrap#3.3.5 
bower install jquery#2.1.4 
knockout#3.3.0 bower_components\knockout 
bootstrap#3.3.5 bower_components\bootstrap 
└── jquery#2.1.4 
jquery#2.1.4 bower_components\jquery 

Nun kann mit dem Editor der Wahl begonnen werden die Anwendung zu erstellen. Die Bibliotheken, die über bower installiert wurden liegen dabei in dem Verzeichnis bower_components, die Node-Pakete liegen in node_modules.

Wenn man nun die Anwendung z.B. in git einchecked oder jemand anderem zur Verfügung stellt, dann muss man diese beiden Verzeichnissen nicht mit weitergeben.

Stattdessen reicht es mit npm install & bower install einfach die in der packages.json und bower.json gespeicherten Pakete und Bibliotheken wieder herzustellen.

Debugging von Nintex Workflows

Das Debuggen von Workflows ist immer wieder eine Herausforderung, insbesondere im Umfeld von SharePoint. Die hauseigenen Workflows, die man mit dem SharePoint-Designer erstellen kann, lassen Funktionen für das Debugging nahezu ganz vermissen. Man kann hier ausschließlich in den Workflow-Verlauf Nachrichten schreiben um nachvollziehen zu können, welchen Weg ein Workflow während der Ausführung gegangen ist. Das ist aus mehreren Gründen “problematisch”:

Man muss sehr viele Nachrichten in den Verlauf schreiben, typischerweise gibt man dort den Wert von Variablen aus und beschreibt den Fortschritt. Diese Workflow-Schritte haben keine funktionale Bedeutung für den eigentlichen Prozess, kosten aber dennoch “Zeit”. Zudem dienen diese Schritte ja auch nicht dem eigentlichen Workflow und “verstopfen” somit den eigentlichen Prozess.

Als Programmierer ist man das “mehr” gewohnt. Wenn man nachvollziehen will warum sich ein Programm auf die eine oder andere Art & Weise verhält, dann “debuggt” man das Programm einfach. Währenddessen kann man sich den Inhalt von Variablen ansehen und somit nachvollziehen welchen Weg ein Programm genommen hat.

Bei Nintex geht das ebenfalls. Neben der visuellen Darstellung des Workflows, der den durchlaufenen Pfad farblich kennzeichnet (grün) und die aktuell ausgeführte Aktion hervorhebt (gelb) gibt es das sogenannte Verbose Logging.

Workflow-Verlauf

Beim Verbose Logging werden bei jeder Aktion die Werte von allen Variablen und den wichtigsten Workflow-Daten zu beginn der Aktion und am Ende der Aktion aufgezeichnet. Wenn man sich anschließend den Ablauf des Workflows ansieht kann man mit einem Klick auf eine Aktion sich all dieser Vorher/Nachher Werte anzeigen lassen. Änderungen, die während der Aktion an Werte vorgenommen wurden werden dabei ebenfalls farblich hervorgehoben.

Verbose Logging

Dabei ist allerdings zu beachten, dass diese Transparenz im Workflow durchaus ihren Preis hat. Das Aufzeichnen dieser ganzen Werte kostet Zeit und all diese Werte müssen in der Nintex-Datenbank gespeichert werden. Laufen sehr viele Workflow-Instanzen parallel, dann kann die Größe der Datenbank auch durchaus schnell anwachsen.

Um das Verbose Logging zu nutzen muss das in den Workflow-Einstellung des jeweiligen Workflows aktiviert werden. Somit werden nicht automatisch für alle Workflows diese Daten gesammelt, sondern man kann das pro Workflow individuell aktivieren. Zudem muss die Funktion auch noch global in der Zentraladministration einmalig aktiviert werden, zusammen mit der Angabe, wie lange die detaillierten Informationen gespeichert werden sollen.

Workflow-Einstellungen

Einstellung zum Verbose-Logging in der Zentraladministration

Wenn bspw. bei einem Workflow das Verbose Logging aktiv ist um den Ablauf auf einem Testsystem genau nachzuverfolgen und dieser Workflow anschließend ohne Anpassung auf ein Produktivsystem transportiert wird, dann muss das nicht zwangsläufig zu Leistungseinbußen führen, wenn auf dem Produktivsystem in der Zentraladministration die Funktion für das Verbose Logging nicht aktiv ist.

Neue Konferenz: ShareDev Cologne

Wenn es um Community-Events geht, dann ist die dotnet Cologne eine der Maßstäbe. Schon seit Jahren reisen immer wieder bekannte Persönlichkeiten aus der DotNet Community nach Köln, um dort an einem Tag geballtes Wissen an die Community zu geben. Dementsprechend ist die Veranstaltung auch immer innerhalb von kürzester Zeit komplett ausgebucht. Dieses Jahr war die Anmeldung keine 10 Minuten offen um alle 400 Karten zu vergeben.

 

ShareDev Cologne am 11. September 2015

 

Am 11. September findet in diesem Jahr zum ersten Mal eine neue Veranstaltung von den gleichen Organisatoren statt: die ShareDev Cologne. Der Fokus im vielversprechenden Session-Plan liegt gezielt auf SharePoint, Office 365 und Azure.

In der Liste der Sprecher finden sich – wie auch schon bei der Schwester-Veranstaltung – viele bekannte Namen aus der deutschsprachigen DotNet Community, darunter 13 MVP´s.

Folgende Zielgruppen werden für die ShareDev angesprochen:

  • Architekten
  • technische Entscheider
  • Software-Entwickler
  • IT-Professionals

Auf jeden Fall eine empfehlenswerte Veranstaltung!

Datenbankzugriff in SharePoint 2013 mit BCS und SQL-Login

Mit dieser Anleitung will ich zeigen, wie man mit dem Secure Store in SharePoint auf Datenbanken über ein SQL-Login zugreifen kann.

Ausgangslage

Ich habe auf einem MS-SQL Server die wohl bekannte NorthWind Datenbank eingerichtet. Auf die Datenbank hat mein Benutzer busitec\eiben Zugriff und es gibt einen SQL-Benutzer mit dem Login „northwnd“.

Externer Inhaltstyp

Zunächst einmal muss der externe Inhaltstyp – wie von Simon auch schon beschrieben – angelegt werden.

image

image

Danach kann man im Vorgangsdesigner eine neue SQL-Verbindung angeben. Hier sind also der Name des SQL-Server (ggf. mit Instanz) und der Name der Datenbank anzugeben. Zudem kann der Verbindung optional noch ein eigene Name gegeben werden.

image

Zunächst wird hier für die Verbindung die Identität des Benutzers verwendet. In diesem Fall bin das also ich, also der Benutzer unter dem der SharePoint-Designer ausgeführt wird.

image

Nun werden alle Tabelle der Datenbank angezeigt. In diesem Fall erstelle ich aus dem Designer alle Vorgänge für die Tabelle „Customers“.

image

Alle Vorgänge bedeutet, dass Operationen zur Listenansicht (zum Lesen aller Elemente und Anzeige in der Listenansicht), zum Lesen eines einzelnen Elements (zur Anzeige in der Dispform oder Editform), zum Aktualisieren eine Elemente (nach der Bearbeitung in der Editform) und zum Erstellen eines neue Elements (durch die Newform) angelegt werden.

Nun können auf Basis dieses externen Inhaltstypes eine Liste und Formulare erstellt werden.

2015-03-20 10_10_41-Liste und Formular für _NorthWind Kunden_ erstellen

Ganz wichtig ist, dass auf dem neu erstellen BCS-Model noch keine Berechtigungen vergeben wurden. Somit kann bisher noch niemand auf die Daten zugreifen. Falls jemand bereits auf die Liste zugreift wird er eine Fehlermeldung von SharePoint erhalten. Also müssen in der Zentraladministration im Business Conectivity Service noch Berechtigungen für das Model vergeben werden.

2015-03-20 10_12_46-Select People and Groups - Internet Explorer

Wenn man nun im SharePoint auf die Liste zugreift, dann erhält man nicht wie erwartet die Liste der Kundendaten.

2015-03-20 10_13_37-Customers - Neuer externer Inhaltstyp (2) Liste lesen - Internet Explorer

Wenn wir noch einmal die Authentifizierungseinstellungen im SharePoint Designer ansehen, dann steht hier, dass der Zugriff auf die Datenbank durch die Windows-Identität des Benutzers erfolgen soll.

image

Das setzt voraus, dass Kerberos-(Constrained-)Delegation eingerichtet wurde. In meinem Fall haben aber nicht alle Benutzer Zugriff auf die Datenbank sondern ich möchten eine dedizierten SQL-Benutzer für die Zugriffe verwenden. Wie man an dem Dialog oben erkennen kann, habe ich hier aber keine Möglichkeit einen Benutzernamen oder Password anzugeben, geschweigen denn, dass ich den kompletten Connection-String angeben kann.

Secure-Store To The Rescue

Zunächst ändern wie die Authentifizierungseinstellungen auf Benutzerdefinierte Identität annehmen und definieren eine Anwendungs-ID für den Secure-Store (in diesem Fall „NorthWindSqlLogin“)

image

Anschließend erstellen wir in der Zentraladministration eine neue Secure-Store Anwendung mit eben diesem Namen „NorthWindSqlLogin“.

2015-03-20 10_16_20-Create New Secure Store Target Application

Im nächsten Schritt geben wir an, welche Felder im Secure-Store zu der Anwendung abgelegt werden sollen. Standardmäßig sind das die Felder Benutzer und Password, wobei das Passwort vom Typ „Windows Password“ ist. Wichtig: dass muss auf „Password“ geändert werden!

2015-03-20 10_16_49-Create New Secure Store Target Application

Anschließend kann noch ein Administrator für die Anwendung bestimmt werden – dieser kann später Benutzername und Passwort der Anwendung vergeben und angeben, wer alles diesen Secure-Store-Eintrag lesen kann.

2015-03-20 10_17_54-

Nun kann für den neuen Eintrag ein Benutzername und Passwort eingegeben und im Secure-Store gespeichert werden.

2015-03-20 10_19_48-

Finale

Beim abschließenden Zugriff auf die Liste werden wie erwartet die Kundendaten aus der NorthWind Datenbank angezeigt.

image

Damit die Anmeldung über das SQL-Login passiert ist es wichtig, dass in der Secure-Store Anwendung das Passwort als „Passwort“ und nicht als „Windows Passwort“ abgespeichert wird. Ansonsten würde eine Authentifizierung mit einem Windows-Account versucht werden – das mag ggf. auch gewollt sein, wenn man z.B. alle Zugriffe auf eine Datenbank über einen einzelnen Windows-Account machen will, aber in diesem Fall war ja explizit ein SQL-Login gewünscht.

UserGroup goes Stockholm!

Dieses Jahr zieh es die European SharePoint Conference (ESPC) im November nach Stockholm. Zum ersten Mal wird die UserGroup Rhein-Ruhr in Form von Karsten, Denis, David, Andrej und mir dort mit einem eigenen Vortrag, unserem Workflow-Shootout, vertreten sein!

Für alle, die noch nie in Stockholm waren oder die gerne zur ESPC möchten (oder beides): es gibt für die ESPC zum einen Promo-Codes mit denen sich an der Konferenzteilnahme sparen lässt, zum anderen können wir aber dort auch als Gruppe buchen und somit günstigere Tarife herausholen.

Wer also daran Interesse hat, der soll sich bei mir melden; wenn wir genug Teilnehmer zusammenhaben werde ich mal entsprechende Gruppenrabatte sichern. Wir freuen uns über alle, die uns in Stockholm besuchen bei unserer Session!

Anlagen versenden per OneDrive und OWA

Dem einen oder anderen ist es vielleicht schon aufgefallen, dass seit kurzem im OneDrive for Business (ODfB) ein Ordner “E-Mail-Anlagen” existiert. Stellt sich die Frage: wofür ist dieser Ordner? Wo kommt der her?

Dabei handelt es sich um ein neues Feature in Office365, genauer gesagt im OWA. Wenn man im OWA eine Anlage in einer Mail versenden will, kann man auswählen ob man eine Datei aus OneDríve versenden möchte oder eine Datei von seinem lokalen Computer versenden will. Bei letzterem kann ich zudem auswählen, dass die Anlagen nicht mit der Mail versendet werden sollen, sondern über mein OneDrive freigegeben werden sollen.

image

Nachdem die Datei in OneDrive hochgeladen wurde, kann ich nun in der Mail noch auswählen, ob der Empfänger die Datei auch bearbeiten kann oder ob dieser die Datei nur ansehen kann.

image

Wenn der Empfänger noch kein Microsoft Konto hat, dann bekommt er zunächst per Mail einen Hinweis, dass er sich ein neues Konto erstellen muss, bevor er sich die gesendete Datei ansehen kann.

image

Ansonsten beinhaltet die Mail wie erwartet lediglich einen Link auf die Datei im OneDrive

image

Im OneDrive sieht man ganz normal die Datei in dem Ordner. Was allerdings auffällt ist, dass es a) kein Ribbon (in diesem Ordner!) gibt und b) zwei neue Icons.

image

Wenn ich nun mir die Freigabeberechtigungen der Dokumente ansehen, dann sind dort genau die Mail-Empfänger zu sehen.

image

Mehr zu dem Feature gibt es auch in dem Blog des Office365 Teams.

Neues Aussehen für Delve

Neue Woche – neue Features Smiley

Dieses mal: Delve.

Es gibt ein paar neue Features in Delve, zum einen gibt es einen schöner gestalteten Kopfbereich, mit Hintergrund (kann man den auch ändern?) von wo aus ich direkt Lync (Chat und Phone) ansprechen kann. Ebenfalls neu ist, dass ich direkt Dokumente in Yammer kommentieren kann.

image

Auch die Profilseite ist neu gestaltet, wobei sich mir noch die Frage stellt, warum es zwei Profil-Seiten gibt, die sich vom Design ähnlich sind, aber dann doch wieder verschieden.

image

Automatische Anmeldung für Dokumente in SharePoint

Eigentlich sollte mit Vista, Windows 7, Windows 8.x alles besser sein – aber ganz so gut ist dann doch nicht alles. Wenn man unter Vista, Windows 7, Windows 8.x aus dem Sharepoint (egal ob 2003, 2007, 2010 oder 2013) ein Office-Dokument öffnet, wird man mindestens einmal beim Öffnen nach seinen Credentials gefragt; das nervt!

Das Problem: Dokumente im Sharepoint werden via WebDAV geöffnet. Nun denkt der IE, dass es sich bei einer URL in der Form servername.busitec.de um eine Internet-Adresse handelt und übermittelt die Login-Credentials nicht (warum auch immer, ist aber in KB 941853 entsprechend dokumentiert). Interessanterweise tritt das Problem nicht auf, wenn man auf die Adresse nur mit der Servernamen zugreift – also ohne Domain-Suffix (siehe KB 941890).

Wer nach dem studieren der beiden KB-Einträge auf die Idee kommt, dass man ja einfach die Automatische Proxy-Suche aktiviert – ätsch, das bringt nix außer extra Wartezeiten beim Öffnen der Dokumente. Der Credential-Dialog kommt auch weiterhin.

Ein wenig weitergesucht – und siehe da, es gibt einen Blogeintrag vom Sharepoint Team, der sich mit dem Problem recht ausführlich beschäftigt. Die Lösung:

  1. In der Registry muss unter HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\WebClient\Parameters ein neuer Eintrag AuthForwardServerList vom Typ “mehrteilige Zeichenfolge” eingefügt werden (geht nur als Admin!).
  2. Diesem kann dann eine Liste von Adresse angegeben werden, an die gefahrlos Credentials übergeben werden dürfen (also z.B. *.busitec.de). Achtung: hier gelten bestimmte Regeln wie mit Wildcards umgegangen werden muss!!
  3. Den Dienst WebClient neu starten (geht wieder nur als Admin 🙂 ), damit die neuen Einstellungen auch geladen werden.
  4. Voila!