Nuget: de app store voor Open Source projecten

De afgelopen maanden en zeker de afgelopen weken zijn redelijk geruisloos een aantal interessante innovaties door Microsoft op de markt gebracht. Ik noem even Asp.Net MVC3, WebMatrix, IISExpress, LightSwitch en Sql Server Compact 4. Tussen al die grote jongens zat ook een onopvallend stukje
innovatie genaamd Nuget.

nuget

Nuget kan het beste omschreven worden als een app store (of market place)
voor opensource projecten. Inmiddels zijn binnen Nuget meer dan 500 bekende en minder bekende open source initiatieven opgenomen. Ik noem b.v. Log4Net,
nHibernate, Elmah, en nUnit. Natuurlijk zijn deze projecten altijd al vrijelijk
op het internet te vinden maar dan moet je ze wel weten te vinden 🙂 En daarnaast zijn er nog de installatie-perikelen en mogelijke afhankelijkheden met andere projecten.

Maar nu hebben we nuget. Hiermee komt het volgende binnen bereik:

  • – Eén galerij met alle
    opgenomen open source projecten, compleet met search
  • – Integratie met Visual Studio 2010
  • – Automatische installatie en deinstallatie
    • Referenties plaatsen naar dll’s
    • Config files uitbreiden met instellingen
    • Extra mappen en bestanden binnen je project aanmaken
    • Uitvoeren van script tijdens installatie en/of deinstallatie
    • Gerelateerde projecten worden ook meegenomen
    • Na deinstallatie wordt alles weer netjes opgeruimd
    • Etc.
  • – Mogelijkheid om extra Powershell scripts te draaien om naderhand dynamisch je projecten aan te passen (zoals het aanmaken van repositories of controllers)

Zie voor meer mogelijkheden de documentatie op codeplex. Overigens is het ook mogelijk om binnen een beschermde omgeving (intranet) een eigen feed toe te voegen met een eigen selectie aan packages. Dit kan via een gesharede map of via een eigen (Asp.Net MVC2) website.

Maar wat moet je doen om een project in de galerij te krijgen?

Stap 1: Wat wil je delen?

De afgelopen weken heb ik in een aantal blogs (1) (2) geschreven over OData in combinatie met security. Hierbij is ook een Basic Authentication implementatie getoond op basis van een HTTP Module. Deze heb ik open source gemaakt door de code te publiceren op CodePlex.

Als distributie heb ik uitsluitend voor Nuget gekozen. Dit betekent
dat ik een package opgebouwd heb die de volgende taken uitvoert:

  • 1. De HTTP Module wordt als DLL toegevoegd aan een web project en een referentie wordt aangemaakt
  • 2. In de web.config wordt de HTTP Module gerefereerd zodat deze bij het starten van de website geladen wordt.
  • 3. Ter informatie wordt de authenticatie modus op None gesteld binnen de web.config
  • 4. Een xml bestand met voorbeeld credentials wordt in de App_Data map geplaatst
  • 5. Een test web-pagina wordt toegevoegd als referentie om de werking te testen. Hierin wordt de de namespace van het project gemerged via een transformatie van $rootnamespace$.

Stap 2: zorg voor een download van de Nuget command line tool

Download  de commandline tool waarmee een package samengesteld kan worden. De exe zal straks gebruikt gaan worden.

Stap 3: Stel de documenten voor de package samen en genereer de package

Maak de volgende directory structuur aan. Ik heb daar de volgende
bestanden geplaatst:

Package
SimpleBasicAuthentication.0.1.nuspec
Content
web.config.transform
TestSimpleBasicAuthentication.aspx.cs.pp
TestSimpleBasicAuthentication.aspx.designer.cs.pp
TestSimpleBasicAuthentication.aspx.pp
App_Data
UserCredentials.xml
Lib
SimpleBasicAuthentication.dll
SimpleBasicAuthentication.pdb
SimpleBasicAuthentication.XML

(Mappen zijn cursief gemaakt)

Hierboven staan de bestanden die samengesteld gaan worden tot de
.nupkg die hieronde in de out directory geplaatst gaat worden.

Package
Out
SimpleBasicAuthenticationModule.0.1.nupkg
Download
NuGet.exe
NuGet Spec.cmd
NuGet Update.cmd
NuGet Pack.cmd

(Mappen zijn cursief gemaakt)

De gedownloade nuget.exe heb ik in de download map geplaatst.
Vervolgens heb ik een aantal cmd bestandjes gemaakt uit gemakzucht om de
gewenste acties uit te voeren.

In SimpleBasicAuthentication.0.1.nuspec zijn basale instellingen
opgeslagen zoals een package naam, auteurs, website en icoon. Deze is in de
basis aangemaakt met de NuGet Spec.cmd

NuGet.exe spec

Overigens is het verstandig om eerst te controleren of er een nieuwere versie
van nuget.exe is. Dit heb ik in enkele dagen al twee keer meegemaakt. De
bestaande exe wordt dan vervangen door een nieuwe versie en de oude wordt
hernoemd tot NuGet.exe.old. Draai hiervoor NuGet Update.cmd

NuGet.exe update

Hierna kan de package gegenereerd worden. Draai hiervoor NuGet
Pack.cmd

NuGet.exe pack ..\SimpleBasicAuthentication.0.1.nuspec -o
..\out

Hiermee worden alle bestanden samengevoegd in de SimpleBasicAuthenticationModule.0.1.nupkg. Zo’n package is overigens een zip
bestand die met bv. winzip uitgepakt kan worden…

Stap 4: Lokaal testen

De package kan nu al getest gaan worden. Voeg de out map toe als
‘feed’ aan delijst van package sources:

Lokaal testen

Hierna is de package lokaal te testen. Probeer jouw package maar eens toe te
voegen aan jouw (web) project:

lokale feed

Wie zijn package in een gesloten omgeving wilt toepassen, zoals in een
intranet, is nu klaar. Wil je de package aan de officiele feed toevoegen, dan
zijn er nog twee extra stappen.


Stap 5: (tussendoor) Publiceer je open source project

Ik heb de code achter mijn package in codeplex beschikbaar gesteld.
Dit geeft namelijk de mogelijkheid aan gebruikers om meer te weten te komen over de werking en ik heb ook een forum om eventuele problemen te loggen. Nuget stelt zelf bv. ook Github voor.

Stap 6: Maak een account aan op de Nuget galerij en publiceer je package

Als je een nieuw account aanmaakt dan zal dit met een verificatie mailtje
beantwoord worden. Ik heb begrepen dat het aanmelding momenteel nog handmatig verwerkt worden. Dit verificatie maitje wordt voor twee zaken gebruikt, voor verificatie en het kenbaar maken welke project je wilt aanbieden.

Nuget

“Click on this link (..) to verify your email address … and … Reply to
this email with a link to the project that you own or plan to upload (e.g. on
github, etc…)”.

Ik heb dus een mailtje teruggestuurd met een link naar mijn codeplex
site. Ik kreeg daarna een nette mail terug: “Your account is now approved”.

Vervolgens kan je dan eindelijk met het account packages gaan
toevoegen. Dit gebeurt met de hierboven beschreven nuget.exe:

nuget push -source http://packages.nuget.org/v1/ MyPackage.1.0.nupkg [SECRET
ACCESS KEY]

Dit is belangrijk. Je krijgt een unieke key toegewezen (die je ook opnieuw
kunt laten genereren). Met die key kun je de gegeneerde .nupkg in de galerij
plaatsen. De unieke key voorkomt op eenvoudige wijze dan een ander nooit jouw
package kan gaan kapen. Vervolgens kun je de pagina in de galerij nog verfraaien
met extra informatie en bv. een screendump.

gallerij

Ga voor mijn bovenstaande bijdrage naar de galerij.

Conclusie

Het concept achter Nuget is niet uniek. Er zijn meer van dit soort distributiekanalen voor bv. de linux omgeving. Maar voor Visual Studio geeft dit
compleet nieuwe dimensie in het gebruik en de acceptatie van open source. Opeens kunnen we zonder drempels en overzichtelijk open source projecten gaan uitproberen en uitwisselen. Wanneer zie ik jouw package in de galerij? Ik hoor het graag in de comments!

Naschrift: Nuget is slechts een handig distributiesysteem (automatische configuratie, updates, etc.) en is een gratis Add-On op Visual Studio. Als de referenties gelegd zijn dan zien collega’s zonder Nuget alleen een extra .config (met informatie voor Nuget) in de root van de applicatie staan. Alles blijft gewoon werken.

Advertenties

Odata Slash PowerPivot: it rocks!

Soms gaat er achter een URL een hele wereld schuil. Dit is zeker het geval
met OData. OData staat voor het Open Data Protocol en is door Microsoft
gedeponeerd. Het is een “Open specificatie belofte” wat betekent dat Microsoft
diegene die een implementatie verzorgt, nooit voor de rechter gedaagd zal worden ( http://www.microsoft.com/interop/osp/default.mspx ).

HTTP Slash Slash

OData biedt de mogelijkheid om data:

  • op een uniforme manier aan te bieden en te wijzigen (REST)
  • via standaarden toegankelijk te maken (HTTP, ATOM, JSON)
  • op eenvoudige wijze te doorzoeken en te filteren is (queries a la LINQ)
  • een zelfbeschrijvende interface te geven ($metadata)

Meer informatie hierover is te vinden op http://www.odata.org/

OData

Voorbeeldje? Vul het volgende eens in, in de browser:

http://transit.cloudapp.net/DevTransitODataService.svc/Arrivals?$filter=%20RouteType%20ne%20’Bus’&$skip=5&$top=2

Dit geeft twee records uit een enorme lijst van ‘aankomsttijden’ waarbij de
eerste vijf overgeslagen worden. En wil je weten hoeveel records er live
aanwezig zijn? Selecteer in de browser dan eens:

http://transit.cloudapp.net/DevTransitODataService.svc/Arrivals/$count

Wil je de interface weten van deze openbare service? Type dan in:

http://transit.cloudapp.net/DevTransitODataService.svc/$metadata

Nu zijn dit GET opdrachten om informatie op te halen. OData ondersteunt ook
de POST, DELETE en UPDATE voor de andere CRUD opdrachten.

En ook kan de serverbelasting gereguleerd worden. Aan de serverkant wordt dan
de data in batches opgestuurd zodat de ontvanger bij iedere batch een
skiptoken krijgt om de volgende batch op te kunnen halen.

OData heeft geen ingebouwde security anders dan filtering maar laat dit over
aan het communicatie protocol (HTTP/HTPPS) en de security van de webservice / webserver.

Hoewel OData zeker geen silver bullet is voor iedere vorm van
dataoverdracht, vind ik het zeer veelbelovend voor Self Service BI, samen met Excel PowerPivot. Gebruikers kunnen nu zelf los op de data en dus is er minder vraag naar voorgebakken rapportages.

Excel PowerPivot

PowerPivot is een gratis plugin voor Excel met een verbeterde
Pivot table en bijbehorende Pivot grafieken. Het meest extreme is dat hierbij
enorme hoeveelheden data (en dan bedoel ik ook echt enorm; ik heb een voorbeeld van 100 miljoen regels !!! gezien) te doorzoeken wat nog steeds redelijk performt. En PowerPivot kan uit vele bronnen data inlezen waarbij deze via eigen relaties aan elkaar te koppelen zijn. Zo is data te combineren uit bv. SQL Server, Azure, Oracle, IBM DB2 en Access.

Maar de data kan ook via OData opgehaald worden. Hierbij wordt zelfs de
automatische paging gepareerd om netjes alle data op te halen.

We roepen dus een OData feed aan:

OData feed in Excel PowerPivot

En zo kunnen we het aantal incidenten fraai visualiseren van de hiervoor
getoonde publieke service:

Excel PowerPivot Graph

LET OP: wat nu volgt is een CSI-achtige uiteenzetting
rond een tekortkoming in de OData service aanroep van PowerPivot. Wil je direct naar de oplossing? Druk dan enkele malen op Page-Down…

En nu wordt interessant…

Zodra je een OData service aanbiedt, ga je nadenken over de beveiliging (..).
In de beslissing neem je dan mee wie wat mag zien en met welke tooling je de
data wilt ontsluiten.  Ik heb al eens geblogged over het gebruik van een APIKey maar deze is niet toe te passen bij PowerPivot. PowerPivot ondersteunt wel Basic authentication en Windows authentication.

SSPI and Basic Authentication

Voor ons huidige project hebben we een eigen Basic Authentication
geïmplementeerd zoals beschreven in OData and Authentication – Part 6 – Custom Basic Authentication

Voor wie dit ook wilt implementeren een aantal tips:

  • Hoewel er over Basic Authentication gesproken wordt, moet de webservice met anonimous geconfigureerd worden in de web.config en in IISBasic authentication hoeft niet actief te zijn op IIS om de oplossing te laten werken
  • het voorbeeld van de web.config uitbreiding is voor IIS7+ geschreven
  • De naam van de module kan beter iets anders geschreven worden. Er kan standaard al een (IIS)module voor Basic Authentication actief zijn en die heet al BasicAuthenticationModule. Dit kan een naam-conflict geven
  • Basic Authentication is een prima authenticatie vanwege de eenvoudige implementatie en de goede testbaarheid
  • Basic Authentication is pas een prima authenticatie als dit gecombineerd wordt met SSL. De wachtwoord gaan onbeschermd over de lijn dus alle communicatie moet versleuteld worden

Maar we voeren de spanning verder op en nu wordt het nogal technisch. We
duiken hier de http-vraag-en-antwoord-spelletjes in en we gebruik hiervoor Fiddler. Fiddler werkt stiekem als proxy voor al het netwerkverkeer op de PC en ziet dus alle requests en bijbehorende responses voorbijkomen. Hiermee kan ik prima controleren wat er allemaal gecommuniceerd wordt…

Onze service is beschikbaar als http://IPAddress/powerusageservice.svc
en deze wordt voornamelijk getest via de browser. Dit gaat echt prima, ook bij
Basis Authentication. Want als de browser een GET uitvoert op de server, zal de
server  in eerste instantie een 401 (Unauthorized) geven. Maar in de header van
de response wordt een WWW-Authenticate: Basic teruggegeven.

401 Unauthorized

Dit wordt dan door de browser opgepakt en die zal een inlogschermpje
geven. Deze authentication challenge zal dan gevolgd worden met een
nieuwe aanroep en met een 200 OK als antwoord. De gebruiker is dan eindelijk
ingelogd. Tussendoor wordt een 307 Temporary Redirect door de server afgegeven zodat de browser naar het juiste adres blijft wijzen. Want de WCF service ziet graag een extra slash (/) achter de URL (http://IPAddress/powerusageservice.svc/).

Het is dus belangrijk dat de browser de eenmaal ingevoerde credentials blijft
doorgeven, ook bij een redirect.

307 Temporary Redirect

Nu komen we bij de uitsmijter: wat gebeurt er als we dezelfde actie uitvoeren
met Excel PowerPivot. Zien wij daar dezelfde reeks? Terug dus naar Excel
PowerPivot. Als ik dezelfde URL http://IPAddress/powerusageservice.svc
en credentials invul bij Excel dan krijg ik bij het testen van de connectie
steeds een 401…

Feed zonder slash

Waarom??? Het was even zoeken maar Fiddler gaf uiteindelijk het juiste
antwoord:

307 Temporary Redirect zonder authentication

We zien hier wederom een nette 401 Unauthorized met daarna de 307
Temporary Redirect. En we zien ook de daarop volgende aanroep  met het grote
verschil dat Excel PowerPivot vergeet om bij de redirect ook de credentials mee
te sturen naar de nieuwe lokatie… Oops! En dat resulteert in de 401
Unauthorized.

Dus wat is nu de oplossing? Dit is te simpel! De service URL moet gewoon
alvast uitgeschreven worden met de extra slash zodat de 307 Temporary Redirect niet nodig is. Dan zal de 401 Unauthorized voor http://IPAddress/powerusageservice.svc/
direct met een 200 OK gevolgd worden.

OData feed in Excel PowerPivot met slash

Conclusie:

OData is echt een interessante mogelijkheid om data als services aan te
bieden. Excel PowerPivot kan hier zeer goed gebruik van maken om enorme
hoeveelheden data simpel te visualiseren. Door een onhandige implementatie van de HTTP 307 Redirect bij een aanroep met Basic Authentication als beveiliging kan de eerste kennismaking flink tegenvallen. Schrijf dus de service URL dus altijd uit, met een slash achter de .svc zoals http://IPAddress/powerusageservice.svc/