3.20M
Категория: ПрограммированиеПрограммирование

Юнит-тестирование унаследованного кода безопасный рефакторинг

1.

e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
E
to
i
d
r
e
g
an
E
to
i
d
h
h
C
C
X #UFADEVCONF
X
F- O
F- O
PD EM
PD EM
D
D
r
e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
r
Юнит-тестирование унаследованного кода
безопасный
рефакторинг
r
o
or
or
or
e
g
an
h
C
X
F- O
PD EM
D
it
d
E
e
g
an
it
d
E
e
g
an
it
d
E
e
g
an
h
h
h
C
C
C
Ястребов
Виктор
-X
-X
-X
F
F
F
O
O
O
к. т. н.,Dведущий
разработчик
компании
“Тензор”D
P EM
PD EM
P EM
http://dc.ufacoder.com
D
D - 2018
D
it
d
E

2.

E
to
i
d
r
r
r
Компания
Тензор
ti o
ti o
Ed
Ed
to
i
d
r
to
i
d
r
E
e
e
e
e
СБИС - сеть
деловых коммуникаций
и обмена
электронными
g
g
g
g
n
n
n
n
a
a
a
a
h
h
h
h
документами
между компаниями,
госорганами
и обыкновенными
XC
XC
XC
XC
F O
F O
F O
F O
D
D
D
D
людьми
P EM
P EM
P EM
P EM
D
D
D
D
Свыше 1 000 разработчиков
Свыше 1 000
000 пользователей
r
o
or
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
t
di
E
Десктопная версия
e
g
n
a
h
C
X
F- O
PD EM
D
E
Веб-решение
e
g
n
a
h
C
X
F- O
PD EM
D
to
i
d
r
Приложение
e
g
an
h
C
X
F- O
PD EM
D
E
2

3.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
r
О чем будем
говорить
ti o
ti o
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
3

4.

e
g
an
E
to
i
d
r
r
r
О чем будем
говорить
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
Принципы
создания тестируемого
кода
h
h
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
XC
F O
D
P EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
XC
F O
D
P EM
D
r
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
4

5.

e
g
an
E
to
i
d
r
r
r
О чем будем
говорить
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
Принципы
создания тестируемого
кода
h
h
h
XC
XC
F O
F Oобъектов
Понятие
поддельных
D
D
P EM
P EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
XC
F O
D
P EM
D
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
5

6.

e
g
an
E
to
i
d
r
r
r
О чем будем
говорить
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
Принципы
создания тестируемого
кода
h
h
h
XC
XC
F O
F Oобъектов
Понятие
поддельных
D
D
P EM
P EM
D
D
Разбор на примере
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
XC
F O
D
P EM
D
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
6

7.

e
g
an
E
to
i
d
r
r
r
О чем будем
говорить
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
Принципы
создания тестируемого
кода
h
h
h
XC
XC
F O
F Oобъектов
Понятие
поддельных
D
D
P EM
P EM
D
D
Разбор на примере
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
XC
F O
D
P EM
D
Общие рекомендации и практические приемы
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
7

8.


e
g
an
E
to
i
d
r
Допущения
ti o
r
e
g
an
Ed
Примеры
с использованием
С++
Ch
Ch
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
X
F- O
PD EM
D
to
i
d
e
g
an
to
i
d
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
8

9.


e
g
an
E
to
i
d
r
Допущения
ti o
r
e
g
an
Ed
Примеры
с использованием
С++
Ch
Ch
X
F- O
• PD Код
упрощен
EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
X
F- O
PD EM
D
e
g
an
e
g
an
to
i
d
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
9

10.

e
g
an
E
to
i
d
r
Допущения
ti o
r
e
g
an
Ed
Примеры
с использованием
С++
Ch
Ch
Используется Google Test
X
F- O
• PD Код
упрощен
EM
D
X
F- O
PD EM
D
e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
https://github.com/google/googletest/tree/master/googletest
r
r
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
10

11.

r
r
r
Пример
унаследованного
кода
ti o
ti o
ti o
Ed
Ed
e
e
g
g
n yzer {
n
a
a
class EntryAnal
h
h
public:
C
C
X Analyze( std::string enam-Xe ) {
F-bool
Oif( enam e.size() < 2 ) { DF O
D
M: " + enam e );
P EM w ebService.LogError(P "ErEror
D
D
return false;
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
}
return dbM anager.IsValid( enam e ) ;
};
}
r
private:
ti o
D atabaseM anager
dbM anager;
Eced w ebServi
W ebServi
ce;
e
g
n
a
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
11

12.

r
r
r
Пример
унаследованного
кода
ti o
ti o
ti o
Ed
Ed
e
e
g
g
n yzer {
n
a
a
class EntryAnal
h
h
public:
C
C
X Analyze( std::string enam-Xe ) {
F-bool
Oif( enam e.size() < 2 ) { DF O
D
M: " + enam e );
P EM w ebService.LogError(P "ErEror
D
D
return false;
}
return dbM anager.IsValid( enam e ) ;
};
}
r
private:
ti o
D atabaseM anager
dbM anager;
Eced w ebServi
W ebServi
ce;
e
g
n
a
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
to
i
d
r
to
i
d
r
E
e
e
g
g
n
n
a W ebService {
a
class
h
h
public:
XC void LogError( std::string
XCm sg ) {
F O
Fщ аяO
/* логика, вклю чаю
D
D
P EM
работу с сетевыPм соединением
*/
EM
D
D
}
};
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
12

13.

r
r
r
Пример
унаследованного
кода
ti o
ti o
ti o
Ed
Ed
e
e
g
g
n yzer {
n
a
a
class EntryAnal
h
h
public:
C
C
X Analyze( std::string enam-Xe ) {
F-bool
Oif( enam e.size() < 2 ) { DF O
D
M: " + enam e );
P EM w ebService.LogError(P "ErEror
D
D
return false;
}
return dbM anager.IsValid( enam e ) ;
};
}
r
private:
ti o
D atabaseM anager
dbM anager;
Eced w ebServi
W ebServi
ce;
e
g
n
a
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
Ed
to
i
d
r
E
e
e
g
g
n
n
a W ebService {
a
class
h
h
public:
XC void LogError( std::string
XCm sg ) {
F O
Fщ аяO
/* логика, вклю чаю
D
D
P EM
работу с сетевыPм соединением
*/
EM
D
D
}
};
class D atabaseM anager {
r
public: or
o
t
t
boolIsVal
di id( std::string enam e ) { Edi
/* E
логика, вклю чаю щ ая
e
e х*/
операции
чтения из базы данны
g
g
}
n
n
a
};ha
h
XC
F O
D
P EM
D
XC
F O
D
P EM
D
13

14.

e
g
an
E
to
i
d
r
r
Внешняяitorзависимость
ti o
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
Взаимодействие есть, а контроля нет
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
14
r

15.

r
r
r
r
Интеграционный
ti o
ti o тест VS iюнит-тест
to
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
e
g
an
Ed
e
g
an
Ed
e
g
an
Ed
h
h
h
C
C
C
X
-X
-X
F- Полный
F
F
контроль
O
O
O
PD EM
PD EM
PD EM
D
D
D
над внешними
зависимостями
Ed
r
ti o
нет
Ed
да
r
ti o
e
e
g
g
nИнтеграционный
n
a
a
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
тест
to
i
d
r
E
e
g
n
Юнит-тест
a
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
15
r

16.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
PD EM
PD EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P EM
P EM
D
D
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
16

17.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
X
X
F- O Результат F- O
• стабилен
PD EM
PD EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P EM
P EM
D
D
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
17

18.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
X
X
F- O Результат F- O
• стабилен
PD EM
PD EM
D
D
• повторим
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P EM
P EM
D
D
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
18

19.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
X
X
F- O Результат F- O
• стабилен
PD EM
PD EM
D
D
• повторим
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P EM
P EM
D
D
• независим
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
19

20.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
• стабилен
PD EM
PD EM
D
D
• повторим
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
E
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P Автоматизация
P EM
EM
D
D
запуска
• независим
to
i
d
to
i
d
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
20

21.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
• стабилен
PD EM
PD EM
D
D
• повторим
e
g
an
h
C
X
F- O
PD EM
D
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P Автоматизация
P EM
EM
D
D
• независим
r
o
t
•Edi Малое
Ed
to
i
d
r
o
t
i
время
d
E
e
g
n
a
h
XC
F O
D
P EM
D
запуска
r
o
t
i
выполнения
d
E
e
g
n
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
21

22.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
• стабилен
PD EM
PD EM
D
D
• повторим
e
g
an
h
C
X
F- O
PD EM
D
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P Автоматизация
P EM
EM
D
D
• независим
r
o
t
•Edi Малое
Ed
to
i
d
r
o
t
i
время
d
E
e
Малое время
g
n
a
h
XC
F O
D
P EM
D
запуска
r
o
t
i
выполнения
d
E
e
компиляции
g
n
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
22

23.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
• стабилен
PD EM
PD EM
D
D
• повторим
• независим
r
o
t
•Edi Малое
e
g
an
h
C
X
F- O
PD EM
D
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P Автоматизация
P EM
EM
D
D
запуска
r
r
o
o
t
t
i выполнения
i
время
d
d
E
E
e
e
Малое время
компиляции
g
g
n
n
a
a
h
h
Простота
чтения -XC
XC
F O
F O
D
D
M
P E
P EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
23

24.

E
to
i
d
r
Исходный
код
ti o
r
Ed
eyzer {
e
class EntryAnal
g
g
n
public: n
a
a
bool
h Analyze( std::string enam eC)h{
C
X if( enam e.size() < 2 ) { -X
F O w ebService.LogError( "Er
F ror:O" + enam e );
D
D
P EM return false;
P EM
}
D
D
to
i
d
r
to
i
d
r
E
E
e
e
classgW ebService {
g
n
n
publ
i
c:
a
a
h
h
voi
d
LogEr
r
or(
st
d:
:
st
ri
ng
m
C
C sg ) {
X
X
/* логика, вклю чаю -щ ая
F- O
Fсоединением
O
работу с сетевы м
*/
D
D
P EM }
P EM
D };
D
return dbM anager.IsValid( enam e );
};
}
private:
r dbM anager;
D atabaseM anager
o
t
W ebService i w ebService;
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
r
to anager {
to
class D atabaseM
i
i
publi
Ec:d
Ed
bool
e IsValid( std::string enam ege) {
g
n /* логика,вклю чаю щ ая an
a
операции чтения из базы
данны х*/
h
h
}
C
C
-X };
-X
F O
D
P EM
D
F O
D
P EM
D
24

25.

E
to
i
d
r
Исходный
код
ti o
r
Ed
eyzer {
e
class EntryAnal
g
g
n
public: n
a
a
bool
h Analyze( std::string enam eC)h{
C
X if( enam e.size() < 2 ) { -X
F O w ebService.LogError( "Er
F ror:O" + enam e );
D
D
P EM return false;
P EM
}
D
D
};
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
to
i
d
r
E
E
e
e
classgW ebService {
g
n
n
publ
i
c:
a
a
h
h
voi
d
LogEr
r
or(
st
d:
:
st
ri
ng
m
C
C sg ) {
X
X
/* логика, вклю чаю -щ ая
F- O
Fсоединением
O
работу с сетевы м
*/
D
D
P EM }
P EM
D };
D
Внешняя зависимость
return dbM anager.IsValid( enam e );
}
private:
r dbM anager;
D atabaseM anager
o
t
W ebService i w ebService;
to
i
d
E
to
i
d
r
r
r
to anager {
to
class D atabaseM
i
i
publi
Ec:d
Ed
bool
e IsValid( std::string enam ege) {
g
n /* логика,вклю чаю щ ая an
a
операции чтения из базы
данны х*/
h
h
}
C
C
-X };
-X
F O
D
P EM
D
F O
D
P EM
D
25

26.

E
to
i
d
r
Исходный
код
ti o
r
Ed
eyzer {
e
class EntryAnal
g
g
n
public: n
a
a
bool
h Analyze( std::string enam eC)h{
C
X if( enam e.size() < 2 ) { -X
F O w ebService.LogError( "Er
F ror:O" + enam e );
D
D
P EM return false;
P EM
}
D
D
to
i
d
r
to
i
d
r
E
E
e
e
classgW ebService {
g
n
n
publ
i
c:
a
a
h
h
voi
d
LogEr
r
or(
st
d:
:
st
ri
ng
m
C
C sg ) {
X
X
/* логика, вклю чаю -щ ая
F- O
Fсоединением
O
работу с сетевы м
*/
D
D
P EM }
P EM
D };
D
return dbM anager.IsValid( enam e );
};
}
private:
r dbM anager;
D atabaseM anager
o
t
W ebService i w ebService;
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
r
to anager {
to
class D atabaseM
i
i
publi
Ec:d
Ed
bool
e IsValid( std::string enam ege) {
g
n /* логика,вклю чаю щ ая an
a
операции чтения из базы
данны х*/
h
h
}
C
C
-X };
-X
F O
D
M
P EВнешняя
D
F O
D
P EM
зависимост
D
26

27.

E
to
i
d
r
Исходный
код
ti o
r
Ed
eyzer {
e
class EntryAnal
g
g
n
public: n
a
a
bool
h Analyze( std::string enam eC)h{
C
X if( enam e.size() < 2 ) { -X
F O w ebService.LogError( "Er
F ror:O" + enam e );
D
D
P EM return false;
P EM
}
D
D
to
i
d
r
to
i
d
r
E
E
e
e
classgW ebService {
g
n
n
publ
i
c:
a
a
h
h
voi
d
LogEr
r
or(
st
d:
:
st
ri
ng
m
C
C sg ) {
X
X
/* логика, вклю чаю -щ ая
F- O
Fсоединением
O
работу с сетевы м
*/
D
D
P EM }
P EM
D };
D
return dbM anager.IsValid( enam e );
};
}
private:
r dbM anager;
D atabaseM anager
o
t
W ebService i w ebService;
e
g
an
Ed
e
g
an
E
to
i
d
r
h
h
Внешние
зависимости
C
C
-X
-X
F O
D
P EM
D
F O
D
P EM
D
r
r
to anager {
to
class D atabaseM
i
i
publi
Ec:d
Ed
bool
e IsValid( std::string enam ege) {
g
n /* логика,вклю чаю щ ая an
a
операции чтения из базы
данны х*/
h
h
}
C
C
-X };
-X
F O
D
P EM
D
F O
D
P EM
D
27

28.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
Как сделать унаследованный код тестируемым
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
28
r

29.

r
r
r
Понятие программного шва
e
g
an
E
to
i
d
e
g
an
E
to
i
d
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
ШовCh — место вChкотором можно
изменить
h
h
C
C
X
X
X
-X этом
поведение
программы,
не
F- O
F- O
F- Oправя ее Fв
O
PD EM
PD EM
PD EM
PD EM
D
D
D
D
месте
• Виды швов:
– Предварительной
обработки
r
r
r
o
ti
ti o
ti o
– Этапа
компиляции
Ed
Ed
Ed
e
e
e
g
g
g
– aКомпоновочный
n
n
шов
n
a
a
h
h
h
C
C
C

Объектный
шов
X
X
X
FFF-
O
PD EM
D
O
PD EM
D
O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
29
r

30.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
e
g
an
h
C
X
F- O
PD EM
D
X
F- O
PD EM
D
r
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
Run-time
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
Компилятор
to
i
d
r
Слои тестирования
to
i
d
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
30

31.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
to
i
d
r
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Run-time
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
31

32.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
to
i
d
r
Машинный код
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Run-time
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
32

33.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
to
i
d
Машинный код
r
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
to
i
d
E
e
gфайл
Исполняемый
n
a
h
XC
F O
D
P EM
D
Run-time
e
g
an
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
33

34.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
to
i
d
Машинный код
r
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
to
i
d
E
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
e
gфайл
Исполняемый
n
a
h
XC
F O
D
P EM приложения
Выполнение
D
Run-time
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
34

35.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
to
i
d
Машинный код
r
Компоновщик
E
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
to
i
d
E
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
C
C
X
X
F- O
F- O
D M
M
PDШов
P
предварительной
обработки
E
E
D
D
r
E
e
gфайл
Исполняемый
n
a
h
XC
F O
D
P EM приложения
Выполнение
D
Run-time
e
g
an
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
35

36.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
Машинный код
r
ti o
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
D M
P
E
Выполнение
приложения
D
Run-time
e
g
an
E
to
i
d
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
C
C
X
X
F- O
F- O
D M
M
PDШов
P
предварительной
обработки
E
E
D
D
Шов этапа компиляции
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
36

37.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
Машинный код
r
ti o
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
D M
P
E
Выполнение
приложения
D
Run-time
e
g
an
E
to
i
d
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
C
C
X
X
F- O
F- O
D M
M
PDШов
P
предварительной
обработки
E
E
D
D
Шов этапа компиляции
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
Компоновочный шов
37

38.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
Машинный код
r
ti o
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
D M
P
E
Выполнение
приложения
D
Run-time
e
g
an
E
to
i
d
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
C
C
X
X
F- O
F- O
D M
M
PDШов
P
предварительной
обработки
E
E
D
D
Шов этапа компиляции
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
Объектный
D шов
Компоновочный шов
38

39.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
код
PDисходный
EM
D
X
F- O
PD EM
D
Компилятор
Машинный код
r
ti o
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
D M
P
E
Выполнение
приложения
D
Run-time
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
h
h
C
C
X
X
F- O
F- O
M
PD Eпредварительной
PDобработки
Шов
EM
D
D
Шов этапа компиляции
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
Объектный
D шов
Компоновочный шов
E
to
i
d
39
r

40.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
r
ti o
Машинный код
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
e
Ed
r
ti o
Исполняемый
ngфайл
a
h
XC
F O
D
P EM приложения
Выполнение
D
Run-time
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
h
h
C
C
X
X
F- O
F- O
M
PD EMШов предварительной
PD Eобработки
D
D
Шов этапа
r компиляции
r
o
ti
ti o
Ed
Ed
e
e
g
g
n
n
a
a
Компоновочный
шов
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
Объектный
D
D шов
40

41.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
Машинный код
r
ti o
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
r
ti o
e
g
Исполняемый
n
файл
a
h
C
X
F- O
D M
P
E
Выполнение
приложения
D
Run-time
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
h
h
C
C
X
X
F- O
F- O
M
PD EMШов предварительной
PD Eобработки
D
D
Шов этапа
r компиляции
to
i
d
to
i
d
E
E
e
e
g
g
n
n
a
a
h
h
Компоновочный
шов
XC
XC
F O
F O
D
D
M
P E
P EM
Объектный
D
D шов
41
r

42.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
r
ti o
Машинный код
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
E
e
g
an
E
to
i
d
r
h
h
C
C
X
X
F- O
F- O
M
PD EMШов предварительной
PD Eобработки
D
D
Шов этапа
r компиляции
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
PD EM
Выполнение
приложения
D
Run-time
e
g
an
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Компоновочный шовh
e
g
an
XC
F O
D
P EM
Объектный
D шов
E
to
i
d
42
r

43.

r
r
r
Признаки
хорошего
юнит-теста
ti o
ti o
ti o
Ed
Ed
e
Полныйngeконтроль над
g
n
a
a
h
h
C
C
Результат
X
X
F- O
F- O
• стабилен
PD EM
PD EM
D
D
• повторим
• независим
r
o
t
•Edi Малое
e
g
an
h
C
X
F- O
PD EM
D
Ed
to
i
d
r
to
i
d
r
E
e
e
внешнимиng зависимостями
g
n
a
a
h
h
XC
XC
F O
F O
D
D
P Автоматизация
P EM
EM
D
D
запуска
r
r
o
o
t
t
i выполнения
i
время
d
d
E
E
e
e
Малое время
компиляции
g
g
n
n
a
a
h
h
Простота
чтения -XC
XC
F O
F O
D
D
M
P E
P EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
43

44.

r
r
r
r
Принцип
наименования
юнит-теста
ti o
ti o
ti o
ti o
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
Ed
e
g
an
Ed
e
g
an
Ed
h
h
h
[ИмяТестируемойРабочейЕдиницы]_
C
C
C
-X
-X
-X
F
F
F
O
O
O
[СценарийТеста]_
PD EM
PD EM
PD EM
D
D
D
[ОжидаемыйРезультат]
r
r
r
ti o
ti o
ti o
Sum_ByDefault_ReturnsZero()
Ed
Ed
Ed
e
e
e
g
g
g
n
n
n
a
a
a
h
h
h
Sum_WhenCalled_CallsTheLogger()
C
C
C
X
X
X
F- O
F- O
F- O
PD EM
PD EM
PD EM
D
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
44
r

45.

E
to
i
d
r
r юнит-теста
r
Структура
ti o
ti o
Ed
e
e
e
g
g
g
n TEST_F( Calcul
n orTest,
n
a
a
a
at
h
h
h
C
C
C
X
X ault_ReturnsZero
Sum _ByDF-ef
-X )
F- O
F
O
O
{
PD EM
PD EM
PD EM
D
Dor calc;
D
Calculat
Ed
r
r
r
ti oint last_sum = cal
ti o c.Sum ();
ti o
Ed
Ed
Ed
e
e
e
g
g
g
n
n
n
a
a
a
h
h
h
C
C
C
X
ASSERT_EQ
X ( 0, last_sum );
X
F- O
F- O
F- O
}
PD EM
PD EM
PD EM
D
D
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
45

46.

E
to
i
d
r
r юнит-теста
r
Структура
ti o
ti o
Ed
e
e
e
g
g
g
n TEST_F( Calcul
n orTest,
n
a
a
a
at
h
h
h
C
C
C
X
X ault_ReturnsZero
Sum _ByDF-ef
-X )
F- O
F
O
O
{
PD EM
PD EM
PD EM
D
Dor calc;
D
Calculat
Ed
1.
r
r
r
ti oint last_sum = cal
ti o c.Sum ();
ti o
Ed
Ed
Ed
e
e
e
g
g
g
n
n
n
a
a
a
h
h
h
C
C
C
X
ASSERT_EQ
X ( 0, last_sum );
X
F- O
F- O
F- O
}
PD EM
PD EM
PD EM
D
D
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
Arrange
e
g
an
h
C
X
F- O
PD EM
D
46

47.

E
to
i
d
r
r юнит-теста
r
Структура
ti o
ti o
Ed
e
e
e
g
g
g
n TEST_F( Calcul
n orTest,
n
a
a
a
at
h
h
h
C
C
C
X
X ault_ReturnsZero
Sum _ByDF-ef
-X )
F- O
F
O
O
{
PD EM
PD EM
PD EM
D
Dor calc;
D
Calculat
Ed
1.
r
r
or
ti oint last_sum = cal
ti o c.Sum ();
ti2.
Ed
Ed
Ed
e
e
e
g
g
g
n
n
n
a
a
a
h
h
h
C
C
C
X
ASSERT_EQ
X ( 0, last_sum );
X
F- O
F- O
F- O
}
PD EM
PD EM
PD EM
D
D
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
Arrange
Act
e
g
an
h
C
X
F- O
PD EM
D
47

48.

E
to
i
d
r
r юнит-теста
r
Структура
ti o
ti o
Ed
e
e
e
g
g
g
n TEST_F( Calcul
n orTest,
n
a
a
a
at
h
h
h
C
C
C
X
X ault_ReturnsZero
Sum _ByDF-ef
-X )
F- O
F
O
O
{
PD EM
PD EM
PD EM
D
Dor calc;
D
Calculat
Ed
1.
e
g
an
E
to
i
d
r
h
C
X
F- O
PD EM
D
Arrange
r
r
r
or Act
ti oint last_sum = cal
ti o c.Sum ();
ti2.
ti o
Ed
Ed
Ed
Ed
e
e
e
e
g
g
g
g
n
n
n
n
a
a
a
a
h
h
h
h
C
C
C
C
3.
Assert
X
ASSERT_EQ
X ( 0, last_sum );
X
X
F- O
F- O
F- O
F- O
}
PD EM
PD EM
PD EM
PD EM
D
D
D
D
48

49.

E
to
i
d
r
r юнит-теста
r
Структура
ti o
ti o
Ed
e
e
e
g
g
g
n TEST_F( Calcul
n orTest,
n
a
a
a
at
h
h
h
C
C
C
X
X ault_ReturnsZero
Sum _ByDF-ef
-X )
F- O
F
O
O
{
PD EM
PD EM
PD EM
D
Dor calc;
D
Calculat
Ed
1.
e
g
an
E
to
i
d
r
h
C
X
F- O
PD EM
D
Arrange
r
r
r
or Act
ti oint last_sum = cal
ti o c.Sum ();
ti2.
ti o
Ed
Ed
Ed
Ed
e
e
e
e
g
g
g
g
n
n
n
n
a
a
a
a
h
h
h
h
C
C
C
C
3.
Assert
X
ASSERT_EQ
X ( 0, last_sum );
X
X
F- O
F- O
F- O
F- O
}
PD EM
PD EM
PD EM
PD EM
D
D
D
D
49

50.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
Понятие поддельных объектов
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
50
r

51.

r
r
Поддельные
реализации
or
ti o
ti o
ti объектов
e
g
an
Ed
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
Ed
h
Fake-объект
C
X
e
g
an
h
C
X
F- O
PD EM
D
E
Задача nge
зделения
a
h
ра
XC
F O
D
P EM
D
E
t
di
or
e
g
an
E
r
to
i
d
r
h
C
X
F- O
PD EM
D
F- O
PD EM
D
Stub-объект
or
t
di
e
g
an
Ed
to
i
d
Mock-объект
or
t
di
E
E
e
e
gЗадача
g
n
n
спознавания
a
a
h
h
ра
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
51

52.

e
g
an
E
to
i
d
r
r
Stub-объект
ti o
e
g
an
Ed
e
g
an
E
to
i
d
r
e
g
an
h
h
h
C
C
C
X
X
X
Взаимодействие
F- O
F- O
F- O
PD EM
PD EM
PD EM
D Тестируемый
D
D
код
e
g
an
h
C
X
F- O
PD EM
D
E
r
to
i
d
r
E
E
e
e
g
g
n
n
Тестовый
код
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
Stub
Взаимоде
йствие
to
i
d
r
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
52

53.

e
g
an
E
to
i
d
r
r
Mock-объект
ti o
e
g
an
Ed
e
g
an
E
to
i
d
r
e
g
an
h
h
h
C
C
C
X
X
X
Взаимодействие
F- O
F- O
F- O
PD EM
PD EM
PD EM
D Тестируемый
D
D
код
e
g
an
h
C
X
F- O
PD EM
D
E
r
to
i
d
r
E
E
e
e
g
g
n
n
Тестовый
код
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
Mock
Взаимоде
йствие
to
i
d
r
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
53

54.

e
g
an
E
to
i
d
r
r
Препроцессор
Ch
e
g
an
E
h
C
X
Модифицированный
F- O
D M
код
Pисходный
E
D
X
F- O
PD EM
D
Компилятор
r
ti o
Машинный код
Компоновщик
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
Слои тестирования
to
i
d
Ed
E
e
g
an
E
to
i
d
r
h
h
C
C
X
X
F- O
F- O
M
PD EMШов предварительной
PD Eобработки
D
D
Шов этапа
r компиляции
r
ti o
e
g
Исполняемый
файл
n
a
h
C
X
F- O
PD EM
Выполнение
приложения
D
Run-time
e
g
an
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Компоновочный шовh
e
g
an
XC
F O
D
P EM
Объектный
D шов
E
to
i
d
54
r

55.

e
g
an
E
to
i
d
r
r
Объектный шов
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
e
g
an
E
to
i
d
r
h
hточка находится
h
h
Разрешающая
на
этапе
C
C
C
C
X
X
X
X
F- O
F- O
F- O
F- O
D M
D M
D M
M
PDсоздания
объектов
P
P
P
E
E
E
E
D
D
D
D
r
r
r
r
Выбор стратегии
выполнения
ti o
ti o
ti o действияitoв
Ed
Ed
Ed
Ed
e
e
e
e
зависимости
от
используемого
объекта
g
g
g
g
n
n
n
n
a
h
XC
F O
D
P EM
D
a
h
XC
F O
D
P EM
D
a
h
XC
F O
D
P EM
D
a
h
XC
F O
D
P EM
D
55

56.

e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
Да
r
Объектный
шовitor
ti o
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
Режим PD EM
D
Тестирования?
Ed
e
g
an
Нет
E
to
i
d
r
h
C
X
F- O
PD EM
D
r
r
r
r
o
o
o
o
t
t
t
t
i
i
i
i
TestingDatabaseManager
DatabaseManager
d
d
d
d
E
E
E
E
e
e
e
e
g
g
g
g
n
n
n
n
a
a
a
a
h
h
h
h
XC
XC
XC
XC
F O
F O База данных
F O
F O
D
D
D
D
M
M
M
P E
P E
P E
P EM
D
D
D
D
56

57.

to
i
d
r
to
i
d
r
to
i
d
r
E
E
E
E
“Выделить
и
Использование
stub
e
e
e
e
g
g
g
g
n
n
n
n
a
a
a
a
переопределить”
h
h
h
h
для
разрыва
зависимости
C
C
C
C
-X
-X
-X
-X
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
F O
D
P EM
D
E
to
i
d
F O
D
P EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
r
to
i
d
r
F O
D
P EM
D
r
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
57

58.

e
g
an
E
to
i
d
r
r
Выделение
ti o зависимости
ti o
r
e
g
an
Ed
h
h
class EntryAnal
yzer {
C
C
publ
Xic:
-X
F-bool
F
O Analyze( std::string enam e )O{
PD EM if( enam e.size() < 2 ) {PD EM
w ebService.LogError( "Er
D
D ror: " + enam e );
return false;
}
return dbM anager.IsValid( enam e );
};
r
}
o
t
i
private:
d
E
D atabaseM anager
dbM anager;
e
W ebServi
g ce w ebService;
n
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
58

59.

e
g
an
E
to
i
d
r
r
Выделение
ti o зависимости
ti o
r
e
g
an
Ed
h
h
class EntryAnal
yzer {
C
C
publ
Xic:
-X
F-bool
F
O Analyze( std::string enam e )O{
PD EM if( enam e.size() < 2 ) {PD EM
w ebService.LogError( "Er
D
D ror: " + enam e );
return false;
}
e
g
an
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
hryAnalyzer {
h
class Ent
C
C
publ
Xic:
-X
F- bool
F
eO) {
O Analyze( std::string enam
PD EM
...
PD EM
D
D
return IsValid( enam e );
}
return dbM anager.IsValid( enam e );
};
r
}
o
t
i
private:
d
E
D atabaseM anager
dbM anager;
e
W ebServi
g ce w ebService;
n
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
protected:
o
t
i std::string enam e ) {
boolIsValid
d(
return E
dbM anager.IsValid( enam e );
e
}
g
ge
n
a
h
n
a
h
private:
D -at
XCabaseM anager dbM anager;-XC
F O ...
F O
};PD
EM
D
PD EM
D
59

60.

r
r
r
Переопределение
зависимости
ti o
ti o
ti o
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
E
to
i
d
r
hryAnalyzer {
h
class Ent
C
C
publ
Xic:
-X
F- bool
F
eO) {
O Analyze( std::string enam
PD EM
...
PD EM
D
D
return IsValid( enam e );
}
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
r
ti o
ti o
virtual bool
d IsValid( std::string enam Eed) {
E
return dbM anager.IsValid( enam e );
e
e
}
g
g
n
n
a
a
he:
h
privat
C
C
XabaseM anager dbM anager;-X
D -at
F O ...
F O
D
D
M
};P E
P EM
D
D
60
protected:

61.

r
r
r
Переопределение
зависимости
ti o
ti o
ti o
h
e
g
an
Ed
class C
TestingEntryAnalyzer :
-X ic EntryAnalyzer {
publ
F O
D
P publ
EMic:
D boolw illBeValid;
};
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
hEntryAnalyzer {
class
C
C
наследование
publ
-X
-X ic:
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
r
h
C
-X
F bool
F
eO) {
O Analyze( std::string enam
PD EM
...
PD EM
D
D
private:
boolIsValid( std::string enam e ) override {
return w illBeVal
id;
r
r
}
to
to
i
d
E
e
g
an
Ed
to
i
d
i
d
E
return IsValid( enam e );
}
r
r
protected:
o
o
t
t
i IsValid( std::string enam e )d{i
virtualbool
d
return E
dbM anager.IsValid( enam e ); E
e
}
g
ge
n
a
h
n
a
h
private:
D -at
XCabaseM anager dbM anager;-XC
F O ...
F O
};PD
EM
D
PD EM
D
61

62.

r
r
r
Переопределение
зависимости
ti o
ti o
ti o
Ed
тестируемый
класс
ge
n
a
h
class C
TestingEntryAnalyzer :
-X ic EntryAnalyzer {
publ
F O
D
P publ
EMic:
D boolw illBeValid;
};
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
hryAnalyzer {
class Ent
C
C
наследование
publ
-X
-Xic:
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
r
h
C
-X
F bool
F
eO) {
O Analyze( std::string enam
PD EM
...
PD EM
D
D
private:
boolIsValid( std::string enam e ) override {
return w illBeVal
id;
r
r
}
to
to
i
d
E
e
g
an
Ed
to
i
d
i
d
E
return IsValid( enam e );
}
r
r
protected:
o
o
t
t
i IsValid( std::string enam e )d{i
virtualbool
d
return E
dbM anager.IsValid( enam e ); E
e
}
g
ge
n
a
h
n
a
h
private:
D -at
XCabaseM anager dbM anager;-XC
F O ...
F O
};PD
EM
D
PD EM
D
62

63.

r
r
r
Переопределение
зависимости
ti o
ti o
ti o
Ed
тестируемый
класс
ge
n
a
h
class C
TestingEntryAnalyzer :
-X ic EntryAnalyzer {
publ
F O
D
P publ
EMic:
D boolw illBeValid;
};
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
hryAnalyzer {
class Ent
C
C
наследование
publ
-X
-Xic:
F O
D
P EM
D
private:
boolIsValid( std::string enam e ) override {
return w illBeVal
id;
r
r
}
to
to
i
d
E
e
g
an
Ed
внедрение
i
d
зависимости
E
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
-X
F bool
F
eO) {
O Analyze( std::string enam
PD EM
...
PD EM
D
D
return IsValid( enam e );
}
r
r
protected:
o
o
t
t
i IsValid( std::string enam e )d{i
virtualbool
d
return E
dbM anager.IsValid( enam e ); E
e
}
g
ge
n
a
h
n
a
h
private:
D -at
XCabaseM anager dbM anager;-XC
F O ...
F O
};PD
EM
D
PD EM
D
63

64.

r
r
r
r
Тестирование
возвращаемого
значения
ti o
ti o
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
h
h
C
C
TEST_F(
-X EntryAnalyzerTest,
-X
F
F
O
O
Analyze_Val
idEntryN am e_RetD
urnsTrue)
P{D EM
P EM
DTestingEntryAnalyzer ea; D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
h
C
X
F- O
PD EM
D
ea.w illBeValid = true;
boolresult = ea.Analyze( "valid_entry_nam e" );
}
r
ASSERT_EQ ( resul
to t,true );
e
g
an
h
C
X
F- O
PD EM
D
i
d
E
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
64
r

65.

r
r
r
r
Тестирование
возвращаемого
значения
ti o
ti o
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
h
h
C
C
TEST_F(
-X EntryAnalyzerTest,
-X
F
F
O
O
Analyze_Val
idEntryN am e_RetD
urnsTrue)
P{D EM
P EM
DTestingEntryAnalyzer ea; D
bool w illBeValid;
boolresult = ea.Analyze( "valid_entry_nam e" );
}
e
g
an
h
C
X
F- O
PD EM
D
i
d
E
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
Ed
h
h
C
C
class
-X TestingEntryAnalyzer : F-X
Fpubl
Oic EntryAnalyzer {
O
PD EM
PD EM
Dpublic:
D
ea.w illBeValid = true;
ASSERT_EQ ( resul
to t,true );
Ed
E
to
i
d
r
};
private:
boolIsValid( std::string enam e ) override {
r
r
o
o
return w til
lBeValid;
t
}
di
di
e
g
an
h
C
X
F- O
PD EM
D
E
e
g
an
h
C
X
F- O
PD EM
D
E
65

66.

озможные
проблемы
при
переопределени
r
r
r
r
ti o
ti o
ti o
ti o
зависимости
Ed
Ed
Ed
Ed
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h EntryAnalyzer {
class
C
X public:
F- O EntryAnalyzer() {
PD EM }
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r

};
e
g
an
h
C
X
F- O
PD EM
D
private:
D atabaseM anager dbM anager;
W ebService rw ebService;
E
to
i
d
class Test
ingEntryAnalyzer :
e
publg
ic EntryAnalyzer {
n
a
h
e
g
an
h
public:
C
C
X
X
F- O}TestingEntryAnalyzer()F{- O
PD EM boolw illBeValid; PD EM
D};
D
E
to
i
d
66
r

67.

озможные
проблемы
при
переопределени
r
r
r
r
ti o
ti o
ti o
ti o
зависимости
Ed
Ed
Ed
Ed
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h EntryAnalyzer {
class
C
X public:
F- O EntryAnalyzer() {
PD EM }
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r

};
e
g
an
h
C
X
F- O
PD EM
D
private:
D atabaseM anager dbM anager;
W ebService rw ebService;
E
to
i
d
class Test
ingEntryAnalyzer :
e
publg
ic EntryAnalyzer {
n
a
h
e
g
an
h
public:
C
C
X
X
F- O}TestingEntryAnalyzer()F{- O
PD EM boolw illBeValid; PD EM
D};
D
E
to
i
d
67
r

68.

to
i
d
r
to
i
d
r
to
i
d
Параметризация
E
E
e
e
ngконструктора.
ng
Использование
stub
e
e
g
g
n
n
a
a
a
h
h
h
для
разрыва
зависимости
C
C
C
-X
-X
-X
E
E
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
F O
D
P EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
to
i
d
r
a
h
XC
F O
D
P EM
D
F O
D
P EM
D
r
e
g
an
r
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
68

69.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
Ed
e
g
n
bool IsValid(
a
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
Ed
e
g
nename
std::string
a
h
C
X
F- O
PD EM
D
IDatabaseManager
to
i
d
r
to
i
d
r
E
E
FakeDatabaseManager
e
e
g
g
n
a
h
XC
F O
D
P EM
D
n
a
h
XC
F O
D
P EM
D
База
to
i
d
)
e
g
an
Ed
h
C
X
F- O
PD EM
D
r
E
E
DatabaseManager
e
e
g
g
n
a
h
XC
F O
D
P EM
данных
D
to
i
d
n
a
h
XC
F O
D
P EM
D
69
r

70.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
};
h
C
X
F- O
PD EM
D
e
g
an
Ed
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
Ed
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
70
r

71.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
};
h
C
X
F- O
PD EM
D
Ed
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
public:
boolW illBeValid;
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
std:
:
stri
ng
enam
e
)
{
a
a
h
h
XC} return W illBeValid;
XC
F O
F O
};
D
D
M
P E
P EM
D
D
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
Ed
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
71
r

72.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
public:
boolW illBeValid;
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
};
h
C
X
F- O
PD EM
D
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
std:
:
stri
ng
enam
e
)
{
a
a
h
h
XC} return W illBeValid;
XC
F O
F O
};
D
D
M
P E
P EM
D
D
h
C
X
F- O
PD EM
D
Ed
class D atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
h
C
X
F- O
PD EM
D
public:
boolIsValid( std::string enam e ) {
r
r
o
o
t
t
i вклю чаю щ ая
i
/* слож ная логика,
d
d
операции
чтения
из
базы
данны
х*/
E
E
}
e
e
};
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
72

73.

r
r
r
место конкретной
or
ti o
ti реализации
ti o – интерфей
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
class EntryAnalyzer {
public:
boolAnalyze( std::string enam e ) {
if( enam e.size() < 2 ) {
w ebService.LogError( "Error: " + enam e );
return false;
}
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
h
C
X
F- O
PD EM
D
return dbM anager.IsValid( enam e );
};
}
private:
D atabaseM anager dbM anager;
W ebService w ebService;
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
73
r

74.

r
r
r
место конкретной
or
ti o
ti реализации
ti o – интерфей
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
h
h
C
C
X
X
F- O
F- O
D M
M
PDAnal
P
bool
yze(
st
d:
:
st
ri
ng
enam
e
)
{
E
E
Denam e.size() < 2 ) {
D
if(
w ebService.LogError( "Error: " + enam e );
return false;
return dbM anager.IsValid( enam e );
};
}
private:
D atabaseM anager dbM anager;
W ebService w ebService;
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
Ed
class EntryAnalyzer {
public:
EntryAnalyzer() :
pD bM anager( std::m ake_unique< D atabaseM anager> () ) {
}
class EntryAnalyzer {
public:
boolAnalyze( std::string enam e ) {
if( enam e.size() < 2 ) {
w ebService.LogError( "Error: " + enam e );
return false;
}
h
C
X
F- O
PD EM
D
Ed
}
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
return pD bM anager-> IsValid( enam e );
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
E
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
74
r

75.

r
r
r
место конкретной
or
ti o
ti реализации
ti o – интерфей
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
h
h
C
C
X
X
F- O
F- O
D M
M
PDAnal
P
bool
yze(
st
d:
:
st
ri
ng
enam
e
)
{
E
E
Denam e.size() < 2 ) {
D
if(
w ebService.LogError( "Error: " + enam e );
return false;
return dbM anager.IsValid( enam e );
};
}
private:
D atabaseM anager dbM anager;
W ebService w ebService;
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
Ed
class EntryAnalyzer {
public:
EntryAnalyzer() :
pD bM anager( std::m ake_unique< D atabaseM anager> () ) {
}
class EntryAnalyzer {
public:
boolAnalyze( std::string enam e ) {
if( enam e.size() < 2 ) {
w ebService.LogError( "Error: " + enam e );
return false;
}
h
C
X
F- O
PD EM
D
Ed
}
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
return pD bM anager-> IsValid( enam e );
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
Где появился баг?
E
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
75
r

76.

r
r
r
место конкретной
or
ti o
ti реализации
ti o – интерфей
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
w ebService.LogError( "Error: " + enam e );
return false;
return dbM anager.IsValid( enam e );
};
}
private:
D atabaseM anager dbM anager;
W ebService w ebService;
e
g
an
h
C
X
F- O
PD EM
D
E
e
Утечка памяти!
g
n
a
h
h
XC
XC
F O
F O
D
D
P Anal
bool
EMyze( std::string enam e ) {P EM
Denam e.size() < 2 ) {
D
if(
h
C
X
F- O
PD EM
D
to
i
d
Ed
class EntryAnalyzer {
public:
EntryAnalyzer() :
pD bM anager( std::m ake_unique< D atabaseM anager> () ) {
}
class EntryAnalyzer {
public:
boolAnalyze( std::string enam e ) {
if( enam e.size() < 2 ) {
w ebService.LogError( "Error: " + enam e );
return false;
}
h
C
X
F- O
PD EM
D
Ed
}
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
return pD bM anager-> IsValid( enam e );
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
E
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
76
r

77.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
};
h
C
X
F- O
PD EM
D
e
g
an
Ed
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
Ed
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
77
r

78.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
h
C
X
F- O
PD EM
D
e
g
an
Ed
h
C
X
F- O
PD EM
D
};
E
to
i
d
Ed
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
virtual ~IDatabaseManager() = default;
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
78
r

79.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
virtual~ ID atabaseM anager() = default;
};
h
C
X
F- O
PD EM
D
Ed
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
public:
boolW illBeValid;
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
st
d:
:
st
ri
ng
enam
e
)
over
ri
de
a
a {
h
h
XC} return W illBeValid;
XC
F O
F O
};
D
D
M
P E
P EM
D
D
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
Ed
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
79
r

80.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
public:
boolW illBeValid;
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
virtual~ ID atabaseM anager() = default;
};
h
C
X
F- O
PD EM
D
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
st
d:
:
st
ri
ng
enam
e
)
over
ri
de
a
a {
h
h
XC} return W illBeValid;
XC
F O
F O
};
D
D
M
P E
P EM
D
D
h
C
X
F- O
PD EM
D
Ed
class D atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
h
C
X
F- O
PD EM
D
public:
boolIsValid( std::string enam e ) override {
r
r
o
o
t
t
i вклю чаю щ ая
i
/* слож ная логика,
d
d
операции
чтения
из
базы
данны
х*/
E
E
}
e
e
};
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
80

81.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
public:
boolW illBeValid;
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
virtual ~ ID atabaseM anager() = default;
};
h
C
X
F- O
PD EM
D
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
st
d:
:
st
ri
ng
enam
e
)
over
ri
de
a
a {
h
h
XC} return W illBeValid;
XC
F O
F O
};
D
D
M
P E
P EM
D
D
h
C
X
F- O
PD EM
D
Ed
class D atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
h
C
X
F- O
PD EM
D
public:
boolIsValid( std::string enam e ) override {
r
r
o
o
t
t
i вклю чаю щ ая
i
/* слож ная логика,
d
d
операции
чтения
из
базы
данны
х*/
E
E
}
e
e
};
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
81

82.

r зависимости
r
r
Разрыв
от базы
данныхitor
ti o
ti o
ti o
e
g
an
Ed
h
C
X
F- O
PD EM
D
class FakeD atabaseM anager :
public ID atabaseM anager {
public:
boolW illBeValid;
e
g
an
Ed
e
g
an
class ID atabaseM anager {
public:
virtualboolIsValid( std::string enam e ) = 0;
virtual~ ID atabaseM anager() = default;
};
h
C
X
F- O
PD EM
D
r
r
o
o
t
t
i anager( boolw ill_be_valid ) : di
FakeD atabaseM
d
W illBeVal
i
d(
E w ill_be_valid ) {
E
}
e
e
g
g
n
n
bool
I
sVal
i
d(
st
d:
:
stri
ng
enam
e
)
override
a
a {
h
h
XC return W illBeValid;
XC
F }O
F O
};
D
D
M
P E
P EM
D
D
h
C
X
F- O
PD EM
D
Ed
class D atabaseM anager :
public ID atabaseM anager {
e
g
an
Ed
h
C
X
F- O
PD EM
D
public:
boolIsValid( std::string enam e ) override {
r
r
o
o
t
t
i вклю чаю щ ая
i
/* слож ная логика,
d
d
операции
чтения
из
базы
данны
х*/
E
E
}
e
e
g
g
};
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
82

83.

e
g
an
E
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
Ed
Ed
e
e
e
class EntryAnalyzer {
g
g
g
n
n
n
public:
a
a
a
hd::unique_ptr< ID atabaseM anager>
h
h
EntryAnalyzer(Cst
& & p_db_m ng ) :
C
C
pD bM anager(
-X std::m ove( p_db_m ng ) ) {F-X
-X
F
F
O
O
O
}
PD EM
PD EM
PD EM
D std::string enam e ) { D
D
boolAnalyze(
r
E
to
i
d
r
E
to
i
d
...
E
t
di
};
or }
return pD bM anager-> IsValid( enam e ) ;
to
i
d
r
E
private:
e
e
std::unique_ptr< ID atabaseM
anager> pD bM anager;g
g
...
an
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
83

84.

e
g
an
E
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
Ed
Ed
r
E
e
e
e
class EntryAnalyzer {
g
g
g
n
n
n
public:
a
a
a
hd:
h
h
EntryAnalyzer(Cst
:unique_ptr< ID atabaseM anager>
&
&
p_db_m
ng
)
:
X std::m ove( p_db_m ng ) ) { -XC
XC
pD bM anager(
F O
F O
F O
}
D
D
D
P EM
P EM
P EM
внедрение
D std::string enam e ) { D
D
boolAnalyze(
...
E
to
i
d
t
di
};
or }
зависимости
return pD bM anager-> IsValid( enam e ) ;
to
i
d
r
E
private:
e
e
std::unique_ptr< ID atabaseM
anager> pD bM anager;g
g
...
an
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
84
r

85.

e
g
an
E
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
Ed
Ed
r
E
e
e
e
class EntryAnalyzer {
g
g
g
n
n
n
public:
a
a
a
hd:
h
h
EntryAnalyzer(Cst
:unique_ptr< ID atabaseM anager>
&
&
p_db_m
ng
)
:
X std::m ove( p_db_m ng ) ) { -XC
XC
pD bM anager(
F O
F O
F O
}
D
D
D
P EM
P EM
P EM
внедрение
D std::string enam e ) { D
D
boolAnalyze(
...
E
to
i
d
t
di
};
or }
зависимости
return pD bM anager-> IsValid( enam e ) ;
to
i
d
r
E
private:
e
e
std::unique_ptr< ID atabaseM
anager> pD bM anager;g
g
...
an
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
85
r

86.

to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
d
E
E
class EntryAnalyzer
e {
e
g
g
public:
n ) :pD bM anager(
n
EntryAnalyzer(
a
a
h d::m ake_unique< D atabaseM anager>
h
st
() ) {
C
C
X
X
}
F- O
F- O
M
Analyze( std::string enam PeD) { M
PDbool
E
E
D if( enam e.size() < 2 ) {
D
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
w ebService.LogError( "Error: " + enam e );
return false;
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
}
r
return pD bM anager-> IsValid( enam e );
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
86

87.

to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
d
E
E
class EntryAnalyzer
e {
e
g
g
public:
n ) :pD bM anager(
n
EntryAnalyzer(
a
a
h d::m ake_unique< D atabaseM anager>
h
st
() ) {
C
C
X
X
}
F- O
F- O
M
Analyze( std::string enam PeD) { M
PDbool
E
E
D if( enam e.size() < 2 ) {
D
e
g
an
r
};
h
C
X
F- O
PD EM
D
E
e
g
an
h
C
X
F- O
PD EM
D
E
E
to
i
d
...
to
i
d
r
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager; };
W ebService w ebService;
e
g
an
E
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
boolAnal
Dyze( std::string enam e ) {
D
}
to
i
d
e
g
an
r
class EntryAnalyzer {
public:
EntryAnalyzer( std::unique_ptr< ID atabaseM anager> & & p_m ng ) :
pD bM anager( std::m ove( p_m ng ) )
{
}
w ebService.LogError( "Error: " + enam e );
return false;
return pD bM anager-> IsValid( enam e );
Ed
to
i
d
}
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
87
r

88.

to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
d
E
E
class EntryAnalyzer
e {
e
g
g
public:
n ) :pD bM anager(
n
EntryAnalyzer(
a
a
h d::m ake_unique< D atabaseM anager>
h
st
() ) {
C
C
X
X
}
F- O
F- O
M
Analyze( std::string enam PeD) { M
PDbool
E
E
D if( enam e.size() < 2 ) {
D
e
g
an
e
g
an
E
E
to
i
d
r
class EntryAnalyzer {
public:
EntryAnalyzer( std::unique_ptr< ID atabaseM anager> & & p_m ng =
std::m ake_unique< D atabaseM anager> () ) :
pD bM anager( std::m ove( p_m ng ) )
{
}
h
C
X
F- O
PD EM
D
w ebService.LogError( "Error: " + enam e );
return false;
boolAnalyze( std::string enam e ) {
}
};
Ed
to
i
d
h
C
X
F- O
PD EM
D
...
r
r
r
return pD bM anager-> IsValid( enam e );
}
}
private:
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
88
r

89.

to
i
d
r
r
r
Внедрение
ti o зависимости
ti o
d
E
E
class EntryAnalyzer
e {
e
g
g
public:
n ) :pD bM anager(
n
EntryAnalyzer(
a
a
h d::m ake_unique< D atabaseM anager>
h
st
() ) {
C
C
X
X
}
F- O
F- O
M
Analyze( std::string enam PeD) { M
PDbool
E
E
D if( enam e.size() < 2 ) {
D
e
g
an
e
g
an
E
E
to
i
d
r
class EntryAnalyzer {
public:
EntryAnalyzer( std::unique_ptr< ID atabaseM anager> & & p_m ng =
std::make_unique<DatabaseManager>() ) :
pD bM anager( std::m ove( p_m ng ) )
{
}
h
C
X
F- O
PD EM
D
w ebService.LogError( "Error: " + enam e );
return false;
boolAnalyze( std::string enam e ) {
}
};
Ed
to
i
d
h
C
X
F- O
PD EM
D
...
r
r
r
return pD bM anager-> IsValid( enam e );
}
}
private:
private:
std::unique_ptr< ID atabaseM anager> pD bM anager;
std::unique_ptr< ID atabaseM anager> pD bM anager;
W ebService w ebService;
W ebService w ebService;
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
89
r

90.

r
r
r
r
Тестирование
возвращаемого
значения
ti o
ti o
ti o
ti o
e
Ed
e
Ed
e
Ed
TEST_F(
EntryAnalyzerTest, Analg
yze_ValidEntryN am e_ReturnsTrue
g
g )
{an
h
C
X
F- O
PD EM
D
}
n
a
h
EntryAnalyzer ea( std::m Cake_unique< FakeD atabaseM anager>
( true ) );
C
-X
-X
F
F
O"valid_entry_nam e" );D O
boolresult = ea.Anal
yze(
PD EM
P EM
D
ASSERT_EQ ( result, tD
rue );
e
g
an
h
C
X
F- O
PD EM
D
n
a
h
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
Ed
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
90
r

91.

r
r
r
r
Тестирование
возвращаемого
значения
ti o
ti o
ti o
ti o
e
Ed
e
Ed
e
Ed
e
g
an
TEST_F(
EntryAnalyzerTest, Analg
yze_ValidEntryN am e_ReturnsTrue
g
g )
{an
h
C
X
F- O
PD EM
D
}
n
a
h
n
a
h
EntryAnalyzer ea( std::m Cake_unique< FakeD atabaseM anager>
( true ) );
C
-X
-X
F
F
O"valid_entry_nam e" );D O
boolresult = ea.Anal
yze(
PD EM
P EM
D
ASSERT_EQ ( result, tD
rue );
class FakeD atabaseM anager : public ID atabaseM anager {
public:
boolowr illBeValid;
or
e
g
an
h
C
X
F- O
PD EM };
D
}
E
t
di
t
di
to
i
d
h
C
X
F- O
PD EM
D
r
E w ill_be_valid ) : w illBeValid(Ew ill_be_valid ) {
FakeD atabaseM anager( bool
e
}
g
ge
n
n
a
a
boolIsValid( std::string
h enam e ) override {
h
C
C
return w illBeValid;
X
X
F- O
F- O
PD EM
PD EM
D
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
91
r

92.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
Разбор на примере
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
92

93.

E
to
i
d
r
e
g
n
class Analyzer
{
a
h
public:
C
Xint Analyze() {
F- Oif( false ==
PD EM if( false ==
D
r
Исходный
код
ti o
e
g
an
h
C
-X
F
O
WinAPIFind()
D )Mreturn
P
WinAPIProc() E) return
D
Ed
e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
1;
2;
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
return 0;
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
93

94.

E
to
i
d
r
e
g
n
class Analyzer
{
a
h
public:
C
Xint Analyze() {
F- Oif( false ==
PD EM if( false ==
D
r
Исходный
код
ti o
e
g
an
h
C
-X
F
O
WinAPIFind()
D )Mreturn
P
WinAPIProc() E) return
D
Ed
e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
1;
2;
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
return 0;
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
94

95.

r
r
r
r
Локализация
внешних
зависимостей
ti o
ti o
ti o
ti o
Ed
e
g
n
class Analyzer
{
a
h
public:
C
Xint Analyze() {
F- Oif( false ==
PD EM if( false ==
D
e
g
an
h
C
-X
F
O
WinAPIFind()
D )Mreturn
P
WinAPIProc() E) return
D
Ed
Ed
e
g
n
class Analyzer
{
a
public:
h
C
int
X Analyze() {
if( false ==
F O
D
P EM if( false ==
D return 0;
1;
2;
return 0;
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
Find() )
Proc() )
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
h
C
X
return
F- 1;O
return
PD EM2;
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
95
r

96.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
e
g
Analyzer
an
e
g
an
Ed
e
g
an
class
{
public:
int Analyze() {
if( false == Find() ) return 1;
if( false == Proc() ) return 2;
h
C
X
F- O
PD EM
D
return
h
C
X
F- O
PD EM
D
0;
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
96

97.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
e
g
Analyzer
an
e
g
an
Ed
Ed
e
g
class Analyzern {
a
public:
h
C
int Analyze()
{
X
if(
false
==
F O
D
false ==
M
P if(
E
Dreturn 0;
class
{
public:
int Analyze() {
if( false == Find() ) return 1;
if( false == Proc() ) return 2;
h
C
X
F- O
PD EM
D
return
h
C
X
F- O
PD EM
D
0;
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
Find() )
Proc() )
e
g
an
h
C
X
F- O
PD EM
D
E
r
E
to
i
d
h
C
X
return 1;
F- O
return D
P 2; EM
D
}
virtual ~Analyzer() = default;
protected:
virtual bool Find() {
return WinAPIFind();
}
virtual bool Proc() {
return WinAPIProc();
}
};
to
i
d
r
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
97

98.

E
r
r
r
Вводим
класс-наследник
ti o
ti o
to
i
d
e
g
class Analyzer
{
n
a
public:
h
C
int Analyze() {
X
F- O if( false ==
PD EM if( false ==
D
return 0;
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
e
e
g
g
class TestingAnalyzer
: public Analyzer
n
n
a
a
{
h
h
C
C
public:
X
-X
findApiCallWillBeReturned;
F- bool
F
O
O
PD EMbool procApiCallWillBeReturned;
PD EM
Dprivate:
D
h
C
X
Find() ) return
F- O 1;
Proc() ) Dreturn
P EM 2;
D
}
virtual ~Analyzer() = default;
protected:
virtual bool Find() {
return WinAPIFind();
}
virtual bool Proc() {
return WinAPIProc();
}
};
to
i
d
Ed
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
virtual bool Find() override
{
return findApiCallWillBeReturned;
}
E
to
i
d
r
r
r
ti o
ti o
virtual bool
d Proc() override
E
Ed
{
e procApiCallWillBeReturned;
e
return
g
g
n
} an
a
h
}; h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
98

99.

E
r
r
r
Вводим
класс-наследник
ti o
ti o
to
i
d
e
g
class Analyzer
{
n
a
public:
h
C
int Analyze() {
X
F- O if( false ==
PD EM if( false ==
D
return 0;
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
e
e
g
g
class TestingAnalyzer
: public Analyzer
n
n
a
a
{
h
h
C
C
public:
X
-X
findApiCallWillBeReturned;
F- bool
F
O
O
PD EMbool procApiCallWillBeReturned;
PD EM
Dprivate:
D
h
C
X
Find() ) return
F- O 1;
Proc() ) Dreturn
P EM 2;
D
}
virtual ~Analyzer() = default;
protected:
virtual bool Find() {
return WinAPIFind();
}
virtual bool Proc() {
return WinAPIProc();
}
};
to
i
d
Ed
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
virtual bool Find() override
{
return findApiCallWillBeReturned;
}
E
to
i
d
r
r
r
ti o
ti o
virtual bool
d Proc() override
E
Ed
{
e procApiCallWillBeReturned;
e
return
g
g
n
} an
a
h
}; h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
99

100.

E
r
r
r
Вводим
класс-наследник
ti o
ti o
to
i
d
e
g
class Analyzer
{
n
a
public:
h
C
int Analyze() {
X
F- O if( false ==
PD EM if( false ==
D
return 0;
e
g
an
e
g
an
h
C
X
F- O
PD EM
D
E
Ed
e
e
g
g
class TestingAnalyzer
: public Analyzer
n
n
a
a
{
h
h
C
C
public:
X
-X
findApiCallWillBeReturned;
F- bool
F
O
O
PD EMbool procApiCallWillBeReturned;
PD EM
Dprivate:
D
h
C
X
Find() ) return
F- O 1;
Proc() ) Dreturn
P EM 2;
D
}
virtual ~Analyzer() = default;
protected:
virtual bool Find() {
return WinAPIFind();
}
virtual bool Proc() {
return WinAPIProc();
}
};
to
i
d
Ed
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
virtual bool Find() override
{
return findApiCallWillBeReturned;
}
E
to
i
d
r
r
r
ti o
ti o
virtual bool
d Proc() override
E
Ed
{
e procApiCallWillBeReturned;
e
return
g
g
n
} an
a
h
}; h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
100

101.

Покрываем
существующую
логику
работы
r
r
r
r
ti o
ti o
ti o
ti o
Ed класса юнит-тестами
Ed
Ed
Ed
e
g
an
e
g
an
e
g
an
h
h
C
C
-X
-X
F
F
Analyze_WhenFindFails_Returns1()
D MO
D MO
{ P
P
E
E
TestingAnalyzer
tf;
D
D
tf.findApiCallWillBeReturned = false;
e
g
an
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
int test_ret = tf.Analyze();
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
}
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
101
r

102.

Покрываем
существующую
логику
работы
r
r
r
r
ti o
ti o
ti o
ti o
Ed класса юнит-тестами
Ed
Ed
Ed
e
g
an
e
g
an
e
g
an
e
g
an
h
h
h
C
C
C
-X
-X
-X
F
F
F
Analyze_WhenFindFails_Returns1()
D MO
D MOAnalyze_WhenProcFails_Returns2()
D MO
{ P
{
P
P
E
E
E
TestingAnalyzer
tf;
TestingAnalyzer tf;
D
D
D
tf.findApiCallWillBeReturned = false;
tf.findApiCallWillBeReturned = true;
h
C
X
F- O
PD EM
D
tf.procApiCallWillBeReturned = false;
int test_ret = tf.Analyze();
int test_ret = tf.Analyze();
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
}
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
or
r
int etalon_ret = 2;
ASSERT_EQ( test_ret, etalon_ret);
}
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
102
r

103.

Покрываем
существующую
логику
работы
r
r
r
r
ti o
ti o
ti o
ti o
Ed класса юнит-тестами
Ed
Ed
Ed
e
g
an
e
g
an
e
g
an
e
g
an
h
h
h
C
C
C
-X
-X
-X
F
F
F
Analyze_WhenFindFails_Returns1()
D MO
D MOAnalyze_WhenProcFails_Returns2()
D MO
{ P
{
P
P
E
E
E
TestingAnalyzer
tf;
TestingAnalyzer tf;
D
D
D
tf.findApiCallWillBeReturned = false;
tf.findApiCallWillBeReturned = true;
h
C
-X
F
O
Analyze_WhenSucceed_Returns0()
{
PD EM
TestingAnalyzer tf;
D
tf.findApiCallWillBeReturned = true;
tf.procApiCallWillBeReturned = false;
tf.procApiCallWillBeReturned = true;
int test_ret = tf.Analyze();
int test_ret = tf.Analyze();
int test_ret = tf.Analyze();
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
}
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
or
or
}
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
r
int etalon_ret = 0;
ASSERT_EQ( test_ret, etalon_ret);
int etalon_ret = 2;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
o
}it
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
103
r

104.

r
r
r
Вносим
изменения
в боевой
класс
ti o
ti o
ti o
Ed
e
g
class Analyzern {
a
public:
h
int Analyze()
{
XCfalse == Find()
if(
Fif( false
O == Proc()
D
P EM
Dreturn 0;
e
g
an
) return
) return
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
e
g
an
h
C
1;
-X
F
O
2;
PD EM
D
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
104

105.

r
r
r
Вносим
изменения
в боевой
класс
ti o
ti o
ti o
Ed
e
g
class Analyzern {
a
public:
h
int Analyze()
{
XCfalse == Find()
if(
Fif( false
O == Proc()
D
P EM
Dreturn 0;
Ed
e
g
an class
) return
) return
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
1;
-X
F
O
2;
PD EM
D
e
g
an
Analyzer
{
public:
int Analyze()
{
WindowsProcessor wp;
return wr.Process();
}
virtual ~Analyzer() = default;
};
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
105

106.

r
r
r
Вносим
изменения
в боевой
класс
ti o
ti o
ti o
Ed
e
g
class Analyzern {
a
public:
h
int Analyze()
{
XCfalse == Find()
if(
Fif( false
O == Proc()
D
P EM
Dreturn 0;
Ed
e
g
an class
) return
) return
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
1;
-X
F
O
2;
PD EM
D
Analyzer
{
public:
int Analyze()
{
WindowsProcessor wp;
return wr.Process();
}
virtual ~Analyzer() = default;
};
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
E
to
i
d
class WindowsProcessor()
{
public:
int Process()
{
if( false == Find() ) return 1;
if( false == Proc() ) return 2;
return 0;
}
protected:
virtual bool Find()
{
return WinAPIFind();
}
r
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
E
to
i
d
virtual bool Proc()
{
return WinAPIProc();
}
};
h
C
X
F- O
PD EM
D
106
r

107.

r
r
r
Поиск
внешних
зависимостей
ti o
ti o
ti o
Ed
e
g
class Analyzern {
a
public:
h
int Analyze()
{
XCfalse == Find()
if(
Fif( false
O == Proc()
D
P EM
Dreturn 0;
Ed
e
g
an class
) return
) return
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
1;
-X
F
O
2;
PD EM
D
e
g
an
Analyzer
{
public:
int Analyze()
{
WindowsProcessor wp;
return wr.Process();
}
virtual ~Analyzer() = default;
};
h
C
X
F- O
PD EM
D
r
Внешние зависимости
ito
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
E
to
i
d
class WindowsProcessor()
{
public:
int Process()
{
if( false == Find() ) return 1;
if( false == Proc() ) return 2;
return 0;
}
protected:
virtual bool Find()
{
return WinAPIFind();
}
r
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
E
to
i
d
virtual bool Proc()
{
return WinAPIProc();
}
};
h
C
X
F- O
PD EM
D
107
r

108.

r
r
r
Поиск
внешних
зависимостей
ti o
ti o
ti o
Ed
e
g
class Analyzern {
a
public:
h
int Analyze()
{
XCfalse == Find()
if(
Fif( false
O == Proc()
D
P EM
Dreturn 0;
Ed
e
g
an class
) return
) return
}
private:
bool Find() {
return WinAPIFind();
}
bool Proc() {
return WinAPIProc();
}
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
1;
-X
F
O
2;
PD EM
D
e
g
an
Analyzer
{
public:
int Analyze()
{
WindowsProcessor wp;
return wr.Process();
}
virtual ~Analyzer() = default;
};
h
C
X
F- O
PD EM
D
r
Внешняя зависимость
ito
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
E
to
i
d
class WindowsProcessor()
{
public:
int Process()
{
if( false == Find() ) return 1;
if( false == Proc() ) return 2;
return 0;
}
protected:
virtual bool Find()
{
return WinAPIFind();
}
r
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
E
to
i
d
virtual bool Proc()
{
return WinAPIProc();
}
};
h
C
X
F- O
PD EM
D
108
r

109.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
e
e
g
g
class IWindowsProcessor
n
n
{
a
a
virtual inthProcess() = 0;
h
C
C
virtual ~IWindowsProcessor()
= default;
X
X
};
F- O
F- O
PD EM
PD EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
109

110.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
Ed
e
e
e
g
g
g
class WindowsProcessor
:
class IWindowsProcessor
n
n
public nIWindowsProcessor
{
a
a
a
{
virtual inthProcess() = 0;
h
h
C
C
C
public:
virtual ~IWindowsProcessor()
= default;
X
X Process() override
-X
};
F- O
F- int
F
{ O
D MO
false == Find() ) returnP1;
PD EM
PD EM if(
false == Proc() ) return 2; E
D
D if(
D
return 0;
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
}
virtual ~WindowsProcessor() = default;
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
or
r
protected:
virtual bool Find()
{
return WinAPIFind();
}
to
i
d
E
e
gbool Proc()
virtual
n
a
{
h
return
WinAPIProc();
C
X
}
F};- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
110

111.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
Ed
Ed
e
e
e TestingWindowsProcessor :
e
g
g
g
g
class WindowsProcessor
:
class
class IWindowsProcessor
n
n public WindowsProcessor
n
public nIWindowsProcessor
{
a
a
a
a
{
virtual inthProcess() = 0;
h
h {
h
C
C
C
C
public:
virtual ~IWindowsProcessor()
= default;
public:
X
X Process() override
-X
-X
};
bool findApiCallWillBeReturned;
F- O
F- int
F
F
{ O
bool procApiCallWillBeReturned;O
D MO private:
D M
false == Find() ) returnP1;
PD EM
PD EM if(
P
E
false == Proc() ) return 2; E
virtual bool Find() override
D
D if(
D
D
return 0;
{
}
r
E
to
i
d
r
E
to
i
d
return findApiCallWillBeReturned;
}
virtual ~WindowsProcessor() = default;
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
E
to
i
d
virtual bool Proc() override
{
return procApiCallWillBeReturned;
}
r
protected:
virtual bool Find()
{
return WinAPIFind();
}
e
g
virtual
n bool Proc()
a
{
hreturn WinAPIProc();
C
X}
F};- O
PD EM
D
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
111

112.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
e
e
class Analyzer
g
g
n
n
{
a
a
public:
h
h
C
C
int Analyze()
X
X
F- {O WindowsProcessor wp;
F- O
PD EM return wr.Process(); PD EM
D }
D
Ed
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
virtual ~Analyzer() = default;
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
};
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
112

113.

r
r
r
Подготовка
к разрыву
зависимости
ti o
ti o
ti o
Ed
e
e
class Analyzer
g
g
n
n
{
a
a
public:
h
h
C
C
int Analyze()
X
X
F- {O WindowsProcessor wp;
F- O
PD EM return wr.Process(); PD EM
D }
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
int Analyze()
virtual ~Analyzer() = default;
e
g
an
h
C
X
F- O
PD EM
D
E
e
g
an
E
E
to
i
d
r
class Analyzer
{
public:
Analyzer() :
pWindowsProcessor( nullptr )
{
pWindowsProcessor = std::make_unique<WindowsProcessor>();
}
h
C
X
F- O
PD EM
D
{
};
to
i
d
Ed
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
return pWindowsProcessor->Process();
}
virtual ~Analyzer() = default;
to
i
d
r
private:
std::unique_ptr<IWindowsProcessor>
};
e
g
an
h
C
X
F- O
PD EM
D
E
pWindowsProcessor;
e
g
an
h
C
X
F- O
PD EM
D
113
r

114.

e
g
an
E
r
r
r
Внедрение
ti o зависимости
ti o
to
i
d
e
g
an
Ed
class Analyzer
{
public:
Analyzer() :
pWindowsProcessor( nullptr )
{
pWindowsProcessor = std::make_unique<WindowsProcessor>();
}
h
C
X
F- O
PD EM
Dint Analyze()
h
C
X
F- O
PD EM
D
e
g
an
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
{
return pWindowsProcessor->Process();
}
virtual ~Analyzer() = default;
to
i
d
r
to
pWindowsProcessor; i
Ed
e
g
n
a
h
C
X
F- O
PD EM
D
private:
std::unique_ptr<IWindowsProcessor>
};
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
114

115.

e
g
an
E
r
r
r
Внедрение
ti o зависимости
ti o
to
i
d
e
g
an
Ed
class Analyzer
{
public:
Analyzer() :
pWindowsProcessor( nullptr )
{
pWindowsProcessor = std::make_unique<WindowsProcessor>();
}
h
C
X
F- O
PD EM
Dint Analyze()
h
C
X
F- O
PD EM
D
e
g
an
Ed
e
g
an
E
to
i
d
r
class Analyzer
{
public:
Analyzer() :
pWindowsProcessor( nullptr )
{
pWindowsProcessor = std::make_unique<WindowsProcessor>();
}
h
C
X
F- O
PD EM
D
void SetWindowsProcessor(
{
h
C
X
F- O
PD EM
D
std::unique_ptr<IWindowsProcessor > &&wp )
return pWindowsProcessor->Process();
}
virtual ~Analyzer() = default;
to
i
d
r
pWindows Processor = std::move( wp );
to
pWindowsProcessor; i
Ed
e
g
n
a
h
C
X
F- O
PD EM
D
private:
std::unique_ptr<IWindowsProcessor>
};
e
g
an
h
C
X
F- O
PD EM
D
E
{
r
}
to
i
d
r
int Analyze()
{
int ret = pWindowsProcessor->Process();
to
i
d
E
E
e
e
return ret; g
g
n
n
}
a
a
virtual ~Analyzer()
= default;
h
h
C
XC
private:-X
F O
F O
std::unique_ptr<IWindowsProcessor>
pWindowsProcessor;
D
D
};
M
P E
P EM
D
D
115
r

116.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
= false;
PD M
SetWindowsProcessor(Estd::move( p_twr ) );
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
or
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
116

117.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
Analyze_WhenFindFails_Returns1()
n
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
= false;
PD M
SetWindowsProcessor(Estd::move( p_twr ) );
D
to
i
d
r
to
i
d
r
E
e
g
n
Создаем
a
h
боевой объект
XC
F O
D
P EM
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
or
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
117

118.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
= false;
PD M
SetWindowsProcessor(Estd::move( p_twr ) );
D
e
g
an
E
to
i
d
r
h
C
XСоздаем
F-stub-объект
O
PD EM
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
or
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
118
r

119.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
= false;
PD M
SetWindowsProcessor(Estd::move( p_twr ) );
D
e
g
an
E
to
i
d
r
h
C
X
F-Настраиваем
O
PD EM
stub-объект
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
or
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
119
r

120.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
false;
PD EMstd::move(=p_twr
f.SetWindowsProcessor(
) );
D
e
g
an
E
to
i
d
r
h
C
X
F- O
PD EMВнедряем
D зависимость
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
or
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
120
r

121.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
false;
PD EMstd::move(=p_twr
f.SetWindowsProcessor(
) );
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
r
h
C
X
F- O
PD EM
D Проводим
тестируемое
действие
}
or
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
121
r

122.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenFindFails_Returns1()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
X
X
tf.findApiCallWillBeReturned
= false;
F- O
F- O
test_ret = tf.Analyze();
PDintEM
PD EM
D etalon_ret = 1;
D
int
Ed
Ed
e
g
n
Analyze_WhenFindFails_Returns1()
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twp->findApiCallWillBeReturned
false;
PD EMstd::move(=p_twr
f.SetWindowsProcessor(
) );
D
int etalon_ret = 1;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
t
di
}
e
g
an
h
C
X
F- O
PD EM
D
E
r
h
C
X
F- O
PD EM
D
int test_ret = tf.Analyze();
ASSERT_EQ( test_ret, etalon_ret);
}
or
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
Оцениваем
результат
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
122
r

123.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenProcFails_Returns2()
a
a
{
h
h
TestingAnalyzer
tf;
C
C
tf.findApiCallWillBeReturned
= true;
-X
-X
F
F
tf.procApiCallWillBeReturned
= false;
O
D MO
PDintEM
P
E
D test_ret = tf.Analyze();
D
Ed
e
g
Analyze_WhenProcFails_Returns2()
n
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
X
p_twp =
std::make_unique<TesingWindowsProcessor>();
F- O
p_twr->findApiCallWillBeReturned
= true;
PD EM
p_twr->procApiCallWillBeReturned
= false;
D std::move( p_twp ) );
f.SetWindowsProcessor(
int etalon_ret = 2;
ASSERT_EQ( test_ret, etalon_ret);
e
g
an
h
C
X
F- O
PD EM
D
E
e
g
an
r
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
int test_ret = t.Analyze();
}
to
i
d
Ed
to
i
d
int etalon_ret = 2;
ASSERT_EQ( test_ret, etalon_ret);
r
to
i
d
}
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
123

124.

E
to
i
d
r
r
r
Обновление
тестов
ti o
ti o
e
e
g
g
n
n
Analyze_WhenSucceed_Returns0()
a
a
{
h
h
C
C
TestingAnalyzer
tf;
-X
= true; -X
Ftf.findApiCallWillBeReturned
tf.procApiCallWillBeReturned
= true; F
O
D
D MO
M
P int
P
E
E
D test_ret = tf.Analyze();
D
Ed
e
g
Analyze_WhenSucceeded_Returns0()
n
a
{
h
Analyzer f;
C
std::unique_ptr<TesingWindowsProcessor>
p_twp =
X
std::make_unique<TesingWindowsProcessor>();
F- O
p_twr->findApiCallWillBeReturned
= true;
PD EM
p_twr->procApiCallWillBeReturned
= true;
D
p_twr->thirdFunclWillBeReturned
= false;
h
C
X
F- O
PD EM
D
E
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
int test_ret = t.Analyze();
}
e
g
an
e
g
an
r
f.SetWindowsProcessor( std::move( p_twp ) );
int etalon_ret = 0;
ASSERT_EQ( test_ret, etalon_ret);
t
di
Ed
to
i
d
int etalon_ret = 0;
ASSERT_EQ( test_ret, etalon_ret);
or
to
i
d
}
e
g
an
h
C
X
F- O
PD EM
D
E
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
124

125.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
h
C
X
F- O
PD EM
D
Общие рекомендации и практические приемы
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
125
r

126.

e
g
an
E
to
i
d
r
r
Рекомендации
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
e
g
an
E
to
i
d
r
h
h
h
hс цель
Общий
принцип:
рефакторинг
кода
C
C
C
C
X
X
X
X
F- O
F- O
F- O
F- O
D M
D M
M
локализации
PD EM
PD мест
обращения
P
к
внешним
P
E
E
E
D
D
D
D
зависимостям
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
126
r

127.

e
g
an
E
to
i
d
r
r
Рекомендации
e
g
an
E
to
i
d
e
g
an
E
to
i
d
r
e
g
an
E
to
i
d
r
h
h
h
hс цель
Общий
принцип:
рефакторинг
кода
C
C
C
C
X
X
X
X
F- O
F- O
F- O
F- O
D M
D M
M
локализации
PD EM
PD мест
обращения
P
к
внешним
P
E
E
E
D
D
D
D
зависимостям
E
to
i
d
r
E
to
i
d
r
E
to
i
d
r
Сохраняем сигнатуры методов при
h
h
h
h
C
C
C
C
внесении
изменений
X
X
X
X
FFFFe
g
an
O
PD EM
D
e
g
an
O
PD EM
D
e
g
an
O
PD EM
D
e
g
an
O
PD EM
D
E
to
i
d
127
r

128.

e
g
an
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
r
Практические
приемы
ti o
ti o
Ed
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
e
g
an
Ed
E
to
i
d
h
C
X
F- O
PD EM
D
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
r
E
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
128

129.


E
to
i
d
r
ge
Один nтест
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
Практические
приемы
ti o
ti o

Ed
e
e
g
g
один результат
работы
n
n
a
a
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
h
C
X
F- O
PD EM
D
r
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
129

130.

e
g
an
E
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
TestingEntryAnalyzer ea;
E
to
i
d
r
}
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i ==
boolb_test_result = (ifalse = = is_valid & & "Error: e"
d
d
ASSERT_EQ ( test_resul
E t, true );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
s_err_m sg );
e
g
an
h
C
X
F- O
PD EM
D
130

131.

e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
TestingEntryAnalyzer ea;
to
i
d
EX
r
}
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i ==
boolb_test_result = (ifalse = = is_valid & & "Error: e"
d
d
ASSERT_EQ ( test_resul
E t, true );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
s_err_m sg );
e
g
an
h
C
X
F- O
PD EM
D
131

132.

e
g
an
E
to
i
d
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
1
2
r
TestingEntryAnalyzer ea;
to
i
d
EX
r
}
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i ==
boolb_test_result = (ifalse = = is_valid & & "Error: e"
d
d
ASSERT_EQ ( test_resul
E t, true );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
s_err_m sg );
e
g
an
h
C
X
F- O
PD EM
D
132

133.

e
g
an
h
C
X
F- O
PD EM
D
1
?
E
to
i
d
r
e
g
an
e
g
an
Ed
e
g
an
r
E
r
E
to
i
d
TestingEntryAnalyzer ea;
r
2 e EX }
h
C
X
F- O
PD EM
D
Ed
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
to
i
d
g
n
a
r
r
Практические
приемы
ti o
ti o
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i ==
boolb_test_result = (ifalse = = is_valid & & "Error: e"
d
d
ASSERT_EQ ( test_resul
E t, true );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
s_err_m sg );
e
g
an
h
C
X
F- O
PD EM
D
133

134.

e
g
an
E
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
Ed
e
g
an
r
E
to
i
d
r
E
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
TestingEntryAnalyzer ea;
E
to
i
d
r
}
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i
ASSERT_EQ ( is_valid, falise );
d
d
ASSERT_EQ ( s_err_m sg,
E "Error: e" );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
134

135.

e
g
an
h
C
X
F- O
PD EM
D
1
?
E
to
i
d
r
e
g
an
e
g
an
Ed
e
g
an
r
E
r
E
to
i
d
TestingEntryAnalyzer ea;
r
2 e EX }
h
C
X
F- O
PD EM
D
Ed
to
i
d
h
h
h
C
C
C
X
X
X
F- OyzerTest,
F- O
F- O
TEST_F( EntryAnal
M
Analyze_TooShort
rorToW ebServer )PD M
PD EM EntryN am e_ReturnsFal
PDseLoggsEr
E
E
{
D
D
D
to
i
d
g
n
a
r
r
Практические
приемы
ti o
ti o
boolis_valid = ea.Analyze( "e" );
std::string s_err_m sg = ea.lastErrM sg;
r
r
o
o
t
t
i
ASSERT_EQ ( is_valid, falise );
d
d
ASSERT_EQ ( s_err_m sg,
E "Error: e" );
E
e
e
g
g
n
n
a
a
h
h
XC
XC
F O
F O
D
D
M
P E
P EM
D
D
e
g
an
h
C
X
F- O
PD EM
D
135

136.


E
to
i
d
r
ge
Один nтест
a
h
XC
F O
D
P EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
r
Практические
приемы
ti o
ti o

Ed
e
e
g
g
один результат
работы
n
n
a
a
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
Ed
h
C
X
F- O
PD EM
D
r
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
e
g
an
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
136

137.

E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
Ed
Ed
e
e
ge
g
g
• Один nтест
— один результат
работы
n
n
a
a
a
h
h
h
C
C
C
X
X публичные методы
X
• Тестируем
только
F- O
F- O
F- O
PD EM
PD EM
PD EM
D
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
137

138.

E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
Ed
Ed
e
e
ge
g
g
• Один nтест
— один результат
работы
n
n
a
a
a
h
h
h
C
C
C
X
X публичные методы
X
• Тестируем
только
F- O
F- O
F- O
PD EM
PD EM
PD EM
• Нет
ветвления D
D
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
• операторы: sw itch, if, else
r
r
o std::for_eachito
• iциклы:
to
for, w hiil
te,
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
e
g
an
h
C
X
F- O
PD EM
D
Ed
r
e
g
an
h
C
X
F- O
PD EM
D
138

139.

E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
Ed
Ed
e
e
ge
g
g
• Один nтест
— один результат
работы
n
n
a
a
a
h
h
h
C
C
C
X
X публичные методы
X
• Тестируем
только
F- O
F- O
F- O
PD EM
PD EM
PD EM
• Нет
ветвления D
D
D
e
g
an
E
to
i
d
r
to
i
d
r
h
C
X
F- O
PD EM
D
• операторы: sw itch, if, else
r
r
o std::for_eachito
• iциклы:
to
for, w hiil
te,
Ed
e
g
Юнит тест
n
a
h
C
X
F- O
PD EM
D

Ed
Ed
r
e
e
g
g
последовательность
вызовов
n
n
a
a
h
h
C
C
X
X
F- O
F- O
PD EM
PD EM
D
D
E
e
методовng+ asser
a
h
XC
F O
D
P EM
D
139

140.

E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
Ed
Ed
e
e
ge
g
g
• Один nтест
— один результат
работы
n
n
a
a
a
h
h
h
C
C
C
X
X публичные методы
X
• Тестируем
только
F- O
F- O
F- O
PD EM
PD EM
PD EM
• Нет
ветвления D
D
D
e
g
an
E
to
i
d
r
to
i
d
r
h
C
X
F- O
PD EM
D
• операторы: sw itch, if, else
r
r
o std::for_eachito
• iциклы:
to
for, w hiil
te,
Ed
Ed
Ed
r
e
e
e
g
g
g
Юнит тест

последовательность
вызовов
n
n
n
a
a
a
h
h
h
C
C
C
X
X
X
Используем
фабрики
F- O
F- O
F- O
PD EM
PD EM
PD EM
D
D
D
E
e
методовng+ asser
a
h
XC
F O
D
P EM
D
140

141.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
Ed
e
g
an
h
C
X
F- O
PD EM
D
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
EntryAnalyzer ea;
ea.Analyze( "nam e1" );

}
e
g
an
E
to
i
d
r
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D

e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
141

142.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
EntryAnalyzer ea;
ea.Analyze( "nam e1" );

}
e
g
an
E
to
i
d
r

e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
r
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
EntryAnalyzer ea(
std::string s_db_nam e );
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D
Ed
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
142

143.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
e
g
an
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
EntryAnalyzer ea;
ea.Analyze( “nam e1" );

}
e
g
an
E
to
i
d
r

e
g
an
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
r
E
r
E
to
i
d
h
C
X
F- O
PD EM
D
EntryAnalyzer ea(
std::string s_db_nam e );
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D
Ed
to
i
d
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
143

144.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
Ed

}
e
g
an
E
to
i
d
EntryAnalyzer ea(
std::string s_db_nam e );
r
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D

e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
E
e
e
std::unique_pt
g r< EntryAnalyzer> CreateD efaultEnt
gryAnalyzer()
n
n
{
a
a
std:
:string s_db_nam e( "D um m m yD B" )
h
h
C( s_db_nam e );
rC
eturn std::m ake_unique< EntryAnalyzer>
X
X
F} O
F O
D
D
P EM
P EM
D
D
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
EntryAnalyzer ea;
ea.Analyze( “nam e1" );
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
144

145.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
Ed

}
e
g
an
E
to
i
d
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D

{
EntryAnalyzer ea(
std::string s_db_nam e );
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
E
e
e
std::unique_pt
g r< EntryAnalyzer> CreateD efaultEnt
gryAnalyzer()
n
n
{
a
a
std:
:string s_db_nam e( "D um m m yD B" )
h
h
C( s_db_nam e );
rC
eturn std::m ake_unique< EntryAnalyzer>
X
X
F} O
F O
D
D
P EM
P EM
TEST_F(
Ent
ryAnal
yzerTest
,
D Analyze_Condition1_ReturnsTrue ) D
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
EntryAnalyzer ea;
ea.Analyze( “nam e1" );
to
i
d
r
}
std::unique_ptr<EntryAnalyzer> p_ea =
CreateDefaultEntryAnalyzer;
p_ea-> Analyze( "nam e1" );
… or
t
di
E
E
e
e
TEST_F( Ent
g ryAnalyzerTest,
g
n
n
Analyze_Condi
tion2_ReturnsTrue )
a
a
{
h
h
std::unique_ptr<Ent
ryAnal
yzer>
p_ea
=
C
XCreateDefaultEntryAnalyzer;
XC
F p_ea-O> Analyze( "nam e2" );
F O
D
D
M
P E
P EM

D}
D
145

146.

e
g
an
E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
e
g
an
Ed
Ed

}
e
g
an
E
to
i
d
TEST_F( EntryAnalyzerTest,
Analyze_Condition2_ReturnsTrue )
{
EntryAnalyzer ea;
ea.Analyze( "nam e2" );
h
C
-X
F
O
PD} EM
D

{
EntryAnalyzer ea(
std::string s_db_nam e );
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
to
i
d
r
E
e
e
std::unique_pt
g r< EntryAnalyzer> CreateD efaultEnt
gryAnalyzer()
n
n
{
a
a
std:
:string s_db_nam e( "D um m m yD B" )
h
h
C( s_db_nam e );
rC
eturn std::m ake_unique< EntryAnalyzer>
X
X
F} O
F O
D
D
P EM
P EM
TEST_F(
Ent
ryAnal
yzerTest
,
D Analyze_Condition1_ReturnsTrue ) D
h
h
C
C
X
X
F- O
F- O
D M
M
PD TEST_F(
P
Ent
ryAnal
yzerTest
,
E
E
D{ Analyze_Condition1_ReturnsTrue ) D
EntryAnalyzer ea;
ea.Analyze( “nam e1" );
to
i
d
r
}
std::unique_ptr<EntryAnalyzer> p_ea =
CreateDefaultEntryAnalyzer;
p_ea-> Analyze( "nam e1" );
… or
t
di
E
E
e
e
TEST_F( Ent
g ryAnalyzerTest,
g
n
n
Analyze_Condi
tion2_ReturnsTrue )
a
a
{
h
h
std::unique_ptr<Ent
ryAnal
yzer>
p_ea
=
C
XCreateDefaultEntryAnalyzer;
XC
F p_ea-O> Analyze( "nam e2" );
F O
D
D
M
P E
P EM

D}
D
146

147.

E
to
i
d
r
r
r
Практические
приемы
ti o
ti o
Ed
Ed
e
e
ge
g
g
• Один nтест
— один результат
работы
n
n
a
a
a
h
h
h
C
C
C
X
X публичные методы
X
• Тестируем
только
F- O
F- O
F- O
PD EM
PD EM
PD EM
• Нет
ветвления D
D
D
e
g
an
E
to
i
d
r
to
i
d
r
h
C
X
F- O
PD EM
D
• операторы: sw itch, if, else
r
r
o std::for_eachito
• iциклы:
to
for, w hiil
te,
Ed
Ed
Ed
r
e
e
e
g
g
g
Юнит тест

последовательность
вызовов
n
n
n
a
a
a
h
h
h
C
C
C
X
X
X
Используем
фабрики
F- O
F- O
F- O
PD EM
PD EM
PD EM
D
D
D
E
e
методовng+ asser
a
h
XC
F O
D
P EM
D
147

148.

E
r
r
r
Где
почитать
подробнее
ti o
ti o
to
i
d
Ed
Ed
e
e
e
g
g
g
• Майкл
Физерс
n
n
n
a
a
a
h
h
h
C
C
C
“Эффективная
работа-Xс унаследованным
X
X кодом”
F- O
F O
F- O
PD EM
PD EM
PD EM
D
D
D
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
r
e
g
an
h
C
X
F- O
PD EM
D
148

149.

E
r
r
r
Где
почитать
подробнее
ti o
ti o
to
i
d
Ed
Ed
e
e
e
g
g
g
• Майкл
Физерс
n
n
n
a
a
a
h
h
h
C
C
C
“Эффективная
работа-Xс унаследованным
X
X кодом”
F- O
F O
F- O
PD EM
PD EM
PD EM
D
D
D
e
g
an
r
E
to
i
d
r
E
to
i
d
h
C
X
F- O
PD EM
D
•Roy Osherove
nd
“The art of unit
r testing”. 2 edition
r
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
e
g
an
h
C
X
F- O
PD EM
D
E
to
i
d
r
e
g
an
h
C
X
F- O
PD EM
D
149

150.

e
g
an
E
to
i
d
r
h
C
X
F- O
PD EM
D
e
g
an
h
C
X
F- O
PD EM
D
e
g
an
E
to
i
d
r
e
g
an
E
to
i
d
r
h
h
C
C
X #UFADEVCONF
X
F- O
F- O
PD EM
PD EM
D
D
E
t
di
or
E
r
to
i
d
r
h
C
X
F- O
PD EM
D
Спасибо за
внимание!
r
r
to
i
d
e
g
an
to
i
d
to
i
d
E
E
E
e
e
e
g
g
g
Ястребов
Виктор
n
n
n
a
a
a
h
h
h
к.т.н., ведущий
“Тензор” XC
XC разработчик компании
XC
[email protected]
F O
F- O
O
PD EM
PD EM
PD EM
http://dc.ufacoder.com
D
D - 2018
D
150
English     Русский Правила