SlideShare a Scribd company logo
Unit Test & TDD
Sendo Workshop
Viet Tran - Sendo Software Architect
viettranx@gmail.com
AGENDA
▸ Unit Test: What & Why
▸ Current problems at Sendo and solution
▸ Clean Architecture
▸ TDD - Test Development Driven
▸ Demo: Write Unit Test, the right way
WHAT IS UNIT TEST ?
Unit testing is a software development process in which the
smallest testable parts of an application, called units, are
individually and independently scrutinized for proper
operation.
WHY UNIT TEST ?
▸ Unit tests detect changes that may break a design contract
▸ Standardize: Unit testing improves the quality of code
▸ Unit testing helps reduce the cost of bug fixes
▸ It's fun
EXAMPLE FOR UNIT TEST
func Sum(x int, y int) int {
return x + y
}
func TestSum(t *testing.T) {
total := Sum(5, 5)
expect := 10
assert.Equal(t, 10, total, "should be qual")
}
EXAMPLE FOR UNIT TEST
func Sum(x int, y int) int {
return x + y
}
func TestSum(t *testing.T) {
tables := []struct {
args []int
expect int
}{
{[]int{5,5}, 10},
{[]int{8,9}, 17},
{[]int{1,0}, 1},
}
for _, c := tables {
actual := Sum(c.args[0], c.args[1])
assert.Equal(t, actual, c.expect, "should
be qual")
}
}
LAUNCHING TESTS
$ go test -v
This picks up any files matching packagename_test.go
$ go test -cover
PASS
coverage: 66.67% of statements
CURRENT PROBLEMS AT SENDO
▸ Have no Unit Test, QC have to test manually and full flow.
▸ High tightly coding, every change might break the others.
▸ Huge function body, very hard to maintain.
▸ CI/CD does not support Unit Test checking.
CURRENT PROBLEMS AT SENDO (CONTINUE)
LOGIC 1 LOGIC 2 LOGIC 3 LOGIC ...Huge Function
DBConcrete Objects REST CALL SERVICE CALL
It's very hard to maintain these stuff
Most of problems in software development
can be solved by delegation
HOW DOES DELEGATION WORKS ?
LOGIN CONCRETE LOGIN DB
I know who you are and what exactly you can do
I need to login Just wait until I finish my job
HOW DOES DELEGATION WORKS ? (CONTINUE)
LOGIN CONCRETE LOGIN DB
I don't know who you are but what exactly you can do
I need to login Just call and I will implement it.
DELEGATION / ABSTRACTION
HOW DOES DELEGATION WORKS ? COME TO TESTING
LOGIN TEST MOCK LOGIN DB
Independently testing: Testing without real DB connection
I need to run testing Simulate all cases of login function
DELEGATION / ABSTRACTION
Instead of direct calling, we use delegation
UNIT TEST EXAMPLE: IS IT A GOOD PRACTICE ?
type Thing struct{}
func InsertThing(doc *Thing) error {
session, err := mgo.Dial("localhost")
if err != nil {
return errors.New("Can not connect to db")
}
defer session.Close()
db := session.DB("test")
db.Collection("things").Insert(doc); err != nil {
return errors.New("Can not insert thing")
}
return nil
}
UNIT TEST EXAMPLE: IS IT A GOOD PRACTICE ? (CONT.)
It's bad practice.
WHY ?
type Thing struct{}
func InsertThing(doc *Thing) error {
session, err := mgo.Dial("localhost")
if err != nil {
return errors.New("Can not connect to db")
}
defer session.Close()
db := session.DB("test")
db.Collection("things").Insert(doc); err != nil {
return errors.New("Can not insert thing")
}
return nil
}
UNIT TEST EXAMPLE (CONTINUE)
type Thing struct{}
func InsertThing(doc *Thing) error {
session, err := mgo.Dial("localhost")
if err != nil {
return errors.New("Can not connect to db")
}
defer session.Close()
db := session.DB("test")
db.Collection("things").Insert(doc); err != nil {
return errors.New("Can not insert thing")
}
return nil
}
CONNECT DB
INSERT THING
UNIT TEST EXAMPLE (CONTINUE)
func TestInsertThing(t *testing.T) {
doc := Thing{}
err := InsertThing(&doc)
assert.NotNil(t, err, "should be not nil")
}
A basic Unit Test for InsertThing
UNIT TEST EXAMPLE (COVERAGE)
type Thing struct{}
func InsertThing(doc *Thing) error {
session, err := mgo.Dial("localhost")
if err != nil {
return errors.New("Can not connect to db")
}
defer session.Close()
db := session.DB("test")
db.Collection("things").Insert(doc); err != nil {
return errors.New("Can not insert thing")
}
return nil
}
func TestInsertThing(t *testing.T) {
doc := Thing{}
err := InsertThing(&doc)
assert.NotNil(t, err, "should be not nil")
}
▸ We need a real DB Connection.
▸ We cannot cover all cases.
UNIT TEST EXAMPLE: SOLUTION
type Thing struct{}
type DataAccessLayer interface {
Insert(collectionName string, docs interface{}) error
}
func InsertThing(dal DataAccessLayer, doc *Thing) error {
if err := dal.Insert("things", doc); err != nil {
log.Println(err)
return err
}
return nil
}
▸ We don' t need a real DB Connection.
▸ We can cover all cases now.
So far, at Sendo, we've had a very big source base.
How to apply delegation ?
Refactor it. Use Clean Architecture
CLEAN ARCHITECTURE
CLEAN ARCHITECTURE: SCALE TO FIT SENDO
USE CASE REPOSITORY MODEL
Implement all RPC methods
Business logic for each method
Implement data accessing
Computing/Processing data
Business model
Implement some validations
Independent flow: Interfaces
CLEAN ARCHITECTURE: SCALE TO FIT SENDO (EXAMPLE)
USE CASE REPOSITORY MODEL
UpdateProduct(product) Product
FindProductById(id)
UpdateProduct(product)
MONGO
FindProductById(id)
UpdateProduct(product)
REDIS
Very simple for micro services
That means it's very easy to test
Unit Test, the right way with TDD
Test Driven Development
TEST DRIVEN DEVELOPMENT FLOW
Write failing test
Run and fail test
Write code to pass
Run and pass test
Refactor
Well, we write Unit Test without
implementing main business logic
It's crazy !!!
That's the way Unit Test is tested.
We never do Unit Test for Unit Test !
Unit Test with CI (Gitlab)
Demo TDD by Coding
Quiz
Thank you

More Related Content

ODP
BDD with Cucumber
PDF
Microservice - Up to 500k CCU
PDF
Domain Driven Design with the F# type System -- F#unctional Londoners 2014
PPTX
Unit Testing And Mocking
PPTX
Clean Code
PPTX
Visitor design pattern
PDF
Introduction to jest
PDF
20220716_만들면서 느껴보는 POP
BDD with Cucumber
Microservice - Up to 500k CCU
Domain Driven Design with the F# type System -- F#unctional Londoners 2014
Unit Testing And Mocking
Clean Code
Visitor design pattern
Introduction to jest
20220716_만들면서 느껴보는 POP

What's hot (20)

PPTX
BDD with SpecFlow and Selenium
PPTX
Functional Patterns with Java8 @Bucharest Java User Group
PPTX
Cucumber BDD
PDF
Clean code
PPTX
Cucumber presenation
PPTX
The redux saga begins
PPTX
Unit tests & TDD
PDF
Java 8 features
PPTX
Testing of React JS app
PDF
Pipeline oriented programming
PPTX
BDD WITH CUCUMBER AND JAVA
PPSX
PPTX
신입 SW 개발자 취업 준비
PDF
Redux Sagas - React Alicante
ODP
Object Oriented Javascript
PDF
Windows Registered I/O (RIO) vs IOCP
PPTX
Katalon Studio - GUI Overview
PDF
Clean Lambdas & Streams in Java8
PDF
Unit Testing in Angular
PPTX
[0410 박민근] 기술 면접시 자주 나오는 문제들
BDD with SpecFlow and Selenium
Functional Patterns with Java8 @Bucharest Java User Group
Cucumber BDD
Clean code
Cucumber presenation
The redux saga begins
Unit tests & TDD
Java 8 features
Testing of React JS app
Pipeline oriented programming
BDD WITH CUCUMBER AND JAVA
신입 SW 개발자 취업 준비
Redux Sagas - React Alicante
Object Oriented Javascript
Windows Registered I/O (RIO) vs IOCP
Katalon Studio - GUI Overview
Clean Lambdas & Streams in Java8
Unit Testing in Angular
[0410 박민근] 기술 면접시 자주 나오는 문제들
Ad

Similar to Unit Test and TDD (20)

PPT
Test Driven Development
PDF
TDD reloaded - JUGTAA 24 Ottobre 2012
PPTX
Best practices unit testing
PPTX
Tdd is not about testing (OOP)
PPTX
In search of JavaScript code quality: unit testing
PDF
Getting Started With Testing
PPTX
Implicit classes - share the knowledge
PDF
1 aleksandr gritsevski - attd example using
PDF
Agile Android
PDF
Testing Django Applications
PPTX
RSpec: What, How and Why
ODP
Grails unit testing
PPT
Test-Driven Development Introduction
PDF
Refactoring
PDF
TDD Flow: The Mantra in Action
PDF
TDD - survival guide
PDF
Agile mobile
PPT
Acceptance Testing With Selenium
PDF
Unit Testing - The Whys, Whens and Hows
PPTX
Test Driven Development: Why I hate it; but secretly love it.
Test Driven Development
TDD reloaded - JUGTAA 24 Ottobre 2012
Best practices unit testing
Tdd is not about testing (OOP)
In search of JavaScript code quality: unit testing
Getting Started With Testing
Implicit classes - share the knowledge
1 aleksandr gritsevski - attd example using
Agile Android
Testing Django Applications
RSpec: What, How and Why
Grails unit testing
Test-Driven Development Introduction
Refactoring
TDD Flow: The Mantra in Action
TDD - survival guide
Agile mobile
Acceptance Testing With Selenium
Unit Testing - The Whys, Whens and Hows
Test Driven Development: Why I hate it; but secretly love it.
Ad

Recently uploaded (20)

PPT
“AI and Expert System Decision Support & Business Intelligence Systems”
PDF
Bridging biosciences and deep learning for revolutionary discoveries: a compr...
PDF
Building Integrated photovoltaic BIPV_UPV.pdf
PPTX
Understanding_Digital_Forensics_Presentation.pptx
PPTX
Big Data Technologies - Introduction.pptx
PPTX
Digital-Transformation-Roadmap-for-Companies.pptx
PDF
Per capita expenditure prediction using model stacking based on satellite ima...
PDF
cuic standard and advanced reporting.pdf
PDF
Electronic commerce courselecture one. Pdf
PPTX
VMware vSphere Foundation How to Sell Presentation-Ver1.4-2-14-2024.pptx
PDF
The Rise and Fall of 3GPP – Time for a Sabbatical?
PDF
NewMind AI Monthly Chronicles - July 2025
PPT
Teaching material agriculture food technology
PDF
Encapsulation_ Review paper, used for researhc scholars
PDF
Peak of Data & AI Encore- AI for Metadata and Smarter Workflows
PDF
TokAI - TikTok AI Agent : The First AI Application That Analyzes 10,000+ Vira...
DOCX
The AUB Centre for AI in Media Proposal.docx
PPTX
PA Analog/Digital System: The Backbone of Modern Surveillance and Communication
PDF
Approach and Philosophy of On baking technology
PDF
Machine learning based COVID-19 study performance prediction
“AI and Expert System Decision Support & Business Intelligence Systems”
Bridging biosciences and deep learning for revolutionary discoveries: a compr...
Building Integrated photovoltaic BIPV_UPV.pdf
Understanding_Digital_Forensics_Presentation.pptx
Big Data Technologies - Introduction.pptx
Digital-Transformation-Roadmap-for-Companies.pptx
Per capita expenditure prediction using model stacking based on satellite ima...
cuic standard and advanced reporting.pdf
Electronic commerce courselecture one. Pdf
VMware vSphere Foundation How to Sell Presentation-Ver1.4-2-14-2024.pptx
The Rise and Fall of 3GPP – Time for a Sabbatical?
NewMind AI Monthly Chronicles - July 2025
Teaching material agriculture food technology
Encapsulation_ Review paper, used for researhc scholars
Peak of Data & AI Encore- AI for Metadata and Smarter Workflows
TokAI - TikTok AI Agent : The First AI Application That Analyzes 10,000+ Vira...
The AUB Centre for AI in Media Proposal.docx
PA Analog/Digital System: The Backbone of Modern Surveillance and Communication
Approach and Philosophy of On baking technology
Machine learning based COVID-19 study performance prediction

Unit Test and TDD

  • 1. Unit Test & TDD Sendo Workshop Viet Tran - Sendo Software Architect viettranx@gmail.com
  • 2. AGENDA ▸ Unit Test: What & Why ▸ Current problems at Sendo and solution ▸ Clean Architecture ▸ TDD - Test Development Driven ▸ Demo: Write Unit Test, the right way
  • 3. WHAT IS UNIT TEST ? Unit testing is a software development process in which the smallest testable parts of an application, called units, are individually and independently scrutinized for proper operation.
  • 4. WHY UNIT TEST ? ▸ Unit tests detect changes that may break a design contract ▸ Standardize: Unit testing improves the quality of code ▸ Unit testing helps reduce the cost of bug fixes ▸ It's fun
  • 5. EXAMPLE FOR UNIT TEST func Sum(x int, y int) int { return x + y } func TestSum(t *testing.T) { total := Sum(5, 5) expect := 10 assert.Equal(t, 10, total, "should be qual") }
  • 6. EXAMPLE FOR UNIT TEST func Sum(x int, y int) int { return x + y } func TestSum(t *testing.T) { tables := []struct { args []int expect int }{ {[]int{5,5}, 10}, {[]int{8,9}, 17}, {[]int{1,0}, 1}, } for _, c := tables { actual := Sum(c.args[0], c.args[1]) assert.Equal(t, actual, c.expect, "should be qual") } }
  • 7. LAUNCHING TESTS $ go test -v This picks up any files matching packagename_test.go $ go test -cover PASS coverage: 66.67% of statements
  • 8. CURRENT PROBLEMS AT SENDO ▸ Have no Unit Test, QC have to test manually and full flow. ▸ High tightly coding, every change might break the others. ▸ Huge function body, very hard to maintain. ▸ CI/CD does not support Unit Test checking.
  • 9. CURRENT PROBLEMS AT SENDO (CONTINUE) LOGIC 1 LOGIC 2 LOGIC 3 LOGIC ...Huge Function DBConcrete Objects REST CALL SERVICE CALL It's very hard to maintain these stuff
  • 10. Most of problems in software development can be solved by delegation
  • 11. HOW DOES DELEGATION WORKS ? LOGIN CONCRETE LOGIN DB I know who you are and what exactly you can do I need to login Just wait until I finish my job
  • 12. HOW DOES DELEGATION WORKS ? (CONTINUE) LOGIN CONCRETE LOGIN DB I don't know who you are but what exactly you can do I need to login Just call and I will implement it. DELEGATION / ABSTRACTION
  • 13. HOW DOES DELEGATION WORKS ? COME TO TESTING LOGIN TEST MOCK LOGIN DB Independently testing: Testing without real DB connection I need to run testing Simulate all cases of login function DELEGATION / ABSTRACTION
  • 14. Instead of direct calling, we use delegation
  • 15. UNIT TEST EXAMPLE: IS IT A GOOD PRACTICE ? type Thing struct{} func InsertThing(doc *Thing) error { session, err := mgo.Dial("localhost") if err != nil { return errors.New("Can not connect to db") } defer session.Close() db := session.DB("test") db.Collection("things").Insert(doc); err != nil { return errors.New("Can not insert thing") } return nil }
  • 16. UNIT TEST EXAMPLE: IS IT A GOOD PRACTICE ? (CONT.) It's bad practice. WHY ? type Thing struct{} func InsertThing(doc *Thing) error { session, err := mgo.Dial("localhost") if err != nil { return errors.New("Can not connect to db") } defer session.Close() db := session.DB("test") db.Collection("things").Insert(doc); err != nil { return errors.New("Can not insert thing") } return nil }
  • 17. UNIT TEST EXAMPLE (CONTINUE) type Thing struct{} func InsertThing(doc *Thing) error { session, err := mgo.Dial("localhost") if err != nil { return errors.New("Can not connect to db") } defer session.Close() db := session.DB("test") db.Collection("things").Insert(doc); err != nil { return errors.New("Can not insert thing") } return nil } CONNECT DB INSERT THING
  • 18. UNIT TEST EXAMPLE (CONTINUE) func TestInsertThing(t *testing.T) { doc := Thing{} err := InsertThing(&doc) assert.NotNil(t, err, "should be not nil") } A basic Unit Test for InsertThing
  • 19. UNIT TEST EXAMPLE (COVERAGE) type Thing struct{} func InsertThing(doc *Thing) error { session, err := mgo.Dial("localhost") if err != nil { return errors.New("Can not connect to db") } defer session.Close() db := session.DB("test") db.Collection("things").Insert(doc); err != nil { return errors.New("Can not insert thing") } return nil } func TestInsertThing(t *testing.T) { doc := Thing{} err := InsertThing(&doc) assert.NotNil(t, err, "should be not nil") } ▸ We need a real DB Connection. ▸ We cannot cover all cases.
  • 20. UNIT TEST EXAMPLE: SOLUTION type Thing struct{} type DataAccessLayer interface { Insert(collectionName string, docs interface{}) error } func InsertThing(dal DataAccessLayer, doc *Thing) error { if err := dal.Insert("things", doc); err != nil { log.Println(err) return err } return nil } ▸ We don' t need a real DB Connection. ▸ We can cover all cases now.
  • 21. So far, at Sendo, we've had a very big source base. How to apply delegation ?
  • 22. Refactor it. Use Clean Architecture
  • 24. CLEAN ARCHITECTURE: SCALE TO FIT SENDO USE CASE REPOSITORY MODEL Implement all RPC methods Business logic for each method Implement data accessing Computing/Processing data Business model Implement some validations Independent flow: Interfaces
  • 25. CLEAN ARCHITECTURE: SCALE TO FIT SENDO (EXAMPLE) USE CASE REPOSITORY MODEL UpdateProduct(product) Product FindProductById(id) UpdateProduct(product) MONGO FindProductById(id) UpdateProduct(product) REDIS Very simple for micro services
  • 26. That means it's very easy to test
  • 27. Unit Test, the right way with TDD Test Driven Development
  • 28. TEST DRIVEN DEVELOPMENT FLOW Write failing test Run and fail test Write code to pass Run and pass test Refactor
  • 29. Well, we write Unit Test without implementing main business logic It's crazy !!!
  • 30. That's the way Unit Test is tested. We never do Unit Test for Unit Test !
  • 31. Unit Test with CI (Gitlab)
  • 32. Demo TDD by Coding
  • 33. Quiz