Blog | DennisSangmo.se

I’ve been using Nhibernate for a while now and found a way to handle queryfiltering when the user needs to have a lot of filter possabilities. That is a big form with a lot of inputs for the user to fill in.

The controlleraction

The controller action might look something like this:

 

The InputModel

As you can see in the gist above its acctually the inputmodel that’s in charge of the condition applying and not the controller itselves. This is done with the magic of Expressions and Funcs in c#. Here it is:

 

In the example above you can see a property being set in the contructor. What this actually means is that when a user is running the action in the controller the modelbinder will create an instance of the inputmodel and the constructor will act as the default values of the filter form. When the user is filling in the form from the view the modelbinder vill override thies values wich we want.

 

Extenssion

Since NHibernate dont actually have a Where method on thier IQueryOver interface wich supports a IEnumerable of conditions we need to create a extenssion method for it. But that is simple enought. It could look something like this:

 

JoinQueryOver

The nice thing with this architecture is that we can expand the inputmodel to handle filtering of fetched objects aswell. I could look something like this:

 

I dont think i need to show you have the inputmodel ”PackageConditions()” method will look like since it will basicly look like the ”Conditions()” method but with the packagetype as Func generic (Func).

 

Maybe in a later blogpost i can tell you guys how you can use this method of filtering with a paged list, where we dont load all rows from the database.

Jag rekomenderar att läsa hela artiklen här: https://github.com/thomasdavis/best-practices

För eget intresse tog jag ut några punkter jag fann intressanta!

 

Don’t do hard things, do easy things.

  • Simple is better than complex.
  • Complex is better than complicated.
  • Flat is better than nested.
  • Readability counts.
  • If the implementation is hard to explain, it’s a bad idea.
  • If the implementation is easy to explain, it may be a good idea.

Refactoring > Rewriting

Common Excuses For A Software Rewrite

  1. The Code Sucks
  2. ”We’re So Much Smarter Now”
  3. We Picked The Wrong Platform/Language

Why Rewriting Is (Almost) Never A Good Idea

  1. It Will Take Longer Than You Think
  2. Markets Change
  3. Existing Customers Become Frustrated
  4. Refactoring Can Cleanup The Code
  5. You Don’t Control The Rewrite, It Controls You

To write effective unit tests, you need to write testable code

Flaw #1: Constructor does Real Work

Warning Signs

  • new keyword in a constructor or at field declaration
  • Static method calls in a constructor or at field declaration
  • Anything more than field assignment in constructors
  • Object not fully initialized after the constructor finishes (watch out forinitialize methods)
  • Control flow (conditional or looping logic) in a constructor
  • Code does complex object graph construction inside a constructor rather than using a factory or builder
  • Adding or using an initialization block

Flaw #2: Digging into Collaborators

  • Objects are passed in but never used directly (only used to get access to other objects)
  • Law of Demeter violation: method call chain walks an object graph with more than one dot (.)
  • Suspicious names: context, environment, principal, container, or manager

Flaw #3: Brittle Global State & Singletons

Warning Signs

  • Adding or using singletons
  • Adding or using static fields or static methods Adding or using static initialization blocks Adding or using registries
  • Adding or using service locators

Flaw #4: Class Does Too Much

Warning Signs

  • Summing up what the class does includes the word “and”
  • Class would be challenging for new team members to read and quickly “get it” Class has fields that are only used in some methods
  • Class has static methods that only operate on parameters

Detta inlägg kommer ge er en beskrivning på hur jag kontrollerar utfallet (assert) av mina tester så de är lättlästa och lätta att underhålla. NUnit är det ramverk jag använder mig av och ni kan hitta det på Nuget.

Standard

Om ni har använt er av NUnit tidigare så vet ni hur det fungerar när man skall kontrollera utfallet. Man måste hela tiden anropa den statiska klassen ”Assert” när man vill testa något. Så som exemplet nedan:

NUnit   
  1. [Test]
  2. public void Test_Int()
  3. {
  4. var toTest = 4;
  5. Assert.AreEqual(4, toTest);
  6. }

Yoda_1

När man läser detta från väster till höger, som man är van vid att göra i vanliga texter, så påminner det mig om Yoda från StarWars. Han är inte direkt känd för att ha den bästa meningsbyggnaden precis. Dessutom har det hänt att man placerar parametrarna fel i anropet, vilket kan leda till lite frågetecken om testet inte skulle gå igenom och man läser felmeddelandet.

Extension

Min lösning på problemet är att använda ”Extensionmethods” som introducerades till C# i version 3.0. Om vi tar samma exempel så ser det ut såhär istället:

Mitt test   
  1. [Test]
  2. public void Test_Int()
  3. {
  4. var toTest = 4;
  5. toTest.ShouldEqual(4);
  6. }

Själva ”extension”-klassen ser ut på följande sätt:

Extension   
  1. public static class NUnitExtensions
  2. {
  3. public static void ShouldEqual(this object a, object b, string message = "")
  4. {
  5. Assert.AreEqual(b, a, message);
  6. }
  7. }

Personligen tycker jag att det är viktigt att skriva lättläst kod även om det betyder en extra klass som tar hand om alla ”extension”-metoder. En annan fördel med detta är att man inte bara behöver testa värdet som skickas in, utan man kan också förändra det. Exempelvis dess typ.

Blanda in ”Generics”

Om vi sedan blandar in ”Generics” i bilden så kan man enkelt få ”extension”-metoderna att retunera värdet och på så sätt fortsätta testa det. Se exemplet nedan:

Testet   
  1. [Test]
  2. public void Test_Int()
  3. {
  4. var toTest = new List<User>
  5. {
  6. new User { Name = "Dennis" }
  7. };
  8. toTest.ShouldBeCountedTo(1)
  9. .And()
  10. .First().Name.ShouldEqual("Dennis");
  11. }

Observera metoden ”And()”. Dess syfte är inte att testa något utan endast att göra ”Assert”:en ännu mer lättläst.  Det är dock en smaksak om man ska använda eller hur ofta man använder den metoden. Kollat vi på ”extension”-metoderna som används i detta exemplet så ser de ut såhär:

Testare   
  1. public static T ShouldNotBeNull<T>(this T a)
  2. {
  3. Assert.IsNotNull(a);
  4. return a;
  5. }
  6. public static IEnumerable<T> ShouldBeCountedTo<T>(this IEnumerable<T> a, int count)
  7. {
  8. a.ShouldNotBeNull();
  9. if(a.Count() != count)
  10. {
  11. throw new Exception(string.Format("Count failed! Expected: {0} but was: {1}", count, a.Count()));
  12. }
  13. }
  14.  
  15. public static T And<T>(this T a)
  16. {
  17. return a;
  18. }

Typa om

En annan sak man kan göra med denna typ av testning är att typa om ett värde samtidigt som man testar det, för att därefter retunera värdet av den rätta typen. Det kan exempelvis se ut såhär:

Testet   
  1. [Test]
  2. public void Test_Int()
  3. {
  4. object toTest = User { Name = "Dennis" };
  5. toTest.ShouldBeOfType<User>()
  6. .And()
  7. .Name.ShouldEqual("Dennis");
  8. }

Som ni kan se så sparar jag ”User” objectet i en ”object”-typad variabel, vilket betyder att man inte når ”Name” egenskapen innan man typat om den.

Testare   
  1. public static T ShouldBeType(this object a)
  2. {
  3. try
  4. {
  5. var tmp = (T)a;
  6. return tmp;
  7. }
  8. catch (Exception)
  9. {
  10. throw new Exception(string.Format("Expexted type: {0}. But was: {1}", typeof(T).Name, typeof(a).Name));
  11. }
  12. }

Smidigt! Eller var tycker du?

Slutligen

Denna metoden gör inte bara att era tester blir lättare att läsa. Utan den gör också att det blir roligare att skriva testerna. Gör mig en tjänst och testa detta i ert nästa projekt!

Detta är ett schema eller skall man säga program som jag utformat åt mig själv. Ni är självklart välkomna att använda den eller delar av den för att uppnå ert sommarmål.

Schemat är format för personer som är nya till träningen eller personer som inte har tränat på ett tag så som jag.

Veckoschema

V2

Lätt
Kondition

V3

Lätt
Kondition

V4

Lätt
Kondition

V5

Lätt
Kondition

V6

Medel
Kondition

V7

Medel
Kondition

V8

Tung

V9

Tung
Fail

V10

Tung

V11

Tung
Fail

V12

Tung

V13

Tung
Fail

V14

Tung

V15

Tung
Fail

V16

Tung

V17

Tung
Fail

V18

Deff
Kondition

V19

Deff
Kondition

V20

Deff
Kondition

V21

Deff
Kondition

V22

Deff
Kondition

Beskrivning

Lätt kondition

Vikter 25-50% av max
Tänk på
  • Fokus på kondition
  • Aldrig köra till fail
  • Få igång pulsen och flåset
Sets/Reps 3/20

Medel kondition

Vikter 50-75% av max
Tänk på
  • Samma som lätt men med tyngre vikter
Sets/Reps 3/12

Tung

Vikter 75-100% av max
Tänk på
  • Lyft, lyft och lyft
  • Fokusera på muskelkontakt
  • Varannan vecka till fail, vilket betyder att ta slut på sig helt i sista set:et. Detta görs genom att sänka vikterna 40-50% direkt efter sista set:et och lyft ett set. Repetera sedan detta utan att pausa.
Sets/Reps 3/8

Deff

Vikter 80-90% av max
Tänk på
  • Gå på morgonprominad
  • Dra ner på kolhydraterna i kosten
  • Få reps och lagom sets
Sets/Reps 3/8

Dagsschema

Kondition

Måndag Rygg, biceps & underarbar
Onsdag Bröst, triceps & axlar
Fredag Lår, vader & mage
Söndag Kondition

Tung

Måndag Rygg & biceps
Onsdag Bröst & triceps
Fredag Lår & vader
Söndag Mage, axlar & underarmar

Skrev ett inlägg till radio- och tv-tjänst facebook-sida som jag tycker alla ska läsa och fråga sig själv ”Får det gå till såhär?”!

 

http://www.facebook.com/psjagbetalar/posts/10151133269767374

Under den senaste tiden har jag lagt märke till allt för många sidor som har svåra eller rent ut sagt dåliga formulär. Med frasen ”dåliga formulär” menar jag inte att man måste fylla i känslig information eller tjänsten på sidan inte är värt tiden man måste lägga på formuläret. Nej, jag syftar på användarupplevelsen där det kan vara svårt att förstå var och hur man skall fylla in sin information.

Jag har därför samlat några konkreta tips som jag tycker ni alltid skall ha med i bakhuvudet när ni skapar eller designar formulär.

1. Visa vad som händer

Det är mycket enerverande när man befinner sig på en sida väntandes utan att få reda på om man väntar förgäves. Det kan exempelvis vara när man fyllt i och skickat in ett formulär och när man klickar på ”Skicka in” utan att det händer något. Många av dessa fall slutar med att man stänger, uppdaterar eller stoppar förfrågan. Med tanke på att alla besökare är olika med olika smärt-trösklar så är det bättre att vara övertydlig.

Ett billigt och relativt enkelt sätt att hålla användarna glada och nöjda i situationer likt denna är att implementera något som visualiserar att servern arbetar. Det räcker med en liten bild som presenteras eller att ”Skicka in” knappen blir inaktiverad.

2. Validera och presentera felen

Att validera sina formulär är något man får lära sig i ett väldigt tidigt om man studerat webbutveckling och om du inte gör det eller om du vet med dig att du skippat det för att spara tid. Ni måste börja validera och förstå hur viktigt det är att användaren får veta vad denne gör för fel.

Alla användare förstår inte alltid vad de gjort för fel när de fyllt i ett formulär, därför kan det vara en god ide att berätta för användaren vad du måste göra för att korrigera felet.

3. Minska risken för felformaterad information

Man kan tro att denna punkt negligerar den tidigare punkten. För om du kan få användaren att förstå vad och hur de skall fylla i sin information i formuläret så kommer de inte få ett valideringsfel presenterat för sig. Men så är det inte.

När man hjälper användaren med formateringen av informationen så undviker man inte bara användaren från att trilla tillbaka vid valideringsfel. Man gör också så användarna inte behöver tänka på hur de skall mata in information och att inte behöva tänka är något som uppskattas!

När kan behöva hjälpa användaren? Vad kan man göra för att minska risken för felformaterad information?

Ett klockrent fall när man eventuellt måste hjälpa användaren är vid ett datumfält. Det finns många sätt att mata in datum på och när det endast finns ett textfält för datumet så kan det vara lagom förvirrande. Min rekommendation är att titta på JQuery UI biblioteket som tillhandahåller en funktion som gör om ett helt vanligt textfält till ett ”datumfält”. Funktionen heter ”datepicker” och har goda möjligheter att anpassas.

Det finns en hel del fler fall det det kan behövas hjälp med formatering så som vid telefonnummer, webbadresser med mera.

4. Smarta standardval

Förvalda alternativ kan vara en bra sak att implementera i sina formulär om man vet ungefär vilken målgrupp man försöker nå. Dock måste man vara medveten om att den del av användare som faktiskt inte lägger mycket möda på formuläret utan bara klickar sig förbi kommer ha angett standard alternativet. I deras fall hade det varit bättre att de fångades av en validator (punkt 2) som faktiskt tvingar dem till att ange något.

Innan man tänker på att ”vara snäll” mot sina användare genom att sätta smarta standard val måste man ställa sig frågan ”Finns där något klockrent standardval för detta fält?”

5. Underlätta ifyllnad

Ett väl-designat och väl-kodat formulär skall inte bara vara lätt att förstå utan det skall också vara lätt att fylla i. Det kan exempelvis vara en sån liten sak som att man skall kunna klicka på texten vid en ”checkbox” för att klicka på boxen. Använd ”label” elementet med andra ord.

När användaren först överblickar formuläret så skall denne förstå vad som är viktigt och vilka delar som är relaterade till varandra. Detta kan man som utvecklare genomföra genom att ställa sig följande frågor:

  • Är storeken på objektet vettigt för dess betydelse?
  • Finns där tillräckligt avstånd mellan formulär-fälten så de inte blandas ihop?
  • Kan man gruppera vissa formulär-fält för att betona deras sammanhållning?
Men precis som allt här i livet så skall allt tas i måttliga mängder och det gäller även denna frågeställning.

6. Hjälp och dokumentation

Det värsta man kan göra som designer eller programmerare är att anta att användarna kommer förstå det man implementerar. Detta är ingen perfekt värld och alla ser på saker olika därför är det viktigt att vara tydlig i sina formulär. Kanske till och med övertydlig.

Hjälp och dokumentation kan komma i olika former. Det kan exempelvis vara så simpelt som en ljusgrå text i text-fältet som suddas bort när användaren fokuserar i fältet. Ibland räcker inte detta utan man får ta till med en ikon som presenterar en informativ ”tooltip” när musen vilar över.

Frågan ni måste ställa er efter ni har implementerat något som förklarar eller hjälper användarna är: ”Kommer detta störa de användarna som inte behöver hjälp?”.

Sammanfattning

Var medvetna att alla nämnda punkter ovan inte alltid kan appliceras i alla situationer. Men se till att alltid ha haft de i bakhuvudet så ni inte missar den gången det verkligen behövs.

Det bästa sättet att lokalisera var och om formulären behövs förbättras är genom att inspektera när en faktisk användare faktiskt får testa era formulär. Få dem att berätta vad de tänker när de testar så kommer ni få god insikt i vilka delar av formuläret som behövs förbättras.

OUYA kontrollen

Det var inte länge sedan jag fick den så kallade ”yellow light of death” på mitt PS3. Efter ett tappert försök att återställa den med en hårfön så fick jag den att fungera i ytterligare 2 månader, men nu har jag gett upp.

Det är i alla fall min anledning till att jag glider från min spelkonsol på TV-apparaten mer och mer.

Jag hittade sedan OUYA-projektet som tände en ny flamma i mig. Jag är riktigt intresserad av deras ide och imponerade över engagemanget det lägger ner. Det faktum att produkten är anpassad för dagens marknad genom att mycket är anpassningsbart och öppet i den gör denna produkten, tror jag, till ett bra alternativ.

Både Twitch.tv och Minecraft kommer finnas på konsolen initialt vilket är ett stort plus!

Det ser ju ljust ut!

De söker just nu stöd för att starta projektet där de satt upp ett mål på $950 000. Idag när jag skriver detta har de samlat in strax över $3 300 000, vilket är positivt för deras framtid. Jag undrar hur mycket Notch (Markus Person, skapare av Minecraft) har donerat i detta projekt.

Panorama - Visby kyrka (S:ta Karin)

Panorama - Fårö rauk