1 / 37

TDD

TDD. Börda, befrielse eller rent av en omöjlighet?. TDD – kort repetition. Röd Skriv först ett test som inte går igenom Grön Gör enklast möjliga implementation för att testet ska gå igenom Refactor Ta bort duplicerad kod. TDD – repetition rött. public class Person {

annick
Download Presentation

TDD

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. TDD Börda, befrielse eller rent av en omöjlighet?

  2. TDD – kort repetition • Röd • Skriv först ett test som inte går igenom • Grön • Gör enklast möjliga implementation för att testet ska gå igenom • Refactor • Ta bort duplicerad kod

  3. TDD – repetition rött publicclass Person { publicvoid SetGivenName(string s) {_givenName = s;} publicvoid SetSurname(string s) {_surname = s;} publicstring Fullname(){ returnnull;} string _givenName, _surname; } [TestFixture]publicclass PersonTests { [Test] publicvoid FullnameEmptyInitially() { Person p = new Person(); A.AreEqual(string.Empty, p.Fullname()); } }

  4. TDD – repetition grönt publicstring Fullname() { string res = string.Empty; return res; } [TestFixture] publicclass PersonTests { [Test] publicvoid FullnameEmptyInitially() { Person p = new Person(); A.AreEqual(string.Empty, p.Fullname()); } [Test]publicvoid FullnameGivenOnly(){ Person p = new Person(); p.SetGivenName("Ingo"); A.AreEqual("Ingo", p.Fullname()); } [Test]publicvoid FullnameSurnameOnly(){ Person p = new Person(); p.SetSurname("Lundberg"); A.AreEqual("Lundberg", p.Fullname()); } [Test]publicvoid FullnameBoth(){ Person p = new Person(); p.SetGivenName("Ingo"); p.SetSurname("Lundberg"); A.AreEqual("Ingo Lundberg", p.Fullname()); } } publicstring Fullname(){ string res = string.Empty; res += _givenName != null ? _givenName : string.Empty; if (_givenName != null && _surname != null) res += " "; res += _surname != null ? _surname : string.Empty; return res; }

  5. TDD och automatik • Vad är syftet med röd, grön, refactor? • Röd; se till att du testar något • Grön; tja dit vill vi ju • Refactor; Ta bort duplicering och låt inte koden ruttna • Leder TDD automatiskt till god design? • Man måste kunna sina OO-principer … eller? • Patterns följer OO-principer

  6. Viktiga TDD-insikter för mig • Du ska känna förtroende till din egen kod • White box • Mockning skapade känslan för vad som är en Unit och när det verkligen är ett Unit-test • Jag växlar mellan state-based och interaction-based testning (http://www.martinfowler.com/articles/mocksArentStubs.html) • xUnit kan användas för värdefulla tester som i strikt mening inte är Unit tester

  7. TDD och Test • Statement coverage • Vid strikt TDD  100% • Defect insertion • Vilken rad i koden som helst som ”görs till fel” ska leda till rött • Förtroende för din kod • Om överskattat förtroende  bug • Vid bug • Hitta felet • Skriva test som exponerar felet • Rätta felet • Vad är alternativet till ej fullständig testsvit? • Inga alls • En större svit • Tillkommer integrations-, system-, acceptanstest, eller vad du nu kallar dem

  8. Mjukvarudesign i allmänhet och objektorienterad design i synnerhet

  9. Ruttnande design • Rigiditet (stelhet) – svårt att ändra då en ändring tvingar dig till ändringar på fler ställen (beroende moduler) • Bräcklighet – en ändring på ett ställe skapar problem på helt andra ställen • Orubblighet – kan inte återanvända koden ens på andra ställen i systemet, än mindre i andra system • Klibbighet – i designen eller miljön • När det är svårt att upprätthålla designen och man tar till hack • Utvecklingsmiljön så seg att man anpassar ändringarna till dess begränsningar • Onödig komplexitet • Onödig repetition • Ogenomtränglighet

  10. Beroendehantering • Förruttnelsen direkt eller indirekt orsakad av olämpliga beroenden mellan moduler • Skapa beroendebrandväggar över vilka beroenden inte propagerar • OO-design == hur man bygger dessa brandväggar • Principer • Tekniker = designmönster

  11. OO-principer • Open Closed Principle; OCP • Liskov Substitution Principle; LSP • Dependency Inversion Principle; DIP • Fler principer på: • http://www.objectmentor.com/resources/articles/Principles_and_Patterns.PDF • http://www.objectmentor.com/resources/articles/srp • Agile Software Development: Principles, Patterns, and Practices av Robert C. Martin

  12. Open-Closed Principle • En modul ska vara öppen för utökningar men stängd för förändringar. (A module should be open for extensions but closed for modification.) • Huh? • Myntat av Bertand Meyer (1988) • OCP är kärnan i möjligheterna/löftena med objektorientering

  13. Liskov’s Substitution Principle • Subtyper måste vara ersättningsbara för sina bastyper (där kod använder bastypen) • Subtypes must be substitutable for their base types • Barbar Liskov (1988)

  14. LSP a.k.a. Design By Contract • DBC - återigen Bertrand Meyer • En metod har Pre- och Post conditions • Rectangle.SetHeight • Pre • Assert: h > 0 • Post • Assert: _h == h • Assert: _w == old._w • Eiffel stöder detta i språket • Kan också uttrycka invarianser

  15. Dependency-Inversion Principle • Högre nivåns moduler ska inte vara beroende av lågnivåmoduler. Båda ska bero på (förlita sig på) abstraktioner. • Den högre nivåns modul står för den viktigaste policyn/strategin/affärsreglerna • Abstraktioner ska inte vara beroende av detaljer. Detaljer ska bero på (förlita sig på) abstraktioner. • Beroende till stabila konkreta klasser (som t.ex. System.String) är inte brott mot DIP. • OCP målet, DIP den primära mekanismen • Vi pratar om beroendebrandväggar nu!

  16. DIP; anti-strukturerad programmering public void Copy() { int c; while((c = ReadKbd()) != EOF) WritePrt(c); } Nytt krav! public void Copy(DeviceReader r, DeviceWriter w) { int c; while((c = r.Read()) != EOF) w.Write(c); }

  17. TDD och design eller vad har OO-principer och designmönster med TDD att göra?

  18. Testbarhet är #1 • Läsbar kod • För vem är kod läsbar? • Gemensamma referensramar • Testbarhet går före läsbarhet • De automatiska testerna i sig berättar om koden

  19. Typiska delar i en app • Domain Model • Persistent via O/R-mappning (object/relational) • Persistence • Data Access Objects • GUI modell • GUI

  20. Typiska delar i en app • TDD av Model • TDD av WebGuiMdl • Test med xUnit av Persistence • Ev. test av WebGuiMdlGlue

  21. TDD av DM • Testa objekt utan att bekymra sig om hur de lagras • POCO; Plain Old CLR Objects • POJO; Plain Old Java Objects • Publika metoder • State-baserad testning (se exempel snart) • Kan involvera mockning/stubbning men inte givet att det gör det

  22. Ett fall för DM • Någon kommer fram till disken med en bok i handen och vill låna den • Bibliotekarie • Låntagare • Bokexemplar

  23. Ett fall för DM [SetUp]protectedvoid Setup() { librarian = new Librarian(); book = new Book("Foo"); bookCopy = new BookCopy(book, 123); borrower = new Borrower(1); } [Test]publicvoid CheckOut() { librarian.CheckOut(borrower, bookCopy); A.AreEqual(borrower, bookCopy.BorrowedTo); A.IsTrue(borrower.IsBorrowing(bookCopy)); }

  24. TDD av GUI • Steg nummer 1; bort med kod från formuläret • Är detta månne ett större problem i MS-världen? • Så lite kod som möjligt ska vara otestad • Testar inte utseende med xUnit • Interaction-based testning (mockning) • State-based asserts förekommer

  25. TDD av GUI

  26. GUI; Mockning av samarbetspartners [SetUp] protectedvoid Setup() { foo = new Book("Foo"); bar = new Book("Bar"); IList books = new ArrayList(); books.Add(foo); books.Add(bar); coll = new DynamicMock(typeof(BookListingMdl.Collab)); coll.SetupResult("GetBooks", books); mdl = new BookListingMdl( (BookListingMdl.Collab)coll.MockInstance); view = new DynamicMock(typeof(BookListingView)); mdl.SetView((BookListingView)view.MockInstance); } [Test]publicvoid Render(){ view.Expect("BookEntry", "Bar", !SEL); view.Expect("BookEntry", "Foo", !SEL); mdl.Render(); view.Verify(); }

  27. GUI; Den testade koden publicvoid Render() { for(int i=0; i<_books.Count; i++) { Book book = (Book)_books[i]; bool selected = i == _selInx; _view.BookEntry(book.Title, selected); } }

  28. Web app

  29. DIP • Kravet på test-barhet leder till en lösning enligt Dependency Inversion Principle • Jag menar det 

  30. (Web) Service • Byt WebGuiMdl mot SvcMdl • Byt WebGuiMdlGlue mot SvcMdlGlue

  31. Andra tester • Persistence • Preparera data i databasen • Kör någon/några DAOs • Rensa i databasen • ”Klister” • Integrationstest, kan använda xUnit

  32. Rubriken Nå? Hur var det nu? Börda, befrielse, …

  33. Börda • Kostnad i att lära sig nytt arbetssätt • Skriva tester • Men det är ju kul! • Du behöver inte vänta till första underhållssvängen för att testerna ska ge återbäring • Måste behärska OO? • Kanske, kanske inte … men ganska många av mina bilder handlar om OO generellt utan direkt koppling till TDD • Kanske andra ser det annorlunda? • Jag råkar ha ganska mycket OO med mig in i TDD-land

  34. Befrielse • Ingenjörsdisciplin • Metodik på en för utvecklaren relevant nivå • Stödjer dig i kampen mot förruttnelsen (OO == beroendehantering) • Kvalitet • Våga ändra/förbättra kod • Utan tester vet man inte om saker rasar samman på andra ställen • Med åren blev iaf jag försiktigare med dans på slak lina  • Med tester kan vi sluta spekulera vad som ska ”OCP:as” • Bra för oss som utvecklare • Bra för kunden • Tillfredsställelse • Rött  • Grönt 

  35. (O)möjlighet • Naturligtvis inte! • Det mesta går att testa • Bryt ut klasser i eget paket • Alla xUnit tester är dock inte TDD • Men vem bryr sig då man har en bra uppsättning automatiska, snabbt exekverande, tester?

  36. Referenser • www.objectmentor.com • www.xprogramming.com • www.nunit.org • www.nmock.org

  37. Ingo • www.ingolundberg.com • www.knowit.se • www.dev112.com

More Related