(python, blocking, method, tmpdir)
| 38 | |
| 39 | @all_pystack_combinations() |
| 40 | def test_single_thread_stack(python, blocking, method, tmpdir): |
| 41 | # GIVEN |
| 42 | |
| 43 | _, python_executable = python |
| 44 | |
| 45 | # WHEN |
| 46 | |
| 47 | with spawn_child_process( |
| 48 | python_executable, TEST_SINGLE_THREAD_FILE, tmpdir |
| 49 | ) as child_process: |
| 50 | with xfail_on_expected_exceptions(method): |
| 51 | threads = list( |
| 52 | get_process_threads( |
| 53 | child_process.pid, stop_process=blocking, method=method |
| 54 | ) |
| 55 | ) |
| 56 | |
| 57 | # THEN |
| 58 | |
| 59 | assert len(threads) == 1 |
| 60 | (thread,) = threads |
| 61 | |
| 62 | frames = list(thread.frames) |
| 63 | assert (len(frames)) == 4 |
| 64 | |
| 65 | filenames = {frame.code.filename for frame in frames} |
| 66 | assert filenames == {str(TEST_SINGLE_THREAD_FILE)} |
| 67 | |
| 68 | functions = [frame.code.scope for frame in frames] |
| 69 | assert functions == ["<module>", "first_func", "second_func", "third_func"] |
| 70 | |
| 71 | *line_numbers, last_line = [frame.code.location.lineno for frame in frames] |
| 72 | assert line_numbers == [20, 6, 10] |
| 73 | assert last_line in {16, 17} |
| 74 | |
| 75 | assert not thread.native_frames |
| 76 | |
| 77 | |
| 78 | def test_single_thread_stack_non_blocking(tmpdir): |
nothing calls this directly
no test coverage detected