<?xml version="1.0" encoding="UTF-8"?>
<posts type="array">
  <post>
    <body>Jeg vil igang med at lave en &quot;Cross Domain Mashup&quot;:http://www.frankvilhelmsen.com applikation der asynkront kan hente data fra forskellige domains. Min klient er i HTML5, CSS3 og naturligvis Javascript. Protokollen er HTTP, kommunikation er asynchronous og indholdet skal v&#230;re JSON fordi det allerede er Javascript, kompakt og ikke beh&#248;ver parsing af nogen art. JSON skal pakkes ind JSONP for at overvinde Same Origin Policy sikkerheds modellen.

Flickr 

Flickr er en fantastisk ressource til at pr&#230;sentere og administrere billeder. De udstiller ogs&#229; en stribe API'er til mange forskellige ting. Jeg har kun interesser for &quot;REST API'et&quot;:http://www.flickr.com/services/api


Den pr&#230;cise URI jeg vil bruge er til min egen foto feed p&#229; flickr. Det er v&#230;rd at bem&#230;rke de sidste parameter i URI'en &quot;format=json&amp;jsoncallback=?&quot;. Disse paramter fort&#230;ller resourcen at response skal v&#230;re i formattet JSON og at kaldet m&#229;ske er Cross Browser og derfor skal JSON pakkes ind som et JSONP kald. Ydermere kan man specificere et callback navn &quot;joncallback=?&quot; ved sp&#248;rgsm&#229;lstegnet hvis man vil have en bestemt metode kaldt n&#229;r script er loadet.

| URI | JSONP |
| &amp;format=json | jsonFlickrFeed({ &quot;title&quot;:&quot;Uploads&quot; }) |
| &amp;format=json&amp;jsoncallback=? |  ({ &quot;title&quot;: &quot;Uploads&quot;}) |
| &amp;format=json&amp;jsoncallback=visfoto | visfotos({ &quot;title&quot;: &quot;Uploads&quot;}) |

Det kan betale sig at unders&#248;ge data grundigt inden man g&#229;r igang med at skrive klienten. Hvis man kan operere/navigere med curl -i URI gennem de &#248;nskede scenarie er man langt. 


Nu klienten. 

&lt;pre&gt;
  $(document).ready(function(){
    $.getJSON(&quot;http://api.flickr.com/services/feeds/photos_public.gne?id=7185299@N07&amp;format=json&amp;jsoncallback=?&quot;,
        function(data){
          $.each(data.items, function(i,item){
            $(&quot;&lt;img/&gt;&quot;).attr(&quot;src&quot;, item.media.m).appendTo(&quot;#images&quot;);
            if ( i == 8 ) return false;
          });
        });
  });
&lt;/pre&gt;

Flickr ressourcen bliver ramt gennem Jquery og henter data. Der itereres gennem data der indeholder title, link til foto location, hvorn&#229;r det er taget og en masse andet. Elementet item.media er en server location men der f&#248;lger et m med som fort&#230;ller noget om de st&#248;rrelse og repr&#230;sentationer som billedet allerede er skaleret til. Pr&#248;v fx at skifte m ud med et s. 

Nu til den n&#230;sten klient app som er twitter updates. Koden herunder henter et antal twitter status update og iterere gennem hver update. Undervejs ledes efter regul&#230;re udtryk der minder om et link tag og hvis udskiftes med et rigtig html link anker. Hver update bliver adderet til hash# div tag. Det er muligt at bruge this[array] til at hente data ud af strukturen. 

L&#230;g ogs&#229; m&#230;rke til at twitter vil have en count parameter med ind for at minimere antal updates over linjen. Bem&#230;rk ogs&#229; at er mere REST aware i det de udnytter HTTP header information om den returnerede repr&#230;sentation og caching TTL i netv&#230;rket. De udnytter infrastrukturen bedre end flickr.  

&lt;pre&gt;
  var regexp = /((ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&amp;%@!\-\/]))?)/gi; 
  $(document).ready(function(){
    $.getJSON(&quot;http://twitter.com/statuses/user_timeline/frankvilhelmsen.json?count=6&amp;callback=?&quot;,
      function(data, textStatus) {
        $.each(data, function(i) {
          var twitter_time = prettyDate(this['created_at'])
          var twitter_uri_encoded_text = this['text'].replace(regexp,'&lt;a href=&quot;$1&quot;&gt;$1&lt;/a&gt;') 
          $(&quot;#statuses&quot;).append(&quot;&lt;li&gt;&quot;+twitter_time+&quot;: &quot;+twitter_uri_encoded_text+&quot;&lt;/li&gt;&quot;);
        });
    });
  });
&lt;/pre&gt;



Server

Indtil nu har jeg kun forbrugt ressource hvor jeg kun kender interfacet men jeg vil jo ogs&#229; gerne udstille mine egne REST baseret Cloud ressourcer. Heldigvis underst&#248;tte rubyonrails dette lige ud af boxen. Min platform er &quot;Heroku | Ruby Cloud, Platform as a Service&quot;:http://heroku.com git og Rails. DNS og alt er sat op. 

&lt;pre&gt;
  p = Post.find(:all, :select =&gt; 'id, title, osv') 
  response_to 
    ...
    format.json {render :json =&gt; @posts, :callback =&gt; [:callback] }
  end 
&lt;/pre&gt;

Det eneste jeg skal g&#248;re for at enable en ressource til cross browser er tilf&#248;je denne &quot;:callback =&gt; [:callback]&quot;. 

Rails har alts&#229; dekoreret JSON til JSONP format uden at jeg beh&#248;ver at g&#248;re mere. Men m&#229;ske ville jeg reagere anderledes p&#229; &#248;nsket om at give parameter som denne med i requestet &quot;&amp;callback=chanceheader&quot;. Direkte til klienten. Og nu er det nemt for koden er n&#230;sen det samme som f&#248;r. 

&lt;pre&gt;
  $(document).ready(function(){
    $.getJSON(&quot;http://XXX/posts/title/all?format=json&amp;callback=?&quot;,
      function(data){
        $.each(data, function(i) {
        $(&quot;#titles&quot;).append(&quot;&lt;li&gt;&quot;+this.post.id+&quot; - &quot; +this.post.title+&quot;&lt;/li&gt;&quot;)
     });
  });
});
&lt;/pre&gt;

 
</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2010-01-22T11:49:10Z</created-at>
    <id type="integer">157</id>
    <published type="boolean">true</published>
    <title>Cross Domain JSONP on Rails</title>
    <updated-at type="datetime">2010-01-22T14:32:11Z</updated-at>
  </post>
  <post>
    <body>For at forst&#229; v&#230;rdien og forholdet mellem virksomhedens SOA l&#248;sninger og mashups er det nyttigt f&#248;rst at forst&#229; hvorfor vi i det hele taget har brug for mashups!

* mashups give dig hurtigere svar
* mashups forbedre din ressourceforbrug (af b&#229;de personale og bl&#248;de/h&#229;rde computing ressourcer)
* mashups hj&#230;lpe dig med at tage fat p&#229; nye forretningsmuligheder ved at lade brugerne sammens&#230;tte data i en opportunistisk m&#229;de

For en SOA enable virksomhed ligger det lige for at bygge og udstille et mashup lag mellem den interne SOA arkitektur og deres kunder. Det vil indkapsle de meget forretnings orienterede services og udstille et klient venligt allotment data lag. Det er for&#248;rigt en god m&#229;de at holde sine klient publicerede interfaces konstante mens den interne SOA protokol sikkert udkommer i flere nye versioner. 

Set i forhold til SOA og alle de komplekse &quot;Entreprise&quot; l&#248;sninger er mashup mere:

* Collaborative. Mashups er designet til at blive m&#230;rket/s&#248;gba/deles med andre. 
* Focused on 'pack'. Mashups er typisk skabt et lille antal selekterede besl&#230;gtede individer. 
* Tidsf&#248;lsomme. Brugernes behov for data er nu. Mashups har normalt n&#230;r real-time levering krav. WWW er real-time. 
* Noninvasive. Der skal ikke indf&#248;res ny infrastruktur eller faglige forbindelser. 
* Limited cleansing. M&#230;ngden af data og behov normalisering b&#248;r sammenlignes med st&#248;rrelsen at et Excel ark. 
* Have a face. Mashups har normalt et ansigt som en widget. 

Mashup applikationer eller mashup widgets lever godt med et SOA endpoint som backend og vil betrakte SOA akitekturen som en service cloud. 

Det vil hj&#230;lpe med til at fragmentere infrastrukturen p&#229; en mere hensynsfuld m&#229;de fremfor at SOA l&#248;sningen b&#229;de skal sig af tunge forretningsm&#230;ssige ting og samtidig henvender direkte til enkelte kunder. Det er her mashup kommer ind i billedet. Et mashup kan bidrage til at skabe en ny, dynamisk, og potentielt stor gruppe af forbrugere til dine tjenester. Og det er derfor en SOA-arkitekt skal bekymre sig om mashups: Mashups kan blive en uvurderlig direkte sammenh&#230;ng mellem en SOA og erhvervslivet i en organisation.

Der findes flere typer af mashups eller arkitektoniske stilarter. Normalt kan man kalde en webside for en mashup n&#229;r den benytter data og funktionalitet fra mere end den server hvor den kommer fra. Ofte vil der ogs&#229; v&#230;re langt mellem de adr&#230;tte kunde relaterede projekter og de afdelinger som skaber services. 

# Klient Mashup er den mest almindelige stil og den er m&#229;lrettet til at eksisterer hos klienten i form af HTML/CSS og Javascript. En fordel er at man delegere datafangst til ud til klienten dermed v&#230;k fra serveren. 
# Data Mashup er mindre kendt idet den kombinere samme type af media og information fra flere forskellige kilder i en enkelt repr&#230;sentation. Denne stil er server-baseret og samler interne og eksterne data til en enkel ny repr&#230;sentation. 
# Enterprise Mashup er i fremgang og fokuser p&#229; at repr&#230;sentere forskelligformede data i en mere enkelt form og fordeler dermed arbejde mellem forretningen, udvikling og ikke mindst hardware. Denne type virker specielt godt i forbindelse med sande adr&#230;tte udviklingsafdelinger der hvor krav til &quot;time to market&quot; og iterativ udviklings proces er et issue. Enterprise Mashups er sikre, visuelle rige web applikationer der eksponere handlingsrettede information fra diverse eksterne og interne informationskilder. 

Mashups synes at v&#230;re en variation af et Design Pattern Facade. En forskel er dog at snitflade/interfacet mellem de enkelte systemdele er mere tydelig og afgr&#230;nsede. Facade pattern er en interproces kommunikation mens mashups er fysiske adskilte gr&#230;nsefladesnit over HTTP. 

Mashups kan med fordel bruges med software as a service(SaaS). Mange mainstream virksomheder kan drage fordel ved brug af mashups til at forenkle deres integration mod interne og eksterne serviceorienterede arkitekturer(SOA) ved at g&#248;re dem tilg&#230;ngelige til mashups. Med standardiserede protokoller skabes en ensartet metode til at f&#229; adgang til oplysninger udfra et bredt s&#230;t af platforme, operativsystemer, programmeringssprog og applikationer. Selv disse kan igen genbruges til at levere helt nye tjenester og applikationer p&#229; tv&#230;rs af organisationer. Det giver virksomhederne fleksibilitet. se OIORest. 

Mashups er velegnet til at skabe rige applikationer med stor udnyttelse af klient tilstand eller state i form af &quot;hateoas&quot;(Hypermedia As the Engine of Application State). Fordi mashup fordre mere tilstand v&#230;k fra serveren opn&#229;s mange fordele. En server med stateless tilstand er en billig server. Man beh&#248;ver ikke replikere tilstand i server farmen. Hvis det er ligemeget hvilken server man rammer er det muligt at skabe skalerbare l&#248;sninger billigt. 

Javascript kan kun kalde den server hvorfra den kommer. Denne sikkerhedsmodel hedder Same Origin Policy(SOP). Hvis javascript kunne kalde servere med ondsindet program stumper kunne man lave &quot;Man-in-the-middle&quot; angrep mellem bank og kunde. Dette er meget komplekse problemstillerer men for specielle applikationer kan man kontrollere denne trafik. Man kan overvinde SOP ved at inds&#230;tte et dynamisk scriptelement i websiden 

Moderne browsere underst&#248;tter kommunikation mellem klient og server og er den vigtigste bestanddel af nye s&#229;kaldte Web 2.0 applikationer. Data hentes uden er reloade websiden ved hj&#230;lp af XMLHttpRequest objektet der lader Javascript etablere HTTP-forbindelser til en ekstern server. Denne form for kommunikation er basen i mashups. 

Resultatet af en asynkront kald fra en browser er data i JSONP format. Mashups bruger JSONP til at lave et lille trick p&#229; klienten s&#229; koden kan kalde tredieparts services uden om SOP. Som regel vil man gerne have overf&#248;rt data i JSON format fordi JSON er valid Javascript pakket ind JSONP formatet. JSONP har en pr&#230;fiks der angiver input som argument for data selv. Navnet p&#229; dette pr&#230;fiks er typisk en javascript callback funktion men det kan ogs&#229; v&#230;re en variabel. JSONP g&#248;r brug af script-tags og dette &#229;bner verden. 

Mashups kan publicere en m&#230;ngde forskellige Web syndication formater som RSS og Atom, REST og SOAP, WSRP kompatibel, blogs, Atoms til mobiltelefon. Netop fordi mashups kan blive eksponeret som REST, WSDL og JSON baserede tjenester ser de ud og f&#248;les som en rigtige SOA baseret tjenester for de udviklere der &#248;nsker at forbruge dem mens de bliver mere af en &quot;bag kulisserne&quot; kerneydelse. 

Mashups versus portaler

Mashups og portaler er sammenl&#230;gning teknologier men alligevel helt forskellige. En Portal samler en masse funktionalitet mens en mashup er et fragment, en &quot;portlet&quot;, og flere mashups kan samles i en enkelt webside. Portal er klassificeret som en traditionel web-server-model med en veldefineret strategi mens mashus er mere l&#248;st definerede &quot;Web 2.0&quot;-teknik. Det siges at en Portal er som en &quot;Salatbar&quot; mens mashup er en &quot;smeltedigel&quot;. Portal styre sit state gennem en event-model defineret gennem et portlet API mens mashup selv har sit interne state og benytter REST baseret CRUD arkitektoniske principper ligesom mashup bruger base standarder som XML, REST og Web Services, RSS og Atom. 

Mashups 

Jeg er ikke i tvivl om at mashup applikationer vil vinde indpas over de n&#230;ste &#229;r. Desv&#230;rre er is&#230;r store virksomheder i Danmark utrolig konservative med hensyn til nye teknologier og der vil sikkert g&#229; adskillige &#229;r inden de helt &#229;benlyse fordele ved mashup sl&#229;r igennem. For mig er fordelene &#229;benlyse. 

Sm&#229; startup virksomheder vil kunne n&#229;r deres m&#229;l hurtigt og effektivt og lade allerede indk&#248;bt infrastruktur h&#229;ndter ting som development, caching, scaling, clientstate, osv. Alle ting som Enterprise verden bruger oceaner af tid og resource p&#229;. 

Utroligt at helt enkelte beslutninger kan resultere i k&#230;mpe fordele. </body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2010-01-18T19:07:49Z</created-at>
    <id type="integer">156</id>
    <published type="boolean">true</published>
    <title>Cross Domain Mashup</title>
    <updated-at type="datetime">2010-01-20T08:14:59Z</updated-at>
  </post>
  <post>
    <body>Sommeren er forbi nu, og den n&#230;rmest fl&#248;j afsted, tomh&#230;ndet st&#229;r du tilbage &amp; ka' slet ikke f&#248;lge med! CV J&#248;rgensen skrev de ord tilbage i 1988 og langt om l&#230;nge, er jeg ved at forst&#229; den reelle betydningen af den s&#230;tning. I sidste julebrev t&#230;nkte jeg p&#229; konceptet tid, og at tiden g&#229;r sin gang ligemeget om vi er med eller ej. 2009 er et af de &#229;r hvor vi har udnyttet tiden tiden til vores fordel og leget at honning og forstand flyder frit. 

Den 9. april 1940 blev hestetrukket artilleri fra Ringsted anbragt i stillinger &#248;st for Ringsted, s&#229; byen om n&#248;dvendigt kunne beskydes, men da der hurtigt kom ordre fra regeringen gennem den kommanderende general om, at der ikke skulle ydes modstand mod den tyske bes&#230;ttelse, s&#229; trak man artilleriet tilbage til kasernen igen, hvor den normale garnisons-tjeneste blev genoptaget. &quot;Ringsted kaserne&quot;:http://www.frankvilhelmsen.com/posts/154-Ringsted-Kaserne

Det herrens &#229;r 2009 var &#229;ret, hvor recessionen i samfundet var s&#229; voldsom, at vores lille familie havde r&#229;d til at k&#248;be hus ved Artilleristen, sjovt nok pr&#230;cis der hvor artilleriet var stille op i 1940. Derfor mente jeg at der var god grund til at d&#248;be huset &quot;skydebanen&quot;. Jeg m&#229; dog erkende, at mit forslag ikke blev vel modtaget. N&#229;r vi kigger tilbage over &#229;ret 2009 er dette husk&#248;b naturligvis det langt det overskyggende emne. 

Det er en utrolig positiv oplevelse at have s&#229; meget plads. T&#230;nk at kunne g&#229; i bad uden at ramle ind i alt ting. Alene den ekstra plads har tilf&#248;rt noget ekstra livskvalitet i vores dagligdag. P&#229; den anden side er det sk&#230;mmende at m&#230;rke hvilken betydning plads og luft har p&#229; ens velbefindende. Siden starten af Juli hvor vi flyttede har vi hver dag, gl&#230;det os til at komme hjem og vi har aldrig brugt s&#229; meget tid til at se p&#229; himlen som nu. Ligeledes varmer det om hjertet at se bambi(er) g&#229; forbi udenfor, vi tror der er en hjorte sti mindre en 3 meter fra vores vindure. 

Der har skam ogs&#229; v&#230;ret en del bekymringer i processen, som at styre havearbejde, carport, stikledninger og flyvende trampoliner har skabt flere problemer, end vi turde dr&#248;mme om. 


Familien

Familien har det godt. Vi har alle fundet os tilrette, og det virker som is&#230;r som Christian har haft godt af transformationen, han nyder at hele grunden er hans egen, og han ikke beh&#248;ver t&#230;nke p&#229; naboerne. Han har f&#229;et nyt v&#230;relse, men synes at hele huset er hans. Meget mod s&#230;dvane er vi nu aktive med forskellige sysler om aftenen n&#229;r vi er kommer hjem fra arbejde. En negativ effekt er, at vi er blevet territoale og bryder os ikke om, at noget eller nogen overtr&#230;der vores rum, hverken hunde eller mennesker :-) 


Christian

Christian vokser i fuld fart nu, og l&#248;sningen er mad, der behager hans &#248;jne og at vi overholder det faktum at han ikke er en dr&#248;vtygge med 4 maver. Han trives over al forventning, og vi er superstolte af ham. Han har s&#229; utroligt meget at sige. Christian er virkeligt begyndt at forst&#229; forskellen mellem godt og ikke s&#229; godt. Udadtil er Christian en glad lille dreng, en rigtig mors dreng men indadtil er han en f&#248;lsom t&#230;nker, som er ved at finde ud af sammenh&#230;ngen mellem det talte ord og reel handling. Hvis Christian oplever at der ting der er sagt ikke f&#248;lges op af handling kan han blive noget s&#229; skuffet. Christian har en stor motor, han kan k&#248;re langt p&#229; meget lidt br&#230;ndstof. Han taler gerne med alle omkring ham, samtidig ogs&#229; kan det knibe med at h&#248;re n&#229;r klassel&#230;ren pr&#248;ver at f&#229; ham til at tie stille. Der er ogs&#229; lidt med bandeord, men den er vi flere der arbejder med. N&#230;ste &#229;r m&#229; vi til at kigge lidt p&#229; noget, der kan styrke koncentrationen. 

&quot;Det s&#230;tter jeg pris p&#229;&quot; har f&#229;et en ny mening i huset. Der er lavet en aftale om, at visse services bliver afregnet, s&#229; fx at t&#248;mme opvaskemaskinen giver en femmer, sl&#229; gr&#230;s giver femten osv. Det er helt sikkert Moffe's karakter afregningsmetode, der har en afsmittende effekt. H&#229;ber Moffe ogs&#229; s&#230;tter pris p&#229; de nye karakterer, for de er rigtig gode! 


Arbejde

Arbejdet dette &#229;r er baseret p&#229; tesen: &quot;work smarter, not hard&quot;. Vi fors&#248;ger at leve op til det at v&#230;re en del af et videnssamfund og reflektere over vores handlinger fremfor at repetere os selv uden bagtanke. Undskyldningen med at kun lave noget halvt, fordi der ikke var mere tid dure ikke. 

Susanne har opn&#229;et en skarpere fokus b&#229;de p&#229; arbejdsproces og metode. Det virker som hun er begyndt at slappe mere af, og det virker ogs&#229; p&#229; os andre. Hun elsker at designe ting eller sammens&#230;tte produkter, og det bliver en stadig st&#248;rre del af hendes job. Hendes evne til at bed&#248;mme designs og trends i tiden er fantastisk, og bliver slet ikke udnyttet fuldt ud. Susanne har en kreativ sj&#230;l med et enormt potentiale, men hun t&#248;r ikke stole fuldt ud p&#229; sin evner. Susanne har i arbejdsmedf&#248;r rejst en del i &#229;r til fx Kina, Hong Kong, Tyskland og England. 

Brug livet og v&#230;r provokerede proaktiv. Dette slogan er fra det pensionsselskab, hvor jeg det sidste &#229;r har siddet i en udviklingsafd. Jeg startede &#229;ret med at v&#230;re ressourceforst&#230;rkning, men langsomt har jeg bev&#230;get mig mere og mere i retning af Enterprise Architect. Det er en rolle der indbyder til en statisk t&#230;nkning/holdning, som jeg har k&#230;mpet mig v&#230;k fra i &#229;revis men min naturlige nysgerrighed og fr&#230;khed f&#248;rer mig ofte i den retning. Min lidenskab for applikations-design er dog uforandret. Det er der, jeg n&#230;res og fyldes af arbejdsiver, og det er ogs&#229; der, hvor behovet er langt st&#248;rst. Det er ikke op til mig at vurdere om slogan holder stik. 

Hos Cybercomgroup har jeg fors&#248;gt at deltage mere engageret i kundekontakt, sociale relationer og faglige netv&#230;rk. Udover det er jeg glad for at kunne hj&#230;lpe forskellige medarbejder med faglig sparing, og om hvordan man udfylder rollen som konsulent. Jeg har &quot;kun&quot; deltaget i tre konferencer i &#229;r, hvoraf jeg p&#229; de to var inviteret som g&#230;st.


Ferie

Vi har ikke holdt rigtig ferie i &#229;r. Susanne har godt nok v&#230;ret p&#229; en sk&#248;n ferie p&#229; Skiatos med sin mor, hvilken vi &quot;andre&quot; var lidt fort&#248;rnede over, idet vi plejer at v&#230;re med p&#229; den lille sk&#248;nne gr&#230;ske &#248;, som vi savner. N&#230;sten samtidig arbejdede jeg h&#229;rdt p&#229; &quot;formen i de italienske dolomitter&quot;:http://www.frankvilhelmsen.com/posts/144-Dolomite-Training-Camp Susanne skal forresten ha en stor tak for at g&#248;re hus-handlen f&#230;rdig fra en Gr&#230;sks strandpromenade, mens jeg cyklede rundt i Italien. P&#229; en eller anden m&#229;de er det fedt at kunne stikke retningen ud og lade andre st&#229; for detaljerne. 

Selv om vores hus fylder en del i dette efter&#229;r, har vi alligevel haft tid til kulturelle tiltag, et par som er v&#230;rd at n&#230;vne er; Carmen i Operaen, Les Miserables p&#229; det ny teater, en tur p&#229; Statens Museum for Kunst og et meget interessant bes&#248;g p&#229; Middelaldercentret. Det er, som vi er ved at se elementer af klassisk musik som attr&#229;v&#230;rdigt. Vores lyst til at invitere g&#230;ster er ogs&#229; kommet tilbage, og vi h&#229;ber, at vi kan lave lidt kvalitetsservering for jer til n&#230;ste &#229;r ved Artilleristen.

Det var tanker fra &#229;ret 2009. H&#229;ber at det n&#230;ste &#229;r vil bringe endnu flere hyggelige stunder sammen med jer alle. 

Ha en rigtig gl&#230;delig jul og et godt nyt&#229;r. 

Susanne, Christian &amp; Frank</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-12-11T07:48:07Z</created-at>
    <id type="integer">155</id>
    <published type="boolean">true</published>
    <title>Julebrev 2009</title>
    <updated-at type="datetime">2009-12-14T09:27:46Z</updated-at>
  </post>
  <post>
    <body>I Ringsteds nordlige del p&#229; Teglovnsvej finder man nogle store r&#248;de kaserne-bygninger, og her har Artilleriets Befalingsmandsskole holdt til i mange &#229;r. I de senere &#229;r har kasernen dog kun v&#230;ret brugt til forskellige stabsfunktioner, og nu er den blevet nedlagt som kaserne og solgt til Ringsted Kommune. Det er imidlertid kasernens historie under anden verdenskrig, der m&#229; v&#230;kke interesse, da denne er ret dramatisk. Den 9. april 1940 blev hestetrukket artilleri fra Ringsted anbragt i stillinger &#248;st for Ringsted, s&#229; byen om n&#248;dvendigt kunne beskydes, men da der hurtigt kom ordre fra regeringen gennem den kommanderende general om, at der ikke skulle ydes modstand mod den tyske bes&#230;ttelse, s&#229; trak man artilleriet tilbage til kasernen igen, hvor den normale garnisons-tjeneste blev genoptaget.

I 1943 gik tyskerne til aktion mod de danske soldater, og p&#229; Ringsted Kaserne forl&#248;b interneringen og hjemsendelsen af de danske soldater forholdsvis udramatisk, men denne begivenhed bet&#248;d, at kasernen derefter blev overtaget af de tyske milit&#230;re myndigheder, der ligeledes beslaglagde et par af de n&#230;rliggende villaer p&#229; Teglovnsvej. I mellemtiden var der opst&#229;et flere danske hj&#230;lpekorps, som dels skulle forberede danskere til tysk milit&#230;rtjeneste og dels hj&#230;lpe tyskerne med opretholde sikkerheden i landet, og nogle af disse hj&#230;lpekorps fik overladt Ringsted Kaserne og de omtalte villaer. P&#229; kasernen rykkede der s&#229;ledes medlemmer af flere forskellige hj&#230;lpekorps ind, f.eks. folk fra Schalburg-Korpset, og kasernen blev s&#229;ledes b&#229;de et milit&#230;rt udannelsessted og et hjemsted for en st&#248;rre styrke med politiopgaver.

At der p&#229; Ringsted Kaserne allerede var placeret danskere i tysk milit&#230;r- og politi-tjeneste fik betydning under den senere folkestrejke i flere store danske byer. Et af kravene i den k&#248;benhavnske folkestrejke var nemlig, at man forlangte det s&#229;kaldte Hipo-korps ud af byen. Dette korps var ment som et hj&#230;lpepolitikorps i tysk tjeneste, der var oprettet af de tyske myndigheder, efter at man havde sl&#229;et til mod danske politi. Hipo-folkene skulle s&#229;ledes erstatte de internerede og flygtede danske politifolk, men Hipo-folkene var overordentligt upopul&#230;re i befolkningen, og det var baggrunden for kravet under folkestrejken om korpsets fjernelse fra K&#248;benhavn. Da de tyske myndigheder gav efter for folkestrejkens krav, s&#229; var det jo helt naturligt at flytte Hipo-korpset til Ringsted Kaserne, hvor man som n&#230;vnt allerede havde placeret folk fra andre danske hj&#230;lpekorps. Derved blev Ringsted Kaserne faktisk det vigtigste tjenestested for danskere i tysk tjeneste, og folkene fra de forskellige hj&#230;lpekorps blev s&#229; samlet operativt i &#8221;Vagtbataljon Sj&#230;lland&#8221;, der dels skulle st&#248;tte tyskerne milit&#230;rt under en evt. allieret invasion og dels udf&#248;re sikkerhedsopgaver af en mere speciel natur for de tyske myndigheder. Da vagtbataljonen netop bestod af folk fra flere forskellige korps, s&#229; fik bataljonen aldrig en egentlig f&#230;lles uniformering. De tjenesteg&#248;rende gik simpelthen i de uniformer, som de havde f&#229;et i deres oprindelige korps, hvorfor man da ogs&#229; p&#229; kasernen havde danskere i tyske h&#230;runiformer, tyske SS-uniformer og forskellige s&#230;rlige danske udgaver af disse uniformer. 

Vagtbataljonen bestod af ca. 700 mand, hvoraf mange faktisk havde kamperfaring fra &#248;stfronten, da de tidligere havde gjort tjeneste i danske V&#229;ben-SS enheder som f.eks. Frikorps Danmark og det senere Pansergrenaderregiment Danmark.

At Ringsted Kaserne var blevet det vigtigste tjenestested for danskere i tysk tjeneste gjorde naturligvis, at kasernen blev bef&#230;stet meget omhyggeligt, da krigen n&#230;rmere sig sin afslutning. De tjenesteg&#248;rende i Vagtbataljon Sj&#230;lland h&#248;rte jo netop til dem, der havde mest at miste i denne situation, og p&#229; kasernen gjorde man da ogs&#229; parat til et s&#229;kaldt pindsvineforsvar, dvs. et forsvar vendt til alle sider. Man opbyggede s&#229;ledes maskingev&#230;rstillinger og lette kanonstillinger hele kasernen rundt og bef&#230;stede den yderligere med pigtr&#229;d. Det var faktisk holdningen i Vagtbataljon Sj&#230;lland, at man skulle forsvare sig, ogs&#229; efter at tyskerne havde kapituleret. Den 5. maj bet&#248;d derfor ikke nogen overgivelse p&#229; Ringsted Kaserne. Vagtbataljonen holdt forsat kasernen, hvad der bekymrede modstandsbev&#230;gelsen, da man kun vanskeligt kunne inds&#230;tte en tilstr&#230;kkelig stor styrke til at erobre kasernen i kamp. Der gik nogle dage, og modstandsbev&#230;gelsen havde f&#229;et ca. 1200 mand samlet i omr&#229;det, hvoraf dog mange kun var ganske let bev&#230;bnet, men rygterne om det forst&#229;ende angreb p&#229; kasernen og det h&#229;bl&#248;se i hele vagtbataljonens stilling gjorde alligevel indtryk, s&#229; vagtbataljonens chef indledte forhandlinger med en dansk officer om en overgivelse.

Efter overgivelsen forefaldt der i &#248;vrigt nogle episoder p&#229; kasernen, som ikke har v&#230;ret omtalt i medierne, da de ikke er s&#230;rligt smigrende for modstandsbev&#230;gelsen. Disse episoder kendes fra flere lokale beboere, der har berettet om dem. I dagene efter overgivelsen f&#248;rte modstandsfolkene s&#229;ledes mange af fangerne fra hj&#230;lpekorpsene ud i kasernens g&#229;rd, &#233;n efter en, sk&#248;d en maskinpistolsalve af lige ved siden af dem, og f&#248;rte dem derefter ind i en anden bygning. Derved opn&#229;ede man, at de tilbageblevne fanger efterh&#229;nden troede, at de alle blev skudt, en efter en, og denne psykiske terror drev modstandsfolkene i flere dage, indtil fangerne blev overladt i det nyopdukkede politis varet&#230;gt. Dette var ikke nogen s&#230;rlig smuk episode, men den afspejler naturligvis bare den ophidsede stemning i for&#229;ret 1945.</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-12-07T17:22:23Z</created-at>
    <id type="integer">154</id>
    <published type="boolean">true</published>
    <title>Ringsted Kaserne</title>
    <updated-at type="datetime">2009-12-07T18:17:04Z</updated-at>
  </post>
  <post>
    <body> En cirkul&#230;r reference er en bidirektionel forbindelse mellem to objekter hvor hver instans har en reference til det andet objekt. I et &quot;garbage collected&quot; system er dette ikke noget problem. Begge objekter vil blive fjernet samtidigt n&#229;r de ikke l&#230;ngere bliver brugt. Ved traversering af stakken holder processen selv &#248;je med objekter som kun bliver refereret fra andre objekter. Hvis systemet er baseret p&#229; en t&#230;llefunktion pr referencer kan ingen af disse objekter blive elimineret fordi referencer t&#230;lleren aldrig kommer tilbage p&#229; 0. I et hybrid system hvor man b&#229;de benytter opt&#230;lling og &quot;garbage collection&quot; vil der opst&#229; en leak fordi der ikke kan erkendes en cirkul&#230;r reference ud fra stakken. 

Der finde mange forskellige implementationer af gode og mindre gode javascript motere. Man kan se en oversigt p&#229; &quot;Timeline of web browsers&quot;:http://upload.wikimedia.org/wikipedia/commons/7/74/Timeline_of_web_browsers.svg 

Man kan fx lege lidt med den cirkul&#230;re reference p&#229; forskellige browser versioner for at se hvor store forskelle der faktisk findes. Det er ikke Javascript som programmeringssprog der er d&#229;rligt, men kun de Javascript fortolkere der benyttes. Desv&#230;rre er det ofte op til den enkelte programm&#248;r at kende til de mange revisioner. Dette issue er vel i virkeligheden det svageste punkt ved Javascript. 

Dette er grunden til at de fleste vil bruge et Javascript bibliotek som er &quot;Cross Browser Enable&quot;:http://en.wikipedia.org/wiki/Cross-browser robust. Disse bibliotker er naturligvis abstraktioner og n&#229;r man arbejder i en &quot;enterprisey&quot;:http://en.wikipedia.org/wiki/Enterprise_software virksomhed kommer der et tidspunkt hvor man m&#229; lave en helt specielt l&#248;sning. Uagtet om ideen er god eller d&#229;rlig. Derfor udvikler du selv to linjer Javascript og inds&#230;tter dem som en HOTFIX og merger dem direkte ind i  produktion. Ups, vi har alle v&#230;ret der. 

&lt;p&gt;Her er et par eksempler p&#229; hvordan man kan &#248;del&#230;gge enhver browsers javascript motor.
&lt;ol&gt; 
    &lt;li&gt;Start din task manager s&#229; du kan se hvad din computer fortager sig!
    &lt;li&gt;Start din alletiders favorit browser!
    &lt;li&gt;Tryk p&#229; knapperne s&#229; hurtigt du kan!
    &lt;li&gt;Hvis du bruger en rigtig browser kan du f&#248;lge CPU usage og Pagefile usage!
    &lt;li&gt;Pr&#248;v gerne forskellige typer og versioner af browserer. 
&lt;/ol&gt;

Jeg h&#229;ber din produktionskode er mere kompleks og det vil v&#230;re langt nemmere at lave disse operationer ved et uheld. Det er let at lave bugs n&#229;r man ikke ved hvordan man laver bugs. Fixing bugs doesn't make the bugs go away!

Eksemplet viser hvordan en cirkul&#230;r reference dannes mellem DOM objektet og Javascript objektet. 

&lt;pre&gt;
    // Circular references between JavaScript and DOM 
    function circular_references_between_javaScript_and_dom() {
        var object;
        object=document.getElementById(&quot;element&quot;);
        document.getElementById(&quot;element&quot;).expandoProperty=object;
        object.bigString=new Array(2000).join(new Array(2000).join(&quot;XXXXX&quot;));
    }
    &lt;div id=&quot;element&quot;&gt;
    &lt;input type=&quot;button&quot; value=&quot;circular_references&quot; onclick=&quot;circular_references()&quot;&gt;
&lt;/pre&gt;

I dette tilf&#230;lde vil mange gode browsere kunne h&#229;ndtere denne function mens andre vil l&#248;be t&#248;r for memory med det samme. Den v&#230;sentligste grund er den valgte memory model i browserens javascript motor. Hvis den er ren &quot;garbage collected&quot; som fx firefox 3 kan den nemt klare beslastningen. M&#229;ske vil den h&#230;nge lidt men ikke mere. IE4+ til IE6 har implementeret en hybrid memory model og kan derfor ikke gennemskue bidirektionelle (cirkul&#230;re) referencer. Jeg har ikke pr&#248;vet med Google Chrome's V8 javascript motor men efter som det er Lars Bak der har bygget den er jeg sikker p&#229; at den nemt kan klare den slags &quot;hotspots&quot;. 

Hvis man har interesse b&#229;de i virtuelle maskiner og Javascript har man nok bem&#230;rket at teamet i &#197;rhus er bemandet med en stor del af del mennesker fra det oprindelige hotspot team. JIT principperne sprang ud af Strongtalk, Smalltalk og programmeringssproget &quot;Self&quot;:http://en.wikipedia.org/wiki/Self_(programming_language) Self er m&#229;ske et af de vanskeligste programmeringssprog at skabe god bytecode for pga de dynamiske egenskaber. V8 motoren bruger mange af de samme teknikker som Java Hotspot for at f&#229; Javascript til at k&#248;re hurtigt. Fx bruger V8 &quot;hidden classes&quot;:http://code.google.com/intl/da-DK/apis/v8/design.html til et forbedre &quot;Fast Property Access&quot; som er dynamisk addition af properties on runtime og derved &#248;ges kontrollen over opslaget af den valgte property betydeligt. N&#229;r Google Chrome OS ogs&#229; kommer p&#229; banen bliver alle disse optimeringer endnu bedre hvilket giver os brugere bedre performance og mindre at t&#230;nke p&#229;. 


Closures and circular references

I den n&#230;ste stump kode kaldes en closure fra Javascript der indeholder en reference til et DOM objekt. DOM elementet har til geng&#230;ld reference til Javasript objektet. Den resulterende cirkul&#230;re reference mellem javascript objekt og DOM objekt for&#229;rsager en memory leak.

Eksemplet viser hvordan man addere et javascript objekt (closure) til DOM objektet. 

&lt;pre&gt;
  // Memory leak by closure 
  function memory_leak_by_closure() {
    var parentDiv = document.createElement(&quot;div&quot;);
        parentDiv.onclick=function(){
            foo();
        };
        parentDiv.bigString = new Array(2000).join(new Array(2000).join(&quot;XXXXX&quot;));
    }
    &lt;input type=&quot;button&quot; value=&quot;memory_leak_by_closure&quot; onclick=&quot;memory_leak_by_closure()&quot;&gt;
&lt;/pre&gt;

Closures er en af de mest kraftfulde funktioner i Javascript men det kan v&#230;re sv&#230;rt at forst&#229; dem. De er nemme at konstruere, selv ved et uheld. Deres eksistens er potentielt farlige for almindelige browsere og det er n&#248;dvendigt at forst&#229;r deres fulde omfang. Dette g&#230;lder ikke kun Javascript.  

Grunden til at jeg sidder og tager enterprisey &quot;Your Moment of Zen&quot; er at vores produktionskode fejler bigtime i IE Explorer version 7- Det er v&#230;rd at huske at version 7 n&#230;sten version 6 med forbedre GC og version 6 n&#230;ste er version 4.5 med lidt hotfix'es.  Nuvel, i Javascript koden er konstrueret en timer som har til m&#229;l at l&#248;be ud af en tidsramme inden nogle andre systemer timer ud, for at forhindre en &quot;ufin&quot; lukning for brugeren. 

M&#229;ske kan man forstille sig de vilk&#229;r vi som softwareudviklere arbejder under i kampen p&#229; at forbedrede interaktionen med brugerne. </body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-11-24T14:13:37Z</created-at>
    <id type="integer">153</id>
    <published type="boolean">true</published>
    <title>Circular reference in JavaScript</title>
    <updated-at type="datetime">2009-11-24T14:28:03Z</updated-at>
  </post>
  <post>
    <body>Hvad har Hercule Poirot, den belgiske mesterdetektiv, Sherlock Holmes, den engelske privatdetektiv, Inspector Hanaud fra det franske French S&#251;ret&#233; plus den altid selvsikre Chief Inspector Jacques Clouseau til f&#230;lles? 

Alle fire roder sig altid ud i de vildeste opklaringer af horrible forbrydelser. Hver is&#230;r benytter de meget forskellige metoder ved deres opklaring. De er is&#230;r gode til at drive en proces som g&#229;r ud p&#229; at p&#229;virker informationshastigheden ved at stresse alle implicerede parter. De arbejder altid med eller fra flere vinkler i parallelle forl&#248;b. De tolker oplysninger forskelligt p&#229; forskellige tidpunkter og undervejs frembringer de uensartede og forskellige dell&#248;sninger. 

Deres selvgl&#230;de kan til tider v&#230;re overv&#230;ldende og de tager enhver udfordringer personligt. Ofte besidder de en eksentrisk adf&#230;rd og kan forsvinde ind i dem dem selv i l&#230;ngere perioder. De isolere sig gerne ved at s&#230;tte andre standby mens de udf&#248;re deres opklaring. De har gennem deres resultater frembragt en tro i omgivelserne p&#229; at de er overlejende og deres bedrifter kan ser som rene kunstv&#230;rker. De arbejder alle udfra en tese om at alt detektivarbejde udspringer af en ressource alene: r&#229; tankekraft. 

Pr&#248;v at skifte billedet af detektiv ud med et billede af en softwareudvikler. Hvis alting stadig passer p&#229; en ansat har du helt sikkert fat i en stjerneressource. Du betaler sikkert en masse i l&#248;n men du f&#229;r i tifold tilbage. 

Hvis du v&#230;lger at bruge de billgeste ressource til opklaring af forbrydelser eller til softwareudvikling m&#229; du selv tage konsekvenserne. 

&quot;Cheap developers are most expensive!&quot;:http://www.frankvilhelmsen.com/posts/127-Cheap-developers-are-most-expensive
</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-11-12T19:58:34Z</created-at>
    <id type="integer">152</id>
    <published type="boolean">true</published>
    <title>Little Grey Cells</title>
    <updated-at type="datetime">2009-11-12T19:58:34Z</updated-at>
  </post>
  <post>
    <body>Titlen p&#229; denne post kan m&#229;ske forekomme misvisende eller ligefrem tvetydig idet den blander to paradigmer, to protokoller og to praktiske modeller. Men netop denne dualisme og tv&#230;rg&#229;ende egenskaber kan resultere i en styrke. Abstrakt handler dette blot om at se p&#229; services som resource. Denne post har absolut intet at g&#248;re med REST men kun om brug og kombination af enkle og gode egenskaber omkring HTTP Applikations Protokollen. 

For at komme i gang vil jeg lige sige et par ord om Mocks. Mocks er objekter der indenholder en forventet reaktion. Man kunne fx mock'e information om &quot;processen af k&#248;be en kop kaffe&quot;:http://www.frankvilhelmsen.com/posts/33-Caf-shop i nogle trin uden af kende hele den samlede proces til bunds. P&#229; den m&#229;de ville kaffe t&#248;rstige sj&#230;le kunne benytte cafe-service'en ved at bestille forskellige type af kaffe. Endda f&#248;r kaffebaren er helt f&#230;rdig. En Stub derimod ville i samme senarie blot returnere den samme kedelige kop kaffe hvergang uden nogen hensyntagen til modtageren. 

Hvad har kaffe med SOAP at g&#248;re? Jo, jeg har modtaget en r&#230;kke l&#248;stformulererede krav til en SOAP service der kan erstatte en ESB. Kravende indeholder ord som enkelhed, robusthed og fleksibel. Sjovt nok h&#230;nger de egenskaber ikke naturligt sammen med de flestes opfattelse af SOAP og WS-. Jeg m&#229; blankt indr&#248;mme at jeg normalt l&#248;ber min vej n&#229;r talen kommer ind p&#229; SOA, SOAP og WS-  &quot;d&#248;dsstjerne teknoliger&quot;:http://www.frankvilhelmsen.com/posts/56-WS-Death-Star 

Men p&#229; samme m&#229;de som en skatterevisor til fest er min interesse altid p&#229; ca. 50 procent n&#229;r noget er dukket op p&#229; omr&#229;det. Min holdning er blot at jeg kan tilf&#248;re mere v&#230;rdi med andre metoder. 

Som udgangspunkt enig med med folkene bag &quot;http://soa-manifesto.org&quot;:http://soa-manifesto.org om at SOA som arkitektur er en god ting og SOAP som protokol er noget markv&#230;rk. Derfor vil jeg bryde alle (mine) principper og fors&#248;ge at angribe med ord som &quot;Brute Force&quot; og &quot;WS-* Duck-Typing&quot;:http://www.frankvilhelmsen.com/posts/21-WS-Duck-typing N&#229;r man operaer med &quot;Brute Force!&quot; metoden er det n&#230;sten det samme bare med mere traditionelle v&#230;rkt&#248;jer. 

Paul Sandoz fra SUN, som i &#248;vrigt sidder i ekspertgrupperne JSR-154, JSR-224, JSR-311 har p&#229; en konference fortalt mig at man kan se p&#229; enhver SOAP besked som en resource. Og hvis ikke er der et design issue. Derfor vil jeg i dette fors&#248;ge at udstille et SOAP endpoint som en resource. Eller rettere, forbrugeren vil ikke opdage en forskel men blot kalde en service som s&#230;dvandeligt men for service udbyderen er der en v&#230;senlig forskel. Klienten kalder med JSR-244 (JAX-WS) og serveren svare med JSR-311(JAX-RS). 

Med denne metode kan jeg overholde WS-* Ducktyping principperne og p&#229; samme tid arbejde highlevel mod HTTP protokollen uden de afledte effekter som codeeksplosion, classeksplosion interoperability og de andre aspekter der bunder i en t&#230;t bundet SOAP protokol. SOAP definere sin egne protokol ovenp&#229; HTTP protokollen og den abstraktion er vigtig set ud fra det perspektiv at man kan skifte transportlag til JMS eller noget andet. Men hvis man kun bruger HTTP som transport er det naturligvis kun en abstraktion der altid vil ende med &quot;Law of leaking abstractions by Joel Spolsky&quot;:http://www.joelonsoftware.com/articles/LeakyAbstractions.html


I denne context er Highlevel er lig med det &quot;Uniforme Interface&quot;:http://www.ics.uci.edu/~fielding/pubs/dissertation/rest_arch_style.htm fra REST der tilbyder ensartede operationer p&#229; tv&#230;rs af alle komponenter. Det er en k&#230;mpe fordel frem for SOAP protokollen hvor hver WSDL definere et specifikt service interface. Med SOAP arbejder man med et lag ovenp&#229; http protokollen mens man med REST arbejder med protokollerne og derfor siges det at abstraktionen mellem de to fremgangsm&#229;der er p&#229; forskellige plan. 

Resoucen 

&lt;pre&gt;
@Path(&quot;/Customer&quot;)
  public class CustomerResource {

  @POST 
  @Consumes(&quot;appliction/soap-xml;charset=UTF-8&quot;)
  @Produces(&quot;appliction/soap-xml;charset=UTF-8&quot;)
  public String method(String body) {
    ...
  }
}
&lt;/pre&gt;

Denne resource klasse repr&#230;sentere en kunde. Path symbolet viser den relative URI til ressourcen. For at kunne attakere denne metode som en resource kan man fx sende et HTTP (@POST) med den rette content-type (@Consumes) i HTTP headeren. Metoden modtager en SOAP besked og returnere en SOAP (@Produces) besked. Hvordan beskeden teknisk behandles i metoden er ligegyldigt. For en brugern af denne SOAP service er det transparent at der benyttes ressource. Ved en fejl i metoden returenes naturligvis en &quot;optional SOAP Fault element&quot;. 

Det er muligt at skabe en @Singelton instans ved at tilf&#248;re en annotation. S&#229;ledes finder der kun den samme ressource for alle consumere og det er muligt at udnytte den feature p&#229; flere m&#229;der end jeg kan komme p&#229; her. Ved Mocking er det selvvalgt en naturlig ting idet man kan &#230;ndre indhold p&#229; ressource output i k&#248;retid. Under normale forhold vil vi naturligvis str&#230;be efter stateless resourcer for at bibeholde egenskaber som skalerbarhed, samtidighed osv. 

Indtil nu er der kun brugt annoteringer fra API'et p&#229; en POJO Java klasse men det er tid at v&#230;lge hvilken implementation der skal bruges. Jeg bruger JAX-RS API og SUN's Jersey 1.1 reference implementation fordi den er langt den mindste jeg kender og har en opstartstid jeg kan udholde. Ikke et ond ord om Apache CXF der har suppport for JAX-RS i sin JAX-WS implementation. Registrering og brug af denne resource kan ske p&#229; flere m&#229;der, b&#229;de standalone og i container. Jersey har en super cool scanner der selv register klasser efter annotationer og binder dem til det rigtige endpoint der dekoreres dels i Web.xml og dels direkte i annotationer. Det bliver ikke bedre end det. :-) 

En af de st&#230;rke sider ved Jersey er deres client interface. Kan ikke lade v&#230;re at vise en stumt kode der simulere et SOAP WS kald mod en ESB eller whatever du nu har. L&#230;g is&#230;r m&#230;rke til den dejligt &quot;Java Fluent Interface&quot;:http://www.frankvilhelmsen.com/posts/111-Fluent-interface m&#229;de man opbygger sin request p&#229;, n&#230;sten i DSL stil. Mange forskellige teknologier har adopteret og overholder HTTP, Servlets og JAX-WS. Det betyder at man kan bruge en ressource som et endpoint for alle komponenter der taler samme sprog. De vil aldrig vide hvad der ramte dem. P&#229; samme m&#229;de kan man bruge klientdelen til at invokere fx ESP endpoints. Det er faktisk sjovt. 

&lt;pre&gt;
  Client client = Client.create();
  WebResource endpoint = client.resource(uri);

  ClientResponse response = endpoint.
      type(&quot;application/soap+xml;charset=utf-8&quot;). 
      accept(&quot;application/soap+xml;charset=utf-8&quot;).
      post(ClientResponse.class, xml);

   int status = response.getStatus();
   String s = response.getEntity(String.class);
&lt;/pre&gt; 

Jersey og hele REST tankegange er baseret t&#230;t omkring HTTP Applikations Protokollen. Man er &quot;ON The Web&quot; eller en del af &quot;The Semantic Web&quot;:http://en.wikipedia.org/wiki/Semantic_Web og ens applikation kan underst&#248;tte &quot;Linkede Data&quot;:http://en.wikipedia.org/wiki/Linked_Data Med disse tanker og metoder smelter applikationen sammen med internettet. 

Den forrige resource &quot;/resource/Customer&quot; vil blive ramt af SOAP klienter. Men jeg kan ikke dy mig for at lade den samme resource blive brugt af simpelt AJAX (Asynchronous JavaScript and XML). Med AJAX kan man fra Javascript kommunikere med en server gennem XMLHttpRequest objektet uden at reload HTML siden. En anden ting er, at man kan kontroller stort set alle de ekstra header informationer som overf&#248;res til serveren hvilkent betyder at man kan rammer en resource fx med en bestemt content-type. 

&lt;pre&gt;
new Ajax.Request(&quot;/resource/Customer&quot;, {
  method:'GET',
  asynchronous:true,
  requestHeaders: ['Content-Type', 'text/html;charset=UTF-8'],
  onSuccess: function(transport){
    $('message').update(transport.responseText);
  },
  onFailure: function(transport){
    $('message').update(transport.responseText);
  }
});
&lt;/pre&gt; 

Denne metode laver en GET p&#229; ressourcen Custormer og forventer at modtage en repr&#230;sentation af dennes response i form af HTML. Hvis man skal bruge JSON skal man kun &#230;ndre content-type til &quot;applikation/JSON&quot;. Hvis man i stedet vil POST'e et &#230;ndret indhold ind i ressourcen kan man bruge denne form:

&lt;pre&gt;
new Ajax.Request(&quot;/resource/Customer&quot;, {
  method:'POST',
  asynchronous:true,
  requestHeaders: ['Content-Type', 'appliction/xml;charset=UTF-8'],
  postBody: $F('body'),
  onSuccess: function(transport){
   ...
&lt;/pre&gt;

Dette POST bindes sammen med ressourcen gennem POST med content-type 'appliction/xml;charset=UTF-8' og forventer at modtage en Customer i XML format som input i HTTP body. Hvis ressourcen ikke har implementeret denne indgang svares med &quot;Status Code 415 Unsupported Media Type&quot;:http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html

Fik jeg s&#229; hvad jeg kom efter? Ja, det synes jeg. Ved at mappe ressource til simulering af SOAP endpoints og Servlets side om side fik jeg en cross platform, cross service implementation og mere clean snitflade uden de logiske layer som jeg hader. H&#229;ber bare at mine kravsstiller ikke vil skifte transport metode. Anyways, det sker nok alligevel aldrig. 

At efterleve DuckTyping principperne er en forn&#248;jelse og jeg har virkelig hygget mig undervejs. Tak til Paul Sandoz for at starte den ide i mit hoved i 2007. 
</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-11-06T17:28:12Z</created-at>
    <id type="integer">151</id>
    <published type="boolean">true</published>
    <title>Mocking SOAP onto Resources</title>
    <updated-at type="datetime">2009-11-06T17:32:11Z</updated-at>
  </post>
  <post>
    <body>Anne Thomas-Manes fra Burton Group introducerede den &quot;Thing Oriented Architecture&quot; (TOA) arkitektur til stor gl&#230;de for de f&#229; &#230;gte RESTafarians der var m&#248;dt op i en eller pakkend sal p&#229; &#229;ret Jaoo. TOA er lig med &quot;The Web is REST and REST is the Web. Der var m&#229;ske ikke s&#229; meget nyt p&#229; Jaoo i &#229;r men der var meget konsolidering af de gamle dyder lige fra Haskell programmering over Lean udviklingsmetodiker til hvordan man s&#230;lger REST opad i sin organisation.

Scott Davis redede min f&#248;rste dag p&#229; Jaoo med hans tale om &#8220;Tale of Slippy Map&#8221;. Dagens &#248;rige program gav ikke den store reaktion men der var et par gode solide pr&#230;sentationer. Min gamle ven Kim Dalsgaard var trackhost p&#229; &quot;Web Oriented Data&quot; som til dels fangede min interesse sammen &quot;Browser as a platform&quot;. Disse to track passer rigtig godt sammen de trak ikke ret mange mennesker. Min interesse er baseret p&#229; at jeg tror p&#229; l&#248;skoblet interconnected data over http protokollen.

Barry Boehm tale om &quot;Scaling Up Agility&quot; var en lang reklame for agile metodikker og metoder og han l&#248;b gennem usecases hvor han beviser hvor langt man kan komme med lean udvikling. Eneste krav er at man skal havde ansat de beste adr&#230;tte resource og g&#248;re forretningen klar til iterativ informations flow hvor adoption af forandring fylder langt mere end gammel planer og rutine processer. Den eneste s&#230;tning som jeg virkelig kan huske fra denne lidt, tr&#230;tte taler, er hans statement om at man altid skal passe p&#229; n&#229;r man f&#229;r tildelt en fuldtidsansat forretningspecielist, m&#229;ske er han den eneste de i virkeligheden kunne undv&#230;re? Og nej, din Compiler Driven Testing (CDT) kan ikke bruge som test tool.

Emil Eifrem leveredere en overbevisende introduktion til Graf databasen Neo4j. Det er ikke ligefrem f&#248;rste gang jeg h&#248;re denne pr&#230;sentation men Emil har udviklet en god sans for kunsten at tale og det er en forn&#248;jelse at v&#230;re vidne til. Is&#230;r bifalder jeg hans annalogi om den kognitive tankegang fra et Whiteboard til den grafforbundende verden hvor relationer og properties er en naturlig del af data i kaotiske former. I vore dage kan en medarbejder have op til 10 jobtitler. Hvordan vil du repr&#230;sentere det? Addere en ny kolonne for hver title? nej vel, din database skal omstruktureres men du i en grafdatabase blot l&#230;gger flere properties p&#229; den node der repr&#230;sentere din medarbejder. M&#229;ske arbejder du et sted hvor alting er veddefineret og statisk og s&#229; kan du roligt fors&#230;tte med RDBMS og ORM.

Michael Feathers gav en gennemrand af Clean Functions. Han pr&#230;senterede en del crap kode for at vi skulle kunne f&#229; invokeret vores logik til at finde nogle gode st&#248;rrelser mht antal kodelinjer, klasser og sammenh&#230;nge mellem opgaver og opdeling. Der findes en flere teknikker og principper bag konceptet &quot;clean code&quot;. Personligt er det mange &#229;r siden jeg har set nogle af dem i brug i Java verden men de er langt mere udbredt i letv&#230;gtkredse.

Brian McBride viser hvordan &quot; Linkend Open Data&quot; og &quot;Semantic Web&quot; h&#230;nger sammen. Han er klar fortaler for &quot;Jena Open Source&quot; for at offentligg&#248;re data p&#229; internettet og hvordan disse data kan udnyttes. Han repetere kort en r&#230;kke principper standarder for Linked Open Data og hvordan man konsumering data til og fra andre formater som fx RDF, RDF, XML, JSON samt SPARQL Query Language. Jeg synes dette omr&#229;de er enormt sp&#230;ndende men jeg m&#229; indr&#248;mme at jeg lukkede &#248;jene lidt at tiden.

Scott Davis n&#230;rmest r&#229;bte dages bedste tale i gang mens mine &#248;jne stod p&#229; vid gab. &quot;The Tale of Slippy Map&quot; Kort fortalt er det historien om google maps og hvordan man skaber oplevelsen af den fede applikation. Hemmeligheden er at man bev&#230;ger sig p&#229; en pane som er noget st&#248;rre end det synlige omr&#229;de og der preloades mens man kigger p&#229; det synlige. Jeg h&#248;re til den meget lille gruppe af mennesker som helst vil v&#230;re helt t&#230;t p&#229; de oprindelige protokoller og derfor at fantastisk at se hvor godt google maps er designet. I &#248;vrigt er det den direkte medvirkende &#229;rsag til den k&#230;mpe susces som maps har f&#229;et. Maps applikationen best&#229;r af en stateless server del der levere koordinater og billeder i 256 x 256 pix. Klient delen er stateful og best&#229;r HTML/DIV med ca. 150 linjer af Javascript og indlejeret stylesheet. S&#229; enkelt at det er grineren. Oplevelsen er meget lig desktop applikation men er velorganiseret snyd for &#8220;the brokken web&#8221;. Mr. Scott f&#229;r ogs&#229; en p&#230;dagogisk topkarakter. Hans pr&#230;sentation er meget velovervejet men ikke tilpasset til europ&#230;iske forhold. Mange selvbestaltede supereksterne f&#248;lte sig helt sikkert forulempet og talt ned til. H&#248;jst kontroversielt.

En sjovt ting jeg har t&#230;nkt over i dag er at mange har brugt s&#230;tningen &#8220;schema-free&#8221; adskillige gange i l&#248;bet af de f&#248;rste taler. Det gl&#230;der mig meget men det g&#248;r &#248;jensynlig mange andre en del nerv&#248;se. I sessionen med Linked data var mange sp&#248;rgsm&#229;l rettet mod det faktum at man ikke har kontrol over data sourcen. Tja, men s&#229;dan er der jo s&#229; meget og endnu et eksemplet p&#229; at man kan kende svaret uden at kunne sp&#248;rgsm&#229;let.

Anden dage p&#229; Jaoo 2009 var rettet mod REST!

Simon Peyton-Jones l&#230;gger for med en fantastiske tale om Haskell. Simon forklare om type klasser som de fungere i haskell, ikke at forveksle med Java og .NET klasser. Haskell er et akademisk funktionelt sprog der ogs&#229; bruges til f&#229; kommercielle applikationer. Et af Haskell&#8217;s mest karakteristiske kendetegn er dens type system, de s&#229;kaldte &#8220;type klasser&#8221;. Type klasser tjener samme form&#229;l, at de klasser af mainstream-OO-sprog men p&#229; en anden m&#229;de. Denne tale begynder med forklare lidt om &#8220;The Birth of Language&#8221; med f&#248;rst een &#8220;geek&#8221; bruger, derp&#229; et par stykker mere, og m&#229;ske kn&#230;kker kurven og sproget et bliver popul&#230;rt udover tekniske venner og m&#229;ske adopteret af den brede masse. Simon er veloplagt og stormer gennem noget kode og beder alle som ikke forst&#229;r detaljerne r&#230;kke armen op. Der er m&#229;ske 500 mennesker i den store sal men ikke en r&#248;re sig. Publikum r&#248;r sig heller ikke der hvor Simon presser en test ind i en funktion der ikke lader sig g&#248;re. Han skure blot ud over salen, r&#230;kker armen op og siger NU.

Rachel Reinitz var en positiv overraskelse. Hun talte om &quot;Extending the Reach of your SOAwith REST&quot;. Rachel er IBM Distinguished Engineer i WebSphere Services. Hun har bygget en stor del af IBM&#8217;s uddannelse p&#229; SOA, Enterprise Service Bus, og Web Services. Rachel er top ESB ekspert. Hun vil ikke reklamere for IBM men: &quot;There are in fact good reasons to use messaging beyond IBM making a lot of money with MQ&quot;. Rachel riser hele web2.0 verden op som IBM ser kagen med Service, not software(SaaS), community added value, semple adgang til data osv.. Der er s&#230;rlige grunde til at v&#230;lge SOA og webservices fremfor REST.. Lad mig v&#230;re &#230;rlig, der er ved at g&#229; salg i den og hun opfinder termen RestfulSOA. Hvis hun viste hvem der skulle tale efter hende ville hun m&#229;ske v&#230;gle sine ord med lidt st&#248;rre omhu.

Anne Thomas-Manes fra Burton Group er en kvinde man lader tale ud.. B&#229;de ved cafeen og n&#229;r hun indtager scenen. Anne er en af NetworkWorld&#8217;s &quot;50 mest magtfulde mennesker og en respekteret ekspert i distribueret computerteknologi. Anne har deltaget i udviklingen af standarder som W3C, OASIS, JCP, UDDI.org, og WS-I. Hvordan s&#230;lger man REST i sin organisation? Forretningen t&#230;nker p&#229; afkast, ikke p&#229; hvilken underlige teknik ting der tales om i udvikling. Der er ingen reel fokus p&#229; teknologien. Elegance dosen&#8217;t sell. Hvis du har en god ide kan du s&#230;lge den til forretningen sammen med indtjenings prospekt og risici beregninger.

REST er pr&#230;cis s&#229; sikker som hvilken som helst anden ting der sendes over http protokollen siger hun. QoS h&#230;nger ikke sammen med om der er en envelope i den besked du sender men mere p&#229; skalerbarhed og p&#229;lideligehed. Med hensyn til at startop projekter mener hun ikke at det kan lade sig g&#248;re uden en &#230;gte RESTafarian som mentor. Programmeringmodellen bag REST og det at se verden som resource er meget sv&#230;r at forst&#229; i detaljer, slet ikke hvis man kommer fra en OO verden. Flere af de h&#229;rdeste RESTafarians udtaler at det kan tage op til frem 5 at forst&#229; alle elementer af REST ROA WOA. REST er en arkitektonisk stil orienteret til at formidle oplysninger om ting. REST er en form for &quot;Thing&#8217;ish Oriented Architecture&quot;.

Ian Robinson er Principal Consultant hos ThoughtWorks og forklare hvordan &#8220;hybermedia&#8221; fungere i et restfuldt milj&#248;. At han bruger Dungeons &amp; Dragons spilscenarie g&#248;r det kun en smule mere tosset. Pointen er at spiltilstanden hverken er hos serveren eller klienten men i linkage'en mellem de to. Dette princip kaldes ogs&#229; HATEOAS(Hypermedia As the Engine of Application State, REST koncept). Man har kun et entry point til spillet og efter en GET til den resource f&#229;r man de n&#230;ste muligheder der findes i spillet lige nu. Hypermedia applikationer r&#229;de bod p&#229; SOA-visionen om et distribueret system baseret p&#229; evolution&#230;re let sammensatte program protokoller

Stefan Tilkov er medstifter og chef konsulent ved innoQ, et teknologi konsulentfirma med kontorer i Tyskland og Schweiz. Stefan har v&#230;ret involveret i udformningen af store, distribuerede systemer i mere end et &#229;rti og anvender en bred vifte af teknologier og v&#230;rkt&#248;jer, der sp&#230;nder fra C++ og CORBA over J2EE/Java EE og Web Services til at Ruby on Rails. Tikov er en mand der t&#248;r sige nogle ting og jeg ser altid hans taler hvis det kan lade sig g&#248;re. I dag handler hans tale kun om at udnytte de mange muligheder for &#230;gte caching der implicit er gemt i http protokollen. Man kan v&#230;re mere eller mindre enig i hans synspunkter og personlige holdninger men hvor er det sk&#248;nt at han virkelig kan bitche over teknologere som ESB, SOA, SOAP etc. Sikker derfor jeg kan li ham? En af de mest fremtr&#230;dende fordele ved at bygge services ved hj&#230;lp af RESTful HTTP er st&#248;tten til caching og man kan uden videre bruge de sande byggesten fra internettet uden at t&#230;nke p&#229; ekstra omkostninger til infrastruktur eller software. REST er en blot at udnytte Internette p&#229; den m&#229;de det er tilt&#230;nkt. Tikov har en interessant vinkel p&#229; hvor man ligger sit REST snit i en traditionel layed applikation. Gr&#230;nsen skal ligge s&#229; t&#230;t p&#229; klienten som overhoved muligt. Hvorfor? Kun klienten har tilstand og resten af middelvaren skal v&#230;re stateless. Cool logik. Mange mennesker sad og s&#229; helt blanke ud. Jeg g&#230;tter p&#229; at man skal ha lavet et par apps i den stil for det falder nemt at tale om.

Dagens REST track p&#229; Jaoo var fortrindeligt sammensat af Tikov. Gennem dagen var dette spor velbes&#248;gt og adoptionskurven m&#229; mindst v&#230;re breakeven. Flere personer jeg talte med gav udtryk for at de n&#230;rmest er eksperter i REST mens deres mangelene forst&#229;else &#229;benlys og det g&#248;r mig lidt urolig for REST fremtiden. Det der kan &#248;del&#230;gge udbredelser af REST til masserne er d&#229;rlig r&#229;dgivning og ringer applikationer som ikke m&#248;der deres krav. Det gode ved hele er at jeg m&#229; v&#230;ret n&#229;et langt i min personlige erfaring med REST siden jeg kan s&#229; tydeligt kan se rigtig og forkert. Dagen gav mig ikke noget ny men jeg er glad for en god portion validering. :-)

Der var ikke en generelt gennemgang af REST og det var m&#229;ske en fejl. Kun specielle emner om REST s&#229;som Hybermedie, HTTP Cachaing, hvordan man ikke laver et nyt RPC kald over XML og ikke mindst om hvordan man promovere REST videre ud og op i virksomheden. Efter min mening kommer den vigtigste pointe Anne Thomas-Manes, Burton Group. Du kan v&#230;lge REST p&#229; lige fod med andre teknologere men husk at allokere en specialist som mentor.

Jeg sad og jokede med en v&#230;ldig flink fyr som lige var kommet fra lufthaven og var en del tr&#230;t. Vi var helt enige om Tikov's jokes om SOA var af en meget ringe karakter. :-)

Cameron Purdy, var manden jeg jokede med. Manden som skabte og solgte Tangosol til Oracle. Han skulle pr&#248;vet at tage et kig bagud for at se om vi kan forudsige hvad der sker i de n&#230;ste &#229;r fremover. Hvad har vi l&#230;rt og hvordan kan vi drage fordel at det. Dette var et retrospektiv tilbageblik p&#229; hvorfor C++ blev glemt over natten da Java kom ind p&#229; scenen. Det sjove er at n&#229;r man nu ser p&#229; Java og alle de ting som sker med fx Cloud Computing, Multi Core hardware og andet kan man nemt forstille sig at nye ting klart overhalder Java over en nat. Cameron pointere at man umuligt kan adoptere Agile udviklings metodik hvis det tager flere dage at lave den mindste forandring. Han bitcher ogs&#229; over Java evner til at lave pauser ved GC, et enormt memory forbrug, en sindsyg ringe startop tid. Faktisk mange af de samme ting som gjorde Java C++ overlegen i sin tid, nu er de ting en h&#230;msko. C++ var fantastisk i sin tid men hvor mange biblioteker finders der lige til C++? Nej vel! Grunden er den simple at man havde automatisk memory h&#229;ndterring. I Java derimod er vi skide ligeglade med memory forbrug, vi smider bare det hele v&#230;k og det var ogs&#229; godt nok i en tid i de n&#230;ste &#229;r vil det blive en stigende forhindring.

Det var min mening at f&#248;lge Cloud tracket i dag men en s&#230;rlig omst&#230;ndighed gjorde at det blev meget anderledes. 

See &quot;Attending Conferences&quot;:/posts/116-Attending-conferences

Kevlin Henney var min redning. Og hvilken en. Filuren var fyldt til bristepunktet og med god grund. Kevlin er en super behagelig taler med klare synspunkter om udviklings metodik. Han er fx ikke s&#230;rlig imponeret af hele den agile bev&#230;gelse. I disse &#229;r er det som man skal udvikle efter agile principper for at cool. SCRUM fx ligger meget v&#230;gt p&#229; proriterede backlog emner mens det man i mange tilf&#230;lde burde fokusere p&#229; var at navigere uden om de v&#230;sentlige risicifaktorer. Det ligger implicit i mange agile metoder at design er behandlet som en kontinuerlig aktivitet men m&#229;ske er design kun en af mange faser i udviklingen. Udvikling er ogs&#229; prototyper til TDD, arkitektur, refactoring og retrospektiv betragtninger med fortl&#248;bende feedback. Men denne erkendelse er ikke nok til at kommunikere hvordan et design bliver dannet og udvikler sig. Design fra kode fragmenter til store systemer kan forudses og diskuteret gennem fort&#230;llinger p&#229; lige m&#229;de som med programmerings episoder og pattern historier. Kevlin har ogs&#229; meget interessante vinkler p&#229; softwaretesting. Han giver nogle pragtfulde eksempler og jeg giver ham ret i at mange laver de mest stupide unittests. And hey,camel case doesn't scale over 40 chars. :-)

Michael Nygard har senest skrevet &quot;Release It! Design and Deploy Production-Ready Software&quot;, en bog, der indenholder mange af hans tanker om udvikling af software som kan overlever i den virkelige verden. Michael bestr&#230;ber sig p&#229; at lindre den daglige smerte for den enkelte udvikler. Han har brugt &#229;r p&#229; at finde ud af hvad det betyder at v&#230;re en professionel programm&#248;r der bekymrer sig om kunst, kvalitet og h&#229;ndv&#230;rk. Han kan ikke fordrage apati eller spildt potentiale. Han taler til udviklere men ogs&#229; i h&#248;j grad til management og andre der bev&#230;ger sig i periferien af udviklings milj&#248;et.

I denne tale fokusere Michael p&#229; tenologi, planl&#230;gning og risk management. N&#229;r man sk&#230;re alt bullshitet v&#230;k er: &quot;projects are experiments&quot;. N&#229;r et firma planl&#230;gger sin fremtid er det altid i gode solide blokke. fx n&#230;ste &#229;r skal vi forbedre vores indtjening med 2.5 procent, ikke 100 procent og ikke -100 procent. Faktum er at alle virksomheder g&#229;r fallit uden at det er planlagt. &quot;requirements are ignorance&quot;, Denne bem&#230;rkning omhandler ikke at du som person er arrogant men blot at du er usikker med det samme du ikke ved noget med 100 procent sikkerhed. Det betyder at du kun kan g&#230;tte rigtigt eller forkert. Men det viser sig at man kan g&#230;tte 90 procent rigtig uden at vide noget med sikkerhed. T&#230;nk p&#229; hvorn&#229;r Johannes Gutenberg tykkede sin f&#248;rste bibel? Det ved du m&#229;ske ikke, men du var at det var f&#248;r &#229;r 1800 og efter &#229;r 1200. Hvis man samler 5 personer vil de med 93 procent sikkerhed repr&#230;sentere gennemsnitsh&#248;jten i verden. Du skal i hverfald aldrig sige: det har jeg ingen ide om! &quot;Guessing is Truth&quot;. Mit g&#230;t er at jeg s&#229; snart som muligt skal h&#248;re Michael tale igen!

Jaoo var for mig endnu en god oplevelse med bravende gode talere. Kun en enkelt gang m&#229;tte jeg forlade en session og ty til min tidligere post om at hvordan man beg&#229;r sig til konferencer. Alt i alt endnu en vellykket Jaoo med en grad af validering af allerede adoptere teknologer og konsolidering af allerede velkende processer. Husk at konferencen f&#248;rst er slut n&#229;r alle omkring dig ved hvad der forgik.

Som professionel udvikler stiller jeg mig det samme sp&#248;rgsm&#229;l efter hver konference: Er der noget jeg vil g&#248;re anderledes i mit job p&#229; baggrund af mine oplevelser p&#229; Jaoo? Ja, jeg vil intensivere min udbredelse af historien om d&#248;dsstjernen og rebelfl&#229;den. Konceptet med et system falder mere og mere til jorden og vi taler mere og mere om at publicere data og linke dem sammen p&#229; forunderlig vis. Koplingerne mellem de enkelte systemdele benytter sig mere og mere at allerede erhverve og gennempr&#248;vet software som fx routere og proxy servere. Oh hey, for sidste gang, klienttilstand findes i klientprogrammet. ikke p&#229; serveren.

&quot;Small Things Loosely Joined Written Fast&quot;:/posts/122-Small-Things-Loosely-Joined-Written-Fast</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-10-06T22:14:08Z</created-at>
    <id type="integer">149</id>
    <published type="boolean">true</published>
    <title>Thing'ish RESTafarian at Jaoo</title>
    <updated-at type="datetime">2009-10-08T11:43:36Z</updated-at>
  </post>
  <post>
    <body>Jeg skal udstille en SOAP WebService fra et et lagacy system. Det er en forholdsvis triviel proces med enkelte retninglinjer men bliver ofte til noget overengineered markv&#230;rk. Min tanke er at det m&#229; kunne g&#248;res p&#229; en let og clean m&#229;de. Efter min mening er begrebet service i forbindelse med IT er desv&#230;rre druknet i forretningprocesser og total mangle p&#229; vision.

Mine forbehold er enkle! Jeg gider ikke skrive en WSDL fil og jeg vil helst ikke compilere tusindvis af filer flere m&#229;neder f&#248;r jeg kender kravene til applikationen. Under normale forhold ville jeg v&#230;re dj&#230;vlens advokat n&#229;r det g&#230;lder SOA, SOAP, Webservices og andre d&#248;dstjerne teknologer. Jeg vil have en service orienteret arkitektur med l&#248;s kobling og bl&#248;d binding mellem komponenterne. 

Her er klasse med noget opdigtet funktionalitet.

&lt;pre&gt;
/**
 * Leagcy business rule
 */
public class Palindrome {
  public static boolean isPalindrome(String word) {
    int left = 0; // index of leftmost unchecked char
    int right = word.length() - 1; // index of the rightmost
    while (left &lt; right) { // continue until they reach center
      if (word.charAt(left) != word.charAt(right)) {
        return false; // if chars are different, finished
      }
      left++; // move left index toward the center
      right--; // move right index toward the center
    }
    return true; // if finished, all chars were same
  }
}
&lt;/pre&gt;

Andrew S. Tanenbaum bog om distribuerede systemer dukker svagt op i min erindring n&#229;r vi taler om server klient applikationer. Derfor f&#248;ler jeg det er vigtigt at pr&#230;cisere context. Det f&#248;rste perspektiv er fra leverand&#248;rens(supplier) synspunkt. Rigtig mange problemer opst&#229;r i forskellige opfattelse af distribuerede systemer og det kan v&#230;re sv&#230;rt over tid at skele mellem hvad der er forbruger og leverand&#248;r i forskellige forretningsomr&#229;der. Leverand&#248;r processer som har flere afh&#230;ngigheder fra andre under-leverand&#248;rer som agere forbruger skal snart omskrives. 

F&#248;rste step er at fremstille en service. Jeg kalder processen for BusinessService men i teorien kunne det v&#230;re hvilken slags forretnings regel eller dataplukning. For at spare taste slag bruger jeg Groovy til service interface. Det statiske metode kald til legacy kassen er verdens v&#230;rste smutter men s&#229;dan er det jo med legacy. 

&lt;pre&gt;
class BusinessService {
  boolean isPalindrome(String word) {
    Palindrome.isPalindrome(word)
  }
}
&lt;/pre&gt;

Dette service objekt skal nu omformes til et endpoint. Denne gang bruger jeg groovyWS til at tale SOAP. Bem&#230;rk navne-sammenfald i konstruktionen der invokere groovy's dynamiske newinstance metode. Objektet kalder jeg for BusinessServiceEndpoint. Grunden er at jeg forst&#229;r at en port p&#229; en maskine er et endpoint mens mange forst&#229;r alt muligt andet. M&#229;ske er jeg for logisk? Logisk er det ogs&#229; at man skal passe meget p&#229; sin service stak og ikke mindst r&#230;kkef&#248;lgen i classpath.

&lt;pre&gt;
  new WSServer(&quot;BusinessService&quot;, &quot;http://localhost:6900/BusinessService&quot;).start()
&lt;/pre&gt;

Det var serverens endpoint. WSDL filen specificere alle n&#248;dvendige forhold omkring hvilken muligheder man som WS forbruger kan opn&#229;. Man kan se WSDL filen live p&#229; url: http://localhost:6900/BusinessService?wsdl

Nu er det tid til at tage det store skridt til h&#248;jre for at lege forbruger(consumer) af webservice. Som klient modtager jeg en url der peger p&#229; et service endpoint. Dette b&#248;r v&#230;re den eneste kobling mellem leverand&#248;r og forbruger. Hvis man har brug for mere som fx, et kompilerer jar arkiv, eller andre artifakter er man bundet for h&#229;rdt sammen. leverand&#248;ren har det med at &#230;ndre i sin kontrakt og fjerne dermed grundlaget for alle forbrugere. L&#248;sningen er enkelt, en leverand&#248;r push'er successivt alle &#230;ndringer til sine forbruger. Eneste forhindring er at man som udstiller af services skal vide hvor mange forbruger man har hvilket totalt &#248;del&#230;gger service tanken. Og Tanenbaum vender sig. 

* SOA er som et autovaskeanl&#230;g, du kan ikke bruge det uden at vide alt. I morgen er vaskehallen fx kun 1m bred men heldigvis ringer tankpasseren rundt til alle med &#230;ndringer.

GroovyWS har en fin klient til Webservices. Klienten skal blot have endpoint og en classloader. Instansen kalder jeg proxy fordi den illustrere det objekt som ligger hos udbyderen. N&#229;r man kalder initalize generes alle de n&#248;dvendige stubs for dig og man kan derefter direkte invokere metoder gennem proxy'en. I dette tilf&#230;lde kalder jeg isPalindrome med argumentet otto.

&lt;pre&gt;
  def proxy = new WSClient(&quot;http://localhost:6900/BusinessService?wsdl&quot;, this.class.classLoader)
  proxy.initialize()
  println proxy.isPalindrome(&quot;otto&quot;) # true
&lt;/pre&gt;

Det fede er naturligvis at der foreg&#229;r en masse nedeunder som jeg ikke engang gider ta mig af. Men dette var ret nemt fordi jeg jo blot bruger samme teknologi p&#229; begge sider af ledningen.

Lad og pr&#248;ve at skifte hele servicestakken p&#229; forbruger siden med noget helt andet. I teorien vil leverand&#248;ren gerne ha at s&#229; mange s&#229; muligt benytter de udstillede services fra s&#229; mange platforme som muligt. Dette er en af de gode grunde til at man ikke skal lade sine EA kommer med alt for mange gode ideer n&#229;r de udvikler meget komplekset WSDL'er. Sikkerhed best&#229;r ikke kun af kompleksitet.

Ruby har en 'soap/wsdlDriver' indbygget man kan bruge til at tilg&#229; soap endpoints. Syntakstisk minder det noget om groovyWS og man operere ogs&#229; direkte p&#229; en proxy uden at t&#230;nke p&#229; at afkode WSDL filen manuelt. Evt kan man se metodernavnen i browseren for derefter at invokere dem. Bem&#230;rk at argumentet i ruby er en hash fremfor en typed parameter. Hvis servicestakken &#230;ndres kan man risikere at skulle bruge andre navne end arg0, arg1 osv. 

&lt;pre&gt;
  require 'soap/wsdlDriver'
  proxy = SOAP::WSDLDriverFactory.new(&quot;http://localhost:6900/BusinessService?wsdl&quot;)
  proxy.create_rpc_driver
  puts proxy.isPalindrome(&quot;arg0&quot; =&gt; &quot;jruby-yburj&quot;)
&lt;/pre&gt;

Indtil nu har vi kun k&#248;rt med SOAP version 1.1. M&#229;ske er det tid at udstille en soap service i version 1.2. En ESB kan nemt udstille services af begge versioner og det ville v&#230;re ret cool fremfor at en central admin bestemmer at der kun findes SOAP version 1.2. Ved en s&#229;dan fremgangsm&#229;de bliver man ramt af en alt for kraftig binding mellem endpoints og services og har voldsomme implikationer for alle forbrugerne.

GroovyWS er ikke klar til soap version 1.2 ud af boksen og det kr&#230;ver for mange omg&#229;elser s&#229; det er tid at skifte til Metro 2.0 for at udstille vores n&#230;ste service som sjovt nok ogs&#229; er palindrome. Legacy klassen er stadig den samme men service wrapperen er udskifte til en POJO java klasse med JAXB annotationer. 

Service endpoint interface(SEI). For ethvert defineret interface i WSDL filen kan man generer en SEI. Fra et Java perspektiv kan man sige at wsdl:porttype mapper lige over til en implementation med annotationen @webservice hvor hver operation defineret i wsdl mapper til en metode i SEI. 

Bem&#230;rk at SOAP 1.2 support is added til JAX-WS 2.2

&lt;pre&gt;
/** SOAP 1.2 WS service */
@WebService
@BindingType(value = &quot;http://java.sun.com/xml/ns/jaxws/2003/05/soap/bindings/HTTP/&quot;)
public class PalindromeService {
  @WebMethod
  public boolean isPalindrome(String word) throws PalindromeServiceException {
    if (word == null || word.length() &lt; 2) {
throw new PalindromeServiceException(&quot;No word added!&quot;, &quot;Must have a word with length over 2 chars.&quot;);
    }
    return Palindrome.isPalindrome(word);
  }
}
&lt;/pre&gt;

Nu er den samme legacy kode alts&#229; d&#230;kket af flere service wrapper med forskellige egenskaber. Jeg kan bedst li Java klasse uden &quot;det tredie sprog&quot; annotationer men okey, det er bedre en r&#229; xml konfiguration. Her er tilf&#248;jet en eksplicit exception og et par valideringsregler. Nu kan vi g&#229; direkte til endpoint som ogs&#229; er en Java klasse som kalder et JAX-WS endpoint og publicer en ny service.

&lt;pre&gt;
public class PalindromeServiceEndpoint {
  public static void main(String[] args) throws Exception {
    Endpoint.publish(&quot;http://localhost:8080/business/ispalindrome&quot;, new PalindromeService());
  }
}
&lt;/pre&gt;

Grunden til at dette er i Java fremfor Groovy er at jeg ikke vil lade JAXB binde superclass metoder. En groovy klasse har et metaClass interface og det kan JAXB ikke h&#229;ndter. Dette kan afhj&#230;lpes ved brug af af en ekstra annotation. Det virker dog ikke s&#230;rligt robust p&#229; den nye metro distribution og jeg synes det forurener koden at man skal fort&#230;lle hvilken objekter der er root.

Nuvel, nu findes en service udbyder som har publiseret en service i SOAP version 1.2. Men beh&#248;ver man ikke vide om den. Vel? Det er nu vigtig at pointere at jeg har kaldt denne post &quot;dynamic&quot; fordi jeg ikke vil tilg&#229; services med en bin&#230;r afh&#230;ngighed. Det er ikke hensigten at modtage en *jar fil fra serviceudbyderen som jeg skal l&#230;gge i min classpath og kode imod fordi jeg ikke vil rammes af namespace &#230;ndringer overalt i min kodebase n&#229;r n&#230;ste version kommer.

Mit udgangspunkt er at alle i teorien kan benytte denne service ligegyldigt hvilken platform og hvilken teknologi de fortr&#230;kker. Jeg vil betragte denne service(endpoint) som et sted at starte og jeg h&#229;ber at wsdl filen fort&#230;ller mig om de n&#230;ste skridt jeg kan tage.

Jeg h&#248;re til den nysgerrige type og vil fors&#248;ge at forbruge denne service med med udgangspunkt i SOAP beskeden selv, alts&#229; &quot;the Envelope&quot;. I konvolutten ligger information om sikkerhed, transaktioner og andre, for mig, ligegyldige ting.

Klient koden til en soap 1.2 besked med standart Java 1.6 indbygende features.

&lt;pre&gt;
QName serviceName = new QName(service_namespace, service_name);
QName servicePort = new QName(service_namespace, service_port);

// Create a service and add at least one port to it.
Service service = Service.create(serviceName);
service.addPort(servicePort, SOAPBinding.SOAP12HTTP_BINDING, service_endpoint);

// Create a Dispatch instance from a service.
Dispatch&lt;SOAPMessage&gt; dispatch = service.createDispatch(servicePort, SOAPMessage.class, Service.Mode.MESSAGE);

// compose a request message
MessageFactory mf = MessageFactory.newInstance(SOAPConstants.SOAP_1_2_PROTOCOL);

// Create a message with the SOAPPART.
SOAPMessage request = mf.createMessage();
SOAPPart part = request.getSOAPPart();

// Obtain the SOAPEnvelope and header and body elements.
SOAPEnvelope env = part.getEnvelope();
SOAPHeader header = env.getHeader();
SOAPBody body = env.getBody();

// Construct the message payload, ant binding type value
SOAPElement operation = body.addChildElement(business_method, &quot;ns1&quot;, service_namespace);
SOAPElement value = operation.addChildElement(&quot;arg0&quot;);
value.addTextNode(business_args);
request.saveChanges();

// Invoke the service endpoint.
SOAPMessage o = dispatch.invoke(request);

// Get reply content
Source sc = o.getSOAPPart().getContent();
&lt;/pre&gt;

I dette eksempel var en IDE n&#248;dvendig b&#229;de fordi der er alt for meget kode og fordi JAXB bibliotekerne i denne EA version er noget forskellige fra den tidligere. Et par ting der er v&#230;rd at l&#230;gge m&#230;rke til: Jeg m&#229; bygge et soap xml request p&#229; Java's kedelige set get'er metodik. Ydermere, tiltrods for at jeg selv har konstrueret denne service m&#229; jeg ind i wsdl filer for at finde navnet hvori input best&#229;r, isPalindrome(String word) er alts&#229; blevet til en r&#230;kke af inputparameter med fortl&#248;bende arg0, arg1 osv. V&#230;k er det fine proxy objekt med stub'ens metode navne og hele interaktionen er alt for lowlevel for min smag. Og man bliver nu n&#248;dt til at bruge en Transformer for at MOF'e til et model objekt.

Klient koden til en soap 1.2 besked med Java 1.6 + Apache CXF.

&lt;pre&gt;
JaxWsDynamicClientFactory dcf = JaxWsDynamicClientFactory.newInstance();

URL serviceEnpoint = new URL(service_endpoint);
QName serviceName = new QName(service_namespace, service_name);
QName servicePort = new QName(service_namespace, service_port);

// create proxy and genered classes from wsdl
Client proxy = dcf.createClient(serviceEnpoint, serviceName, Thread.currentThread().getContextClassLoader(), servicePort);

// call method on proxy
Object[] res = proxy.invoke(business_method, business_args);

// use the new genered class in this classloader
Object palindrome = Thread.currentThread().getContextClassLoader().loadClass(business_class).newInstance();

p(palindrome.getClass());
p(palindrome.getClass().getMethods() );
&lt;/pre&gt;

Ahhh, noget mindre kode men stadig langt mere verbose en klienten med groovyWS. Men jeg fik min dynamiske proxy som svare til objektet p&#229; den anden side og det er muligt at kalde metoder direkte p&#229; proxy objektet. Hvor kom klient objektet fra? Tja de blev generet af wsgen udfra wsdl filen p&#229; samme m&#229;de som man ville g&#248;re p&#229; normal vis blot runtime. Ved den traditionelle metoder vil model v&#230;re dekoreret med referacer fra wsgen p&#229; compiletidspunkt hvor man med denne metoder f&#248;rst kender service objekterne runtime, dvs at ens model er uden reference til de generede service objekter.

Hvilket p&#229;pege et helt nyt sp&#248;rgsm&#229;l. Vil jeg arbejde p&#229; med en masse generede filer fra WSDL import eller vil jeg mappe en masse v&#230;rdier i wrapper klasser? Sjovt nok er der ikke en perfekt l&#248;sning p&#229; nogen af disse problemer.

N&#229;r et projekt i start fasen beslutter at bruge SOA/Webservices er det ikke fragmenteringen af service der kommer i f&#248;rste r&#230;kke. En regel siger at gamle udk&#248;rte lagacy systemer, og forretningens for&#230;ldede tanke m&#248;nstre, specificere det nye service layout. Lad mig g&#230;tte, dine services er store WS beskeder og det er kun n&#248;dvendigt at kalde ca 5 service for at udf&#248;re alle forretnings processer.

Hvis du kan svare ja til forg&#229;ende s&#230;tning har du en h&#229;rd kobling i dit system. Din udviklingsgruppe generet en domain model ud fra WSDL'er og der findes tusindvis af referencer til dine propriet&#230;re domain model. Den hurtige siger: vi har en rig domain model med et mapping layer! Okey, fint men samme problematik.

S&#229; hvordan opn&#229;r man en l&#248;s kobling med SOA og WebServices?

Kom til at t&#230;nke p&#229; at man ogs&#229; kunne omskrive legacy klasse til groovy.. 

&lt;pre&gt;
  def isPalindrome(String word)  {  word == word.reverse() }
&lt;/pre&gt;

</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-09-16T07:45:30Z</created-at>
    <id type="integer">147</id>
    <published type="boolean">true</published>
    <title>Dymamic SOAP</title>
    <updated-at type="datetime">2009-10-14T11:58:59Z</updated-at>
  </post>
  <post>
    <body>Hold da k&#230;ft hvor jeg er tr&#230;t af h&#229;ndv&#230;rkere! Nej, i dette tilf&#230;lde er h&#229;ndv&#230;rkerne faktisk super gode og grundige. Det er mere den administrende virksomhed bagved som fors&#248;ger at snyde mig. Virksomheden er EBK Huse A/S, Slagelse, de bygger arkitekttegnet individuel byggeri. Byggeteknisk er de rigtig gode. 

Jeg har k&#248;bt en arkitekttegnet individuel carport til kr. 300.000.- 

N&#229;r de vil &#248;ge deres fortjeneste benytter de et ord over for os novicer. N&#229;r de n&#230;vner ordret &quot;individuel l&#248;sning&quot; betyder det er der ikke f&#248;lger noget som helst med. Det du faktisk k&#248;ber er et skelet uden ganske almindelige forkommeden elementer. Efter min bedste overbevisning er ting som lys i en carport helt naturligt. Men nej. Hvad med isolering? Nej, det er vist heller ikke med selvom vi er blevet lovet at en lille fryser skulle kunne holde udhuset frostfrit. Hvad med str&#248;m udtag s&#229; vi selv kan s&#230;tte lys op? Nej, det er ikke med i prisen. Hvordan kan man s&#229; s&#230;tte en fryser til? Hvad med ledning til udhus? Nej, der er for langt til huset er svaret fra den markedansvarlige hos EBK.   

N&#229;r man skr&#230;ller alt larmen er der kun et signal tilbage. De vil t&#248;rre mig for penge. 

Jeg k&#248;bte en f&#230;rdig l&#248;sning med det hele og stillede ikke sp&#248;rgsm&#229;lstegn ved hverken pris eller indretning. Min klare forventning til en f&#230;rdig l&#248;sning indeholder ogs&#229; at lyset t&#230;nder i carporten n&#229;r jeg kommer hjem. Men min terminologi er langt fra den samme som EBK's administration. En sjov ting er det at deres dygtige h&#229;ndv&#230;rkere er p&#229; min side. Faktisk stoppede de arbejde i den tro at de manglede materialer og ikke kunne forst&#229; de manglen tiltag.      

Skylden er naturligvis min egen. Min forst&#229;else for at man eksplicit skal eftersp&#248;rge alle individuelle krav er for underudviklet. F&#248;ler jeg mig til grin. Ja fuldst&#230;ndigt. F&#248;ler jeg mig snydt? Ja, fuldst&#230;ndigt. Vil jeg v&#230;re kunde hos EBK igen. Nej. Jeg kan ikke selv bygge noget som helst, derfor k&#248;ber jeg ting. Og hvis det betyder at jeg alligevel skal bruge tid p&#229; at s&#230;tte mig ind i alle aspekter gider jeg ikke. 

S&#229; hvis du ikke har god tid til at detage i alle detaljer find en anden forretning end EBK i Slagelse. Eller m&#229;ske kan du li at f&#248;le dig snydt!

</body>
    <category-id type="integer" nil="true"></category-id>
    <created-at type="datetime">2009-08-17T16:25:45Z</created-at>
    <id type="integer">146</id>
    <published type="boolean">true</published>
    <title>Cheap Craftsmanship</title>
    <updated-at type="datetime">2009-08-19T07:26:09Z</updated-at>
  </post>
</posts>
