Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
G
googletest
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Chen Yisong
googletest
Commits
e7bb5ede
Commit
e7bb5ede
authored
May 05, 2009
by
zhanyong.wan
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Improves the error message for leaked mocks to include the test name (by Zhanyong Wan).
parent
125783fb
Show whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
73 additions
and
15 deletions
+73
-15
gmock-port.h
include/gmock/internal/gmock-port.h
+3
-3
gmock-spec-builders.cc
src/gmock-spec-builders.cc
+18
-2
gmock_output_test.py
test/gmock_output_test.py
+39
-9
gmock_output_test_.cc
test/gmock_output_test_.cc
+11
-0
gmock_output_test_golden.txt
test/gmock_output_test_golden.txt
+2
-1
No files found.
include/gmock/internal/gmock-port.h
View file @
e7bb5ede
...
...
@@ -166,16 +166,16 @@ inline To down_cast(From* f) { // so we only accept pointers
return
static_cast
<
To
>
(
f
);
}
// The GMOCK_COMPILE_ASSERT macro can be used to verify that a compile time
// The GMOCK_COMPILE_ASSERT
_
macro can be used to verify that a compile time
// expression is true. For example, you could use it to verify the
// size of a static array:
//
// GMOCK_COMPILE_ASSERT(ARRAYSIZE(content_type_names) == CONTENT_NUM_TYPES,
// GMOCK_COMPILE_ASSERT
_
(ARRAYSIZE(content_type_names) == CONTENT_NUM_TYPES,
// content_type_names_incorrect_size);
//
// or to make sure a struct is smaller than a certain size:
//
// GMOCK_COMPILE_ASSERT(sizeof(foo) < 128, foo_too_large);
// GMOCK_COMPILE_ASSERT
_
(sizeof(foo) < 128, foo_too_large);
//
// The second argument to the macro is the name of the variable. If
// the expression is false, most compilers will issue a warning/error
...
...
src/gmock-spec-builders.cc
View file @
e7bb5ede
...
...
@@ -168,6 +168,8 @@ struct MockObjectState {
// invoked on this mock object.
const
char
*
first_used_file
;
int
first_used_line
;
::
std
::
string
first_used_test_case
;
::
std
::
string
first_used_test
;
bool
leakable
;
// true iff it's OK to leak the object.
FunctionMockers
function_mockers
;
// All registered methods of the object.
};
...
...
@@ -203,8 +205,13 @@ class MockObjectRegistry {
const
MockObjectState
&
state
=
it
->
second
;
internal
::
FormatFileLocation
(
state
.
first_used_file
,
state
.
first_used_line
,
&
cout
);
cout
<<
" ERROR: this mock object should be deleted but never is. "
<<
"Its address is @"
<<
it
->
first
<<
"."
;
cout
<<
" ERROR: this mock object"
;
if
(
state
.
first_used_test
!=
""
)
{
cout
<<
" (used in test "
<<
state
.
first_used_test_case
<<
"."
<<
state
.
first_used_test
<<
")"
;
}
cout
<<
" should be deleted but never is. Its address is @"
<<
it
->
first
<<
"."
;
leaked_count
++
;
}
if
(
leaked_count
>
0
)
{
...
...
@@ -357,6 +364,15 @@ void Mock::RegisterUseByOnCallOrExpectCall(
if
(
state
.
first_used_file
==
NULL
)
{
state
.
first_used_file
=
file
;
state
.
first_used_line
=
line
;
const
TestInfo
*
const
test_info
=
UnitTest
::
GetInstance
()
->
current_test_info
();
if
(
test_info
!=
NULL
)
{
// TODO(wan@google.com): record the test case name when the
// ON_CALL or EXPECT_CALL is invoked from SetUpTestCase() or
// TearDownTestCase().
state
.
first_used_test_case
=
test_info
->
test_case_name
();
state
.
first_used_test
=
test_info
->
name
();
}
}
}
...
...
test/gmock_output_test.py
View file @
e7bb5ede
...
...
@@ -64,6 +64,7 @@ GOLDEN_NAME = 'gmock_output_test_golden.txt'
GOLDEN_PATH
=
os
.
path
.
join
(
gmock_test_utils
.
GetSourceDir
(),
GOLDEN_NAME
)
def
ToUnixLineEnding
(
s
):
"""Changes all Windows/Mac line endings in s to UNIX line endings."""
...
...
@@ -109,15 +110,38 @@ def RemoveMemoryAddresses(output):
return
re
.
sub
(
r'@\w+'
,
'@0x#'
,
output
)
def
NormalizeOutput
(
output
):
"""Normalizes output (the output of gmock_output_test_.exe)."""
def
RemoveTestNamesOfLeakedMocks
(
output
):
"""Removes the test names of leaked mock objects from the test output."""
return
re
.
sub
(
r'\(used in test .+\) '
,
''
,
output
)
def
GetLeakyTests
(
output
):
"""Returns a list of test names that leak mock objects."""
# findall() returns a list of all matches of the regex in output.
# For example, if '(used in test FooTest.Bar)' is in output, the
# list will contain 'FooTest.Bar'.
return
re
.
findall
(
r'\(used in test (.+)\)'
,
output
)
def
GetNormalizedOutputAndLeakyTests
(
output
):
"""Normalizes the output of gmock_output_test_.
Args:
output: The test output.
Returns:
A tuple (the normalized test output, the list of test names that have
leaked mocks).
"""
output
=
ToUnixLineEnding
(
output
)
output
=
RemoveReportHeaderAndFooter
(
output
)
output
=
NormalizeErrorMarker
(
output
)
output
=
RemoveLocations
(
output
)
output
=
RemoveMemoryAddresses
(
output
)
return
output
return
(
RemoveTestNamesOfLeakedMocks
(
output
),
GetLeakyTests
(
output
))
def
IterShellCommandOutput
(
cmd
,
stdin_string
=
None
):
...
...
@@ -167,9 +191,8 @@ def GetShellCommandOutput(cmd, stdin_string=None):
return
string
.
join
(
lines
,
''
)
def
GetCommandOutput
(
cmd
):
"""Runs a command and returns its output with all file location
info stripped off.
def
GetNormalizedCommandOutputAndLeakyTests
(
cmd
):
"""Runs a command and returns its normalized output and a list of leaky tests.
Args:
cmd: the shell command.
...
...
@@ -177,22 +200,29 @@ def GetCommandOutput(cmd):
# Disables exception pop-ups on Windows.
os
.
environ
[
'GTEST_CATCH_EXCEPTIONS'
]
=
'1'
return
NormalizeOutput
(
GetShellCommandOutput
(
cmd
,
''
))
return
GetNormalizedOutputAndLeakyTests
(
GetShellCommandOutput
(
cmd
,
''
))
class
GMockOutputTest
(
unittest
.
TestCase
):
def
testOutput
(
self
):
output
=
GetCommandOutput
(
COMMAND
)
(
output
,
leaky_tests
)
=
GetNormalizedCommandOutputAndLeakyTests
(
COMMAND
)
golden_file
=
open
(
GOLDEN_PATH
,
'rb'
)
golden
=
golden_file
.
read
()
golden_file
.
close
()
# The normalized output should match the golden file.
self
.
assertEquals
(
golden
,
output
)
# The raw output should contain 2 leaked mock object errors for
# test GMockOutputTest.CatchesLeakedMocks.
self
.
assertEquals
([
'GMockOutputTest.CatchesLeakedMocks'
,
'GMockOutputTest.CatchesLeakedMocks'
],
leaky_tests
)
if
__name__
==
'__main__'
:
if
sys
.
argv
[
1
:]
==
[
GENGOLDEN_FLAG
]:
output
=
GetCommandOutput
(
COMMAND
)
(
output
,
_
)
=
GetNormalizedCommandOutputAndLeakyTests
(
COMMAND
)
golden_file
=
open
(
GOLDEN_PATH
,
'wb'
)
golden_file
.
write
(
output
)
golden_file
.
close
()
...
...
test/gmock_output_test_.cc
View file @
e7bb5ede
...
...
@@ -258,6 +258,16 @@ TEST_F(GMockOutputTest, CatchesLeakedMocks) {
// Both foo1 and foo2 are deliberately leaked.
}
void
TestCatchesLeakedMocksInAdHocTests
()
{
MockFoo
*
foo
=
new
MockFoo
;
// Invokes EXPECT_CALL on foo.
EXPECT_CALL
(
*
foo
,
Bar2
(
_
,
_
));
foo
->
Bar2
(
2
,
1
);
// foo is deliberately leaked.
}
int
main
(
int
argc
,
char
**
argv
)
{
testing
::
InitGoogleMock
(
&
argc
,
argv
);
...
...
@@ -266,5 +276,6 @@ int main(int argc, char **argv) {
testing
::
GMOCK_FLAG
(
catch_leaked_mocks
)
=
true
;
testing
::
GMOCK_FLAG
(
verbose
)
=
"warning"
;
TestCatchesLeakedMocksInAdHocTests
();
return
RUN_ALL_TESTS
();
}
test/gmock_output_test_golden.txt
View file @
e7bb5ede
...
...
@@ -298,4 +298,5 @@ Stack trace:
FILE:#: ERROR: this mock object should be deleted but never is. Its address is @0x#.
FILE:#: ERROR: this mock object should be deleted but never is. Its address is @0x#.
ERROR: 2 leaked mock objects found at program exit.
FILE:#: ERROR: this mock object should be deleted but never is. Its address is @0x#.
ERROR: 3 leaked mock objects found at program exit.
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment