PDF

Transcription

PDF
SOFTWARE DEVELOPMENT NETWORK
MAGAZINE
IN DIT NUMMER O.A.:
Introduction to Razor Syntax <
Duet Enterprise <
Building a Custom Health Rule <
Best practices bij het vervangen van een SCOM Gateway Server <
Nummer 108 februari 2011 SDN Magazine verschijnt elk kwartaal en is een uitgave van Software Development Network
108
www.sdn.nl
advertorial
NjdsptpgufoBdinfb;tusbufhjtdifqbsuofstcjkefpouxjllfmjohwboWjtvbmTuvejp3121
ÒBdinfbxjmsb{foetofm
lvoofojotqfmfopq
pouxjllfmjohfojoefnbsluÓ
Foto: Hans Barten
Bdinfbjtffoxbbsefwpmmftusbufhjtdif
qbsuofswboNjdsptpgu/Ejucmjklupoefsnffsvju
ifugfjuebuefwfs{flfsbbsiffgunffhfebdiu
cjkefpouxjllfmjohwboNjdsptpguWjtvbmTuvejp
3121/ÒNjdsptpgucftdipvxupotbmtffowboef
nfftujoopwbujfwfwfs{flfsbbstufsxfsfmeÓ-
{fhuBdinfbÕtqsjodjqbmbsdijufduBmfyUijttfo/
Afgelopen zomer was Achmea’s
2010 en de ‘Application Lifecycle
Alex Thissen een week lang te gast
Management omgeving’ Team
bij het Windows Communication
Foundation Server 2010) was
Foundation team op Microsofts
Achmea in een vroeg stadium
hoofdkantoor in het Amerikaanse
betrokken, vertelt Thissen. “We
Redmond. “Er zijn op de hele wereld
hebben ideeën en suggesties aan-
maar zes bedrijven die daarvoor
geleverd en Microsoft gewezen
werden uitgenodigd, dus ik beschouw
op bugs en verbeterpunten, zoals
het wel als een eer dat Achmea deel
bijvoorbeeld bij het berekenen
uitmaakt van dit selecte groepje.
van de burnrate van code. Dat is
Microsoft luistert echt naar Achmea,
nuttig voor ons én nuttig voor
ze beschouwen ons als een bedrijf
Microsoft.”
dat voorop wil lopen. We spraken
Voor Achmea is Visual Studio
bijvoorbeeld over Microsofts onder-
Team System belangrijk bij het
daarop onder andere hun bloeddruk en body mass
steuning van IBM Websphere MQ,
ontwik kelingen van software
index meten en sportieve prestaties vergelijken met
waarvoor wij andere communicatie-
aan de voorkant, zoals webappli-
die van topsporters.”
patronen mogelijk wilden maken.
caties en mobiele applicaties, en
Maar ook de koppeling tussen
voor integratie-oplossingen met
Agile
Sharepoint en SAP was onderwerp
behulp van webservices. “Voor
Daarnaast draagt de Microsoft-software bij aan de
van gesprek.”
Achmea wordt het internet steeds
toenemende vraag naar transparantie en voorspel-
Microsoft-topman Scott Guthrie,
belangrijker, niet alleen om schades
baarheid, vindt Thissen. “Team Foundation Server
alias ‘Scott Gu’, was onlangs te gast
te melden of verzekeringen af te
houdt alle stappen in het ontwikkelproces bij, vast-
op de Achmea-burelen. Thissen: “Ja,
sluiten, maar ook voor allerlei
gelegd in hiërarchische workitems. Zo bieden wij
dat zijn inspirerende sessies. In mijn
zaken op het gebied van preventie.
onze klanten – de mensen in de business van Achmea
vakgebied heeft hij de status van
Zo hebben we in opdracht van
– optimaal inzicht in het proces.”
een popster, dus je begrijpt dat het
Zilveren Kruis Achmea de game
Last but not least is Thissen tevreden met MSF Agile,
geweldig sparren is met zo’n man.”
‘Mep je fit’ ontwikkeld voor Micro-
het processjabloon dat Visual Studio Team System
Alex Thissen: “Microsoft luistert echt naar Achmea.”
softs ‘computertafel’ Surface.
voert. “Dat betekent dat we snel en flexibel kunnen
Mep je fit
Ook tijdens de Olympische Winter-
bouwen, in korte iteraties met de klant. Dat is precies
Bij de ontwikkeling van Visual
spelen hadden we in het Holland
wat we nodig hebben, want Achmea wil razendsnel
Studio Team System (bestaande uit
Heineken House een gezondheids-
kunnen inspelen op nieuwe ontwikkelingen die zich
ontwikkelomgeving Visual Studio
installatie staan; bezoekers konden
voordoen in de markt.”
Colofon
Uitgave:
voorwoord
Software Development Network
Negentiende jaargang
No. 108 • februari 2011
Bestuur van SDN:
Remi Caron, voorzitter
Rob Suurland, penningmeester
Marcel Meijer, secretaris
Beste SDN magazine lezer,
Redactie:
Remi Caron en Marcel Meijer
(redactie@sdn.nl)
Aan dit magazine
werd meegewerkt door:
Aan dit magazine werd meegewerkt door:
Roel Hans Bethlehem, Christiaan Heidema,
Bob Swart, Stefan Kamphuis, Peter Donker,
Maarten van Stam, Alexander Meijers, Remi
Caron, Marcel Meijer en natuurlijk alle
auteurs!
Listings:
Zie de website www.sdn.nl voor eventuele
source files uit deze uitgave.
Vormgeving en opmaak:
Reclamebureau Bij Dageraad, Winterswijk
www.bijdageraad.nl
©2011 Alle rechten voorbehouden. Niets uit
deze uitgave mag worden overgenomen op
welke wijze dan ook zonder voorafgaande
schriftelijke toestemming van SDN. Tenzij
anders vermeld zijn artikelen op persoonlijke
titel geschreven en verwoorden zij dus niet
noodzakelijkerwijs de mening van het bestuur en/of de redactie. Alle in dit magazine
genoemde handelsmerken zijn het eigendom van hun respectievelijke eigenaren.
Het jaar is al weer een tijdje bezig. Inmiddels hebben we het eerst event EngineerWorld
(georganiseerd samen met Sogeti) alweer achter de rug. Het volgende reguliere SDN event
staat gepland vrijdag 18 maart. Dit event staat weer bol van de content. Sessies over
AppFabric, ALM voor Azure projecten, SharePoint Document management, Blend for
Developers, Claimbased security, Delphi XE, Intraweb, Razor, DNN RadEditor en DNN in
combinatie met Entity Framework. Traditioneel zal er tijdens dit event ook de Algemene Leden
vergadering. Dit is nog maar een kleine greep. Kijk op de website voor meer informatie.
Let op, ons tijdschema is veranderd. We beginnen om 9:30 en eindigen rond half vijf.
Met het nieuwe jaar zijn er ook een aantal wijzigingen in de organisatie. Sandra de Ridder van
de UX track heeft ons verlaten. Ze kon de werkzaamheden voor de SDN niet meer goed
combineren met haar werk en prive leven. Marcel van Kalken van de Delphi track heeft ook
zijn taken neergelegd. Beide danken wij hartelijk voor hun inzet de afgelopen jaren en
wensen ze succes voor de toekomst. De organisatie is daarentegen ook uitgebreid met
Alexander Meijers voor de Information Worker track en Roel Hans Bethlehem voor de
Architecture track. Alexander en Roel Hans welkom bij de club, we gaan er een mooie tijd van
maken. Ook hebben we dit jaar twee nieuwe corporate sponsoren IBM en Compuware. Daar
zullen we de komende tijd veel meer over horen en van zien.
Dit magazine staat bol van de artikelen. Van het Nieuwe werken tot SCOM en twee artikelen
over Razor. Kortom wederom een magazine waar je je kennis mee kan verbreden. De
volgende magazines gaan we meer richten op 4 standaard categorieen (Cloud, Mobile, Client
apps en Web apps), natuurlijk blijven Delphi en DotNetNuke het hele palet compleet maken.
We zijn altijd op zoek naar leuke artikelen van een tot twee pagina’s. Mocht je interesse
hebben, meldt je dan bij redactie@sdn.nl. Wij kunnen je ook helpen met schrijven.
Veel leesplezier!
Groeten
Marcel Meijer
Adverteerders
Achmea
4DotNet
Sogeti
Bergler
Triple A
Uniface
Barnsten/Embarcadero
Microsoft
Macaw
2
6
8
18
23
29
34
51
52
Adverteren?
Informatie over adverteren en de advertentietarieven kunt u vinden op www.sdn.nl
onder de rubriek Magazine.
magazine voor software development 3
Agenda 2011
Inhoud
03
Voorwoord
Tech-Ed Middle East 2011 . . . . . .8 maart
Marcel Meijer
Tweede WAZUG meeting . . . . . .17 maart
04
04
05
SDN Event maart + ALV . . . . . . .18 maart
Anky Persoons
07
CodeCamp / . . . . . . . . . . . . . . . . . . . . . .
SharePoint Saturday . . . . . . . . .26 maart
09
SharePoint Conference 2011 . .3 oktober
Introduction to Razor Syntax
Introduction to the Delphi Open Tools API
Wat is er zo moeilijk aan een
mobiele applicatie?
Jaap van Ekris
Drag and Drop deel 2:
Bestanden slepen naar de Windows Explorer
Eric Roosendaal
20
Mixing Scrum and Smart
Sander Hoogendoorn
24
SDN Event December 2011 .9 december
Azure VM Role
Cary Jensen
19
SDN Event juni 2011 . . . . . . . . . . .17 juni
Leer Het Nieuwe Werken van een ZZP’er!
Andrew Nurse
16
SDN Magazine 109 . . . . . . . . . . . .20 mei
Agenda
Marcel Meijer
12
DevDays 2011 . . . . . . . . . . . . . . .28 april
Inhoudsopgave
Introduction to the code coverage tooling
in Rational Application Developer
Paul Klicnik
30
Duet Enterprise
Christian Siegers en Mark IJsselstein
32
Historie en toekomst van
Database Change Management
Ben Suurmeijer
36
Webservices en transacties
Michiel van Otegem
38
Building a custom Health Rule
Anita Boerboom
42
“Nieuw” in Nederland: NLDeveloper
Robert Blom
43
Best practices bij het vervangen van
een SCOM Gateway Server
Mark Wolzak
46
De uiterste houdbaarheidsdatum
van requirements
Sander Hoogendoorn
47
DotNetNuke supports Razor
Charles Nurse
50
Reflection loops of Agile
Joachim Nilsson
IW
Anky Persoons
Leer Het Nieuwe Werken
van een ZZP’er!
Steeds meer bedrijven stappen over op Het Nieuwe Werken. Vaak richten ze zich bij de
invoering ervan sterk op de praktische aspecten (ICT, HR, facilitair). Wat ze vaak uit het oog
verliezen is de cultuuromslag die nodig is om deze verandering succesvol te laten verlopen.
Op dat vlak kunnen ze veel leren van ZZP’ers, die bij het werken als ondernemer hebben
moeten leren omgaan met vrijheid, verantwoordelijkheid en het zoeken naar balans.
Méér dan leuke ICT-tooltjes
Er is veel te doen over Het Nieuwe Werken (HNW). Eind 2010 was er
zelfs “De Week van Het Nieuwe Werken” en in 2011 zullen we er
alleen maar meer over horen. Iedereen heeft het erover, wil het graag
(of juist niet), moet het van zijn baas, vindt er iets van, of vindt het niks.
In de pers worden steeds weer dezelfde praktijkvoorbeelden aangehaald: Microsoft, Interpolis.
Is HNW een hype of het begin van een tijdperk waarin mensen anders
omgaan met hun werk, hun tijd, het samenwerken met anderen en
hun werk-privébalans? Worden we beter presterende, meer tevreden
werkers of is het vooral een marketingterm waarmee ICT-bedrijven
hun oplossingen verkopen, HRM-adviseurs hun uren en interieurarchitecten hun adviezen?
Verantwoordelijkheid nemen
Veel mensen denken dat Het Nieuwe Werken betekent dat je hetzelfde
werk blijft doen, maar dat je zelf bepaalt wanneer en waar je dat doet.
In de praktijk is het echter niet zo eenvoudig. Het is meer dan thuiswerken, communiceren met nieuwe slimme ICT-middelen, geen vaste
werkplek meer hebben op kantoor en zelf je tijd kunnen indelen. Dat
zijn eigenlijk maar bijkomende verschijnselen, die echter vaak de aandacht trekken en het zicht vertroebelen op waar HNW echt over gaat.
In de kern gaat HNW over zelf
verantwoordelijk zijn voor je werk
In de kern gaat HNW over zelf verantwoordelijk zijn voor je werk. Dat
werk bestaat uit opdrachten met een duidelijk omschreven eindresultaat, een deadline en tussentijdse evaluaties. Een medewerker heeft
geen inspanningsverplichting meer, maar een resultaatverplichting. Dit
heeft nogal wat gevolgen voor de werknemer en voor de manier
waarop hij samenwerkt met managers, collega’s en ondergeschikten.
En voor de balans tussen werk en privé. Want die zakelijke telefoontjes komen ook gewoon binnen als je net je kind uit school hebt
gehaald. Werknemers hebben dus nieuwe vaardigheden nodig:
zelfsturing, ondernemendheid, planning, grenzen bewaken.
Het nieuwe managen
Ook de rol van de manager verandert. Als niemand nog een 40-urige
werkweek heeft, hoe stuur je dan je team aan? Je moet leren om te
beoordelen op resultaat, niet meer op aanwezigheid. Vertrouwen
neemt de plaats in van controle. Je zult meer aandacht moeten
besteden aan de synergie in het team en aan de onderlinge
communicatie en uitwisseling van informatie.
Misschien hebben de ZZP’ers
HNW wel uitgevonden
Kortom, HNW vraagt om een cultuuromslag. Een omslag van
eenrichtingsverkeer naar een dialoog, van delegeren naar coachen,
en van werk of privé naar werk én privé. Dan krijgen medewerkers de
ruimte om mee te denken, beslissingen te nemen en productiever
te zijn.
ZZP’ers werken al heel lang “Nieuw”
Terwijl bedrijven en hun medewerkers hun best doen om HNW onder
de knie te krijgen, vergeten we met zijn allen dat er een grote groep
werkers is die al veel langer met dit bijltje hakt. HNW is eigenlijk niets
nieuws onder de zon. Dat is het wel voor mensen die in loondienst
werken en gewend zijn om 9 uur te starten en om 5 uur weer uit te
klokken, om vervolgens op dezelfde snelweg weer in dezelfde file te
gaan staan, net als hun collega’s. Maar niet voor de Vrije Werkers,
Zelfstandige Professionals of - zoals ze meestal genoemd worden ZZP’ers. Voor velen van hen was de wens om op deze manier te
kunnen werken zelfs een belangrijke reden om uit loondienst te gaan
en “voor eigen rekening en risico” aan de slag te gaan. Misschien
hebben de ZZP’ers HNW wel uitgevonden.
Ga maar na: veel zelfstandige professionals wisselen het werken in
hun thuiskantoor af met werken bij de klant en met besprekingen op
verschillende locaties met mede-ZZP’ers en andere samenwerkingspartners. Ze doen overdag een boodschap, gaan sporten of halen de
kinderen uit school, en werken dan ’s avonds of in het weekend nog
een paar uur. In drukke tijden maken ze wat meer uren, in rustige
tijden kan het even een tandje lager. Er is vaak één PC voor zakelijke
en privéaangelegenheden. Ze doen hun eigen acquisitie en voeren
voor hun klanten vaak projectmatige werkzaamheden uit, waarbij een
vooraf afgesproken resultaat op een bepaalde datum moet worden
opgeleverd. Deze professionals hebben de strijd om de werk-privé
balans al gestreden. En vaak niet zonder moeite: zeker ondernemers
zijn (in het begin) geneigd meer te werken dan goed is voor henzelf en
de privésituatie. En ze vormen dus uitstekende rolmodellen en vraagbaken voor medewerkers die HNW onder de knie moeten krijgen.
magazine voor software development 5
IW
De ZZP’er als voorbeeld van ondernemerschap
Toch hebben managers in HNW-bedrijven juist vaak moeite om de
ingehuurde ZZP’ers het vertrouwen te geven dat bij HNW hoort.
Ze hebben ze het liefst zichtbaar om zich heen, en niet thuiswerkend.
Ze zijn immers per uur ingehuurd en dan wil je ook zien dat die uren
allemaal gemaakt worden.
Als ZZP’er kan ik medewerkers
coachen in het wennen aan HNW
Wat een gemiste kans! Want is HNW eigenlijk niet gewoon: ondernemerschap onder de vleugels van de werkgever? Het is werken met
meer vrijheid en verantwoordelijkheid, zonder de risico's van het echte
ondernemen te dragen. Wie kan er dan beter kennis en ervaring hierover delen dan een ZZP-‘er?
medewerkers, die dan ook niet goed de stap durven maken naar
locatie-onafhankelijk werken.”
Terwijl het voor Gary heel gewoon is om resultaatgestuurd te werken.
Als ZZP’er werkt hij immers zowel op uurbasis als op projectbasis. “Ik
ben gewend om zelf mijn tijd in te delen en flexibel samen te werken
met andere teamleden, of dat nu vaste of tijdelijk ingehuurde medewerkers zijn, of medewerkers van een externe leverancier. Als teamlid
met HNW-ervaring kan ik de andere teamleden tussen de bedrijven
door begeleiden bij het wennen aan HNW en ze suggesties geven
over beschikbaarheid, balans, communicatie met collega’s en omgaan
met vrijheid en verantwoordelijkheid.”
Veel ZZP’ers delen Gary’s ervaringen. Wanneer zij de ruimte krijgen
zodat ook zij optimaal kunnen functioneren kunnen zij op een natuurlijke manier in de dagelijkse werksituatie optreden als “rolmodel” en
de andere teamleden laten zien hoeveel winst Het Nieuwe Werken kan
opleveren. Voor het bedrijf, maar zeker ook voor de medewerkers.•
Een ZZP’er die ervaring heeft opgedaan met HNW bij opdrachtgevers
is Gary Wenneker. Hij werkt als zelfstandig SharePoint specialist en
komt al jarenlang “bij de klanten thuis”. Hij vertelt: “Sinds een paar jaar
zie ik in steeds meer bedrijven Het Nieuwe Werken opkomen. De
meeste medewerkers vinden die nieuwe vrijheid prettig, maar het
maakt mensen ook onzeker. Hoe bereikbaar moet je zijn? Moet je niet
vaker je gezicht laten zien op kantoor? Wanneer kun je je collega’s
wel, of juist niet, bellen?”
Daarnaast ervaart Gary ook dat managers worstelen met HNW. “Zeker
als het gaat over tijdelijk ingehuurde krachten. Die moeten toch
eigenlijk wel gewoon op kantoor werken. Dat betekent dan voor die
manager dat hij zelf ook veel op kantoor aanwezig is om de voortgang
in het oog te houden. Zodat hij niet een goed voorbeeld is voor zijn
Ankie Persoons
Ankie Persoons is directeur van ICTProfessionals, een maatschap van
zelfstandige ICT-ers die de afstand
tussen werken in loondienst en zelfstandig werken verkleint. Ze heeft
brede communicatie-ervaring in de
ICT-branche en is Social Mediaconsultant en trainer.
The
one-stopcompany
companyfor
for.NET
.NETdevelopment
development
The one-stop
Maak
uwuw
dromen
waar!
Maak
dromen
waar!
Kijk voor alle belevenissen op www.4dotnet.nl
Heeft u altijd al willen rijden in een Ferrari of een keer zweefvliegen?
Boek dit voorjaar een
training bij 4DotNet en
krijg een unieke belevenis
van ons cadeau!
Lees alles over deze
droomactie op
www.4dotnet.nl
Een keer rijden in een Ferrari of zweefvliegen.
actie is geldig t/m 30 juni 2011
Wie droomt daar nou niet van? Boekt u voor 31 maart een training bij 4DotNet dan krijgt u van
ons een unieke belevenis cadeau!
TEST CENTER
6
4DotNet bv t Paradijsweg 2 t 7942 HB Meppel t t. 0522-24 14 48 t info@4dotnet.nl
t www.4dotnet.nl
TEST CENTER
MAGAZINE
4DotNet bv Paradijsweg 2 7942 HB Meppel t. 0522-24 14 48 info@4dotnet.nl www.4dotnet.nl
CLOUD
Marcel Meijer
Azure VM Role
Veel standaard ASP.NET webapplicaties kunnen in principe redelijk
eenvoudig naar de Azure Cloud gebracht worden. Uiteindelijk is de
Azure Cloud een Microsoft .NET platform met nagenoeg dezelfde omgelijkheden1. Maar als je applicatie heb die niet is op het Microsoft
.NET platform, dan is de Azure VM Role een goede mogelijkheid. Je
legacy applicatie moet dan wel te gebruiken zijn op Windows 2008
server. Op dit moment het enige mogelijke Operating system voor de
VM Role.
Een VM voor de VM Role moet natuurlijk op een bepaalde manier opgebouwd zijn. Op deze site wordt dat keurig stap-voor-stap uitgelegd.
http://msdn.microsoft.com/en-us/library/gg433125.aspx. Een dergelijke VM kan gemaakt worden op een Windows 2008 R2 server met
Hyper-V. Tijdens de installatie van deze VM kun je dan je “legacy”
applicatie installeren.In een van de stappen moet je Windows Azure
VM Role Integration Components installeren. Deze software installeert
ook iets om te connecten met de storage.
Nadat je de VM dan gesysprepd hebt, dan kun je deze uploaden naar
Azure. Ook deze stappen staan op bovenstaande site uitgelegd. In
het kort komt het erop neer, dat je een Windows Azure SDK command prompt in Administrator mode starten. Dan moet je met het
CSUPLOAD tool de connectionstring vast leggen, dat zie je in het eerste deel. Daarna begint de daadwerkelijke upload.
Bij het preparen worden er twee tijdelijke bestanden aangemaakt.
Eentje met de extensie .PREPED en eentje met de extensie .DIGEST.
Tijdens deze upload actie zie je dan op het Windows Azure portaal de
status PENDING. Als de upload klaar is, dan zie je op de command
line en op het Windows Azure portaal het volgende.
Als je de VM dan geupload hebt, dan is er geen mogelijkheid om de
VM te starten. In Visual Studio moet je een Virtual Machine role toevoegen aan je project. Daarbij kies je dan de geuploade VHD. Dit kan
pas als de upload daadwerkelijk klaar is
Dit moment moet de VM en de applicatie nog in hetzelfde zone staan.
Dit zal wel te maken hebben met de beta fase waarin de VM role verkeerd. Je krijgt een foutmelding tijdens het deployen als dit niet klopt.•
Zoals uit het figuur blijkt, begon het tool CSUPLOAD gewoon met het
voorbereiden van de upload. Maar toen het feitelijk uploaden moest
beginnen, kwam onderstaande foutmelding. In de cirkel zie je dat ik inderdaad “Anywhere Europe” gekozen had, dat is per definitie geen
single location .
1
Uiteraard is dit niet altijd zomaar waar en zitten hier soms nog een paar
haken en ogen aan.
Marcel Meijer
Gelukkig is het tool wel handig opgezet. Het hele preparing gedeelte
hoeft niet nog een keer te gebeuren, hij begint nu met het feitelijk uploaden. Dit duurt wel een tijdje.
Marcel Meijer werkt als Software
Developer / Solution Architect bij
VX Company. Hij is .NET track
owner en bestuurslid bij de SDN
en MVP.
magazine voor software development 7
Als het een ICT-er is,
zit hij bij Sogeti.
Wat kun je? Die vraag stelt ieder bedrijf met een vacature. Wie ben je? Die vraag stelt Sogeti
ben je dan aan het juiste adres. Ruim 100 ervaren
meteen daarna. We vinden het belangrijk dat je bij ons past. Want een ICT-er van Sogeti is
Javanen werken bij Sogeti aan het realiseren van
geen gemiddelde ICT-er. Het is er een met uitgesproken eigenschappen.
complexe en innovatieve oplossingen voor haar
Gedreven. Resultaatgericht. En niet snel tevreden. Natuurlijk: plezier hoort erbij. Maar we
gaan op de eerste plaats voor de inhoud. Zo kennen klanten ons. Zo kennen we elkaar.
klanten. Aangezien vakmanschap bij Sogeti hoog
in het vaandel staat, wordt er veel tijd geïnvesteerd
in het vergroten van kennis en de persoonlijke
ontwikkeling van de Java professionals. Het behalen
Microsoft-specialisten
meest gecertifi ceerde organisaties in de branche.
van Java certificeringen is daar onlosmakelijk mee
Stel, je hebt een passie voor Microsoft. Je bent een
Qua omgeving kun je denken aan ALM, VSTS 2010,
verbonden. Sogeti heeft dan ook niet voor niets de
kei in applicatieontwikkeling en -architectuur. En je
.NET4.0, Offi ce 2010, SharePoint 2010, Azure en
best gecertificeerde Java Community van Nederland.
wilt verder in je vakgebied. Dan is Sogeti het bedrijf
BPOS. Terwijl de projecten enorm gevarieerd zijn.
voor jou. Met 700 Microsoft-professionals behoren
Van BizTalk-implementaties en end-user BI-oplos-
Wil jij met jouw kennis en ervaring onze Microsoft
we tot de grootste Microsoft-communities van
singen tot de omvangrijkste integratie ooit van
Community of Java Community versterken?
Nederland. Bovendien verwachten onze klanten
SharePoint in Dynamics CRM.
Neem dan gerust contact met ons op of kijk op
werkenbijsogeti.nl.
innovatie, zodat je echt al je kennis inzet. Wat ons
betreft wordt die kennis steeds breder en dieper;
JAVA-specialisten
we dagen je uit om het maximale uit jezelf te halen.
Als je passie hebt voor het Java vakgebied, dan
Bijvoorbeeld door je cursussen en opleidingen
wil je natuurlijk ook werken bij het bedrijf met de
aan te bieden. We zijn niet voor niets een van de
beste Java Community van Nederland. Bij Sogeti
.NET
Andrew Nurse
Introduction to Razor Syntax
Since about 1996, writing websites on the ASP.Net platform has involved working with the
“angle-bracket percent” (<%) syntax (sometimes called “WebForms syntax”) I’m sure we’re all
familiar with. From Classic ASP right up to ASP.Net 4.0, if you worked with the Microsoft Web
Platform, you probably worked with this syntax. However, with the release of the MVC framework in 2009 (more than 13 years after Classic ASP 1.0), the community started to explore new
languages and new ways of writing web pages. Last year, we started investigating ways in
which we could revamp the ASP.Net syntax, and the result of that process is Razor.
In this article, I will describe the motivations behind developing Razor, and give an overview of
the syntax.
What is Razor?
When we started designing Razor, we took a simple snippet of
pseudo-code as an example:
<ul>
href=”/Products/@product.Id”>@product.Name</a></li>
}
</ul>
Listing 3: The @ at work.
foreach(var product in Products) {
<li><a href=”/Products/product.Id”>product.Name</a></li>
}
</ul>
Listing 1: What the developer means
This is what the developer means; what they want their code to do.
However, in most web languages, like the traditional ASP.Net syntax,
you have to write something like this:
<ul>
<% foreach(var product in Products) { %>
However, Razor does more than just cut down on extra characters.
The magic of Razor lies in how it unifies two languages, the serverside code and the client-side markup. Razor has a fairly deep understanding of C#, VB and HTML and it uses that understanding to cut
back on the extra syntax users need to write. For example, in Listing
3, you’ll notice that there are @ characters indicating where we switch
to code, but nothing to indicate that we’ve gone back to markup. The
Razor parser understands that immediately after the first @, there’s a
foreach statement, so it assumes that when that statement is finished,
you’re ready to go back to markup. Similarly, the parser is able to
detect the <li> tag and treat it’s contents as markup. Razor also allows
continued nesting of markup within code and vice-versa.
<li><a
href=”/Products/<%=product.Id%>”><%=product.Name%></a></li>
<% } %>
</ul>
Getting Started with Razor
To get started with Razor, you can download Microsoft WebMatrix
from http://www.microsoft.com/web/webmatrix/. Everything you need
is installed as part of that package.
Listing 2: What the developer has to write, in WebForms syntax.
So, we stripped all the extra control characters out and started again,
back to the first example. We wanted to find a way to blend server-side
code and client-side markup with as few characters as possible. The
answer was a single character.
The answer was a single character
What makes Razor so different from other languages is that it only has
one major control character, the at-sign (@). Going back to the earlier
example, writing it in Razor would require only 3 control characters
instead of 18 control characters:
<ul>
@foreach(var product in Products) {
Razor files have one of two extensions, indicating which language the
server-side code is written in. If you are using C#, the file extension is
CSHTML. If you are using VB.Net, the file extension is VBHTML. For
the most part, the server-side languages work the same way in Razor,
but there are a few cases where one language works a little differently
than the other. I’ll highlight those cases when we get to them.
A Razor Document
A Razor document starts with HTML. Until you need to start inserting
some server-side code, a Razor file is just like a plain HTML file. When
you’re ready to go in to code, you start a code block.
Code Blocks
Code Blocks in Razor are started with a single @, followed immediately by a C# or VB block construct (like foreach, or If). If you want code
that isn’t within the body of a block statement (for example, you want
to declare some variables or calculate some values), you can create a
generic code block using @{ in CSHTML, or @Code in VBHTML.
<li><a
magazine voor software development 9
.NET
@{ var foo = GetFoo(); }
@<text>This is also valid, and it won’t have any tags
<p>This is just regular markup!</p>
around it!</text>
@if(foo != null) { foo.Bar(); }
<text>This is still NOT valid!</text>
Dim p = <p>This is actually an XML Literal, and not
considered markup!</p>
Listing 4a: C# - Code Blocks
Dim p = <text>Same for this!</text>
@Code
}
Dim foo = GetFoo()
End Code
Listing 5b: VB - Mixing Markup and Code
<p>This is just regular markup!</p>
@If foo IsNot Nothing
foo.Bar()
End If
Listing 4b: VB - Code Blocks
Notice that there are no Razor constructs necessary in order to mark
the end of a code block, the code block ends when it would naturally
be expected to end.
Mixing Code and Markup
On the web, code isn’t very useful unless it can be used to control the
output of client-side markup. In Razor, any code block can contain
markup blocks within it. In fact, those markup blocks can then contain
further code block which can contain further markup blocks. You can
nest them as deeply as you need!
In CSHTML, mixing markup in to your code is as easy as just typing
some HTML! However, there are two rules to keep in mind. First, markup is only allowed at the start of a C# statement, you can’t place
markup in the middle of a statement. Second, you must start your
markup with a tag and all the tags must have a matching closing tag
(or be self closed, like <br/>). For those cases where you don’t want
to have an outer tag (like <p>) rendered around your text, you can use
a special tag called <text>. The <text> tag is only used to define the
boundaries of your markup, and it will not actually be rendered.
Once inside the tag, everything until the matching close tag is
considered HTML, including additional tags. You can also use the @
character to start another code block. This is why it’s so essential to
close your tags. If you don’t, the parser can’t determine where the
markup block ends, so it doesn’t know when to switch back to code.
Unfortunately, this is also one place where CSHTML and VBHTML
differ. Due to the complexity of the VB language, and the XML literals
feature, we aren’t able to be quite as smart when parsing VB. So in
VBHTML, when you want to switch from Code back to markup, you
must use the @ character again. You can still use the <text> tag as
before and
The following example shows some valid and invalid ways of putting
markup inside C# and VB code:
@if(foo) {
Partials, Layouts and Sections
Often, when writing a web application, you will find it necessary to
extract out common view logic into a component. In ASP.Net
WebForms, these are called UserControls and in ASP.Net MVC and
WebPages, we call them Partials. Razor supports rendering partials
using the RenderPage method. For example, consider a partial like
the following (shown only in C#, but the VB code is similar):
The current time is @PageData[0]
Listing 6: _Time.cshtml Partial Page
Let’s note a few things about this file. First, the file-name starts with an
“_”. In both ASP.Net WebPages and MVC, this indicates to the Razor
engine that the file cannot be served on it’s own. With traditional
ASP.Net syntax, UserControl have a different file extension (ascx) which
prevents them from being served. However, all Razor pages written in
the same language have the same extension, so we use the “_” to denote pages which are not to be served on their own. Second, is the
PageData collection. When rendering a partial page, this collection will
contain all of the extra arguments that were provided to the RenderPage method. So to use this partial, we would write code like this:
<p>@RenderPage(“_Time.cshtml”, DateTime.Now)</p>
Listing 7: Using the Time Partial
The first argument to RenderPage is the virtual path to the page we
want to render, and the remaining arguments are passed on to that
page.
One of the most popular features of ASP.Net is master pages. Razor
has a concept similar to master pages, called layout pages. A layout
page is a template, much like a master page, which has placeholders
where each specific page’s content will be rendered. As with partial
pages, layout pages are not directly requested, they are linked to a
content page. When the user requests the content page, the Razor
engine runs the page and collects up all the content to be rendered.
It then checks to see if the page defines a layout page and if so,
passes the content to that page and renders it.
Here’s a simple example of a content page:
@{
<p>This is valid</p>
<text>This is also valid, and it won’t have any tags around
Layout = “_Layout.cshtml”;
}
it!</text>
string p = <p>This is NOT valid!</p>;
@section Header {
string p = <text>Nor is this!</text>;
}
This is the header
}
@section Footer {
This is the footer
Listing 5a: C# - Mixing Markup and Code
}
@If Foo
This is the body
@<p>This is valid</p>
<p>This is NOT valid</p>
10
MAGAZINE
Listing 8: Content Page – Content.cshtml
.NET
Let’s review this code from the top. First, we need to attach a layout
page to our content page. We do this by simply setting the Layout
property in a code block. You can use any code you want to set this
property, even load it from config files or a database. Next, we define
a Header section. Just like master pages allow for multiple content
placeholders, Razor content pages can define multiple sections, as
well as a special “body” section. Each named section is defined using
the @section keyword (in both C# and VB). In C#, we use “{“ and “}”
to delimit the boundaries of the section. In VB, the “End Section” keyword is used, much like existing VB constructs like “If”. Any content
which is not contained in a section is considered part of the “body”,
which is a special unnamed section. Then, after our header section,
we define some body content and then a footer section.
There are also some cases where it doesn’t make sense to have a
body. For example, if you have a three column layout, you may want
to have three sections “Col1”, “Col2” and “Col3” and no body. In
Razor, as long as you have at least one @section block, you can omit
the body completely.
Now that we have a content page, let see what the layout page would
look like:
End Function
End Functions
The time is: @CurrentTime()
Listing 9b: VB - Functions Block
It is also often necessary to import classes and types from other
namespaces into your Razor pages, and for this we provide the
@using/@Imports keyword:
@using System.IO
@{
// Now I can use FileStream!
Stream s = new FileStream();
}
Listing 10a: C# - Using Statement
@Imports System.IO
@Code
<html>
‘ Now I can use FileStream!
...
Dim s as Stream = New FileStream()
<body>
End Code
<div id=”header”>@RenderSection(“Header”)</div>
<div id=”body”>@RenderBody()</div>
Listing 10b: VB – Imports Statement
<div id=”footer”>@RenderSection(“Footer”, required:
false)</div>
</body>
</html>
Finally, Razor also includes its own server-side commenting feature.
This allows you to write comments in both code and markup block, as
well as comment out chunks of Razor code. This syntax is the same
in both languages:
Listing 9: Layout Page - _Layout.cshtml
This will be rendered!
The layout page contains all the outer HTML markup we need to
define our page, then it uses the RenderSection and RenderBody
methods to render the sections defined by our content page. The
RenderSection method injects the section with the specified name,
and the RenderBody method injects the content which was not part
of a section. Here, we’ve also specified that the footer section is not
required. Normally, if we try to render a section the content page does
not define, we get an run-time error, but by setting the “required” parameter to false, we tell the run-time that this section is optional.
Layout pages can also be nested, so our _Layout.cshtml file above
could have specified a further layout page simply by setting the
Layout property.
Other Bits of Syntax
Sometimes it is necessary to define common functions that will be
used throughout the page. For this purpose, Razor has a “functions”
keyword which allows you to insert C# or VB function declarations.
For example:
@functions {
@* But this will not, because it is a comment *@
Listing 11: Razor Comments
Conclusion
This is by no means a complete review of the features of Razor, there
are a few more cool features to check out, so I recommend you check
out the http://www.microsoft.com/web/webmatrix site and click the
Learn tab to learn more about Razor, ASP.Net WebPages and
WebMatrix. I hope you’re as excited to use Razor as we were to write
it. We really believe this is a revolutionary new syntax and hope that
you find it useful! •
Andrew Nurse
Andrew is a developer on the
ASP.Net team at Microsoft and
works on the Razor parser.
public DateTime CurrentTime() {
return DateTime.Now;
}
}
The time is: @CurrentTime()
Listing 9a: C# - Functions Block
@Functions
Public Function CurrentTime() as DateTime
Return DateTime.Now
magazine voor software development 11
DELPHI
Cary Jensen
Introduction to the Delphi
Open Tools API
In a recent article in this magazine I wrote about how you can add custom key bindings to
Delphi's editor. In response, I received a number of questions about the mechanisms that
permit Delphi developers to access something as internal as the code editor. This mechanism
is called the open tools API, or OTA for short. It's been around since the very earliest days of
Delphi, and it’s one of the more powerful, and least exploited areas of Delphi development.
This is the first in a two part series on Delphi's open tools API. In this
article I provide you with an overview of the OTA, and provide an
example of a project that adds menu items to Delphi's menu. In the
next article in this series, I will discuss a more complicated OTA
implementation. Specifially, I will show you how to write a wizard that
you can install into the Object Repository.
deprecated, and the OTA is now entirely based on interfaces. And,
with the release of the Galileo IDE (initially available in the now defunct
C#Builder), the reliance of the OTA on pure interface definitions is
complete.
Overview of the Delphi Open Tools API
Since Delphi 1, the Delphi IDE has provided developers with access
to some of its most internal features. It is through this mechanism that
tools such as CodeSite, CodeRush, and GXperts, and the like, have
been able to extend the capabilities of Delphi beyond those
implemented by the Delphi team.
A Brief Overview of Interfaces
Because they are so central to Delphi's open tools API, let's take a
brief look at interfaces and their implementation. To begin with, an
interface is a definition of public methods and properties. Interfaces
serve as a sort of template for classes, defining the methods and
properties that a class which implements the interface must support.
In that sence, an interface defines a contract that a class must
observe, without defining how that contract must be implemented.
In the early days of Delphi, the open tools API was based on virtual,
abstract base classes that provided templates for the features
exposed through the OTA. In those days, you descended a custom
class from one of these abstract classes, or one of their partially
concrete descendants.
One of the crucial features of an interface is that it provides for
polymorphism without relying on common class ancestors. In other
words, two classes that implement the same interface are assignment
compatible with respect to that interface, regardless of what classes
they descend from.
It was a little clumsy in the early days. Even adding a single new component to the component palette required a complete re-compilation
of the installed visual component library (VCL). Nonetheless, it was a
groundbreaking capability.
As far as the open tools API is concerned, these interfaces play two
distinct roles. On the one hand, these interfaces define the collection
of methods and properties that must be implemented in the classes
that you create to implement your OTA features. (Well, that's not
entirely accurate. The OTA also includes several interfaces, such as
IOTAProjectWizard, that define no methods or properties. These
interfaces are identifiers, and are used to signal to Delphi something
about what roles the implementing object plays.)
There have been many changes to the Delphi language over the years,
and the open tools API has evolved along with it. Two of the major enhancements to Delphi that have had a profound influence on the open
tools API was the introduction in Delphi 3 of packages and interfaces.
With design-time packages, it became possible to easily install OTA
extensions without re-compiling the entire VCL. On the other hand,
some of the OTA extensions didn't actually require additions to the
VCL. Instead, some of them, such as Object Repository wizards, were
added to Delphi by compiling your Wizard class in a DLL. Delphi loaded that DLL based on entries that you made to the Windows registry.
The second role of these interfaces is to define the methods and
properties that are available for your use in objects that the OTA supplies for you. Specifically, there are numerous objects that you can use
to do such things as manipulate Delphi's menus, toolbars, and glyphs.
Similarly, there are objects that the OTA provides so that you can interact with the debugger, the code editor, the Object Repository, the
Message pane, code completion, and much more.
While packages made the installation of OTA classes easier, the
introduction of interface support in the Delphi language had a much
more profound influence on the architecture of the OTA. While
interfaces were used sparingly when first introduced, they have grown
exponentially more important in defining the application programming
interface of the OTA. Indeed, the abstract classes of old are long
These interfaces are actually divided into two groups, the native tools
API (NTA) and the open tools API (OTA). The NTA is used to access the
Delphi IDE objects, such as the menus and toobars. The NTA is
defined by a single interface, INTAServices.
By comparison, the OTA is a collection of interfaces that represent
various facilities that the OTA makes available to you.
12
MAGAZINE
DELPHI
These include IOTACodeCompletionServices, IOTADebuggerServices,
and IOTAKey BindingServices, to name just a few.
(x86)\Embarcadero\RAD Studio\8.0\lib\win32\release (omit the
(x86) if you are using a 32-bit operating system).
The objects provided you by the NTA and OTA are accessed through
a single interface, IBorlandIDEServices. The object that implements
this interface is assigned to a global variable named BorlandIDE
Services that is declared in the ToolsAPI unit.
To access a service of the NTA or OTA you cast BorlandIDEServices
to the appropriate interface. Actually, a better way to put this is that you
should first ask whether or not BorlandIDEServices implements an
object that implements the service you are interested in, and if so, then
perform the cast.
The Supports function, defined in the SysUtils unit, is the preferred
technique for performing this task. For example, consider the
following code
var
MessageService: IOTAMessageServices;
begin
if Supports(
Fig 1: Configuring the package to be a design time package
BorlandIDEServices,
IOTAMessageServices,
MessageService) then
begin
//CustMessage is a class that
//implements IOTACustomMessage
MessServ.AddCustomMessage(CustMessage.Create);
end;
Actually, this little code sample is a good representation of just how you
approach the open tools API. Specifically, you use the Delphi provided
object that implements the IOTAMessageServices interface to add a
message to the Message pane (in this particular example). However,
the method, AddCustomMessage, takes a single argument of the type
IOTACustomMessage. That interfaces is one that you must implement
in an object that you define.
Next, we will add a unit in which we will define a class that implements
the IOTAMenuWizard interface. To do this, use the following steps:
1. Select File | New | Unit.
2. Add the following units to the interface section uses clause:
ToolsAPI, SysUtils, Menus, Dialogs.
3. Add a class that descends from TNotifierObject and implements
the IOTAWizard and IOTAMenuWizard interfaces. In addition, add a
declaration of a no-parameter procedure named Register. The
interface section of this unit should now look like the code that
appears in Listing 1.
4. Next, implement the methods of the TMenuDemo class and the
Register procedure as shown in Listing 2.
interface
uses ToolsAPI, SysUtils, Menus, Dialogs
In other words, Delphi provides some of the implementations of OTA
(and NTA) interfaces, while you will supply additional objects that
implement OTA interfaces, when necessary.
type
TMenuDemo = class(
TNotifierObject, IOTAWizard, IOTAMenuWizard
A Simple OTA Demonstration
In the following project I am going to show you how to add your own
menu items to Dephi's main menu using both the OTA and NTA. One
of these menu items is added by implementing the IOTAMenuWizard
interface, which you can use to add a single menu item to Delphi's
Help menu.
)
procedure MenuClick(Sender: TObject);
constructor Create;
{ IOTAWizard }
//Basic information about the wizard
function GetIDString: string;
function GetName: string;
The second technique is more general, in that you can add one or
more menu items to any of Delphi's menus. This second technique
makes use of the NTA (and also requires greater care on your part, as
you can seriously damage the Delphi IDE if you make mistakes).
function GetState: TWizardState;
procedure Execute;
{ IOTAMenuWizard }
//Implement this interface to add an item
//to the Help menu
To begin with, you start with a design time package. Use the following
steps to begin the project
1. From Delphi's main menu, select File | New| Package.
2. Right click the newly created package in the Project Manager
and select Options.
3. From the Description page of the Project Options dialog box,
set Usage options to Designtime only.
4. Right-click the project in the Project Manager and select Add
Reference. Add the designide.dcp package to the project.
In Delphi XE, this project is located by default in C:\Program Files
function GetMenuText: string;
end;
procedure Register;
Listing 1
implementation
procedure Register;
begin
magazine voor software development 13
DELPHI
RegisterPackageWizard(TMenuDemo.Create);
end;
item created by the implementation of IOTAMenuWizard. Similarly, you
will find the Custom Menu Item menu item at the bottom of Delphi's
Project menu, as shown in Figure 2.
{ TMenuDemo }
constructor TMenuDemo.Create;
var
NTAServices: INTAServices;
MainMenu: TMainMenu;
Menu1, NewMenu: TMenuItem;
begin
if Supports(
BorlandIDEServices,
INTAServices,
NTAServices) then
begin
MainMenu := NTAServices.MainMenu;
Menu1 := MainMenu.Items.Find('Project');
if Menu1 <> nil then
begin
NewMenu := TMenuItem.Create(MainMenu);
NewMenu.Caption := 'Custom Menu Item;
Fig. 2: A custom menu item appears in Delphi's Project menu
NewMenu.OnClick := MenuClick;
Menu1.Add(NewMenu);
end
end;end;
procedure TMenuDemo.Execute;
Conclusion
This article has given you a basic introduction to using Delphi's open
tools API as well as its native tools API. In the next article in this series,
we will take a look at a more complicated OTA project, one that adds
a new custom wizard to Delphi's Object Repository. •
begin
ShowMessage('Your OTA object is executing');
end;
Cary Jensen
function TMenuDemo.GetIDString: string;
begin
Result := 'JDSI.MenuDemo';
end;
function TMenuDemo.GetMenuText: string;
begin
Result := 'Select Me';
end;
function TMenuDemo.GetName: string;
begin
Result := 'Simple Menu Demo';
end;
Cary Jensen is President of Jensen
Data Systems, Inc., a training and
consulting company that won the
2002 and 2003 Delphi Informant
Readers Choice Awards for Best
Training. He is an award-winning
author of 20 books, including
Advantage Database Server: A Developers Guide (2007, Sybase),
Building Kylix Applications (2001, Osborne/McGraw-Hill), JBuilder
Essentials (1998, Osborne/ McGraw-Hill), and Delphi in Depth
(1996, Osborne/McGraw-Hill).
For information about onsite training or consulting services, you
can contact Cary at cjensen@JensenDataSystems.com or visit
his web site at www.JensenDataSystems.com.
function TMenuDemo.GetState: TWizardState;
begin
Result := [ToolsAPI.wsEnabled];
end;
procedure TMenuDemo.MenuClick(Sender: TObject);
begin
ShowMessage('This is where your new menu ' +
'item will do something cool');
DELPHI
TIP:
end;
IntraWeb XI in Delphi XE
Listing 2
The final step is to save your project and then install it. After saving your
project, right-click the project in the Project Manager and select
Install.
Once it has been installed, you will find two new menu items added to
Delphi's menu. On the Help menu you will find the Select Me menu
14
MAGAZINE
De "bundled" versie van IntraWeb bevat niet langer alle features en mogelijkheden. Zo is o.a. ISAPI Deployment tegenwoordig uitgesloten van de gratis bundled features.
Zie http://www.atozed.com/intraweb/featurematrix.aspx voor
een overzicht van de versies en wat het kost om naar IntraWeb
XE Ultimate over te stappen met daarin alle features.
SDN > Update
De bekende quote Premature Optimization is
the root of all evil van Donald Knuth uit 1974
(http://pplab.snu.ac.kr/courses/adv_pl05/
papers/p261-knuth.pdf) is ook vandaag nog
een bekend anti-pattern.
Als programmeur probeer je van te voren al in
gedachten je programma te optimaliseren.
In 97% van de gevallen is de bedachte optimalisatie zo klein dat het (bijna) niets oplevert.
Vandaar dat vaak wordt aangeraden om het
programma eerst laten werken, leesbare code
produceren, tests schrijven en dan als je
ervaringscijfers hebt, dan te optimaliseren.
Ik heb zelf gevoetbald en was noch een Sneijder noch een Robben.
Wou altijd mooi scoren maar miste net doel. In ons collectieve
geheugen staat Nederland - Spanje, Robben dribbel op Casillas
gegrift. Ik zag die bal er al in gaan en droomde van een weeklang feest.
Die teen van Casillas stond echt niet in het design, effectief was het
zeker want het Spaanse doel bleef leeg.
premature
optimization
is the root
of all evil
Zet een club van software architecten bij elkaar
en iedereen optimaliseert vanuit zijn invalshoek.
Geeft regels mee voor de bouw vanuit zijn
gedachtenwereld. Hoe groter de organisatie,
hoe meer acrchitectuur regels, design authorities, wijzigings advies commissies en andere
ballotages je door moet. Zelf heb ik al een paar
projecten meegemaakt waar het
budget op ging in de architectuur fase door de
constante drang naar optimalisaties vanuit
verschillende hoeken. Erger nog het kan
leiden tot een verlamming als je je het
doel uit het oog verliest. Samen
denken we na over academische
oplossingen voor een praktisch
probleem van de klant zonder
aandacht voor het probleem van
de klant zelf.
Nu vraag je je vast af hoe Robben en Casillas in premature optimization passen. Soms moet je gewoon springen en kijken hoe ver je komt,
tegen het gras of de bal wat meer hoogte geven, niet nadenken
gewoon doen. Die terrabytes in je hoofd en de ervaring die je hebt
laten de software wel werken. Schrijf het duidelijk op en maak het
testbaar. De optimalisatie komt dan vanzelf want de code is test- en
leesbaar en toegankelijk voor je collega’s die je bij de optimalisatie
kunnen helpen. In 2012 worden we kampioen!
Roel Hans Bethlehem •
magazine voor software development 15
MOBILE
Jaap van Ekris
Wat is er zo moeilijk aan een
mobiele applicatie?
Mobiele applicaties zijn helemaal hot. Eigenlijk tel je als bedrijf niet mee als je geen mobiele app
levert aan je klanten. Niet alleen de usual suspects als Nederlandse Spoorwegen en OV9292
maar ook Albert Heijn, TNT Post, QPark en Rabobank proberen actief een plekje te verwerven
op het meest private stukje electronica wat we kennen: onze telefoon.
Technisch is het ook niet zo moeilijk: er zijn voor Apples iOS, Googles
Android en Microsofts Windows Phone zeer goede ontwikkelstudio’s
beschikbaar. Het is geen drag-and-drop ontwikkelwerk, maar het
scheelt erg weinig. De applicaties zijn functioneel vaak geen rocketscience. Feit is dat als je voor de desktop kunt ontwikkelen je ook voor
de telefoon kunt ontwikkelen.
Toch zit er wel een voetangel. Een groot deel van de gedownloade
applicaties blijft ongebruikt. Slechts 25% van de gebruikers koopt ooit
een applicatie. Dus er zijn wel degelijk een hoop applicaties die bij
nader inzien gewoon “rommel” zijn in de ogen van de gebruiker.
In dit artikel gaan we in op wat de rommel van de top-applicaties
onderscheidt. We beginnen met het uitleggen van het meest
fundamentele verschil tussen desktop en mobiele applicaties: de
gebruikerscontext. Daarna kijken we naar de impact hiervan op de
user-interface en gebruikte techniek.
Gebruikerscontext
De gebruiker en zijn context is zonder twijfel het grootste verschil
tussen desktop en mobiele applicaties. De desktop gebruiker zit in
het algemeen relaxed op een vertrouwd plekje zijn werk met zijn
computer te doen. Kern hiervan is dat hij de omgeving vertrouwt en
dat hij bezig is met zijn werk op de computer. De mobiele gebruiker is
bezig in een onvertrouwde omgeving en heeft zijn telefoon nodig om
hem te helpen beslissingen te nemen in die omgeving. Kern hiervan is
dat de gebruiker in een onvertrouwde (wellicht zelfs onbetrouwbare of
potentieel vijandige) omgeving bezig is beslissingen te nemen waarbij
zijn telefoon hem moet helpen. De mobiele gebruiker moet, in
tegenstelling tot de desktop gebruiker, real-life beslissingen nemen en
wil eigenlijk helemaal niet bezig zijn met die applicatie. De mobiele
applicatie is voor de gebruiker is slechts een noodzakelijk kwaad om
zijn omgeving beter te begrijpen.
Doordat de mobiele applicatie slechts een middel is tot een hoger
gebruikersdoel, ontstaat er een soort ongeduld bij de gebruiker. Als
de applicatie te traag is of teveel aandacht opeist zal hij de
applicatie terzijde schuiven en gewoon “blind” beslissingen gaan
nemen zoals hij vroeger ook deed: op een gegeven moment moet je
als gebruiker gewoon die trein gaan pakken, in plaats van uitzoeken
welke van de vele opties de meest optimale is. De wereld om de
applicatie gaat door en de gebruiker dus ook, met of zonder
applicatie.
Gek genoeg is de benaderingswijze van veel software ontwikkelaars
er een van het laten krimpen van een desktop-applicatie. Men heeft
te veel informatie in de applicatie, de user interface is te
complex en er wordt vaak geen rekening gehouden met technische
beperkingen van mobiele toestellen.
16
MAGAZINE
Keep it simple
Een van de belangrijkste basisprincipes is “hou het simpel”. Dat klinkt
makkelijk, maar de praktijk wijst uit dat het ontzettend moeilijk is een
applicatie eenvoudig te maken voor de gebruiker: het vereist de moed
om keuzes te maken.
Een van de belangrijkste keuzes is het beperken van de applicatie tot
één heel specifieke taak van de gebruiker. Een mobiele applicatie dient
een bepaald doel en daar moet dus niet teveel franje in komen, omdat
dat domweg in de weg gaat zitten bij gebruik. Een interessant voorbeeld hiervan is bijvoorbeeld de NS Reisplanner Xtra, die geen enkele
informatie bevat over de prijs van een reis. Hij is puur bedoeld om
mensen treinreizen efficient te laten plannen. Overigens moet ook bij
deze applicatie wel een kritische kanttekening worden gezet: er is een
deel in de applicatie gereserveerd voor marketing-acties, wat kostbare ruimte in de navigatiebalk kost. Als men dergelijke informatie zou
willen bieden, zou je eigenlijk moeten overwegen een tweede
applicatie te bouwen. SPB Traveller doet dit structureel: alle
onderdelen (vluchtplanning, currency-converter, woordenboek, etc.)
worden ook als losse applicatie geinstalleerd, zodat er vlot genavigeerd kan worden.
User interface
Een belangrijk onderdeel van de applicatie is de user interface.
Belangrijk is om te onthouden dat de niet de tijd, zin of
aandacht heeft om precieze handelingen uit te voeren. Ook moet
informatie zeer overzichtelijk zijn om snel te kunnen analyseren. Dit
betekent dat de applicatie hier ook op ingericht zijn. Dit uit zich op
verschillende vlakken: het visuele deel van de de user interface maar
ook de page-flow en de informatie die ingevuld moet worden in de
interacties.
Een belangrijke wake-up call voor GUI ontwerpers is dat mensen hun
applicatie ook gebruiken, maar dan ook echt overal. Onderzoek laat
zien dat veel mensen hun telefoon gebruiken als ze in bed liggen of op
de WC zitten. Maar ook treinstations en bushaltes zijn vaak favoriete
plekken om even wat te gaan doen. Dit laatste brengt nogal wat uitdagingen, zeker in Nederland en noord Europa. Mensen hebben
’s winters handschoenen aan of zijn onnauwkeurig door de koude.
Kleine controls op zo’n telefoonscherm zijn dan ook volstrekt uit den
boze, gewoon omdat het niet te bedienen is. Een scherm moet goed
te bedienen zijn met een dikke handschoen aan of koude handen.
Ook mensen die meer bezig zijn met hun omgeving zitten nog wel
eens een paar milimeter mis. Grote knoppen met duidelijke gevolgen
zijn dan ook essentieel. Daar faalt eigenlijk de iPhone GUI al een beetje:
daar staan eigelijk al te kleine knoppen op.
MOBILE
Bedenk ook dat een gebruiker veelal informatie in een oog-opslag
moet kunnen interpreteren, zonder al teveel analyse van zijn kant.
In de desktop wereld kun je probleemloos informatie op een visueel
aantrekkelijke, maar onoverzichtelijke, manier presenteren: de gebruiker moet er toch nog zijn eigen analyse op los laten. Een mobiele
gebruiker wil graag snel hapklare informatie hebben die zijn beslissing
in de wereld zal gaan beinvloeden. Je eindigt dan al snel in tabelgeorienteerde vormgeving. Visueel wellicht niet de mooiste oplossing,
maar vaak wel de meest effectieve. Soms moet je een hele andere
aanpak kiezen: file-informatie moet je wellicht niet als lijst van files
weergeven (wat een behoorlijke wissel trekt op de topografische
kennis van de gebruiker), maar meer als kaart van Nederland met rood
snelwegen of gekleurde gebieden.
Denk ook aan het minimaliseren van “vereisten” van een huisstijl.
Bijvoorbeeld de NS heeft in haar NS Reisplanner Xtra een plaatje
zitten die bijzonder veel ruimte inneemt. Ruimte die anders door
nuttige informatie gebruikt zou kunnen worden. Maar ook zaken als
logo’s, beeldelementen en standaard icoontjes kunnen op een klein
scherm wel eens zeer veel ruimte kosten of erg onduidelijk
overkomen. Het is verstandiger om te kijken hoe de applicatie het
beste uit de verf komt, en dan pas een huisstijl hier passend in te
krijgen, dan de huisstijl leidend te laten zijn.
Page-flow is een volgend punt van aandacht. Die moet niet te
complex zijn, maar zeker ook niet te lang. Een gebruiker raakt snel
afgeleid, en de vraag “waar was ik ook al weer” is foutgevoelig en helpt
niet bij het vlot uitvoeren van de dingen die hij snel wilde doen.
Idealiter bestaat een handeling uit maximaal 3 tot 4 verschillende
schermen die erg duidelijk maken waarmee de gebruiker bezig is.
Denk ook over de gevolgen van de pageflow na: de gebruiker is
bijzonder doelgericht en zal alles doen om die taak te volbrengen.
Het beste voorbeeld hiervan is het navigatiepakket van de ANWB, wat
niet toeliet dat de gebruiker de bestemming invoerde of wijzigde als de
auto bewoog. Doel van de ANWB was om veiliger weggedrag te
stimuleren. Gevolg was echter dat de gebruiker met enige vorm van
creativiteit de GPS deactiveert en vervolgens alsnog zijn bestemming
ingeeft/wijzigt. Gevolg is dus een agressievere en veel meer afgeleide
bestuurder dan de bedoeling van de ANWB was. Ongemerkt zitten
dit soort zaken in elke applicatie: een tunnelvisie van hoe het
gebruiksscenario verloopt is handig, maar zeker niet altijd de realiteit.
Ingevoerde informatie is een verhaal apart. Veel devices kennen een
on-screen toetsenbord of zelfs een (klein) fysiek toetsenbord. Veel
ontwikkelaars zien dit als een excuus om dit ook te gebruiken. Het
gebruik van zo’n toetsenbord is alles behalve comfortabel: er zijn zelfs
specifieke RSI-varianten voor dit soort gebruik ontdekt. Een paar
tekens is vaak nog te doen, maar grotere stukken tekst zijn voor
gebruikers vaak erg vervelend. Soms is het een bruikbaar scenario
om complexe informatie via een website in te voeren en dan naar het
toestel te syncen. Zo werken de reisschema’s van TripIT bijvoorbeeld.
Voorkomen dat een gebruiker veel informatie moet invoeren is
belangrijk omdat het afleid van het primaire doel van de gebruiker: zijn
omgeving managen.
Technische mogelijkheden en beperkingen
Ook technische mogelijkheden en beperkingen spelen een sterke rol
bij de kwaliteit van een mobiele applicatie. Het is voor een gebruiker
zeer vreemd als technische mogelijkheden onbenut blijven of als je
ingaat tegen technische beperkingen.
Een smartphone heeft zeer veel technische mogelijkheden. Technisch
gezien zijn ze bijna gelijk aan laptops van 3 jaar terug met office
volledig geinstalleerd. Maar een smartphone weet tegenwoordig ook
zijn eigen locatie en heeft een camera. Het is voor gebruikers dan ook
zeer vreemd als je als applicatiebouwer daar geen gebruik van maakt.
Het zou bijvoorbeeld bijzonder vreemd zijn als je bij de NS Reisplanner de startlocatie handmatig zou moeten ingeven. Hoogstwaarschijnlijk is dat het dichtsbijzijnde station. Maar ook verwacht de
gebruiker bijvoorbeeld dat Appie, de Albert Heijn boodschappenlijst,
gewoon automatisch het juiste filiaal selecteert. Maar de gebruiker
verwacht ook integratie met de agenda en contactpersonen. Gewoon
omdat het technisch mogelijk is en hem veel complex werkt bespaart.
Maar de smartphone kent ook zijn technische beperkingen: met name
de accu is een van de belangrijkste. Als je als applicatie de accuduur
significant verkort, door veel van de GPS, CPU of internet-verbinding
te vragen, dan pak je figuurlijk de telefoon van de gebruiker af. Je
verkort de bruikbare tijd van een telefoon voor de gebruiker. Dus veel
energie gebruiken door intensief energie-slurpende hardware te
gebruiken is niet verstandig. Dat is de manier om slechte reviews te
krijgen met de opmerking “battery drain”.
Een ander punt is de internetverbinding. De telecom-operators willen
ons erg graag laten geloven dat hun netwerk overal aanwezig is met
voldoende bandbreedte. Dit is niet het geval: de dekking door hun
netwerken valt in de praktijk gewoon erg tegen. Zelfs al zou je goede
dekking hebben, valt de kwaliteit daarvan vaak tegen door verstoringen door gebouwen of warmtewerende beglazing. Bovendien raken
netwerken erg snel overbelast: een grote storing op Utrecht Centraal
en je krijgt in de wijde omtrek geen data-verbinding meer. Een volledige afhankelijkheid van internet is dus iets wat je als ontwikkelaar
moet zien te vermijden als het mogelijk is.
Conclusie is dus dat het bij mobiele applicaties veel minder over de
harde techniek van API-calls en code gaat, maar veel meer nadenken
over hoe de applicatie gaat functioneren in de context van een
gebruiker die iets wil realiseren. Bij mobiele applicaties gaat het veel
meer om hoe de gebruiker snel zijn beoogde taak kan realiseren, en
dat vergt speciale aandacht voor wat de functionaliteit is, hoe de GUI
er uit ziet en de oplossing technisch wordt opgezet. •
Jaap van Ekris
Jaap van Ekris (Det Norske Veritas)
is een Microsoft Most Valuable Professional, gespecialiseerd in Mobiele
applicaties, hoe ze passen in het
levensritme van hun gebruikers
en de business modellen achter
applicaties.
SDN Event
18 maart 201
1
aanmelden v
ia
www.sdn.nl/sd
e
magazine voor software development 17
((1%((7-(,7(5
,6(,*(1%$$6
=RJDDWGDWWHJHQZRRUGLJ%HQMHHHQPDDOHUYDUHQJHQRHJLQGH,&7GDQNLHVMHYRRUHHQEHVWDDQ
DOV]HOIVWDQGLJRQGHUQHPHU:HUNJHQRHJ'XL]HQGHQIUHHODQFHUVJLQJHQMHYRRU+HWHQLJHPLQ
SXQWMHDDQKHWRQGHUQHPHUVFKDSLVKHWJHPLVDDQ]HNHUKHGHQGLHYDQ]HOIVSUHNHQG]LMQYRRUHHQ
ZHUNQHPHU:DQWHHQYDNEHNZDPHHQDPELWLHX]H,&7HULVQLHWSHUGHÀQLWLHHHQFRPPHUFLsOH
GXL]HQGSRRWRIKRXGWHUQLHWYDQRPHHQXLWJHEUHLGHDGPLQLVWUDWLHWHYRHUHQHQRSHQVWDDQGH
IDFWXUHQQDWHEHOOHQ'HZDUPHGHNHQYDQHHQYDVWGLHQVWYHUEDQGKHHIWRRNYRRUGHOHQ
'HVFKRHQZULQJW
%HUJOHU&RZHHWZDDUGHVFKRHQZULQJW$OVIUHHODQFHUYHUGLHQMHLQGHUHJHOPppU'HORNURHS
LVQDXZHOLMNVWHZHHUVWDDQ'DDURPNULMJMHYDQRQVHHQGHUGHRSWLHZDDULQGHYULMKHLGYDQ
IUHHODQFHQVDPHQYDOWPHWGH]HNHUKHLGYDQHHQYDVWGLHQVWYHUEDQG'HVOHXWHOYDQGHIRUPXOH
LVGDWMH²QDDVWKHWEDVLVVDODULVYRRUHHQJURRWGHHO]HOIGHKRRJWHYDQMHLQNRPHQEHSDDOW
%HWHUYRRUMRXEHWHUYRRU%HUJOHU&R
-LM FRQFHQWUHHUW DOOH DDQGDFKW RS KHW SURMHFW %HUJOHU &R QHHPW RQGHUWXVVHQ GH YHUDQW
ZRRUGLQJYRRUDFTXLVLWLHHQDOOHSULPDLUHHQVHFXQGDLUHDUEHLGVYRRUZDDUGHQ'DDUPHHEHQMH
%HUJOHU1HGHUODQG%9
RQPLGGHOOLMNHQGHÀQLWLHIYHUORVWYDQMHHLJHQDGPLQLVWUDWLHYRHUHQHQRQGXLGHOLMNKHGHQURQG
%LMVWHU$
YHU]HNHULQJHQDXWRHQSHQVLRHQRSERXZ'DDUNRPWQRJELMGDWMHPHWHHQYDNJHULFKWHWUDLQLQJHQ
+;%UHGD
HQRSOHLGLQJHQRSPDDWNXQWYROJHQ'DWLVEHWHUYRRUMRXHQEHWHUYRRU%HUJOHU
7
)
S]#EHUJOHUFRQO
(HQEHHWMH,7HUZHUNWELM%HUJOHU
%HUJOHU &R PDDNW GHHO XLW YDQ %HUJOHU ,&7 'H]H RQGHUQHPLQJ LV DO GHUWLJ MDDU DFWLHI LQ
VRIWZDUHRQWZLNNHOLQJ:LM]LMQRS]RHNQDDUHUYDUHQVSHFLDOLVWHQRSKHWJHELHGYDQ0LFURVRIW
9HVWLJLQJHQ
1(7-DYD-((HQWHVWHQGLHRSNRUWHWHUPLMQLQ]HWEDDU]LMQ:LOMLMHHQEHHWMHHLJHQEDDVHQ
%UHGD$PVWHUGDP
HHQEHHWMH%HUJOHUNLMNGDQRSRQ]HZHEVLWHEHUHNHQMHWRHNRPVWLJHVDODULVHQQHHPFRQWDFW
5RWWHUGDP$SHOGRRUQ
RSPHWHHQYDQRQ]HYHVWLJLQJHQ0DLOHQNDQRRNS]#EHUJOHUFRQO
.NET
Eric Roosendaal
Drag and Drop deel 2:
Bestanden slepen naar
de Windows Explorer
Laten we om te beginnen aannemen dat u een ListBox hebt, gevuld
met filenamen, zoals hieronder.
}
}
Nu moet het Draggedeelte nog daadwerkelijk worden ingevuld. Het
eerste gedeelte is eenvoudig: de ListBox heeft een property Selected
Items die alle geselecteerde items bevat. Doorloop deze collectie en
verzamel alle geselecteerde items in een generic List van strings.
List<string> list = new List<string>();
foreach (var x in listBox1.SelectedItems)
{
list.Add(x.ToString());
}
Maar dan moet de data nog meegegeven worden bij DoDragDrop, en
daarvoor is een speciaal object nodig. Zo’n object heet een Data
Object. Dit moet nieuw worden gemaakt en bovendien moet er bij
worden aangegeven, dat het een object moet worden voor het
verslepen van bestanden. Daarvoor is een speciaal formaat nodig en
dat heet DataFormats.FileDrop. Tenslotte wordt het object gevuld met
de inhoud van de List die dan eerst moet worden omgezet in een
string-array. De code ziet er dan zo uit:
DataObject data =
Hoe kunt u nu een aantal van deze bestanden verslepen naar de
Windows Explorer? Omdat het handiger is om meer bestanden tegelijk te kunnen slepen stellen we de SelectionMode van de ListBox in op
MultiExtended.
Het implementeren van bestanden
slepen is redelijk straightforward
De code voor het starten van een Dragactie via het MouseMove Event
is al in deel 1 aan de orde geweest. De code luidde als volgt (voor het
waarom precies verwijzen we gaarne naar deel 1):
if ( isdragstart )
{
if( Math.Abs(e.Location.X - dragstartposition.X) >
SystemInformation.DragSize.Width / 2
|| Math.Abs(e.Location.Y - dragstartposition.Y) >
SystemInformation.DragSize.Height / 2)
{
isdragstart = false;
// perform the drag
new DataObject(DataFormats.FileDrop, list.ToArray());
listBox1.DoDragDrop(data, DragDropEffects.Copy);
U zult nu merken dat u bestanden van de ListBox naar een folder kunt
slepen. •
Eric Roosendaal
Eric Roosendaal is trainer bij
Compu'Train. Hij is afgestudeerd in
Scheikunde, maar eind jaren '80
geswitcht naar IT, met name naar
Development. Sinds medio jaren '90
in dienst van Compu'Train als specialist voor alle programmeertalen,
de laatste jaren met name .NET (VB
en C#). Hij is Microsoft Certified
Trainer, gecertificeerd sinds 1995. Eric is te bereiken via
eroosendaal@computrain.nl.
magazine voor software development 19
ARCHITECTURE
Sander Hoogendoorn
A recipe for enterprise agile.
Mixing Scrum and Smart
To cut to the chase, those of you who have worked on enterprise or service oriented projects before
already know this. These types of projects are characterized by a large number of organizational,
functional and technically complicating factors. Enterprise software development projects are
surrounded by a large number of complicating characteristics and challenges:
• Many different stakeholders
Projects have many different parties in the organization that are
involved. Often such projects realize goals for different departments
or divisions in the organization. As an example I once coached a
project that served 22 different departments. Quite often these
departments or division try to achieve overlapping or even
contradicting goals.
• Business processes
In general enterprise projects (re-)implement (parts of) business
processes that are key to the organizations success, rather than
building a straightforward web application.
• Complex software architectures
Most likely, enterprise projects implement business processes in a
complex IT landscape or architectures. Think of landscapes that
host many different applications all tied together.
• Many external dependencies
Often, such complex IT landscapes contain components that are
20
MAGAZINE
outside of the organization. Services that run outside the corporate
firewall, with other parties. A well-known issue to agile projects is
that of availability. We need the new version of the service in this
iteration, but the other party runs a waterfall project that will not
deliver this year.
• Changing requirements
In enterprise projects, requirements change continuously. Either by
changing insights during the project, but more often due to
changing legislation or regulations.
• Many different types of deliverables
Traditionally these projects count many different types of
deliverables. Think of service description, user interface, process
models, non-functional requirements, workflow, project plans, test
plans and many, many others.
• Multiple roles
Large organizations have many different roles that are involved in
projects. There are business analysts, enterprise architects,
information analysts, testers, release managers, SAP developers,
web developers, SAP functional consultants,
Thus these projects often become a mission impossible, and fail in
large numbers. Such projects are difficult to estimate, therefore hard
to plan. For developers it’s tough to build the software, often with many
new techniques and technologies, and even worse for testers, these
projects are sheer impossible to test well. This is where a structured
agile approach should come to the rescue.
Being agile in enterprise projects
Independent of the approach that is applied, or the agile process that
is followed, being successful in agile projects follows a number of key
principles:
• Multi-disciplinary teams
Instead of different roles such as analysts, designers, developer and
testers working in consecutive stages in a project, all roles collaborate in implementation individual work items from heads to tails.
• Short iterations
Project work in short time boxes, in most cases 2, 3 or 4 weeks.
During such an iteration, a number of work items is planned,
completed and evaluated – with different terminology in use with
different agile processes.
• A small standardized unit of work
Projects require a small unit of work, to be able to deliver a number
of them in a single iteration. Large work items such as traditional
use cases therefore do not apply well.
• Testing from day one
Testing is an important discipline during agile projects. Testers are
involved from the very first iteration, when the first work items are
realized. Note that testing in most projects goes way beyond the
obvious unit testing – which is actually a developer technique.
ARCHITECTURE
• Continuous measurement
Successful agile projects continuously measure their progress.
Since they are always delivering individual work items, measurement in agile projects is easy.
• Continuous (process) improvement
At the end of each iteration not only the realized work items are
evaluated, but also the project approach itself is evaluated, leading
to highly effective project approaches.
Scrum in a nutshell
When organizations first start with agile projects Scrum is often the
process of choice. At this point in time, Scrum is by far the most
popular and best known agile approach. Scrum is a straightforward
lightweight agile process that offers a collection of highly applicable
principles and techniques for short iterative projects and is easy to
understand. It also specifies a remarkable terminology with scrums,
sprints and user stories.
In a nutshell, Scrum is characterized as follows:
• Sprints
Projects are divided into iterations, called sprints. In general these
are 2 to 4 weeks.
• Backlogs
Work items still to be done during a project reside in a so called
project backlog. At the start of each sprint items from the backlog
are placed in the sprint backlog. These are the worked items to be
realized.
• Sprint cycle
All iterations follow the same simple process, with an iteration kickoff, actual work and a retrospective workshop for evaluation.
• User stories
The main unit of work is usually the user story, although this is not
mandatory. This rather informal requirements technique is shared
with the agile process extreme programming.
• Planning
In general the project and sprint planning is visualized in task
boards, which usually are put up on a wall using post-its. Progress
is monitored by using burn down charts, a straightforward diagram
that on a daily basis displays the number of points still to realize.
A trend line in the burn down chart extrapolated from the points
identifies the likely project end date. Again this technique is shared
with a number of other agile processes, including Smart and
extreme programming.
• Delivery
Every iteration or sprint results in fully delivered products, software
or otherwise.
Scrum has proven to be a successful approach in many (smaller scale)
web projects. In larger, more complex, service or cloud oriented and
enterprise projects, I think Scrum needs to be augmented to fit the
project and its environment. Let me explain.
Beyond lightweight agile
When applying Scrum or other lightweight agile processes such as
Crystal Clear or the set of lean principles (applied to software
development that is) to more complex projects of all sorts, you might
recognize a number of shortcomings:
• Business goals
It is often unclear how the work items in such projects (in most
cases user stories) link back to business goals, stakeholders and
business processes to implement.
• Analysis and design.
Although many people in the so-called agile community will now
think I’m promoting a waterfall approach, in most agile approaches
there are hardly any analysis or design activities or deliverables
defined. For instance, it is undefined how the backlog in a Scrum
project is assembled. Let me assure you, in more complex projects
some analysis and design is required, albeit not in big-upfrontdesign mode.
• Architecture
The same argument goes for software architecture. Most agile
approaches lack decent software architectural activities and
deliverables. Architecture is often assumed as-is. If you’re
implementing business processes that run through a systems
landscape of over 40 collaborating systems, you will definitively
need to design your architectures, but again this need not be in
big-upfront-architecture mode.
• Roles
Scrum and extreme programming describe a very limited set of roles
that, although looking slick, in most projects does not adhere to the
standing organization. There’s often enterprise architects,
information analysts, business analysts, middleware developers,
application management, testers, release manager. How will a
project work with all those roles? There’s a bit more to it than just
saying they are allowed to participate in the daily scrum.
• Testing
Apart from the obvious (developer) techniques such as unit testing,
the role of testing more specifically – which is essential in larger agile
projects – is not very well described in lightweight agile approaches.
• User stories
Although very flexible, user stories are a highly unstructured unit of
work, despite efforts in epics or story maps. Applying such an
unstructured unit of work may result in low re-use, non-repeatable
estimation, difficult to standardize development, testing and
measurement beyond the individual projects. In a multi-project
environment user stories will block progress and reuse (of for
instance metrics and code).
• Delivery cycle
Scrum does not specify the organization of delivery of the products
to different environments such as test, acceptance and (pre)production (so called OTAP).
When executing large, more complex, service oriented or enterprise
projects, I therefore strongly recommend to overcome these
limitations by augmenting Scrum and the likes with additional
techniques.
Smart accelerators
In my personal experience in enterprise projects I have had very good
experiences with mixing the agile process Scrum with the best
magazine voor software development 21
ARCHITECTURE
practices from another agile process called Smart to overcome the
drawbacks of the aforementioned approach.
Smart originated from the Netherlands in 1998 and was originally
designed to implement best practices for DSDM, an iterative
approach that was popular in those days. Later Smart grew out to a
stand-alone agile approach that particularly combines well with other
more basis agile approaches such as Scrum and extreme programming, but also aligns well with PRINCE2.
More specifically Smart puts accents on aspects in project that are
only marginally highlighted in other agile approaches. As an example
Smart adds the following accelerators to projects:
• Preliminary iterations
Preliminary iteration types Propose and Scope is where work items
are added to the backlog such as a modeling business processes,
modeling smart use cases, creating an estimate, creating a costbenefit analysis, writing a project plan (not that obvious it seems),
first-cut software architecture set-up, development environment
set-up, project kick-off, team education and first-cut user interface
guidelines.
• Smart use cases
Next to the more “non-functional” work items mentioned above,
Smart introduces the well-known smart use cases requirements
technique. Smart use cases not only model the needs of the user,
but also identify workflow and reusable back-end services. This
technique allows for identifying re-use, repeatable and reliable
estimation, and very good traceability between requirements,
architecture and code, great functional testing capabilities. An
absolute must in enterprise projects.
• Estimates
Estimation of size and complexity of a project is estimated and
measured in smart use case points, defined on a scale from 1 to 10.
Smart use case points of course come from estimating the size or
complexity of smart use cases, and is a highly pragmatic and
repeatable technique..
• Work item life cycle
Where Scrum’s work item life cycle contains to-do, working and
done, in Smart, work items are delivered through a slightly more
structured life cycle, that allows for all roles in enterprise projects to
be maximally involved in a collaborative manner. Due to the life
cycle, work items need not be broken down in tasks, a cumbersome and highly unstructured element of Scrum. In Smart work
items simply move through the stages of the life cycle (in most cases
in one or two days), the progress of which can be shown easily on
a dashboard.
• Designing
During the daily stand-up meeting, it is decided whether or not a
design session is required. This time-boxed design session
addresses the design or a single smart use case. Most project will
22
MAGAZINE
organize this design session directly after the daily stand-up. On a
typical time scale, if the stand-up runs from 10:00 to 10:15, the
design session runs from 10:15-11:00. During such sessions all
roles that need to deliver input to this particular use case participate. Of course also the developer and tester are present, so all
roles create a homogeneous view of the smart use case at hand.
• Smart testing
Working with user stories will normally not result in a very efficient
test approach, as user stories do not add structure to the project.
Smart describes a standardized approach on functional testing in
agile projects of course based on smart use cases.
• Stabilizing iteration
Usually the last iteration of a Smart project or the last one to an
upcoming release is used to round off remaining work items, build
issues, bugs, and remaining features. This iteration is merely used
to stabilize the solution. In Smart this iteration type if referred to as
Finalize.
Blending Scrum and Smart
Besides defining an obvious project life cycle, these best practices
from Smart blend in really well with the more lightweight approach of
Scrum and extreme programming. This leads to the following best
practices:
• Initial backlog
The initial backlog of the project is filled with the work items Smart
recommends, rather than assuming a user story filled backlog.
When prioritizing work items for the first sprint in a mixed Scrum
and Smart project, it is very likely that these are picked. As a result,
after one or two iterations, a project plan for the remainder of the
project is produced, containing at least an estimate, based on the
smart use cases that are also defined during these iterations (of
course without any analysis or design, just the diagrams, the ovals
and the actors).
• Iteration kick-off
After the initial work-items are cleared from the backlog, the smart
use cases become the primary work item type in the project. During
sprint kick-off a number of smart use cases is picked to implement
in the next sprint.
• Dashboard
The traditional Scrum task board is replaced by Smart’s agile dashboard, containing columns for the stages in the work item life cycle
– In Iteration, Designing, Working, Testing, Rework, Accepted. If
appropriate additional columns can be added, e.g. when testing is
split up in Developer Testing and Customer Testing.
• Points
The progress in the project is not measured in story points, but
rather in smart use case points.
ARCHITECTURE
very well aligned with the organizations release calendar.
This approach of mixing best practices, techniques and tools from
Scrum, Smart over the past 12 years has proven to be very successful in a variety of projects and project types, including larger Java and
.NET projects. service oriented projects, business intelligence projects,
and even packaged implementations.
Moreover, when augmented with more technical best practices from
extreme programming, such as refactoring, continuous integration,
pair programming, and test driven development (smart use cases are
a very good unit for unit testing code) projects are aligned to deliver ontime, on-budget, and with just-enough documentation and fitting
(reusable) features.
As former US president Bush used to say: failure is not an option. •
• Scrum meeting
The focus of the daily scrum meeting shifts a bit as it is also used
to answer the question: what still needs to be done on the smart
use case(s) we’re currently working on to get them accepted?
• Design
Host the design sessions as Smart recommends, preferably right
after the daily scrum meeting.
• Testing
As the work item life cycle clearly stipulates, functional testing, often
done manual is all in a days work. The role of the testers here becomes imminent in the project.
• Finalize
Projects have to decide when to apply a Finalize iteration to stabilize the solution and round up loose ends. Depending on the type
of project, these iteration can be the very last sprint, but also can be
Sander Hoogendoorn
Principal Technology Officer and
Agile thought leader Capgemini
www.smartusecase.com
www.sanderhoogendoorn.com
The Triple A Company = SharePoint. Ruim 11 jaar verzorgen wij de implementatie van Microsoft SharePoint voor organisaties
uit diverse markten. Daar zijn we trots op en we willen graag dat je in die trots gaat meedelen. Ter uitbreiding van het team
zijn wij per direct op zoek naar een:
SharePoint Managing Consultant M/V
Als Managing Consultant kun je jouw team van SharePoint Consultants stimuleren en richting geven. Je zorgt er voor dat
planningen gemaakt en gehaald worden. Je begeleidt projecten en springt in als het moeilijk wordt.
Functie-eisen:
ƒ Universitair/HBO werk- en denkniveau.
ƒ Minimaal vier jaar ervaring met SharePoint implementaties en managementprojecten.
ƒ Hoge mate van zelfstandigheid.
ƒ Projectmanagement en coaching is een tweede natuur.
Over The Triple A Company:
The Triple A Company is informeel, kenmerkt zich door ͞ĂůůĞƐŵĂŐƚĞŶnjŝũŚĞƚǀĞƌďŽĚĞŶŝƐ͕͟ĞŶŬĞŶƚĞĞŶƉůĂƚƚĞhiërarchie. We zijn
een flexibel, innovatief en een vooruitstrevend bedrijf met een sterk concurrerend en onderscheidend vermogen in de markt,
experts.
Interesse?
Herken je jezelf in het profiel en wil je deze uitdaging aangaan? We ontvangen je Curriculum Vitae samen met je motivatie graag
voor 31 maart 2011 op werken@triplea.net of per post t.a.v. Dhr. A.M.C. Deibel, 5301 LJ, Zaltbommel.
Voor meer informatie verwijzen wij u naar onze website www.triplea.net. Voor aanvullende informatie kunt u contact opnemen
met Dhr. A.M.C. Deibel op: 0418 -510 570.
CORE
SYSTEMS
Paul Klicnik
Introduction to the code coverage tooling in
Rational Application Developer
Code coverage is an important aspect of software testing, and can be considered fundamental to the overall system testing of a component. The motivation behind coverage tooling is
simply to give you (as a developer or tester) more insight into the areas of code that are being
exercised by a set of test cases. This information is useful because you can then use it to
devise new test cases to achieve adequate coverage.
The IBM® Rational® Code Coverage feature is a tool that integrates
with IBM® Rational® Application Developer. You can use it to
generate and analyze coverage statistics for your Java applications.
The tooling generates statement coverage statistics for the application
under test (that is, the number or percentage of lines in your
application that have been executed).
Instrumentation
In order to properly analyze the coverage statistics in the Rational
Code Coverage feature, it is important to understand the technology
used behind the scenes.
Rational Code Coverage uses an instrumentation engine to
manipulate the bytecode of a class and inject custom calls to the
coverage data collection engine. Figure 1 provides a high-level
overview of the process:
By definition, a basic block is a set of instructions that cannot be
branched into or out of. The key idea here is that when the first
instruction runs, all of the subsequent instructions in that block are
guaranteed to be executed without interruption. It follows that a basic
block can be conceptually considered a single group or block of
instructions. In general, basic blocks end on branch, call, throw or
return statements.
An executable unit begins at the start of every basic block and at any
instruction that corresponds to a line of source code that is different
than the previous instruction. What differentiates an executable unit
from a basic block is the condition that triggers the end of the
executable unit. For example, the divide instruction is not considered
to be the end of an executable unit despite the fact that it can throw
an exception.
The instrumentation engine in Rational Code Coverage is used to
inject custom code at the start of every executable unit. Consequently,
you can customize the Rational Code Coverage feature to report
statistics down to the executable unit level of granularity (in other
words, block coverage). Figure 2 provides an overview of how the
instrumentation engine modifies the bytecode to support code
coverage.
Fig. 1: Overview of the Rational Code Coverage execution
environment
Fig. 2: Overview of the bytecode instrumentation
Basic blocks versus executable units
The instrumentation engine operates on units of bytecode called
executable units. The definition of executable unit is slightly different
than the traditional definition of basic block, but the differences are
important to take into account when the results are analyzed.
24
MAGAZINE
Generating coverage statistics in RAD
One of the major advantages of the Rational Code Coverage feature
is that you can enable it on any Java project in RAD by navigating to the
Code Coverage panel in the project Properties, as shown in Figure 3.
CORE
SYSTEMS
Fig. 4: UML diagram for the sample application
Fig. 3: Code Coverage panel in the project Properties
While in the Java perspective in RAD, you can start the TestCar.java
test by right-clicking TestCar.java and selecting Run As > JUnit test.
The results of the JUnit test will appear in the JUnit view as normal. The
coverage results are integrated into the RAD UI, and you can analyze
them by switching back to the Package Explorer. Figure 5 displays a
sample result set for the TestCar.java test.
Select the Enable code coverage check box in Figure 3 to enable
code coverage for the project, and to instrument the classes in your
project under the covers. You can also use this panel to customize
acceptable coverage levels for each step of granularity. The supported levels of granularity are described following:
• Type coverage: the percentage of types covered in a class
• Method coverage: the percentage of methods covered in a class
• Line coverage: the percentage of lines covered in the class file
• Block coverage: the percentage of blocks covered in a class file.
Note that a block refers to an executable unit (as described
previously)
You can also specify custom filters, and they are used to control what
gets instrumented in your project. By default, all of the classes in your
project are instrumented, but you can create custom filters to exclude
target packages or specific types, if there is a need to restrict the
results.
Package Explorer
After you enable code coverage on a project, coverage statistics will
be generated the next time that the application is launched. Note that
statistics will not be generated for all types of launch configurations
automatically. Table 1 displays the launch types that are supported
from within RAD.
Launch Type
Java Applet
OSGi Framework
JUnit
JUnit Plug-in Test
Java Application
Eclipse Application
Standard Widget Toolkit (SWT) Application
Table 1. Supported launch configurations
A sample application has been provided (see link at the bottom of this
article) and will be used throughout this article. The application is a
simple representation of different vehicles (car, van, motorcycle, and so
on) and the various parts associated with each vehicle. The UML diagram outlining the structure of this application is displayed in Figure 4.
There are two JUnit tests already defined in the project: TestCar.java
and TestCarImproved.java. As the names suggest, these tests target
the Car.java class.
Fig. 5: Coverage results for TestCar.java displayed in the Package
Explorer
By default, the UI is annotated with only the line coverage information;
however, you can change this in the workbench Preferences, and
optionally choose to include coverage for packages, types, and
blocks. The percentage beside each Java item is a breakdown of the
line coverage for the last execution. You can drill down into the
various Java artifacts (for example, classes, types, and methods) in
the Package Explorer to get coverage statistics at a lower level of
granularity.
The results are color-coded depending on the success rate: by
default, red indicates that the acceptable coverage level has not been
met while green indicates that the appropriate coverage level was
achieved. Naturally, the goal of the test is to reach an acceptable
coverage level on the classes of interest.
magazine voor software development 25
CORE
SYSTEMS
Based on the results shown in Figure 5, the first test was inadequate:
the Car class (and abstract parents AbstractFourWheelVehicle and
Vehicle) did not reach appropriate coverage level. Luckily, you have a
second attempt to execute: TestCarImproved.java. Again, you can
execute the test as a normal JUnit and the results are automatically updated in the Package Explorer (Figure 6).
was not covered. There is a slight advantage in viewing the results in
the Java Editor because it also indicates the partially covered lines.
Partially covered lines can occur when there is more than one
executable unit on a line of source code, but only one of them has
been executed. As an example, look at the first line of code in the
setTargetSpeed(int speed) method shown in Figure 7: the first
executable unit is the if statement, and the second executable unit is
the return statement. By default, a partial line is colored in yellow.
Generating reports
You can compile the code coverage results into reports and view them
in RAD, or save them to the file system for future analysis. You can
generate two different types of reports: Workbench reports (Eclipsebased) and HTML reports. To generate a report, select Run > Code
Coverage > Generate Report. Figure 8 shows the report generation
dialog.
Fig. 6: Code coverage results for TestCarImproved.java displayed in
the Package Explorer
Java editor
Line coverage results are also displayed and marked in the Java
editor, and you can use it to give a more precise indication of which
lines are covered in each class. After coverage statistics have been
generated, you can open any class in your project with the Java
editor, and the left ruler bar in the editor shows the coverage
information. Figure 7 displays the results for Vehicle.java:
Fig. 8: Report generation dialog
You can create and view a report in RAD using the Quick View option
on the dialog, or save it to the file system using the Save Report
option.
Fig. 7: Coverage results displayed in the Java editor
The color indicators are the same as they are in the Package
Explorer. That is, by default a green line was covered and a red line
26
MAGAZINE
Workbench reports
The workbench reports (also known as Eclipse-based reports)
provide a consolidated view of all of the coverage statistics for your
project, and contain coverage information for all of the classes in your
project at execution time. Figure 9 shows a populated Eclipse-based
report. Workbench reports have the added advantage of being
integrated in RAD, so you can use them as a quick tool to provide
insight into the parts of your code that require improved test coverage.
As Figure 9 shows, the statistics in a workbench report contain
coverage information for all levels of granularity: from a package to a
method. Right-clicking any of the Java artifacts displays a pop-up
menu with two additional actions: Show in Package Explorer and
Open in Java Editor. These are useful tools for identifying and investigating areas of code with low coverage, because they highlight the
elected area of code by opening it in the appropriate viewer or editor.
CORE
SYSTEMS
A quick overview of the expected
parameters is outlined in Table 2. Both
approaches to instrumentation will output a baseline file. A baseline file is a notion specific to the Rational Code
Coverage feature. The baseline file contains an index of all of the classes in your
project, and maintains additional metadata about each class.
Fig. 9: Coverage results in an Eclipse-based report
HTML reports
HTML reports display the same type of information provided in the
Eclipse-based report, but in HTML format. These reports are particularly useful when saved to the file system, because they provide a way
for the coverage results to be analyzed independently of RAD, shared
with team mates, or published to a Web site for viewing.
Generating statistics outside of the workbench
One of the major features of the Rational Code Coverage tool is its
ability to generate statistics outside of RAD. This provides extra
flexibility and enables you to customize your environment to take
advantage of the Rational Code Coverage feature in your systems.
For example, one natural combination would be to set up a nightly
build environment and generate statistics with JUnit tests on the nightly
driver. You can integrate the Rational Code Coverage feature into your
environment by performing the following three steps: instrumentation,
execution, and report generation.
Step 1. Instrumentation
There are two different approaches that you can use to instrument
your application. The first is to use the instrument.bat/sh script
provided in the <RAD_HOME>/plugins/com.ibm.rational.llc. engine_
<date>/scripts directory. This article does not focus on this script, but
you can reference the RAD documentation for more information if
necessary. The second approach is to use the instrumentation Ant
task provided by the Rational Code Coverage feature. Listing 1 shows
an example usage of the instrument task configured to target the
sample application in this article.
<target name="instrument">
<taskdef name="instrument"
This file is used at the reporting step
(Step 3) to determine which classes in
your application were not covered. This
step is necessary because the Rational
Code Coverage data collection engine is
only notified of a class when it is loaded
by Java™ Virtual Machine (JVM), and so
a list of the classes that were not executed cannot be determined without additional metadata. If the baseline file is not
present at reporting time, the classes that were not loaded will be absent from the report.
Parameter
Description
The path to the project on the file system
outputDir
(Optional) The output directory of the instrumented project.
If not specified, the classes in the buildPath will be
instrumented in place.
baseLineFile (Optional) The output location of the baseline project
index file. See the following paragraph for more
information on this file.
saveBackups
(Optional) Set to true if the original class files should
be backed up before instrumenting.
buildPath
Table 2: Input parameters for instrumentation tasks
Step 2. Execution
In order to execute the instrumented classes, the Java environment
must be configured correctly at launch. The two specific parameters
needed for execution are explained below:
• -Dcoverage.out.file=<absolute path to output file>: the file
specified by this JVM argument is the output location of the coverage
statistics
• Add the <Rational Application Developer HOME>/plugins/
com.ibm.rational.llc.engine_<date>/RLC.jar to the classpath:
because the code has been instrumented with callbacks to the the
Rational Code Coverage data collection engine, the RLC.jar file needs
to be on the classpath at runtime.
These parameters can be supplied to a JUnit Ant task. Listing 2
provides example usage.
classname="com.ibm.rational.llc.engine.instrumentation.
anttask.InstrumentationTask"
classpath="{path to com.ibm.rational.llc.engine plugin}"/>
<instrument saveBackups="true"
baseLineFile="project.baseline"
buildPath="VehicleProject"
outputDir="VehicleProjectInstr"/>
</target>
<target name="run">
<junit showoutput="true" fork="yes">
<jvmarg value="-Dcoverage.out.file={absolute path to the
output file}"/>
<classpath>
<pathelement location="{absolute path to the
<Rational Application Developer
HOME>/plugins/com.ibm.rational.llc.engine_<date>
Listing 1: Example usage of instrument Ant tasks on the sample
application in this article
/RLC.jar file}"/>
<pathelement location="{path to the project classes}"/>
<pathelement path="{absolute path to the junit.jar}" />
</classpath>
magazine voor software development 27
CORE
SYSTEMS
<test name="com.ibm.vehicles.tests.TestCar"
outfile="TestCar" />
</junit>
</target>
Listing 2: Example of how to specify the the Rational Code
Coverage feature arguments in an Ant launch
Step 3. Report generation
You can generate reports using another Ant task provided by the
Rational Code Coverage feature. This task uses the reporting
functionality provided by the BIRT Eclipse.org project, and thus requires that you download the BIRT V2.3.2 Reporting Engine standalone
offering. This can be done by navigating to http://www.eclipse.org/birt/
download, select the V2.3.2 release and downloading the Report
Engine offering. Note that this Ant task can only produce HTML
reports.
Listing 3 provides sample usage of the reporting Ant task. Note that,
as input, it requires the coveragedata file generated in Step 2 and
(optionally) the baseline file generated in Step 1.
Fig. 10: Coverage results in an HTML report •
<target name="generate-report">
Paul Klicnik
<path id="lib.path">
<pathelement location="{absolute path to the
<Rational Application Developer HOME>/plugins/
com.ibm.rational.llc.common_<date>.jar plugin}"/>
<pathelement location="{absolute path to the
<Rational Application Developer HOME>/plugins/
com.ibm.rational.llc.report_<date> plugin}"/>
<pathelement location="{absolute path to the
<Rational Application Developer HOME>/plugins/
org.eclipse.equinox.common_<date>.jar plugin}"/>
<fileset dir="{absolute path to the BIRT ReportEngine
directory}\lib" includes="*.jar"/>
</path>
Paul Klicnik is a Software Developer
at IBM Toronto lab in Markham
Ontario. He has worked on Code
Coverage since 2008, and worked
in the general area of performance
and testing tools since 2006. Paul
has worked on several key IBM
products, including IBM Rational
Performance Tester and IBM
Rational Application Developer, as well as the Eclipse Test and
Performance Tools Project (TPTP) project.
<taskdef name="code-coverage-report"
classname="com.ibm.rational.llc.report.birt.adapters.ant.
ReportGenerationTask"
classpathref="lib.path"/>
<code-coverage-report
outputDir="{absolute path to the report output directory}"
TIP:
coverageDataFile="{absolute path to the coveragedata file
generated in step 1}"
baseLineFiles="{absolute path to the baseline file
generated in step 1}"/>
</target>
Listing 3: Example usage of the report generation Ant task on the
sample application in this article
An example HTML report is displayed in Figure 10. Generating HTML
reports using the Ant task provides a means by which users can view
the statistics generated in an Ant environment independently of RAD.
Try it out!
The downloads section of this article at http://www.ibm.com/developerworks/rational/library/10/introtocodecoveragetoolinrationalapplicationdeveloper/ provides sample scripts and build files for an Ant
environment that can be used to instrument, execute, and generate
reports on the sample application. If you're interested in testing this
environment out, refer to the README file in the Standalone.zip file.
28
MAGAZINE
Windows Azure gebruik
Azure kost geld voor het verbruik van Rekenkracht (CPU), Storage en Netwerk verkeer. Bij een MSDN account kun je Azure subscription instellen. Deze subscription heeft een aantal services
zonder kosten, zoals 750 Small compute uren per maand, 10 Gb
Storage, 3 SQL Azure web databases en nog een paar. Ruime
voldoende voor wat development en probeersels. Als je over je
budget heen gaat, dan moet je als nog betalen. Tegenwoordig
krijg je een mail Microsoft Online Services als boven een bepaald
percentage van je basis eenheden zit. Erg handig, zo hou je de
extra kosten een beetje in de hand.
Microsoft heeft daar iets aan veranderd. Vorige week kreeg ik een
mail van de Microsoft Online Services met de mededeling ik dat
ik 75% van mijn basis eenheden zat.
ZZZLFXFRP
)5((
&ORVLQJ.H\QRWH$GGUHVVDQG4$
%UHDNRXW6HVVLRQVDQG4$
%UHDNRXW6HVVLRQVDQG4$
2SHQLQJ.H\QRWH$GGUHVVDQG4$
ARCHITECTURE
Christian Siegers en Mark IJsselstein
Duet Enterprise
Duet is het product dat door SAP en Microsoft samen is ontwikkeld om business oplossingen
te bieden die gebruik maken van software van beide leveranciers. Vaak hebben bedrijven SAP
producten voor backend processen en Microsoft producten voor werkplekken (Windows,
Office, eventueel SharePoint). Duet is een oplossing om de sterke punten van beide platforms
met elkaar te combineren.
In de huidige versies van Duet wordt een aantal standaard scenario’s geleverd, die met geringe
configuratiemogelijkheden enigszins aangepast kunnen worden aan de klant. Duet biedt geen
ondersteuning om nieuwe scenario’s te ontwikkelen, dus als de benodigde functionaliteit niet
aanwezig is zal een andere oplossing gekozen moeten worden.
SAP en Microsoft komen
nu met een nieuwe versie,
namelijk Duet Enterprise
Niet zozeer een nieuwe versie van Duet maar een
compleet nieuw ontwikkelplatform. Duet Enterprise
biedt out-of-the-box een
toolset waarmee je zelf
business scenario’s kunt
realiseren. Er is gekozen
om zoveel mogelijk gebruik
te
maken
van
de
bestaande producten van
beide leveranciers en dus
zo min mogelijk nieuwe
tools en componenten te
introduceren. Duet Enterprise draait als add-ons op SharePoint 2010 en SAP, waardoor
de technische omgeving vele malen simpeler is geworden.
Wat biedt Duet Enterprise aan functionaliteit
In bovenstaande komt nog geen Duet Enterprise functionaliteit voor,
deze integratie kan ook met SAP en SharePoint (dus zonder Duet
Enterprise) worden gerealiseerd. De toegevoegde waarde is redelijk
subtiel, maar zeker op de lange termijn (volgende versies) erg belangrijk. Duet Enterprise levert op hoofdlijnen de volgende functionaliteit:
• Gateway aan de SAP zijde (IWF)
• Workflow integratie
• Technische integratie
• Platform capabilities
Gateway aan de SAP zijde
Bedrijven hebben een divers SAP landschap, waarin meerdere SAP
producten zitten en waarin meerdere versies van SAP tegelijk in
gebruik zijn. Om te zorgen dat vanuit SharePoint geen rekening hoeft
te worden gehouden met welk product, versie of technologie gebruikt
wordt voor de verschillende SAP entiteiten, is gekozen om aan de SAP
zijde een gateway te implementeren. Deze wordt de Information
Worker Framework (IWF) genoemd. Hierin kun je entiteiten definiëren/samenstellen die je vanuit SAP beschikbaar wil maken voor
30
MAGAZINE
SharePoint.
Tevens geef je aan hoe deze entiteiten zich verhouden tot de
verschillende bestaande SAP entiteiten uit het SAP landschap. Dus
concreet welk SAP product, welke versie en welke technologie wordt
gebruikt om de data te lezen en schrijven. Vervolgens wordt die
entiteit op uniforme wijze aan SharePoint gepresenteerd middels
webservices. Alle webservices die SharePoint nodig heeft om de
entiteit te onderhouden worden beschikbaar gemaakt. Denk hierbij
aan ‘selecteer één object’, ‘selecteer alle objecten’, ‘voeg object toe’,
etc. Als een nieuwe versie van een SAP product in gebruik wordt
genomen, dan hoeft alleen de definitie van de entiteiten in de IWF te
worden aangepast en blijft de interface naar SharePoint gelijk.
Workflow integratie
Een andere feature die Duet Enterprise levert is workflow integratie.
In SAP is het mogelijk meerdere soorten workflows te definiëren.
De focus van Duet Enterprise ligt op goedkeuringsprocessen.
Een voorbeeld is als iemand vakantie aanvraagt, dan moet de
verantwoordelijke manager dit goedkeuren. Duet Enterprise levert de
mogelijkheid om de goedkeuringsstappen te integreren met SharePoint en Outlook. Als een stap in SAP actief wordt, dan wordt voor
deze stap een gelijkwaardige workflowstap in SharePoint gegenereerd.
Per stap heeft de beslisser dan de keuze of hij de goedkeuring doet
in SAP, SharePoint, Outlook of op z’n smartphone. Nadat een beslissing is genomen, worden de workflow in SAP en SharePoint automatisch met elkaar gesynchroniseerd.
Voordeel is dat je hiermee alle collaboration features van SharePoint
kan gebruiken. Je kan dan andere mensen om advies vragen, je goedkeuring aan een ander delegeren, je kan discussies voeren en documenten delen.
Technische integratie
De technische integratie wordt gerealiseerd door in SAP webservices
beschikbaar voor SharePoint te maken. SharePoint gebruikt BCS
(Business Connectivity Services) en BDC (Business Data Catalog) om
de SAP webservices te consumeren. Hiermee kunnen SAP entiteiten
in een ‘external list’ worden geladen. Een external list is een lijst in
SharePoint met data die niet in SharePoint zelf is opgeslagen. Deze
data kan vanuit de external list in een SharePoint site worden getoond
en gewijzigd.
ARCHITECTURE
Platform capabilities
Duet Enterprise zorgt voor onderliggende ontwikkelplatform functionaliteit, met name Single SignOn (SSO), traceability in de logging en
error handling.
Single SignOn
SSO tussen SAP en SharePoint was tot nu toe technisch ingewikkeld.
Duet Enterprise maakt gebruik van de SharePoint 2010 feature
Security Token Service (STS) STS maakt gebruik van claims based
authentication. STS maakt het mogelijk om op basis van een Windows
login toegang te krijgen tot andere systemen door credentials van
andere systemen te koppelen aan een Windows login. Met Duet
Enterprise wordt binnen STS de Windows login van de gebruiker
vertaald naar de SAP ID van die gebruiker. Gevolg is dat van alle
acties die een gebruiker doet, wordt gevalideerd door SAP of die
gebruiker daar de benodigde rechten toe heeft. Het enige wat nog
moet gebeuren is de mappingtabel tussen Windows en SAP identiteit
te vullen in SAP.
Traceability
Het is belangrijk om processen integraal te kunnen volgen voor
auditing doeleinden en wanneer een fout optreedt. Auditing wordt bijvoorbeeld gebruikt om te kunnen achterhalen welke gebruiker
bepaalde data heeft benaderd of aangepast of een beslissingstap
heeft uitgevoerd. Als processen van SAP naar SharePoint lopen en
weer terug, dan moeten de processtappen in SAP gerelateerd kunnen
worden aan die in SharePoint. Duet Enterprise zorgt ervoor dat in de
logging op basis van IDs terug is te vinden bij welk SAP proces een
SharePoint proces hoort (en andersom).
Error Handling
Duet Enterprise zorgt ervoor dat fouten die optreden in SAP netjes en
uniform worden teruggegeven aan SharePoint. Ontwikkelaars hoeven
dus niet allerlei verschillende soorten foutafhandelingen te implementeren.
Voordelen van het platform
Het SAP-SharePoint en Duet Enterprise platform biedt de volgende
voordelen.
• Collaboration mogelijkheden rondom ‘SAP beslissingen’.
Processen die voorheen binnen SAP plaatsvonden en waarover
werd gecommuniceerd via email, losse documenten en ander
communicatiemiddelen, worden nu ondersteund door een
geïntegreerde omgeving.
• Geïntegreerde zoekfunctionaliteit.
Op basis van SharePoint Federated Search kun je tegelijk in
SharePoint, SAP en eventuele andere systemen zoeken. Hierbij
wordt rekening gehouden met de SAP rechten die de zoekende
gebruiker heeft.
• Outlook offline functionaliteit.
In de 2010 versie van Outlook kun je data uit
SharePoint lijsten offline beschikbaar maken.
Hierbij wordt de gehele inhoud van de lijst lokaal in een database opgeslagen. Deze data
kan worden gelezen en gewijzigd. Als je weer
connectie hebt, worden de wijzigingen naar de
server gepubliceerd. Deze functionaliteit werkt
out-of-the-box en kan ook gebruikt worden
voor lijsten met externe data zoals data uit een
SAP systeem. De lokale data is ook door
andere Office onderdelen te gebruiken, dus bij
het maken van een offerte in Word kunnen de
klantgegevens automatisch worden ingevuld
door het selecteren van een klant uit het SAP
systeem, ook als je offline bent.
• No-code customization.
Er is veel effort gestopt om te zorgen dat de scenario’s kunnen
worden gemaakt zonder dat hiervoor gecodeerd hoeft te worden.
Bijna alles kan door configuratie worden gerealiseerd.
Conclusie
Duet Enterprise is een oplossing om Microsoft SharePoint en
daarmee Office te integreren met SAP systemen. Het bouwt voort op
de reeds aanwezige functionaliteit van deze producten. Hierdoor is
het voor zowel eindgebruikers, ontwikkelaars en beheerders vertrouwd
terrein. Duet Enterprise is niet nodig voor het realiseren van één enkele
technische interface tussen SharePoint en SAP. Als een bedrijf kiest
om bedrijfsprocessen met SAP te ondersteunen en het SharePoint/Office platform kiest voor de gebruikersinterface, dan moeten
de technische beginselen als SSO en auditing goed geregeld zijn.
In dat geval is Duet Enterprise de enige logische keuze voor de
toekomst. •
Christian Siegers
Christian Siegers is werkzaam bij
Capgemini als Managing Consultant. In projecten wordt Christian ingezet als Solution Architect.
Christian richt zich voornamelijk op
de Microsoft technologie en heeft
zijn roots in de integratie liggen. Het
integreren van Microsoft technologieën met de cloud als het integreren van een Microsoft platform met een SAP platform hoort tot
Christian’s specialiteiten.
Mark IJsselstijn
Mark is an architect with 11 years of
experience working mostly with
Microsoft-related technology.
magazine voor software development 31
DATABASES
Ben Suurmeijer
Historie en toekomst van
Database Change Management
Sinds tientallen jaren halen veel organisaties voordeel uit het gebruik van geaccepteerde en
bewezen Software Change Management (SCM) principes. Processen zoals “file locking”, “check
in / check out”, “compare and merge” en “rollbacks” stellen organisaties in staat om op een
productieve en gecontroleerde manier wijzigingen aan te brengen in hun applicaties.
Echter, binnen de database wereld werkt het hele principe van SCM niet bijzonder goed.
De belangrijkste reden is dat databases totaal anders zijn gestructureerd dan traditionele
programma code (zoals Java en .NET), en om die reden kunnen de traditionele SCM producten, zoals bijvoorbeeld IBM Rational of Subversion, niet gebuikt worden in de databasewereld.
Het gevolg is een enorme kloof tussen SCM en database ontwikkelactiviteiten.
De problematiek van database veranderingen
Een database is, in tegenstelling tot een softwareprogramma bijvoorbeeld, geen verzameling bestanden, en door het filesysteem wordt
een database meestal gezien als één groot bestand. Bij veranderingen
in het programma code, wordt er een kopie van het programmabestand gemaakt en vindt de ontwikkeling van code plaats op deze
lokale kopie.
Een database is echter geen verzameling bestanden, maar een
centraal middel waar iedereen toegang tot heeft en waar ontwikkelaars tegelijkertijd wijzigen in aan kunnen brengen. Er worden zelden
kopieën gemaakt voor elke individuele ontwikkelaar. In situaties waar
dit wel gebeurt, moet er nagedacht worden over hoe deze verschillende kopieën van de database voordurend gesynchroniseerd
kunnen worden om databaseconsistentie te garanderen. Een lastig
probleem. Verder moet er rekening gehouden worden met versiebeheer, en bestaat er geen zogenaamde “debug” omgeving.
Ook een gestructureerd proces van ontwikkeling, waarbij aanpassingen door van de ontwikkelafdeling door worden gegeven aan QA
(Quality Assurance), integratie en vervolgens productie, stuit bij database ontwikkeling op problemen. Bij de ontwikkeling van program-
32
MAGAZINE
macode omvat dit proces weinig meer dat het simpelweg kopiëren en
registreren van individuele bestanden. Echter, het verplaatsten van
database objecten is niet zo eenvoudig. Het is niet zonder meer
mogelijk een gewijzigde tabel vanuit ontwikkeling in productie want
dan gaat alle productiedata verloren.
In tegenstelling tot een software ontwikkelaar, die gebruik maakt van
een SCM oplossing, waarbij een gedetailleerde registratie van alle veranderingen wordt bijgehouden, moeten database ontwikkelaars vaak
handmatig een lijst bijhouden met alle database wijzigingen. Geloof
het of niet maar, maar ik heb wel eens een database ontwikkelaar gezien die alle modificaties bijhield op gele Post-It briefjes die verspreid
waren over zijn bureau en beeldscherm.
Met andere woorden, database ontwikkeling is een totaal andere tak
van sport dan traditionele programmacode ontwikkeling.
Als gevolge van de enorme verschillen tussen software ontwikkeling en
database ontwikkeling, is een geautomatiseerd proces voor Database
Change management (DCM) á la SCM nooit echt van de grond
gekomen, en wordt er noodgedwongen gebruik gemaakt van een
breed scala van handmatige processen en work-arounds.
DATABASES
Een work-around: DDL export
De meest bekende work-around is de database definition language
(DDL) te exporteren om een databasestructuur te definiëren, en deze
vervolgens als bestanden veilig te stellen binnen een traditionele SCM
oplossing (zie diagram). Echter, dit proces is verre van waterdicht.
Niemand kan namelijk verwachten dat ontwikkelaars daadwerkelijk
consequent dit proces volgen voor iedere veranderingen die ze
aanbrengen in een database. En wat gebeurt er als iemand alleen
maar de database aanpast, en niet de bijbehoorde SCM bestanden?
Hoe wordt er omgegaan met deze inhoudelijke veranderingen? Een
veranderde waarde van een parameter (in bijvoorbeeld een lookup of
metadata tabel), kan invloed hebben op het gedrag van een applicatie programma en moet goed beheerd worden. De vraag is alleen hoe?
In dat geval moet er handmatig code geschreven worden om de
wijzigingen in de databasestructuur mogelijk te maken zonder verlies
van data. Dit is niet alleen erg tijdrovend, maar ook er foutgevoelig.
Bovendien is deze handmatige code geen deel van een zogenaamd
application lifecycle management (ALM) proces, en volgt hierdoor niet
de zelfde regels en voorwaarden als bij normale programmacode.
De eerste generatie database change management
De eerste generatie database change management producten zijn in
principe geautomatiseerde “vergelijk en synchroniseer” oplossingen
die het mogelijk maken verschillende databaseomgevingen met elkaar
te vergelijken. Dit type oplossingen genereert rapporten die de
verschillen aangeven, waarna er automatisch code gegenereerd kan
worden om de verschillen te compenseren. Dit type oplossingen biedt
een belangrijke verbetering in het database change management
proces. Door het geautomatiseerde karakter wordt het aantal fouten
als gevolg van handmatig handelen in belangrijke mate gereduceerd.
Echter, veel change management problemen worden met de eerste
generatie van database change management producten nog steeds
niet geadresseerd:
• Wat gebeurt er bijvoorbeeld als er veranderingen in de testomgeving worden aangebracht? Dan kan het gebeuren dat de
referentieomgeving niet langer identiek is, en wijzigingen kunnen
verloren gaan.
• Een andere vraag is wat er precies gebeurt tijdens een
ontwikkelcyclus? Welke stappen zijn in deze cyclus genomen.
Er was geen informatie beschikbaar over hoe het uiteindelijke
resultaat is bereikt.
• Kan iedereen die toegang heeft tot een database wijzigingen
aanbrengt in de database?
• Welke veranderingen zijn door wie, wanneer gemaakt?
• Is database ontwikkeling effectief gesynchroniseerd met de
software ontwikkeling?
• Hoe te handelen bij gedeeltelijke distributie van de veranderingen?
Bijvoorbeeld de noodzaak een applicatie aanpassing te distribueren
zonder een andere, minder stabiele aanpassing?
In vergelijk tot moderne SCM oplossingen, biedt de eerste generatie
database change management producten weinig meer dan “vergelijk
en synchroniseer”. Ze bieden zeker niet de complete functionaliteit
van moderne SCM oplossingen, zoals bijvoorbeeld de mogelijkheid
veranderingen terug te draaien (rollback), check in / check out, file
locking, baseline settings, code merging en veranderingsrapporten
voor auditing en regelgeving. Omdat deze eerste generatie database
change management producten nog steeds niet in staat is naar
tevredenheid veranderingen te managen, is het wellicht beter deze
producten te categoriseren als database development management in
plaats van database change management producten.
database veranderingen te beheren, in principe een oplossing die
dezelfde functionaliteit kan bieden als traditionele SCM oplossingen:
1. Het afdwingen van formele, gedisciplineerde database change
management processen en workflows
2. Het werk van verschillende database ontwikkelteams synchroniseren en coördineren
3. Het ondersteunen van de volledige database ontwikkelcyclus, vanaf
ontwikkeling via Q&A, naar integratie en tenslotte productie.
4. Beheren en volgen van veranderingen
5. Het bieden van een goede, stabiele centrale opslag (repository) voor
het opslaan van een veranderingshistorie voor auditing doeleinden
6. Het koppelen van database veranderingen met traditionele
SCM projecten
7. Database veranderingen distribueren door middel van SCM taken
Om dit te realiseren, moeten de nieuwe generatie database change
management oplossingen het complete palet van software change
management functionaliteit in een database wereld gaan ondersteunen. In tegenstelling tot de eerste generatie oplossingen, welke zoals
we hebben gezien niet meer biedt dan een “vergelijk en synchroniseer” product, moeten moderne database change management oplossingen vandaag de dag een uitgebreid scala aan functionaliteiten
kunnen bieden waaronder object locking, check in / check out,
baseline setting, samenvoegen van code en een rollback van
veranderingen.
In plaats van het foutgevoelige en handmatige proces waar database
ontwikkelaars vandaag de dag noodgedwongen gebruik van maken
om aanpassingen in de database te maken, hebben ontwikkelaars
een dwingende behoefte aan een manier wijzigingen direct en
effectief aan te kunnen brengen in de structuur van de database.
Maar, ook de nieuwe generatie database change management oplossingen is niet geheel zonder uitdagingen. Een moet bijvoorbeeld
een nieuw type centrale opslag (repository) worden gecreëerd die
zowel speciale attributen, database objecten als ook database inhoud
kan opslaan. Verder is er het probleem van het beheren en coördineren van de centrale resources en de gekopieerde resources.
Een veranderingsproces moet worden gedefinieerd en worden
afgedwongen, en de activiteiten van de diverse ontwikkelteams moet
worden gesynchroniseerd. Database ontwikkeling moet worden
gekoppeld met traditionele SCM componenten zoals versiebeheer,
verandering sets (change sets) of activiteiten.
Maar ondanks deze uitdagingen, biedt een succesvolle implementatie van de nieuwe generatie database change management oplossingen enorme voordelen. De crux is de juiste database change
management oplossing te vinden, en de focus te houden op risico
beheersing. Een goede database change management oplossing van
de nieuwe generatie moet aan de volgende eisen voldoen:
•
•
•
•
•
•
De nieuwe generatie database change management
Vandaag de dag zijn database ontwikkelaars meer en meer op zoek
naar een oplossing die hen in staat stelt het volledige proces van
Procedures moeten worden afgedwongen zodat wijzigingen
alleen via een SCM workflow doorgevoerd kunnen worden.
Database ontwikkeling moet zodanig worden gedaan dat
botsingen en conflicten voorkomen kunnen worden.
Standaarden moeten gedefinieerd kunnen worden en worden
afgedwongen via check in / check out en labels.
Een compleet audit trail van alle veranderingen moet kunnen
worden vastgelegd.
Een automatische rollback van veranderingen, zowel in
ontwikkel- als ook in productieomgevingen moet mogelijk zijn.
De uitrol van verschillende databases moet volledige
geautomatiseerd plaats kunnen vinden, met three-way
comparison en analyse met gebruik maken van het samenvoegen van database code.
magazine voor software development 33
DATABASES
dbMaestro TeamWork
Teamwork van dbMaestro maakt het mogelijk om database ontwikkeling een integraal onderdeel van een gedisciplineerd SCM proces
te maken in plaats van een handmatig proces of, op zijn best,
semigeautomatiseerd proces. TeamWork voldoet in alle opzichten aan
de eisen voor een nieuwe generatie database change management
oplossingen, en vergroot in belangrijke mate de voordelen voor
organisaties die een SCM proces volgen voor zowel software
ontwikkeling als ook database ontwikkeling.
De database developer community heeft behoefte aan oplossingen
met voordelen als object-locking en auditing, die een nauwere controle
biedt van de ontwikkelprocessen binnen een team. Deze benadering
biedt tevens de mogelijkheid tot het distribueren van veranderingen
en versie beheer van database objecten en schema’s.
Innovatieve volgende generatie database change management
oplossingen, zoals dbMaestro TeamWork™, bieden al de hiervoor
beschreven mogelijkheden, plus heel veel meer. •
Veranderingen in databases kunnen nu op eenzelfde manier gevolgd
worden als veranderingen in de software code, waardoor het
complete ontwikkel project, inclusief database veranderingen, op een
gecontroleerde, geregistreerde en gestandaardiseerde wijze uitgerold
kan worden. Teamwork integreert met oplossing als IBM Rational.
Ben Suurmeijer
Ben Suurmeijer is ruim 17 jaar actief
in de IT. Eerst als Unix systeembeheerder en Oracle DBA, later als
pre sales bij onder andere Amerikaanse en Israëlische bedrijven,
maar altijd op het gebied van IT
Beheer. www.go-esi.com/blog /
blog.dbmaestro.com
Conclusie
Programma code ontwikkelaars hebben meer dan 20 jaar de voordelen ervaren van het gebruik van SCM oplossingen. Het is nu tijd om
een database change management proces naar hetzelfde niveau te
tillen als een SCM proces, en database ontwikkelaars en DBAs
dezelfde mate van eenvoud en procesmatige beveiliging te bieden bij
database ontwikkeling. Integratie met bestaande, traditionele SCM
producten biedt een homogeen ontwikkelproces, identiek voor
programmacode ontwikkeling als ook voor de ontwikkeling van
database objecten.
!
uw
Nie
DB PowerStudio
voor SQL Server
Tot 31 maart 2011 extreem voordelig! Ga naar: www.barnsten.com
Change
Manager
RapidSQL
SQL Scripting,
Query Building,
Versiebeheer,
ObjectManagement
+
Beheer alle
veranderingen
op alle databases
(data, schema, config)
www.barnsten.com
34
MAGAZINE
SQL
Optimizer
+
Ontdek,
diagnosticeer en
optimaliseer
slechte code
DBArtisan
+
Voor al je development & database tools.
Alle beheertaken
vanuit 1 scherm,
DB migraties,
user management
023 - 542 22 27
SDN > Update
Delphi Nieuws
De afgelopen maanden zijn er verschillende ontwikkelingen en technische publicaties op het gebied van
Delphi geweest. Hierbij een overzicht van het meest
in het oog springende en interessante nieuws.
Delphi XE Starter Edition
REST Servers in Delphi
XE Using DataSnap
Embarcadero is weer begonnen met een aantal RAD in Action white
papers. De eerste is half januari gepubliceerd op de website van Embarcadero, en er zullen er meerdere volgen. REST Servers in Delphi XE
using DataSnap geschreven door Marco Cantù kan gelezen worden
te http://www.embarcadero.com/rad-in-action/datasnap-rest waar
ook videos en voorbeeld code te vinden is.
Andere RAD in Action white papers die zullen volgen zijn o.a. Delphi
Prism XE for iPhone Development door Brian Long, en een Delphi XE
DataSnap XE Case Study geschreven door Bob Swart (met een
webinar gepland op woensdag 2 maart 2011).
SDE
18 maart 2011
Het duurt nog even, maar over een paar
weken staat de december SDE weer
voor de deur. Het Delphi Development
Network heeft een drietal sprekers
gevonden die samen weer vier sessies
zullen verzorgen.
Pawel Glowacki
Pawel Glowacki, de Embarcadero Technical
Lead voor Delphi in EMEA, zal laten zien
“What’s Cooking” in de labs voor de komende “Pulsar” release van Delphi, en zal
daarbij ook het laatste nieuws delen m.b.t.
Delphi en de ontwikkelingen voor en met Delphi. Voor eventueel nieuws over 64-bits en/of
Mac is dit de sessie om niet te missen…
Bob Swart
Bob Swart zal de nieuwe mogelijkheden van
IntraWeb XI in Delphi XE laten zien, en daar-
Op 1 februari 2011 heeft Embarcadero een goedkoper
Starter Edition uitgebracht van Delphi XE. Met een New User
prijs van 199 Euro (ex.BTW) maar een “Upgrade van elke andere IDE (inclusief Notepad++)” prijs van 149 Euro (ex.BTW)
is deze versie gericht op de hobbyist of de starter die met weinig budget toch met Delphi XE aan de slag wil. Er zitten wel
enkele beperkingen in Delphi XE: zo is database toegang
beperkt tot de BDE (dat wil je niet) of InterBase met IBX, en
zitten er geen web, cloud of multi-tier zaken in (maar daar
moet je dan ook de Professional of Enterprise versie voor
kopen). Iedereen die Delphi XE Starter Editie koopt kan de
PDF Delphi XE Starter Essentials gratis downloaden van de
Registered Users pagina, of in paperback formaat kopen van
Lulu.com via http://www.lulu.com/product/14723094
Ook zijn speciale upgrade prijzen naar Delphi XE Enterprise
en RAD Studio XE Enterprise aangekondigd, geldig tot het
einde van dit kwartaal. Zie http://www.delphixe.nl voor meer
details.
mee een introductie geven voordat Bruno
Fierens er in zijn sessie dieper op in kan gaan
met onder andere de IntraWeb iPhone controls. In deze sessie komen de verschillende
edities van IntraWeb XI (personal, standard en
ultimate) aan de orde – zowel de bestaande
als nieuwe features. Deployment als standalone toepassing of ISAPI DLL zal gedemonstreerd worden, net als URL Mapping, de
nieuwe Authentication en AJAX support voor
snelle en interactieve web Applications.
Bruno Fierens
Bruno Fierens van TMS Software uit België
zal een tweetal sessies voor ons verzorgen:
Extending the Delphi IDE en Getting the most
out of IntraWeb. In de eerste sessie zullen verschillende types van IDE extensies uitgelegd
worden gerealiseerd aan de hand van de
open tools API (OTAPI) Dit gaat van extensies op de Delphi repository, access van de
project manager, custom toolpanels in the
IDE toevoegen en access tot de Delphi code
editor. De extensies worden geillustreerd
door kleine voorbeelden en daarnaast worden ook een aantal gratis extensies gepubli-
ceerd door TMS software gedemonstreerd.
Voor performante en gebruiksvriendelijke web
applicaties staan in IntraWeb client-events,
asynchrone events en updates ter beschikking. In de sessie wordt gedemonstreerd hoe
deze technieken aangewend worden in the
TMS IntraWeb grids. Verschillende asynchrone en client-side features van de grids
komen aan bod. Daarnaast komen ook de
TMS IntraWeb iPhone controls aan bod die
eveneens via veel async functionaliteit toelaten iPhone, iPad web applicaties te ontwikkelen met Delphi en IntraWeb.
Erik van de Wetering
Erik van de Wetering van Marik Computers
zal een sessie doen over een Applicatie Framework met o.a. Datasnap in XE. De sessie
start met een korte intro van het project Applicatie Framework, en laat o.a. zien hoe de
dataset structuur opgebouwd wordt via datasnap tijdens runtime (server-side en clientside). Ook zien we een ClassForName functie
van Java in Delphi, Firebird sql en views, en
Delphi programma’s via Remote Applications
van Win2008.
magazine voor software development 35
.NET
ASP
Michiel van Otegem
Webservices en transacties
Transacties zijn bedacht om systemen consistent te houden en worden daarom ook al decennia gebruikt.
De ondersteuning voor transacties is om die reden ook bedacht voor webservices in de vorm van de
WS-AtomicTransaction standaard. Maar is dat wel een goed idee?
Juval Löwy, verantwoordelijk voor de C# coding standards van IDesign
en schrijver van onder andere Programming .NET Components en
Programming WCF Services (beide uitgegeven door O’Reilly), heeft
wel eens gezegd dat iedere applicatie die geen gebruik van transacties maakt speelgoed is (“Any application not using transactions is a
toy”). Dit is natuurlijk wat gechargeerd, maar het is niettemin belangrijk om op z’n minst na te gaan of je applicaties transacties nodig heeft.
Daarbij moet je bedenken hoe je het systeem consistent wilt houden.
Een inconsistent systeem doet immers niet wat het moet doen, omdat
het gegevens bevat die elkaar tegenspreken. Dit zelf oplossen is over
het algemeen een heidens karwei, omdat de complexiteit snel oploopt.
Bij vijf operaties in een transactie is het aantal permutaties 5! (=12), bij
tien operaties 10! (=3.600.000). Transacties zijn daardoor vaak de
beste oplossing. Het is niet voor niets dat .NET vanaf 2.0 uitstekende
ondersteuning biedt voor transacties middels de TransactionScope
(daarvoor al via System.EnterpriseServices), en dat technologieën als
LINQ-to-SQL en het Entity Framework alle wijzigingen met SaveChanges automatisch in een transactie verpakken. Ook in Windows
Communication Foundation is het eenvoudig om services te maken
die transacties ondersteunen (of vereisen). Om te beginnen moet je in
het operation contract aangegeven dat de betreffende service operation transacties ondersteunt. Dit doe je met het TransactionFlow
attribuut, zoals in Listing 1.
[OperationContract]
[TransactionFlow(TransactionFlowOption.Allowed)]
void MyServiceMethod(string someParam);
ervoor kiest een Operation Behavior te gebruiken, zoals in Listing 2, zal
een exception de transactie automatisch afbreken. Zonder exception
wordt aangenomen dat de operatie geslaagd is.
[OperationBehavior(TransactionScopeRequired=true,
TransactionAutoComplete=true)]
public void MyServiceMethod()
{
// Implementatie hier
}
Listing 2: Operation Behavior voor automatisch transactiebeheer.
Dat we webserivces die over de hele
wereld verspreid zijn in een enkele
transactie kunnen betrekken betekent
niet dat we dit ook moeten doen
Om transacties mogelijk te maken, moet je wel een binding kiezen die
transacties ondersteunt. De belangrijkste binding die dat niet doet is
BasicHttp, maar voor de meeste andere bindings is dit geen probleem.
Je moet deze binding daarnaast ook configureren om transacties te
ondersteunen en dat doe je als volgt:
Listing 1: Operation Contract met ondersteuning voor transacties.
<binding name="MyBinding" transactionFlow="true" />
De complexiteit loopt bij transacties al
snel op. Een transactie met 10 operaties kent 3.600.000 permutaties
Andere waardes voor TransactionFlowOption zijn Mandatory (verplicht)
en NotAllowed (niet toegestaan). Met de instelling Allowed zijn transacties toegestaan, maar kan een client de service ook aanroepen zonder een transactie te gebruiken. Uiteraard kan een service intern dan
nog steeds wel een transactie gebruiken. Andere services die door de
client aangeroepen worden zullen daarin echter niet meedraaien.
Met de TransactionFlow goed ingesteld, moet je nog wel zorgen dat
de operaties die je maakt aangeven of wat hun betreft de transactie
geslaagd is. Dit kun je declaratie doen met een Operation Behavior of
in code door expliciet OperationContext.Current.SetTransaction
Complete() aan te roepen voordat de functie retourneert. Wanneer je
36
MAGAZINE
In .NET is het kinderspel om een client te maken die een transactie
gebruikt bij het aanroepen van een service die dit ondersteunt. De
bindingconfiguratie wordt automatisch overgenomen uit de metadata
en daardoor wordt een aanroep binnen een TransactionScope automatisch gedaan met een transactie. WCF kiest hierbij automatisch het
meest optimale protocol voor de transactie, waarbij het kan kiezen uit
OleTx en WS-AtomicTransaction (WSAT). OleTx is een Windows-only
protocol dat uitstekend werkt binnen een lokaal netwerk. Zodra het
echter nodig is om ook andere services te betrekken, zoals services
gemaakt met Java’s WCF tegenhanger Web Services Interoperability
Technology (WSIT), zal WCF automatisch schakelen naar WSAT. Dit
kan ook als de transacties oorspronkelijk in OleTx gestart is. Dit is
volledig transparant en je hoeft je hier dus niet om te bekommeren.
Met WS-AtomicTransaction is het in principe mogelijk om webservices
die over de hele wereld verspreid zijn te betrekken in een enkele transactie. Dat we dat kunnen betekent echter niet meteen dat we dat ook
moeten doen. WS-AtomicTransaction werkt op basis van 2-phase
commit. Dit betekent dat de zogenaamde Transaction Co-ordinator
(TC), de regisseur van de transactie, eerst aan alle deelnemers in een
.NET
ASP
transactie vraagt of de transactie doorgang kan vinden. Wanneer alle
deelnemers daarop bevestigend antwoorden, laat de TC de transactie doorgaan en moeten de wijzigingen definitief gemaakt worden door
alle deelnemers. Deelnemers die in de eerste fase een OK gegeven
hebben, kunnen hier niet op terugkomen. Dit systeem werkt uitstekend, maar geeft wel een nadeel: locking. Zolang de TC nog niet aangegeven heeft dat de transactie door mag gaan, houdt de transactie
in principe een lock op resources die betrokken zijn bij de transactie.
Deze resource, zoals een database record of een bestand, mogen in
de tussentijd niet door andere operaties gewijzigd worden en (afhankelijk van het Isolation Level) mogen de wijzigingen ook nog niet zichtbaar zijn voor andere operaties. Dit geldt bijvoorbeeld ook als de TC
na de eerste fase, maar voor de tweede crasht en een tijd uit de lucht
is. In zulk soort situaties zijn resources zo lang geblokkeerd dat dit
enorme problemen voor een systeem op kan leveren. Maar zelfs als
alles goed gaat is het nog zo dat locks niet erg lang mogen duren.
Meer dan een seconde kan al geweldige gevolgen hebben voor een
systeem waar een hoop wijzigingen op gedaan worden.
Binnen een applicatie en zelf binnen een lokaal netwerk is dit nog wel
te realiseren, maar is een van de deelnemers bijvoorbeeld een webservice in Singapore, dan kan een enkele request-response al 10
seconden duren. Dan duurt een 2-phase commit in vergelijking een
eeuwigheid. Afgezien van de technische implicaties is er ook nog een
ander vraagstuk. Door een webservice aan te bieden aan een derde
met ondersteuning voor transacties, geef je eigenlijk een deel van de
controle over je eigen systeem uit handen. De gemiddelde systeembeheerder zal hier van gruwen, en terecht!
Had er dan nooit een standaard als WS-AtomicTransactions moeten
komen? Of had deze nooit in WCF en WSIT geïmplementeerd moeten worden? Dat is ook wel weer een brug te ver. Transacties hebben
ook in de wereld van webservices hun waarde. Je moet alleen goed
nadenken over wanneer je ze wel of niet moet gebruiken. Het beste is
om hier binnen een organisatie richtlijnen voor op te stellen. Je kunt
hierbij services bijvoorbeeld verdelen in categorieën op basis van hun
functie en plek in een proces. Zo kun je bijvoorbeeld services onderscheiden die een bepaalde basisfunctie bieden, zoals het versturen
van een email.
Dergelijke “basisservices” worden altijd in de context van bedrijfslogica uitgevoerd en zijn dus een goede kandidaat om in een transactie mee te draaien. Services die deze services aanroepen zitten op
een hoger niveau en daarvan zou je bijvoorbeeld kunnen bepalen dat
ze niet deel mogen nemen in een transactie, maar er wel een mogen
initiëren om de lager gelegen services te coördineren. Transacties buiten de grenzen van het eigen netwerk zijn meestal geen goed idee,
dus je moet wel hele goede redenen hebben om dat toe te staan. Voor
multi-nationals kan ook de latency een rol spelen in de richtlijnen.
Persoonlijk vind ik het heel handig om de richtlijnen die je kiest vast te
leggen in een duidelijk plaatje. Een plaatje kun je namelijk makkelijk
ergens ophangen om mensen te herinneren aan de richtlijnen.
Bovendien zijn plaatjes beter te onthouden dan regeltjes tekst.
Afbeelding 1 laat een voorbeeld zien van een plaatje waarin de
transactierichtlijnen gevat zijn. •
Afbeelding 1, Voorbeeld transactiesrichtlijnen
26 maart 2011
CodeCamp
TIP:
Als je Google Chrome installeert kun je de standaard Search
engine instellen. Daarvoor kun je kiezen uit: Google, Yahoo en
Microsoft Bing. Dus zelfs in Chrome kun je bingen ;-)
Op 26 maart 2011 zal SharePoint Saturday en de
volgende CodeCamp in Nederland georganiseerd
worden door de gezamelijke communities. Blijf op
de hoogte via Twitter en vol http://twitter.com/
codecampnl
E-Office (www.e-office.com) is platina sponsor en
Macaw (www.macaw.nl) is gold sponsor.
magazine voor software development 37
IW
Anita Boerboom
Building a custom Health Rule
SharePoint 2010 and governance are tightly connected these days. Governance consists of
policies, roles, responsibilities and processes to ‘avoid’ chaos in the SharePoint environment.
Some of the possible policies implemented by an organization can be monitored by SharePoint
itself by the new feature called SharePoint Health Analyzer. The Health Analyzer is rule based
and the rules check the farm for potential problems. SharePoint has several out of the box rules,
like ‘Drives are running out of disk space’ and ‘The server farm account should not be used for
other services’. To make administrators aware of possible issues with the farm all errors are
listed in the Health Reports list. To monitor additional items not available out of the box, custom
health rules can be built.
Functionality of the custom health rule
Sandboxed solutions can be monitored a little bit better than SharePoint default provides.
When the Microsoft SharePoint Foundation Sandboxed Code Service
is started sandboxed solutions can be deployed and used. To
monitor the resources consumed by the sandboxed solutions a
couple of timer jobs measure and collect the consumed resources:
• Solution Daily Resource Usage Update
• Solution Resource Usage Log Processing
• Solution Resource Usage Update
It is possible to deploy sandboxed solution when the timer jobs are
not running. In that case the resources consumed by the sandboxed
solutions are not measured. This means when the sandboxed solutions are consuming a lot of resources the farm can get down in not a
nice way. One of the strengths of sandboxed solutions is that they are
hosted in a partially trusted context so they do not affect the rest of the
SharePoint implementation...
•
•
•
•
Summary - the title for the rule
Explanation - displayed in the Health Reports list when the rule fails
Remedy - displayed in the Health Reports list when the rule fails
ErrorLevel - severity of the failure of the rule
All rule definitions can be found in the rule definition list: Central
Administration, Monitoring, Review rule definitions. The Health Reports
list can be found in the Central Administration, Monitoring, Review
problems and solutions. The Health Reports list explains the issue,
failing servers and services and the remedy to the problem.
The difference between the two lists is that the rule definition list
displays all the existing rules; the Health Reports list displays the rules
which cause problems in the farm.
The rules are categorized in both lists. Code listing 1 lists the custom
rule in the Configuration category.
public override SPHealthCategory Category
{
get
{
Wouldn’t it be nice to be sure the timer jobs are running when the
Sandboxed Code Service is running?
return SPHealthCategory.Configuration;
}
One of the strengths of sandboxed
solutions is that they are hosted in a
partially trusted context so they do
not affect the rest of the SharePoint
implementation
}
Listing 1: Override the Category property
The title of the rule can be set by overriding the Summary property as
shown in code listing 2.
public override string Summary
{
get
{
return "Verify the sandbox related jobs are started.";
Build the rule
To set up a health analyzer rule an empty SharePoint project is
created. A class is added which inherits from SPHealthAnalysisRule.
This is the class to implement the rule definition. The class can also be
inherited from SPRepairableHealthAnalysisRule. This means the rule
can repair the problem itself. When inheriting from SPRepairableHealthAnalysisRule the method Repair() has to be implemented as well.
To define a rule some properties has to be overridden:
• Category - rule definitions are grouped by Category in the
default view
38
MAGAZINE
}
}
Listing 2: Override the Summary property
The Summary is shown in the rule definition list and the health reports
list. The custom rule can be scheduled by overriding the AutomaticExecutionParameters property. In the get accessor a SPHealth
AnalysisRuleAutomaticExecutionParameters object is returned.
When the property isn’t overridden the rule can be scheduled
IW
manually by a farm administrator.
public override SPHealthAnalysisRuleAutomaticExecutionParameters
AutomaticExecutionParameters
{
get
{
The code in listing 4 checks if the Sandboxes Code Service is started.
If the service is started, it checks if the timer jobs involved in measuring the resources consumed by the solutions are enabled. When the
service isn’t started there are no running sandboxed solutions and no
resources have to be measured. The AddJobTitle() method adds the
title(s) of the disabled job(s) to a generic list of strings as stated in code
listing 5.
SPHealthAnalysisRuleAutomaticExecutionParameters
private void AddJobTitle(SPJobDefinition job)
parameter = new
SPHealthAnalysisRuleAutomaticExecutionParameters();
{
parameter.Schedule = SPHealthCheckSchedule.Hourly;
if (job.IsDisabled)
parameter.Scope = SPHealthCheckScope.Any;
{
jobTitleOfDisabledJobs.Add(job.Title);
parameter.RepairAutomatically = false;
}
parameter.ServiceType = typeof(SPTimerService);
}
return parameter;
}
}
Listing 5: Collection of titles of disabled jobs
Listing 3: Overriding property SPHealthAnalysisRuleAutomatic
ExecutionParameters
The generic list is used at the Explanation property to inform the farm
administrator exactly which job(s) aren't enabled. Code listing 6 overrides the Explanation property and returns an informative message
including the titles of the jobs which aren’t enabled.
In code listing 3 the rule is scheduled on an hourly basis and the scope
is set to SPHealthCheckScope.Any. This means the rule will run on an
hourly basis on the first available computer with the specified service.
The code that identifies the real problem is the Check() method. The
Check() method returns the outcome of the check: SPHeathStatus.Failed or SPHealthStatus.Passed. When SPHeathStatus.Failed is
the result of the check, the rule will be displayed in the Health Reports
list to make the administrator aware of the problem.
public override string Explanation
{
get
{
string jobTitles = string.Empty;
for (int i = 0; i < jobTitleOfDisabledJobs.Count; i++)
{
public override SPHealthCheckStatus Check()
jobTitles += jobTitleOfDisabledJobs[i].ToString();
{
if (i != jobTitleOfDisabledJobs.Count - 1)
jobTitleOfDisabledJobs.Clear();
{
SPUserCodeService userCodeService =
}
jobTitles += " / ";
SPUserCodeService.Local;
}
if (userCodeService.IsEnabled)
return "The Microsoft SharePoint Foundation Sandboxed
{
Code Service is started, but not all the " +
using (SPSite site = new SPSite("your_site_url"))
"timerjobs are: " + jobTitles;
foreach (SPJobDefinition job
in site.WebApplication.JobDefinitions)
}
}
{
switch (job.Title)
{
Listing 6: Display an informative message in the Explanation
property of the rule
case "Solution Daily Resource Usage Update":
AddJobTitle(job);
break;
case "Solution Resource Usage Log Processing":
Besides explaining the issue in detail a message can be displayed to
the administrator on how to act on the issue. Code listing 7 overrides
the Remedy property.
AddJobTitle(job);
break;
case "Solution Resource Usage Update":
public override string Remedy
{
AddJobTitle(job);
get
break;
{
return "Start the timerjobs: Solution Daily Usage
default:
Update, Solution Resource Usage Log Processing
break;
and/or Solution Resource Usage Update.";
}
}
}
}
if (jobTitleOfDisabledJobs.Count != 0)
{
Listing 7: Override the Remedy property
return SPHealthCheckStatus.Failed;
}
}
Code listing 8 overrides the ErrorLevel property and sets the severity
of the issue to Warning.
return SPHealthCheckStatus.Passed;
}
Listing 4: Implementation of the Check() method
magazine voor software development 39
IW
public override SPHealthCheckErrorLevel ErrorLevel
}
{
}
get
catch (Exception ex)
{
{
return SPHealthCheckErrorLevel.Warning;
throw new Exception("There was an error removing
}
the health rule: " + ex.Message);
}
}
}
Listing 8: Override the ErrorLevel property
Listing 9: Register and unregister the rule
Deploy the rule
The rule can be deployed by adding a farm level scoped feature
to the solution, and add an event receiver to the feature.
Code listing 9 overrides the FeatureInstalled and FeatureUninstalling
to register and unregister the rule.
After the deployment, the rule can be found in the rule definition list:
Central Administration, Monitoring, Review rule definitions. Details of
the rule are shown in Figure 1.
public override void FeatureInstalled
(SPFeatureReceiverProperties properties)
{
try
{
Assembly currentAssembly = Assembly.GetExecutingAssembly();
IDictionary<Type, Exception>
exceptions =
SPHealthAnalyzer.RegisterRules(currentAssembly);
if (exceptions != null)
{
Fig. 1: The rule definition
if (exceptions.Count == 0)
{
//ok
}
The default view of the rule definition list is showing all the defined rules
EXCEPT the rules defined with the category ‘System’. Of course it's
possible to create an additional view to show all the rules.
else
{
//something went wrong, take appropriate action
}
}
Run and test the rule
By disabling for example the ‘Solution Daily Resource Usage Update’
job and the ‘Solution Resource Usage Update’ job the rule can be
tested to fail.
}
catch (Exception ex)
{
throw new Exception("There was an error registering
the health rule: " + ex.Message);
}
}
public override void FeatureUninstalling
The rule is scheduled to run every hour as defined in code listing 3
and shown in Figure 1. To speed things up the rule can be selected to
run directly by pressing Run Now. The timer job which actually runs the
Health Analyzer jobs, dependent of the schedule, is in this case
Health Analysis Job (Hourly, Microsoft SharePoint Foundation Timer,
Any Server). The job can be found in Central Administration, Monitoring, Review Job Definitions. By selecting the job title the details of the
job are shown and the job can run immediately by selecting Run Now.
(SPFeatureReceiverProperties properties)
{
The rule fails and shows up in the Health Reports list as shown in
Figure 2.
try
{
Assembly currentAssembly = Assembly.GetExecutingAssembly();
IDictionary<Type, Exception>
exceptions =
SPHealthAnalyzer.UnregisterRules(currentAssembly);
Fig. 2: The rule fails
if (exceptions != null)
{
if (exceptions.Count == 0)
{
The little yellow sign at the bottom of the icon in Figure 2 shows a
visual representation of the ErrorLevel set in code listing 8. The Summary of the rule set in code listing 2 is displayed as the title of the rule.
//ok
}
else
{
//something went wrong, take appropriate action
}
40
MAGAZINE
The details of the rule can be viewed by selecting the text in the
Health Reports list. A dialog opens as shown in Figure 3. Note that
the Explanation of the rule changes when different sandbox timer jobs
are disabled or enabled and the rule is reanalyzed. The Explanation
property displays exactly which timer jobs aren´t enabled.
IW
Keep in mind to attach the debugger to the timer services when
debugging the rules: OWSTimer.exe process.
DELPHI
TIP:
CD/DVD Drive Openen
Soms is het handig om de CD/DVD driver van je computer of
laptop te openen. Hier kunnen we de mciSendString functie uit
de MMSystem unit gebruiken. Om de CD drive te openen moeten we de string “Set cdaudio door open wait” sturen, en om
hem te sluiten de string “Set cdaudio door closed wait”.
Om een specifieke drive X te openen kunnen we de string “X:
Alias Drive_X type cdaudio” sturen om X: als alias voor Driver_X
op te geven, gevolgd door “set Drive_X door open”. De volgende functie kan gebruikt worden om een willekeurige Drive te
openen, of de default driver (als je #0 meegeeft als argument):
function OpenDrive(DriveLetter: Char): LongInt;
var
ParamString: string;
Fig. 3: Details of the failed rule
begin
if DriveLetter = #0 then
Settings are not updated
It is possible that a property like the category will change during
development. A mistake is easily made and the rule has to move from
the Configuration to the Performance category. Code listing 10
displays the minor change in code.
begin
ParamString := 'set cdaudio door open';
Result := mciSendString(PChar(ParamString),nil,0,0)
end
else
begin
public override SPHealthCategory Category
ParamString := DriveLetter + ': Alias Drive_' +
{
DriveLetter
get
+ ' Type CDAudio';
{
Result := mciSendString(PChar('open ' +
return SPHealthCategory.Performance;
ParamString),nil,0,0);
}
if Result = 0 then
}
Result := mciSendString(PChar('set ' + 'Drive_' +
DriveLetter
Listing 10: Changing the Category of the rule definition
After the deployment of the solution with the changed Category
property the rule fails, but the rule shows up at the 'old' category
Configuration.
This is one of the possible 'issues' which can occur if the Timer
Service Recycle timer job isn’t restarted. The job is like an iisreset, but
for the timer service, it recycles the Timer Service to free resources.
Conclusion
It is a good practice to implement health rules to monitor the farm, be
informed about issues and take the appropriate action. The rules are
not that hard to program, but can be really useful to have an overview
of issues.Whenever possible implement health rules that comply with
the governance plan of the organization. It will be easier and maybe
avoids chaos in the SharePoint environment. •
Anita Boerboom
Anita Boerboom is an independent
SharePoint developer and consultant in The Netherlands. She
combines programming knowledge
with good communication skills and
a high quality standard in all her
projects. Anita has worked in
several industries with focus on
several knowledge areas within
SharePoint. She's very fond of the
jQuery library SPServices.
+ ' door open'),nil,0,0)
end
end;
TIP:
Het Windows Phone 7 product team heeft het boek over
Programming the Windows Phone 7 van Charles Petzold
beschikbaar gesteld aan de community. In dit boek kun je alles
lezen, hoe je zelf applicaties kunt maken voor de Windows Phone
7. In principe heb je daarvoor geen toestel nodig en kun je alles
uitproberen in de emulator.
Het boek is te downloaden op: http://bit.ly/9PBQNr en de
bijbehorende sources op: http://bit.ly/aB0N08.
magazine voor software development 41
GENERAL
Robert Blom
“Nieuw” in Nederland:
NLDeveloper
De marktwaarde van elke software-ontwikkelaar wordt al jaren bepaald door de expertise die
hij of zij meebrengt. Elke werkgever is tenslotte gebaat bij goed-functionerende software, of er
nu sprake is van een detacherings-opdracht of het uitvoeren van projecten onder eigen dak.
Het is daarom niet verwonderlijk dat er voortdurend wordt bijgeleerd: via cursussen, seminars,
workshops, competence centers, fora etc.
Een forum is al jaren een bekende ontmoetingsplaats om kennis te
delen: de een vraagt, de ander antwoordt, weer een ander corrigeert
of vult aan. Het succes van Wikipedia is hierop gebaseerd, duizenden
auteurs bepalen het succes en de waarheidsgetrouwheid.
In de wereld van software-ontwikkeling zijn er op internet vanzelfsprekend al verschillende fora te vinden. Het ene forum is populairder
dan de ander of richt zich op één specifieke ontwikkelomgeving. En
vaak is het antwoord op een brandende vraag in het buitenland en/of
in een andere taal te vinden. Daarbij blijft Google een veelgebruikt
vertrekpunt voor een prangende vraag.
Een forum in je eigen moerstaal blijft toch het meest ideaal. Want wat
is er nou handiger om via het forum nog even - in je eigen taal - contact met de vragensteller op te nemen of om via het forum een gezamenlijk probleem aan te pakken. Het onderwerp sfeer is daarmee een
‘hot issue’ geworden. Elke moderator probeert zijn (of haar!) forum uit
te bouwen, veel leden te werven en qua inhoud en populariteit op internet tot een succes te maken. Wat dat betreft heeft NLDeveloper als
kennistank, forum, blog of ‘ontmoetingsplaats’ niets nieuws te melden.
NLDeveloper is daardoor altijd op de hoogte van de nieuwste ontwikkelingen; een voorsprong die natuurlijk ten goede komt aan de actieve
leden van het forum. Op zowel de website als via Twitter, Facebook,
LinkedIn en media besteden we aandacht aan nieuwe ontwikkelingen
en technieken die de moderne software-ontwikkelaar helpt nog beter
in zijn/haar werk te worden en te blijven.
NLDeveloper komt niet zomaar uit de lucht vallen. In een tijd dat
Cloud-computing en Social Media het gesprek van de dag zijn, zijn
de moderators (en tevens initiatiefnemers) al jaren werkzaam in de wereld van software-ontwikkeling en hebben hun sporen op dit gebied al
lang verdiend. Betekent dat dan een probleemloze start van het
nieuwe forum? Mede-initiatiefnemer Robert Blom: “Welnee. Elke
nieuwe site, forum, blog, concept of dienst op internet vraagt om
voortdurende aandacht en waar nodig bijsturen. Natuurlijk, de site kan
alleen een succes worden bij voldoende ‘verstandige’ vragen en ‘verstandige’ antwoorden. Ongeacht het kennisniveau van de bezoeker:
men moet zich op NLDeveloper thuis (gaan) voelen. Tweerichtingsverkeer dus. Maar ook de artikelen, blogs, speciale aanbieden, berichtgevingen, aankondigingen moeten aantrekkelijk zijn én blijven.
Waarbij ook de sfeer niet uit het oog verloren wordt.”
NLDeveloper is dus nieuw. De mensen achter de website willen een
modern, informatief en succesvol platform realiseren. Dit kan uitsluitend met de medewerking van lezers en leden. “Heb je vragen en/of
opmerkingen, aarzel dan niet om contact met ons op te nemen of een
vraag te stellen op ons forum. Alleen met elkaar kunnen we NLDeveloper voor elkaar een succes laten worden.”
Meer weten? Kijk op www.nldeveloper.com. Wedden dat het klikt? •
Robert Blom
En toch is er wat nieuws onder de zon. NLDeveloper richt zich niet op
één specifieke ontwikkeltaal! . En dat is handig voor leden, lezers én
bedrijven als Microsoft (.Net, VB), Sun (Java/J2EE), Embarcadero (Delphi, Prism) en Oracle. Als lid van NLDeveloper blijf je op de hoogte
van de nieuwste ontwikkelingen. Je maakt deel uit van een netwerk
van professionele ontwikkelaars die elkaar op een professionele wijze
te hulp staan. Hierdoor is er altijd een technische vraagbaak binnen
handbereik waardoor je bij het oplossen van vraagstukken een aanzienlijke tijdwinst realiseert. Zowel formeel als informeel heeft het
NLDeveloper uitstekende contacten met leveranciers.
42
MAGAZINE
Robert Blom adviseert en produceert. Voegt de daad bij het woord.
Met als resultaat: een lange reeks
aan enthousiaste opdrachtgevers.
Plus een lange reeks succesvolle
brochures, websites en andere uitingen. Complete producten, van
concept tot uitvoering - inclusief design, fotografie, copywriting, drukwerk en meer. Kortom, alles wat u
nodig hebt om u met effect in de markt bekend te stellen. Zie
ook www.RobertBlom.nl
GENERAL
Mark Wolzak
Best practices bij het vervangen van een
SCOM Gateway Server
Bij het monitoren van agents binnen System Center Operations Manager (SCOM) 2007 R2
wordt gebruik gemaakt van Kerberos voor onderlinge authenticatie binnen de trust boundary van
een domein. Buiten trust boundaries wordt gebruik gemaakt van certificaten. Sinds SCOM 2007
kan voor monitoring van agents buiten de trust boundary ook gebruik gemaakt worden van een
Gateway server.
De gateway server wordt geplaatst binnen de trust boundary van de
agents en verzorgt authenticatie voor de agents met de managementgroup met behulp van een certificaat. Omdat de agents zich in
dezelfde trust boundary bevinden als de gateway kunnen zij zich
authenticeren bij de gateway met behulp van Kerberos en hebben
hierdoor zelf geen certificaat nodig. Dit kan een aanzienlijke besparing
opleveren in beheer van certificaten op het moment dat er veel agents
in betreffende omgeving gemonitord moeten worden. Een ander voordeel is dat de agents zelf geen internetverbinding nodig hebben.
Op den duur kan het noodzakelijk worden om een gateway server te
vervangen, bijvoorbeeld doordat hardware verouderd is. De procedure die hiervoor is beschreven in de Operations Administrator’s Guide
van Microsoft werkt echter niet altijd vlekkeloos. In dit artikel worden
een aantal extra benodigde stappen besproken om tot het gewenste
eindresultaat te komen.
De procedure volgens Microsoft in praktijk gebracht
De procedure zoals beschreven in de SCOM 2007 R2 Operations
Administrators Guide1 is als volgt:
1. Log in op een managementserver (MS) met een account dat lid is
van de Operations Manager Administrators groep en open de
console;
2. Ga naar het Administration scherm en ga naar Administration >
Device Management en klik ‘Agent Managed’;
3. Selecteer de Computers waarvoor de primary managementserver
gewijzigd moet worden, doe rechtermuisklik en selecteer ‘Change
Primary Management Server’;
4. De-installeer de gateway server software van de computer;
5. Verwijder de gateway server uit de groep.
Met deze procedure bestaat er een kans dat de agents communicatie verliezen met de managementgroep. Vooral als agents niet geconfigureerd zijn met een failover managementserver.
In principe zou nu het volgende moeten gebeuren:
1. De Root Management Server (RMS) verwerkt de aanpassing
waardoor de ‘state cookies’ van Gateways (GTW) ‘A’ en ‘B’ en van
‘Agt X’ verlopen en deze een nieuwe configuratie nodig hebben;
2. Gateway ‘A’ controleert of zijn state cookie nog geldig is en vraagt
de nieuwe configuratie op;
3. De nieuwe configuratie wordt overgebracht naar Gateway ‘A’ waarin
is aangegeven dat ‘Agt X’ moet rapporteren aan Gateway ‘B’;
4. ‘Agt X’ controleert of zijn state cookie nog geldig is en vraagt de
nieuwe configuratie op;
5. De nieuwe configuratie wordt overgebracht naar ‘Agt X’ waarin is
aangegeven dat ‘Agt X’ moet rapporteren aan Gateway ‘B’;
6. Communicatie met Gateway ‘B’ wordt opgestart en ‘Agt X’
rapporteert voortaan met Gateway ‘B’.
Op het moment dat de configuratie gewijzigd wordt volgens bovenstaande procedure zullen agents die niet geconfigureerd zijn met een
failover managementserver, connectie met de managementgroep verliezen. De oorzaak hiervan ligt primair in de volgorde waarin de configuratie wordt ontvangen en de wijze waarop de managementservers
hierop reageren. Omdat in stap 3 de configuratiewijziging aankomt bij
Gateway ‘A’ zal deze server elke volgende communicatie met ‘Agt X’
weigeren. Volgens de configuratie van deze gateway communiceert
‘Agt X’ immers niet langer met Gateway ‘A’. Dit betekent dat de agent
na stap 4 de communicatie met de managementgroup verliest.
Symptomen bij verliezen communicatie
De symptomen voor het verliezen van de communicatie zullen terug
te vinden zijn in de console en in de ‘Operations Manager’ eventlogs
van de agent en van de oude en de nieuwe gateway server.
Console
In de console zal een heartbeat failure te zien zijn waardoor de agent
grijs weergegeven zal worden in de console.
magazine voor software development 43
GENERAL
Tevens zullen in de alertview de volgende errors te zien zijn
Agent
In de eventlog zal bij het maken van een connectie met de oorspronkelijke Gateway server een error met eventid 20070 met als source
‘OpsMgr Connector’ optreden.
1. Verwijder een gateway server pas (stap 5 in de procedure) op het
moment dat alle agents succesvol communiceren met hun nieuwe
managementserver;
2. Zorg ervoor dat agents, indien er een nieuwe primaire
managementserver aangewezen wordt, de oorspronkelijke
managementserver, al dan niet tijdelijk, als failover management–
server toegewezen krijgen.
Indien de oorspronkelijke gateway server niet meer ingezet kan
worden, bijvoorbeeld doordat deze niet meer actief is, kan de
configuratie van de agent ook handmatig aangepast worden.
Naast de error in de eventlog is het probleem te zien in de configuratie van de agent in de registry onder ‘HKLM\SOFTWARE\Microsoft\Microsoft Operations Manager\3.0\Agent Management
Groups\[Managementgroup Name]\Parent Health Services\0’.
Hier zal te zien zijn dat de genoemde managementserver (AuthenticationName en NetworkName), nog steeds de oude server betreft.
Oorspronkelijke en nieuwe Gateway server
In de eventlogs van de oorspronkelijke en de nieuwe gateway server
zullen errors met respectievelijke EventId’s 20000 en 20022 van
Source ‘OpsMgr Connector’ gelogd worden. Hierbij geeft de eerste
aan dat een device welke geen lid is van de managementgroup heeft
geprobeerd contact te maken. De tweede geeft aan dat de agent geen
heartbeat heeft.
Oorspronkelijke gateway server als failover aanwijzen
Door het inzetten van de oorspronkelijke managementserver als
failover management server is de agent geautoriseerd om contact op
te nemen met de managementgroup via zijn oorspronkelijke primaire
managementserver en wordt de agent in staat gesteld om de juiste
configuratie op te halen van de managementgroup.
Oplossen en voorkomen
Het beschreven probleem kan het best opgelost en voorkomen worden door bij het vervangen van een gateway server een aantal regels
aan te houden:
De procedure kan uitgevoerd worden met behulp van onderstaande
powershell script (uit te voeren via de operations manager shell):
01234567890123456789012345678901234567890123456789012
3456
44
MAGAZINE
GENERAL
$primaryMS = Get-GatewayManagementServer
| where {$_.Name -eq 'ExtGWt02.clientx.local'}
$failoverMS = Get-GatewayManagementServer
| where {$_.Name -eq 'ExtGWt01.clientx.local'}
$agent = Get-agent
7. Verifieer dat ‘Specify Management Group Information’ is aangevinkt
en klik ‘Next’;
8. Onder ‘management server’ kan nu de juiste managementserver
aangegeven worden. Klik ‘Next’ en klik ‘Install’.
Na afloop van deze installatie zal de communicatie met de managementgroup hervat worden.
| where {$_.Name -eq 'ExtADt01.clientx.local'}
Set-ManagementServer -AgentManagedComputer: $agent
-PrimaryManagementServer: $primaryMS
-FailoverServer: $failoverMS
In bovenstaand voorbeeld is ExtGWt01.clientx.local de originele
managementserver (gateway) en ExtGWt02.clientx.local de nieuw in te
zetten managementserver (gateway).
Conclusie
De procedure die door Microsoft is beschreven voor het vervangen
van een Gateway server functioneert niet altijd vlekkeloos. Problemen
die hieruit voortvloeien zijn echter niet onoverkomelijk en kunnen voorkomen worden door een paar eenvoudige regels te hanteren. •
1
http://download.microsoft.com/download/B/F/D/BFDD0F66-1637-4EA3-
8E6E-8D03001E5E66/OM2007R2_OperationsAdministratorsGuide.docx
Na uitvoeren van het script zal communicatie met de managementgroup hersteld worden en kan, zodra de agent de nieuwe configuratie opgehaald heeft, de failover managementserver verwijderd worden
uit de configuratie van de agent door onderstaande script via de
operations manager shell uit te voeren:
Mark Wolzak
Ik ben 10 jaar werkzaam in de IT en
als ontwerper infrastructuur / consultant werkzaam bij Info Support in
Veenendaal. Ik werk onder andere
met SQL Server, ISA/TMG, Exchange en System Center Virtual
Machine manager, maar heb me gespecialiseerd in System Center
Operations Manager waarvoor ik diverse implementaties heb verzorgd
$primaryMS = Get-GatewayManagementServer
| where {$_.Name -eq 'ExtGWt02.clientx.local'}
$agent = Get-agent
| where {$_.Name -eq 'ExtADt01.clientx.local'}
Set-ManagementServer -AgentManagedComputer: $agent
-PrimaryManagementServer: $primaryMS
bij uiteenlopende klanten.
.NET
TIP:
Welke .NET versie draai ik
Als je wilt weten welke versie van het .NET framework je allemaal hebt geinstalleerd, kun je dat doen door in de registry te
zoeken en de directories op je disk te controleren. Maar dit is
er arbeidsintensief en niet geheel foutloos. Via twitter kwam
deze link http://www.asoft.be/prod_netver.html.
Handmatig aanpassen van de configuratie
Indien de oorspronkelijke gateway server niet meer ingezet kan worden kan onderstaande procedure gebruikt worden om de configuratie aan te passen:
1. Stop de service ‘System Center Management’ op de server waar de
agent draait;
2. Verwijder de inhoud van de directory ‘D:\Program Files\System
Center Operations Manager 2007\Health Service State\Connector
Configuration Cache\[Managementgroup name]’;
3. Open ‘Add/Remove programs’ (of ‘Programs and Features’ in
server 2008)
4. Selecteer ‘System Center Operations Manager 2007 R2 Agent’ en
klik ‘Change’;
5. Klik ‘Next’, selecteer ‘Modify’ en ‘Next’;
6. Selecteer ‘Modify Management Group’, selecteer de juiste
managementgroup en klik ‘Next’;
magazine voor software development 45
GENERAL
De uiterste houdbaarheidsdatum
van requirements
Onlangs gaf ik – voor de zoveelste keer – training in het identificeren en modelleren van smart use cases.
Dit keer bevond ik me in de hippe ruimtes van Meeting Plaza Utrecht, boven het altijd sfeervolle Hoog
Catharijne. Tijdens de goed verzorgde lunch werd het onderwerp al snel bepaald door de uiterste houdbaarheidsdatum. Van levensmiddelen, maar meer nog, van requirements.
Stickeren
In de horeca is het al jaren een goed gebruik, het stickeren van levensmiddelen, zo weet ik van afzichtelijke televisieprogramma’s als
Keuringsdienst Van Waren. Een eenvoudige sticker vertelt wanneer
het product is opengemaakt, en tot wanneer het houdbaar is. Is deze
uiterste houdbaarheidsdatum verstreken, dan wordt het product weggegooid, onbruikbaar voor consumptie. Tenminste dat hoop je dan.
Maar dan. De uiterste houdbaarheidsdatum van requirements?
Het onderwerp kwam ter tafel toen een van de cursisten vertelde op
dit moment te werken aan de requirements van een request
for change (RFC) die inmiddels twee jaar oud is. Twee jaar oude
requirements? De kans is groot dat deze requirements inmiddels al
behoorlijk beschimmeld zijn; wet- en regelgeving is gewijzigd en de
wensen van de gebruikers zijn ontegenzeggelijk veranderd. Als tijdens
een gemiddeld project de requirements al 20-25% wijzigen, hoe
vergaat het dan requirements die ergens op een plank liggen te
verstoffen?
Requirements en kaas
Welbeschouwd zijn requirements te vergelijken met kaas. Je hebt
jonge requirements, net rijp genoeg om te consumeren, jong belegen
requirements die eigenlijk al hadden moeten worden gerealiseerd, en
dan oude requirements, die opzichtig beginnen te brokkelen. Tenslotte
zijn alle ongebruikte requirements overjarig. Wellicht smaakvol, maar
ze vallen al uit elkaar op het moment dat ze worden gehanteerd.
En net als kaas die op een plank ligt te rijpen verdienen requirements
dezelfde zorgzame aandacht willen ze na een of twee jaar nog
consumeerbaar zijn. Ze moeten worden omgedraaid, geevalueerd en
verzorgd. Gebeurt dit niet dan verschimmelen ze en moeten ze
eenvoudigweg uit de handel worden genomen, ongeschikt voor
comsumptie. Ik denk dan ook dat het een goed idee is ook requirements te stickeren, net als alle andere bederfelijke waar. Wanneer zijn
ze aangemaakt, en belangrijker nog, wanneer dienen de requirements
gerealiseerd te zijn voor ze definitief verschimmelen.
Maar wanneer zijn onze requirements eigenlijk bedorven? Een kritisch
agile luisteraar zal wellicht zeggen dat requirements beginnen met rotten zodra ze zijn opgeschreven. Immers, voortschrijdend inzicht begint
direct te werken. Misschien is het een idee om een standaardtermijn
voor bederf te hanteren – zeg een half jaar. En misschien zijn requirements voor de user interface wel nog sneller bedorven. Die krijgen dan
een sticker van drie of vier maanden. En wanneer requirements over
hun uiterste houdbaarheidsdatum heen zijn? Niet aarzelen. Gewoon
weggooien!
YAGNI
Het is overigens goed mogelijk de uiterste houdbaarheidsdatum te
rekken. Hier komt het bekende YAGNI-principe goed van pas.
You aren’t gonna need it. Ofwel voorkom in projecten al het werk dat
op dit moment (nog) niet nodig is. Doorvertaald naar requirements
komt dit er op neer dat alhoewel het verstandig is aan het begin van
een project vast te stellen welke requirements we graag willen
implemeteren, de details van deze requirements pas echt nodig zodra
de implementatie ervan begint. En dat is mogelijk pas veel later.
Dit verklaart ook deels het succes van agile, kort-iteratieve projecten.
De details (analyse en ontwerp) van een requirement worden pas
bepaald zodra deze tijdens een van de iteraties daadwerkelijk wordt
gebouwd. Zo wordt voorkomen dat er vroeg in een project veel werk
in requirements wordt gestoken die nooit worden gerealiseerd, zoals
in watervalprojecten nog wel eens het geval is. En bovendien, wanneer
de details bijvoorbeeld pas na een half jaar worden onderzocht, is het
voortschrijdend inzicht van dat half jaar automatisch geborgd. Om in
de metafoor te blijven, zo zijn requirements altijd vers.
Ik benieuwd overigens wat de uiterste houdbaarheidsdatum van deze
column zal blijken te zijn. •
46
MAGAZINE
DOT
NET
NUKE
Charles Nurse
DotNetNuke
supports Razor
On January 13th at CodeMash in Sandusky, Ohio, Microsoft introduced Razor - a new
lightweight syntax for developing WebPages as part of its WebMatrix offering. In a separate
article in this issue, Andrew Nurse, one of the developers who created Razor describes the
motivations behind this new syntax and an overview of the syntax itself. In this article I will focus
on how you can use Razor scripts in DotNetNuke 5.6.1.
The Razor Host Module
In addition to the new bits that are available as part of the WebMatrix
suite, the Razor parser and the new WebPages Framework requires
ASP.NET 4.0. As we still wish to retain compatibility with ASP.NET 3.5
we cannot directly integrate support for Razor scripts into the
DotNetNuke core, as this will force all of our users to upgrade to
ASP.NET 4.0.
Therefore, our approach to providing support for Razor scripts is to
provide a “Razor Host” module. If DotNetNuke users wish to use
Razor scripts as part of their sites, they will need to install this module.
A Beta of this module has been available since early December and
was used as the basis for the recent Hackathon contest. However,
DotNetNuke 5.6.1 will contain an initial release of the Razor Host
module.
Adding the Razor Host Module to a Page
An instance of this module can be added to a DotNetNuke page in the
usual way (see Figure 1).
The resulting module looks pretty sparse (see Figure 2). The body of
the module does not display anything - as no script is selected - and
there is only a single Action – Edit Script - which allows Host users to
create and edit scripts.
Fig. 2: The Razor Host Module on a page
Only Host Users can Create or Edit
Razor Scripts
It is very important to note that the only users who will see the “Edit
Script” Action button or menu item are Host (or Super) Users. This is
because you can do anything in Razor script, so only users with the
highest level of access should be able to create Razor scripts.
Configuring the Razor Host Module
As with most modules in DotNetNuke the Razor Host module does
have settings - actually a single setting - the ability to select a previously created Razor script (see Figure 3).
Fig. 1: Adding an instance of the Razor Host module to a page
Fig. 3: Setting the Razor Script to use
magazine voor software development 47
DOT
NET
NUKE
While editing and creating scripts can only be done by a Host User,
any user with Edit permissions can select an existing script.
In the example shown in Figure 3, selecting the PageInfo.cshtml script
will result in the module displaying the content shown in Figure 4.
The Text Area does not provide any Syntax Highlighting (or Syntax
checking). But if you want some “Syntax Highlighting” you can use
the WebMatrix IDE to modify the script files (Figure 6) or even Visual
Studio 2010.
Note that in the WebMatrix IDE the C# code has a different highlighting
than the HTML.
Hosting the Razor Engine
So far we have seen how we can use the Razor Host Module, but
how is this achieved?
Razor can actually be thought of as a templating engine and if you are
planning on building a module that requires templates you might want
to consider Razor. So, by describing how we host the Razor Engine
hopefully I will be able show how you might do that.
Fig. 4: The Rendered Razor Script
Creating and Editing Razor Scripts
So selecting a previously created script is fairly easy, but how can we
edit or create scripts. When logged in as a Host user, selecting the
previously described “Edit Script” Action will bring up the “Edit Script”
control (Figure 5).
The WebPage Class
The WebPage Class (actually WebPageBase) is the basis of the new
WebPages Framework, in the same way that the “Page” class is the
basis of the WebForms Framework.
Essentially the approach we use in our “Razor Host” module is as
follows.
1. Identify the Razor script file (e.g. Twitter.cshtml)
2. Call BuildManager.GetType(scriptFile) to create an instance of
WebPage. Note that the System.Web.WebPages assembly
contains a special class - PreApplicationStartCode - that ensures
that the extensions cshtml and vbhtml are registered with the
BuildManager
3. Call the ExecutePageHierarchy method of the WebPage class and
capture the rendered content.
4. Create a LiteralControl with the rendered content and add it to the
control tree.
In order to achieve this there are two new classes in a new assembly
(DotNetNuke.Web.Razor.dll) which is distributed as part of the “Razor
Host” Module.
Fig. 5: Editing a Razor Script using the Edit Script control
This control allows you to:
• Add a new Script File
• Choose a Script file to Edit
• Modify the Script source in the Text Area
• Set the current Script to be the Active Script (Is Active) - as an
alternative to choosing the “Active” script in the Module Settings
• Save the Modified Script.
The script files are all stored in the “Scripts” sub-folder.
1. RazorModuleBase – this class implements IModuleControl by
sub-classing ModuleUserControlBase
2. DotNetNukeWebPage – this class subclasses WebPageBase and
provides some DNN specific enhancements.
The RazorModuleBase Class
The RazorModuleBase class is where everything comes together. All
DNN Modules need to implement the IModuleControl Interface - this
is how the module injection logic knows what to inject. RazorModuleBase is a new base class that implements IModuleControl and is used
as the base class for the Razor Host Module.
In the OnPreRender method of the class we first check if our script RazorScriptFile - exists. If it does we call the CreateWebPageInstance
method to get an instance of the DotNetNukeWebPage.
Protected Overrides Sub OnPreRender(ByVal e As System.EventArgs)
MyBase.OnPreRender(e)
Try
If File.Exists(Server.MapPath(RazorScriptFile)) Then
Dim instance As Object = CreateWebPageInstance()
If instance Is Nothing Then
Throw New InvalidOperationException( _
String.Format( _
Fig. 6: Editing a Razor Script using the WebMatrix IDE
48
MAGAZINE
CultureInfo.CurrentCulture, _
DOT
NET
NUKE
"The webpage found at '{0}' was not created.", _
RazorScriptFile))
End If
Private Function CreateWebPageInstance() As Object
Dim type As Type = BuildManager.GetCompiledType(RazorScriptFile)
Dim instance As Object = Nothing
Dim webPage As DotNetNukeWebPage =
TryCast(instance, DotNetNukeWebPage)
If type IsNot Nothing Then
instance = Activator.CreateInstance(type)
End If
If webPage Is Nothing Then
Throw New InvalidOperationException( _
String.Format( _
Return instance
End Function
CultureInfo.CurrentCulture,
"The webpage at '{0}' must derive from
Listing 3: The CreateWebPageInstance method
DotNetNukeWebPage.",
RazorScriptFile))
End If
Earlier in this article I mentioned that BuildManager knew to “build” a
WebPage instance from a cshtml or vbhtml because of some code
that exists in the WebPages Framework that registers the extension.
webPage.SetContext(Me.ModuleContext)
InitHelpers(webPage)
Dim writer As New StringWriter
webPage.ExecutePageHierarchy(
New WebPageContext(HttpContext), writer, webPage)
Controls.Add(
New LiteralControl(Server.HtmlDecode
So why do we get an instance of DotNetNukeWebPage rather than an
instance of WebPage?
The answer lies in the included web.config file (Listing 4) that sits in the
same folder as the Razor Host Module. By default the Razor Engine
will return an instance of WebPage, but this can be modified in the
new system.web.webPages.razor section of web.config, where we
have indicated that an instance of DotNetNukeWebPage should be
returned.
(writer.ToString())))
End If
Catch ex As Exception
ProcessModuleLoadException(Me, ex)
End Try
<system.web.webPages.razor>
<pages pageBaseType="DotNetNuke.Web.Razor.DotNetNukeWebPage">
<namespaces>
<add namespace="Microsoft.Web.Helpers" />
<add namespace="WebMatrix.Data" />
End Sub
</namespaces>
</pages>
Listing 1: The OnPreRender method of the RazorModuleBase class
We then set the WebPage’s module context by calling its SetContext
method. This allows us to access the ModuleContext in Razor script.
Finally we call the WebPage’s ExecutePageHierarchy method to get
the rendered content, which we add as a LiteralControl to the Controls
collection of the module.
In the above description I glossed over two important points: the
RazorScriptFile property and the CreateWebPageInstance property.
The RazorScriptFile Property
The RazorScriptFile property (Listing 2) returns the virtual path of a
“default” script file. In the Razor Host module, we override this
property and return the currently selected script, but the default
behaviour in the base class is to return “MyScript.cshtml” if the current
control is “MyScript.ascx”.
Protected Overridable ReadOnly Property RazorScriptFile As String
Get
Return Me.AppRelativeVirtualPath.Replace("ascx", "cshtml")
End Get
End Property
Listing 2: The RazorScriptFile property
The CreateWebPageInstance Method
The CreateWebPageInstance method (Listing 3) uses the RazorScriptFile property to create an instance of a DotNetNukeWebPage
(Listing 3), calling BuildManager.GetCompiledType, which returns a
Type and then calling Activator.CreateInstance to return an instance of
the DotNetNukeWebPage.
</system.web.webPages.razor>
Listing 4: The Razor Host Module’s web.config file
Conclusion
Razor is an exciting addition to our list of technologies that we can
use to create dynamic webistes. By hosting the Razor Engine in
DotNetnuke, the Razor Host Module can be used to host Razor scripts
in DotNetNuke 5.6.1.
Take the opportunity to investigate Razor by installing the Razor Host
Module and play with the included script files – or goto the DotNetNuke site (www.dotnetnuke.com) and download one of the Razor
Hackathon entries. •
Charles Nurse
Since 2006 he has been Senior Architect for DotNetNuke Corporation
the creators of the DotNetNuke
Open Source Web Application Platform. Charles has been working
with the .NET Framework since its
first release, specializing in Web Applications using ASP.NET and he is
a Microsoft MVP and an ASPInsider.
He has spoken at many major conferences including the Software Developers Conference (SDC) (www.sdc.nl), DevConnections
(www.devconnections.com), DevTeach (www.devteach.com)
and Microsoft Tech Days, and he is a frequent speaker at local
User Groups and Code Camps.
magazine voor software development 49
GENERAL
Joachim Nilsson
Reflection loops of Agile
The agile way of working has now come upon us with full strength; some projects with poor
results and others with excellent results. Since the agile way includes elements of selfimprovement, any poor results should soon become good ones and finally excellent ones.
As a Software Engineer, I really like this way to work since it provides me with some great tools.
In the pre-agile world, I could sometimes feel that I and my team at
times would drift away from the solution we were supposed to create.
The time to market is putting pressure on the deliveries, and a
complex technological surrounding forced us to work in a speed that
left no time to correct bad input values in requirements. When
thinking about this I also came to an insight that the agile practices that
I have selected to work with, gives me a scheduled time to reflect.
Reflection loop 1: Self
Start by looking at Test Driven Development or TDD. When we
implement this in both unit testing and automated functional testing,
the practice will force us to reflect on and validate the requirements as
a first step. So before starting to write a single line of code, we make
sure that our requirements are testable since otherwise we cannot
write our automated tests for the feature. The reflection is done by the
test writer him- or herself and is done within a very short time frame.
assumptions and limitations that need to be handled? The one thing
I want to improve on is to hold demos more often, for any type of
change that can be demonstrated:
• Test cases - to verify with stakeholders that the requirements are
interpreted correctly.
• Architectural changes – to make our surrounding teams understand
how the latest code works.
• Working code – the normal demonstration
Reflection loop 5: Retrospective
We hold our retrospective once a sprint as normal. And this is the best
practice of all because it allows our team to constantly improve in a
pace that fits us. It also provides feedback and learning to the department in terms of how we can make all teams work more efficient.
Reflection loop 2: The pair
Pair programming is my next selected practice. It is seldom implemented to 100% since it appears to cut the production speed in half.
And that is true!
It is true - if all developers
• …never write any poorly designed code
• …never introduce any bugs
• …and always are up to date with the architecture of the rest of the
development department.
If you have this situation in your teams: Congratulations!
When pair programming actually is done, it will give the benefit of
forcing the developer to reflect on the design and solution of the
problem. If the design is incorrect or the solution seems unclear,
the navigator or co-pilot will interrupt with a question. In order to
answer, the developer must of course have a clear thought of the
solution or think about it for a while. The reflection is done together with
the team mate and perhaps a few times during the day.
Reflection loop 3: Stand-up meeting
When I look at the stand-up meeting with reflection in mind, I see that
in order to get the reflective mindset in the team it is best if my team
members are all focused on the same task. When they have different
tasks, the interest between the team members decreases and I end
up with sub tasks being forgotten or issues being missed. Done
properly, with same goal in mind and with an attitude to help each
other, I find that reflection is done in the whole team.
Reflection loop 4: Demonstration
When we do demonstrations from our team, we invite the product
owners, the architects and the other teams that work in our product.
It is an excellent way to get feedback on the completed task. Can we
consider it done or not. Are there any issues that have arisen from our
50
MAGAZINE
Summary
To summarize, I find that the practices I have chosen to follow will allow
me and my team to reflect in a number of ways, starting from the
smallest feedback loop up to the largest.
This is also a lesson that I think is worth sharing, to find reasons
behind the agile practices that you choose to follow. Reasons are of
course several, but bring them up to discussion within your own team
and see that it will be a lot easier to follow practices since there is a
common understanding of why you do the things you do. •
Joachim Nilsson
Joachim Nilsson is a consultant at
Capgemini, Sweden. He has a
M.Sc. in computer sciences from
Lund institute of Technology and
has been working in different roles
of software development during the
last 16 years.
0HOGXQXDDQRS
'HY'D\VQO
.RPQDDU'HY'D\V
'HY'D\VLVKpWJURRWVWH0LFURVRIWHYHQWLQ
1HGHUODQGYRRUVRIWZDUHGHYHORSPHQWHQ
VRIWZDUHDUFKLWHFWXXU/DDWXLQVSLUHUHQ
HQVFKULMIXLQYRRU'HY'D\V
'RQGHUGDJHQYULMGDJ
HQDSULO
:RUOG)RUXPLQ'HQ+DDJ
7RSVSUHNHUV'HY'D\V
0LOHV0LNH
9LWRUULR%HU WRFFL5RE
E%HDXFKHPLQ
7DXOW\%ULDQ.HOOHU%R
VWHU,QJR5DPPHU
9D
V
HQ
P
OH
&
VL
DV
0
WK
%H
URVLVHHQQRJ
&KULVWLDQ:HLMHU-HVV3
V
YHOHDQGHUHWRSVSUHNHU
O
3UHFRQIHUHQFHVHVVLHVRSDSUL
PELQHHUG
$]XUH²LQGHSWKWUDLQLQJGDJJHFR
LQJHHQ
VWUDLQ
LGLQJ
UEHUH
PHWHHQRQOLQHYRR
QEHSHUNW
HQR
GDJ
Q
DVVH
GDDJVH$]XUHS
JHQ
DLQLQ
QHWU
RQOL
VLJKW
WRHJDQJWRW3OXUDO
RS²
:LQGRZV3KRQH²KDQGVRQZRUNVK
QH
ERXZMHHHUVWH$SSYRRU:LQGRZV3KR
ODFH
UNHWS
HQPDDNGH]HEHVFKLNEDDULQGHPD
%HODQJULMNHRQGHUZHUSHQ
‡ &ORXGGHYHORSPHQWPHW:LQGRZV$]XUH
‡ :LQGRZV3KRQHGHYHORSPHQW
‡ :HEGHYHORSPHQWPHWRD09&5D]RU
5HVW2'DWD$631(76LOYHUOLJKWHQ+70/
‡ $OOHVRYHU9LVXDO6WXGLRPHWRD/LJKW6ZLWFK
,QWHOOLWUDFH7)6HQ]
‡ 7HYHQVGLYHUVHVHVVLHVRYHU1(7)UDPHZRUN
6KDUH3RLQWGHYHORSPHQWHQ64/
'D\VQO
0HOGXQXDDQRS'HY
Wat
W
at doe jij vvolgende
olgende maand?
::ŝũďŽƵǁƚĚĞŶŝĞƵǁĞǁĞďĂƉƉůŝĐĂƟĞǀŽŽƌĠĠŶǀĂŶĚĞƚŽƉĚƌŝĞǀĞƌnjĞŬĞƌĂĂƌƐŝŶEĞĚĞƌůĂŶĚ͕
ŝũďŽƵǁƚĚĞŶŝĞƵǁĞǁĞďĂƉƉůŝĐĂƟĞǀŽŽƌĠĠŶǀĂŶĚĞƚŽƉĚƌŝĞǀĞƌnjĞŬĞƌĂĂƌƐŝŶEĞĚĞƌůĂŶĚ͕
ǁĂĂƌŵĞĞŵĞŶƐĞŶƐŶĞůĞŶĞĞŶǀŽƵĚŝŐŽŶůŝŶĞŚƵŶǀĞƌnjĞŬĞƌŝŶŐĞŶŬƵŶŶĞŶĂĨƐůƵŝƚĞŶ͕ŝŶnjŝĞŶ
ǁ
ĂĂƌŵĞĞŵĞŶƐĞŶƐŶĞůĞŶĞĞŶǀŽƵĚŝŐŽŶůŝŶĞŚƵŶǀĞƌnjĞŬĞƌŝŶŐĞŶŬƵŶŶĞŶĂĨƐůƵŝƚĞŶ͕ŝŶnjŝĞŶ
ĞĞŶďĞŚĞƌĞŶ͘:ĞnjĞƚũŽƵǁĐƌĞĂƟĞǀĞŝĚĞĞģŶŽŵŝŶƐůŝŵŵĞĐŽĚĞĞŶŐĞďƌƵŝŬƚĚĞŶŝĞƵǁƐƚĞ
ŶďĞŚĞƌĞŶ͘:ĞnjĞƚũŽƵǁĐƌĞĂƟĞǀĞŝĚĞĞģŶŽŵŝŶƐůŝŵŵĞĐŽĚĞĞŶŐĞďƌƵŝŬƚĚĞŶŝĞƵǁƐƚĞ
͘͘EdƚĞĐŚŶŽůŽŐŝĞŽŵĨƌŽŶƚͲĞŶĚƐƚĞŵĂŬĞŶŵĞƚĚĞďĞƐƚĞŬŽƉƉĞůŝŶŐĞŶŶĂĂƌďĂĐŬŽĸĐĞĞŶ
EdƚĞĐŚŶŽůŽŐŝĞŽŵĨƌŽŶƚͲĞŶĚƐ ď
ďĞƚĂĂůƐLJƐƚĞŵĞŶǀĂŶĚĞŬůĂŶƚ͘
ĞƚĂĂůƐLJƐƚĞŵĞŶǀĂŶĚĞŬůĂŶƚ͘
:ŝũďĞŶƚŶĂŵĞůŝũŬĞĞŶƐƉĞĐŝĂůŝƐƚĚŝĞǁĞůƌĂĂĚǁĞĞƚŵĞƚ^W͘Ed͕η͘Ed͕^ŚĂƌĞWŽŝŶƚĞŶ^Y>͘
:ŝũďĞŶƚŶĂŵĞůŝũŬĞĞŶƐƉĞĐŝĂůŝƐƚĚ //ĞŵĂŶĚĚŝĞĂůƟũĚŽƉnjŽĞŬŝƐŶĂĂƌŶŝĞƵǁĞŬĞŶŶŝƐĞŶĂůƐĞĞƌƐƚĞŵĞƚĚĞƚĞĐŚŶŽůŽŐŝĞǀĂŶŵŽƌŐĞŶ
ĞŵĂŶĚĚŝĞĂůƟũĚŽƉnjŽĞŬŝƐŶĂĂ ǁŝůǁĞƌŬĞŶ͕ŵĂĂƌŽŽŬŝĞŵĂŶĚĚŝĞŐĞŶŝĞƚǀĂŶŚĞƚƐƵĐĐĞƐĚĂƚĚĞŬůĂŶƚǀĂŶĚĂĂŐďŽĞŬƚŵĞƚũŽƵǁ
ǁ
ŝůǁĞƌŬĞŶ͕ŵĂĂƌŽŽŬŝĞŵĂŶĚĚ ŝŝŶŶŽǀĂƟĞǀĞŽƉůŽƐƐŝŶŐĞŶ͘
ŶŶŽǀĂƟĞǀĞŽƉůŽƐƐŝŶŐĞŶ͘
::ŝũĚĞĞůƚŐƌĂĂŐũĞǀŝƐŝĞĞŶŬĞŶŶŝƐŵĞƚũĞŽŵŐĞǀŝŶŐ͕njŽǁĞůĨLJƐŝĞŬĂůƐŽŶůŝŶĞ͕ĞŶǁĞƌŬƚƐĂŵĞŶ
ŝũĚĞĞůƚŐƌĂĂŐũĞǀŝƐŝĞĞŶŬĞŶŶŝƐ
ŵĞƚĂŶĚĞƌĞĞǀĞůŽƉĞƌƐ͕ĞƐŝŐŶĞƌƐ͕ƌĐŚŝƚĞĐƚĞŶĞŶŶĂůŝƐƚĞŶĂĂŶĚĞďĞƐƚĞŽƉůŽƐƐŝŶŐĞŶǀŽŽƌ
ŵ
ĞƚĂŶĚĞƌĞĞǀĞůŽƉĞƌƐ͕ĞƐŝŐŶ ĚĞŬůĂŶƚ͘:ĞǁĞĞƚŚŽĞũĞǁĞƌŬĞŶƉƌŝǀĠǀůĞŬŬĞůŽŽƐŬƵŶƚĐŽŵďŝŶĞƌĞŶĞŶŽŶĂĬĂŶŬĞůŝũŬǀĂŶƟũĚ
Ě
ĞŬůĂŶƚ͘:ĞǁĞĞƚŚŽĞũĞǁĞƌŬĞŶ
ĞĞŶƉůĂĂƚƐĚĞŽƉƟŵĂůĞďŝũĚƌĂŐĞůĞǀĞƌƚĂĂŶũĞƚĞĂŵ͘
ŶƉůĂĂƚƐĚĞŽƉƟŵĂůĞďŝũĚƌĂŐĞů
Volgende
Volgende
de maand werk
w
jij bij Macaw.
.NET Developer
D
DĂĐĂǁŝƐEĞĚĞƌůĂŶĚƐŐƌŽŽƚƐƚĞ͕ƵŝƚƐůƵŝƚĞŶĚŝŶDŝĐƌŽƐŽŌƚĞĐŚŶŽůŽŐŝĞŐĞƐƉĞĐŝĂůŝƐĞĞƌĚĞ͕/dĚŝĞŶƐƚǀĞƌůĞŶĞƌ͘KŶnjĞŬĞŶŶŝƐ
ĂĐĂǁŝƐEĞĚĞƌůĂŶĚƐŐƌŽŽƚƐƚĞ͕ƵŝƚƐůƵŝƚĞŶĚŝŶDŝĐƌŽƐŽŌƚĞĐŚŶŽůŽŐŝĞŐĞƐƉĞĐŝĂůŝƐĞĞƌĚĞ͕/dĚŝĞŶƐƚǀĞƌůĞŶĞƌ͘͘KŶnjĞŬĞŶŶŝƐ
ŝŝƐŐĞďƵŶĚĞůĚŝŶǀŝĞƌ^ŽůƵƟŽŶĞŶƚĞƌƐĚŝĞnjŝĐŚƌŝĐŚƚĞŶŽƉŚĞƚƌĞĂůŝƐĞƌĞŶǀĂŶĐŽůůĂďŽƌĂƟĞǀĞƉŽƌƚĂůĞŶ͕DƐLJƐƚĞŵĞŶ͕
ƐŐĞďƵŶĚĞůĚŝŶǀŝĞƌ^ŽůƵƟŽŶĞŶƚĞƌƐĚŝĞnjŝĐŚƌŝĐŚƚĞŶŽƉŚĞƚƌĞĂůŝƐĞƌĞŶǀĂŶĐŽůůĂďŽƌĂƟĞǀĞƉŽƌƚĂůĞŶ͕DƐLJƐƚĞŵĞŶ͕
ŝŶƚĞƌŶĞƚĞŶĐŽŵŵĞƌĐĞƐŝƚĞƐ͕ďƵƐŝŶĞƐƐƐŽůƵƟŽŶƐ͕ZDƐLJƐƚĞŵĞŶĞŶĂƉƉůŝĐĂƟĞďĞŚĞĞƌĞŶŚŽƐƟŶŐĚŝĞŶƐƚĞŶ͘
ŝŶƚĞƌŶĞƚĞŶĐŽŵŵĞƌĐĞƐŝƚĞƐ͕ďƵƐŝŶĞƐƐƐŽůƵƟŽŶƐ͕ZDƐLJƐƚĞŵĞŶĞŶĂƉƉůŝĐĂƟĞďĞŚĞĞƌĞŶŚŽƐƟŶŐĚŝĞŶƐƚĞŶ͘
ĞnjŽĞŬǀŽŽƌŵĞĞƌŝŶĨŽƌŵĂƟĞŽǀĞƌĚĞnjĞĞŶĂŶĚĞƌĞǀĂĐĂƚƵƌĞƐŽŶnjĞǁĞďƐŝƚĞwww.echtleukwerk.nlŽĨŶĞĞŵĐŽŶƚĂĐƚŽƉ
ĞnjŽĞŬǀŽŽƌŵĞĞƌŝŶĨŽƌŵĂƟĞŽǀĞƌĚĞnjĞĞŶĂŶĚĞƌĞǀĂĐĂƚƵƌĞƐŽŶnjĞǁĞďƐŝƚĞwww.echtleukwerk.nlŽĨŶĞĞŵĐŽŶƚĂĐƚŽƉ
ŵ
ŵĞƚŽŶnjĞĂĨĚĞůŝŶŐZĞĐƌƵŝƚŵĞŶƚǀŝĂϬϮϬͲϴϱϭϬϱϭϬŽĨrecruitment@macaw.nl͘
ĞƚŽŶnjĞĂĨĚĞůŝŶŐZĞĐƌƵŝƚŵĞŶƚǀŝĂϬϮϬͲϴϱϭϬϱϭϬŽĨrecruitment@macaw
w.nl͘