Files
codeql/swift/codegen/test/test_render.py
Paolo Tranquilli 773ef62406 Swift: added trapgen
This checks in the trapgen script generating trap entries in C++.

The codegen suite has been slightly reorganized, moving the templates
directory up one level and chopping everything into smaller bazel
packages. Running tests is now done via
```
bazel run //swift/codegen/test
```

With respect to the PoC, the nested `codeql::trap` namespace has been
dropped in favour of a `Trap` prefix (or suffix in case of entries)
within the `codeql` namespace. Also, generated C++ code is not checked
in in git any more, and generated during build. Finally, labels get
printed in hex in the trap file.

`TrapLabel` is for the moment only default-constructible, so only one
single label is possible. `TrapArena`, that is responsible for creating
disjoint labels will come in a later commit.
2022-04-28 12:01:59 +02:00

92 lines
2.7 KiB
Python

import sys
import pathlib
from unittest import mock
import pytest
from swift.codegen.lib import paths
from swift.codegen.lib import render
@pytest.fixture
def pystache_renderer_cls():
with mock.patch("pystache.Renderer") as ret:
yield ret
@pytest.fixture
def pystache_renderer(pystache_renderer_cls):
ret = mock.Mock()
pystache_renderer_cls.side_effect = (ret,)
return ret
@pytest.fixture
def sut(pystache_renderer):
return render.Renderer()
def test_constructor(pystache_renderer_cls, sut):
pystache_init, = pystache_renderer_cls.mock_calls
assert set(pystache_init.kwargs) == {'search_dirs', 'escape'}
assert pystache_init.kwargs['search_dirs'] == str(paths.templates_dir)
an_object = object()
assert pystache_init.kwargs['escape'](an_object) is an_object
assert sut.written == set()
def test_render(pystache_renderer, sut):
data = mock.Mock()
output = mock.Mock()
with mock.patch("builtins.open", mock.mock_open()) as output_stream:
sut.render(data, output)
assert pystache_renderer.mock_calls == [
mock.call.render_name(data.template, data, generator=paths.exe_file, guard=None),
]
assert output_stream.mock_calls == [
mock.call(output, 'w'),
mock.call().__enter__(),
mock.call().write(pystache_renderer.render_name.return_value),
mock.call().__exit__(None, None, None),
]
assert sut.written == {output}
def test_render_with_guard(pystache_renderer, sut):
guard_base = pathlib.Path("test", "guard")
data = mock.Mock()
output = guard_base / "this" / "is" / "a" / "header.h"
with mock.patch("builtins.open", mock.mock_open()) as output_stream:
sut.render(data, output, guard_base=guard_base)
assert pystache_renderer.mock_calls == [
mock.call.render_name(data.template, data, generator=paths.exe_file, guard="THIS_IS_A_HEADER_H"),
]
def test_written(sut):
data = [mock.Mock() for _ in range(4)]
output = [mock.Mock() for _ in data]
with mock.patch("builtins.open", mock.mock_open()) as output_stream:
for d, o in zip(data, output):
sut.render(d, o)
assert sut.written == set(output)
def test_cleanup(sut):
data = [mock.Mock() for _ in range(4)]
output = [mock.Mock() for _ in data]
with mock.patch("builtins.open", mock.mock_open()) as output_stream:
for d, o in zip(data, output):
sut.render(d, o)
expected_erased = [mock.Mock() for _ in range(3)]
existing = set(expected_erased + output[2:])
sut.cleanup(existing)
for f in expected_erased:
assert f.mock_calls == [mock.call.unlink(missing_ok=True)]
for f in output:
assert f.unlink.mock_calls == []
if __name__ == '__main__':
sys.exit(pytest.main())