def test_accessible_to_own_session_only(self): description = {"analyzer": "problems2testsuite_analyzer", "reason": "Application has been killed", "backtrace": "die()", "duphash": "TASK_NEW_PROBLEM_SESSION", "uuid": "TASK_NEW_PROBLEM_SESSION", "executable": "/usr/bin/foo", "type": "abrt-problems2-accessible-to-own-session"} # Create task, run it and stop after temporary entry is created root_task_path = self.root_p2.NewProblem(description, 0x1 | 0x2 | 0x4) root_task = wait_for_task_status(self, self.root_bus, root_task_path, 2) task = Problems2Task(self.bus, root_task_path) self.assertRaisesDBusError( "org.freedesktop.DBus.Error.AccessDenied: " "The task does not belong to your session", task.getproperty, "Status") root_task.Cancel(0) # let abrt-dbus finish its work load time.sleep(1) if __name__ == "__main__": abrt_p2_testing.main(TestTaskNewProblem)
def test_get_new_foreign_problem(self): description = {"analyzer": "problems2testsuite_analyzer", "reason": "Application has been killed", "backtrace": "die()", "duphash": "TASK_NEW_PROBLEM", "uuid": "TASK_NEW_PROBLEM", "executable": "/usr/bin/foo", "type": "abrt-problems2"} # Create task, run it and stop after temporary entry is created task_path = self.root_p2.NewProblem(description, 0x1 | 0x2 | 0x4) task = wait_for_task_status(self, self.root_bus, task_path, 2) details = task.getproperty("Details") self.assertIn("NewProblem.TemporaryEntry", details) new_problems = self.p2.GetProblems(0x1 | 0x2, dict()) self.assertIn(details["NewProblem.TemporaryEntry"], new_problems) task.Cancel(0) time.sleep(1) new_problems = self.p2.GetProblems(0x1 | 0x2, dict()) self.assertEqual(0, len(new_problems)) if __name__ == "__main__": abrt_p2_testing.main(TestGetProblems)
data = entry.ReadElements(["passwd"], 0x0) self.assertNotIn("passwd", data) def test_pipes(self): entry = Problems2Entry(self.bus, self.p2_entry_path) rp, wp = os.pipe() try: entry.SaveElements({"pipe0": dbus.types.UnixFd(rp)}, 0) data = entry.ReadElements(["pipe0"], 0x0) self.assertNotIn("pipe0", data) os.write(wp, b"Epic success!") os.close(wp) wp = -1 entry.SaveElements({"pipe1": dbus.types.UnixFd(rp)}, 0) data = entry.ReadElements(["pipe1"], 0x0) self.assertIn("pipe1", data) self.assertEqual(data["pipe1"], "Epic success!") finally: os.close(rp) if wp != -1: os.close(wp) if __name__ == "__main__": abrt_p2_testing.main(TestSaveElements)
self.assertEqual(len(self.ac_signal_occurrences), 1, "Session emitted a signal") self.assertEqual(self.ac_signal_occurrences[0], 1, "Authorization request was accepted") self.logger.debug("Going to check Session object") # Give abrt-dbus some time to deal with a disappeared session. time.sleep(1) self.logger.debug("Opening a temporary DBus connection") bus = dbus.SystemBus(private=True) bus.set_exit_on_disconnect(False) p2s = Problems2Session(bus, p2s.getobject().object_path) exception_msg = "org.freedesktop.DBus.Error.UnknownMethod: " \ "No such interface " \ "'org.freedesktop.DBus.Properties' on object " \ "at path {0}".format(p2s.getobject().object_path) self.assertRaisesDBusError(exception_msg, p2s.getproperty, "IsAuthorized") self.logger.debug("Closing the temporary DBus connection") bus.close() if __name__ == "__main__": abrt_p2_testing.main(TestSessionLimits)
self.problems = list() def _bunch_of_new_problems(self, upper_limit): self.problems = list() for i in range(0, upper_limit): problem_path = create_problem(self, self.p2, wait=True) self.problems.append(problem_path) def test_new_problem_time_limit(self): self.assertRaisesProblems2Exception( "Too many problems have been recently created", self._bunch_of_new_problems, 11) self.p2.DeleteProblems(self.problems) time.sleep(16) self.assertRaisesProblems2Exception( "Too many problems have been recently created", self._bunch_of_new_problems, 3) self.assertGreaterEqual(len(self.problems), 1, "The limit has been restored") if __name__ == "__main__": abrt_p2_testing.main(TestNewProblemTimeLimit)
description=description, wait=True) time.sleep(30) uuid, duphash = create_problem(self, self.p2, bus=self.bus, description=description, wait=False) self.loop_counter += 1 self.wait_for_signals(["Crash"]) self.assertEqual(len(self.crash_signal_occurrences), 2, "Duplicate Crash signal wasn't emitted") self.p2_entry_path = self.crash_signal_occurrences[1][0] self.assertEqual(origin, self.p2_entry_path, "Crash signal was emitted with wrong UID") self.assertEqual(os.geteuid(), self.crash_signal_occurrences[1][1], "Crash signal was emitted with wrong UID") p2e = Problems2Entry(self.root_bus, self.p2_entry_path) self.assertEqual(uuid, p2e.getproperty("UUID")) self.assertEqual(duphash, p2e.getproperty("Duphash")) self.assertEqual(2, p2e.getproperty("Count")) if __name__ == "__main__": abrt_p2_testing.main(TestCrashSanity)
self.task = abrt_p2_testing.Problems2Task(self.bus, task_path) self.task.getobjectproperties().connect_to_signal( "PropertiesChanged", self.handle_properties_changed_signal) status = self.task.getproperty("Status") self.assertEqual(0, status) details = self.task.getproperty("Details") self.assertDictEqual(details, dict()) self.task.Start(dict()) self.wait_for_signals(["PropertiesChanged"]) self.assertEqual(self.task_running, 2) self.assertEqual(self.task_stopped, 1) self.assertEqual(self.task_done, 1) results, code = self.task.Finish() self.assertEqual(0, code) self.assertIn("NewProblem.Entry", results) self.assertRegexpMatches(results["NewProblem.Entry"], "/org/freedesktop/Problems2/Entry/.+") self.p2.DeleteProblems([str(results["NewProblem.Entry"])]) if __name__ == "__main__": abrt_p2_testing.main(TestNewProblem)
tasks = list() for path, bus in task_paths: tasks.append(Problems2Task(bus, path)) for i in range(0, 60): for t in tasks: status = t.getproperty("Status") if status == 4: results, code = t.Finish() self.assertIn("Error.Message", results) self.assertRegexpMatches(results["Error.Message"], "Failed to create new problem " "directory: Problem data is " "too big") tasks.remove(t) elif not status == 1: self.fail("Unexpected task status: %s" % (str(status))) if not tasks: break time.sleep(1) self.assertFalse(tasks) for _, _, _, huge_file in buses: huge_file.close() if __name__ == "__main__": abrt_p2_testing.main(TestConcurency)
def test_get_new_foreign_problem(self): description = {"analyzer": "problems2testsuite_analyzer", "reason": "Application has been killed", "backtrace": "die()", "duphash": "TASK_NEW_PROBLEM", "uuid": "TASK_NEW_PROBLEM", "executable": "/usr/bin/foo", "type": "abrt-problems2"} # Create task, run it and stop after temporary entry is created task_path = self.root_p2.NewProblem(description, 0x1 | 0x2 | 0x4) task = wait_for_task_status(self, self.root_bus, task_path, 2) details = task.getproperty("Details") self.assertIn("NewProblem.TemporaryEntry", details) new_problems = self.p2.GetProblems(0x1 | 0x2, dict()) self.assertIn(details["NewProblem.TemporaryEntry"], new_problems) task.Cancel(0) time.sleep(1) new_problems = self.p2.GetProblems(0x1 | 0x2, dict()) self.assertEquals(0, len(new_problems)) if __name__ == "__main__": abrt_p2_testing.main(TestGetProblems)
self.assertIn("delete_two", elements, "the other elements have disappeared") self.assertIn("delete_six", elements, "the other elements have disappeared") p2e.DeleteElements(["delete_one", "delete_two", "delete_six"]) elements = p2e.getproperty("Elements") self.assertNotIn("delete_one", elements) self.assertNotIn("delete_two", elements) self.assertNotIn("delete_six", elements) p2e.DeleteElements([]) for path in ["/tmp/shadow", "/tmp/passwd"]: with open(path, "w") as tmp_file: tmp_file.write("should not be touched") resp = p2e.DeleteElements(["/tmp/shadow", "../../../../tmp/passwd"]) try: os.unlink("/tmp/shadow") except OSError as ex: self.fail("removed an absolute path: %s" % (str(ex))) try: os.unlink("/tmp/passwd") except OSError as ex: self.fail("removed a relative path: %s" % (str(ex))) if __name__ == "__main__": abrt_p2_testing.main(TestDeleteElements)
self.assertTrue( len(reasonlist) == 1, "not returned fd when ALL_FD | ONLY_TEXT requested") fd = reasonlist["reason"].take() try: # try read few more bytes to verify that the file is not broken data = os.read(fd, len("Application has been killed") + 10) self.assertEqual( "Application has been killed", data.decode(), "invalid data read from file descriptor : '%s'" % (data)) finally: os.close(fd) def test_read_byte_elements(self): exp = { "bytes": dbus.types.Array( bytearray([ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0xA, 0xB, 0xC, 0xD, 0xE, 0xF ]), "y") } p2e = Problems2Entry(self.bus, self.p2_entry_path) elements = p2e.ReadElements(exp.keys(), 0x20) self.assertDictContainsSubset(elements, exp) if __name__ == "__main__": abrt_p2_testing.main(TestReadElements)
self.assertEqual(3, len(reports), "missing reports") exp = [ ("ABRT Server", {"BTHASH": "0123456789ABCDEF", "MSG": "test"}), ("Server", {"URL": "http://example.org"}), ("Server", {"URL": "http://case.org"}), ] for i in range(0, len(exp) - 1): self.assertEqual(exp[i][0], reports[i][0], "invalid reported_to label") self.assertEqual(exp[i][1], reports[i][1], "invalid reported_to value") solutions = p2e.getproperty("Solutions") self.assertEqual(0, len(solutions), "No Solutions") semantic_elements = p2e.getproperty("SemanticElements") self.assertEqual(0, len(semantic_elements), "No SemanticElements") if __name__ == "__main__": abrt_p2_testing.main(TestProblemEntryProperties)
p = self.p2.GetProblemData(self.p2_entry_path) expected = { "analyzer": (10, len("problems2testsuite_analyzer"), "problems2testsuite_analyzer"), "type": (10, len("problems2testsuite_type"), "problems2testsuite_type"), "reason": (22, len("Application has been killed"), "Application has been killed"), "backtrace": (6, len("die()"), "die()"), "executable": (10, len("/usr/bin/foo"), "/usr/bin/foo"), "hugetext": (73, os.path.getsize("/tmp/hugetext"), "/var/spool/abrt/[^/]+/hugetext"), "binary": (9, os.path.getsize("/usr/bin/true"), "/var/spool/abrt/[^/]+/binary"), } for k, v in expected.items(): if self.assertIn(k, p): print("Missing %s" % (k)) continue g = p[k] self.assertRegex(g[2], v[2], "invalid contents of '%s'" % (k)) self.assertEqual(v[1], g[1], "invalid length '%s'" % (k)) self.assertEqual(v[0], g[0], "invalid flags %s" % (k)) if __name__ == "__main__": abrt_p2_testing.main(TestGetProblemDataSanity)
reasonlist = p2e.ReadElements(["reason"], 0x10) self.assertTrue(len(reasonlist) == 0, "returned text when ONLY_BIN requested") reasonlist = p2e.ReadElements(["reason"], 0x04) self.assertTrue(len(reasonlist) == 1, "not returned text when ONLY_TEXT requested") self.assertEqual(reasonlist["reason"], "Application has been killed", "invalid data returned") reasonlist = p2e.ReadElements(["reason"], 0x01 | 0x04) self.assertTrue(len(reasonlist) == 1, "not returned fd when ALL_FD | ONLY_TEXT requested") fd = reasonlist["reason"].take() try: # try read few more bytes to verify that the file is not broken data = os.read(fd, len("Application has been killed") + 10) self.assertEqual("Application has been killed", data.decode(), "invalid data read from file descriptor : '%s'" % (data)) finally: os.close(fd) def test_read_byte_elements(self): exp = { "bytes" : dbus.types.Array(bytearray([0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0xA, 0xB, 0xC, 0xD, 0xE, 0xF]), "y") } p2e = Problems2Entry(self.bus, self.p2_entry_path) elements = p2e.ReadElements(exp.keys(), 0x20) self.assertDictContainsSubset(elements, exp) if __name__ == "__main__": abrt_p2_testing.main(TestReadElements)
p = self.p2.GetProblems(0, dict()) self.assertNotIn(one, p) self.assertIn(two, p) self.assertIn(three, p) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, [two, three, one]) p = self.p2.GetProblems(0, dict()) self.assertNotIn(one, p) self.assertNotIn(two, p) self.assertNotIn(three, p) self.p2.DeleteProblems([]) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, ["/invalid/path"]) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, ["/org/freedesktop/Problems2/Entry/FAKE"]) if __name__ == "__main__": abrt_p2_testing.main(TestDeleteProblemsSanity)
self.assertTrue( self.another_p2_session.getproperty("IsAuthorized"), "Token Authorization made Session authorized") self.another_p2_session.RevokeAuthorization() self.assertRaisesDBusError( "org.freedesktop.DBus.Error.AccessDenied: Failed to authorize Session: " "No such token", self.another_p2_session.Authorize, {'problems2.peer-bus': self.bus.get_unique_name(), 'problems2.peer-token': token}) def test_random_bus(self): with authorize_session(self) as p2_session: token = p2_session.GenerateToken(0) self.assertRaisesDBusError( "org.freedesktop.DBus.Error.Failed: Failed to authorize Session: " "No peer session for bus 'fooblah'", self.another_p2_session.Authorize, {'problems2.peer-bus': "fooblah", 'problems2.peer-token': token}) self.assertFalse( self.another_p2_session.getproperty("IsAuthorized"), "Token Authorization made Session authorized") if __name__ == "__main__": abrt_p2_testing.main(TestSessionAuthorizationPassing)
self.assertIn("delete_six", elements, "the other elements have disappeared") p2e.DeleteElements(["delete_one", "delete_two", "delete_six"]) elements = p2e.getproperty("Elements") self.assertNotIn("delete_one", elements) self.assertNotIn("delete_two", elements) self.assertNotIn("delete_six", elements) p2e.DeleteElements([]) for path in ["/tmp/shadow", "/tmp/passwd"]: with open(path, "w") as tmp_file: tmp_file.write("should not be touched") resp = p2e.DeleteElements(["/tmp/shadow", "../../../../tmp/passwd"]) try: os.unlink("/tmp/shadow") except OSError as ex: self.fail("removed an absolute path: %s" % (str(ex))) try: os.unlink("/tmp/passwd") except OSError as ex: self.fail("removed a relative path: %s" % (str(ex))) if __name__ == "__main__": abrt_p2_testing.main(TestDeleteElements)
if self.assertTrue(len(self.ac_signal_occurrences) == 3, "Pending signal 2 wasn't emitted"): self.assertEqual(1, self.ac_signal_occurrences[2], "Pending signal 2 value") self.assertFalse(p2_session.getproperty("IsAuthorized"), "Pending authorization request 2 made Session authorized") self.wait_for_signals(["AuthorizationChanged"]) if self.assertTrue(len(self.ac_signal_occurrences) == 4, "Authorized signal wasn't emitted"): self.assertEqual(0, self.ac_signal_occurrences[3], "Authorized signal value") self.assertTrue(p2_session.getproperty("IsAuthorized"), "Authorization request did not make Session authorized") p2_session.RevokeAuthorization() self.wait_for_signals(["AuthorizationChanged"]) if self.assertTrue(len(self.ac_signal_occurrences) == 5, "Revoked authorization session signal wasn't emitted"): self.assertEqual(2, self.ac_signal_occurrences[0], "Revoked authorization session signal value") p2_session_path = self.p2.GetSession() p2_session = Problems2Session(self.bus, p2_session_path) self.assertFalse(p2_session.getproperty("IsAuthorized"), msg = "still authorized") if __name__ == "__main__": abrt_p2_testing.main(TestSession)
if self.p2_entry_duplicate_path: self.p2.DeleteProblems([self.p2_entry_duplicate_path]) def test_duplicates(self): description = {"analyzer": "problems2testsuite_analyzer", "reason": "Application has been killed", "backtrace": "die()", "duphash": "NEW_PROBLEM_DUPLICATES", "uuid": "NEW_PROBLEM_DUPLICATES", "executable": "/usr/bin/true", "type": "abrt-problems2-dupes"} task_path = self.p2.NewProblem(description, 0x1) self.p2_entry_path = wait_for_task_new_problem(self, self.bus, task_path) task_duplicate_path = self.p2.NewProblem(description, 0x1) self.p2_entry_duplicate_path = wait_for_task_new_problem( self, self.bus, task_duplicate_path) self.assertEqual(self.p2_entry_path, self.p2_entry_duplicate_path) self.p2_entry_duplicate_path = None if __name__ == "__main__": abrt_p2_testing.main(TestDuplicates)
self.p2.DeleteProblems([one]) p = self.p2.GetProblems(0, dict()) self.assertNotIn(one, p) self.assertIn(two, p) self.assertIn(three, p) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, [two, three, one]) p = self.p2.GetProblems(0, dict()) self.assertNotIn(one, p) self.assertNotIn(two, p) self.assertNotIn(three, p) self.p2.DeleteProblems([]) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, ["/invalid/path"]) self.assertRaisesDBusError(DBUS_ERROR_BAD_ADDRESS, self.p2.DeleteProblems, ["/org/freedesktop/Problems2/Entry/FAKE"]) if __name__ == "__main__": abrt_p2_testing.main(TestDeleteProblemsSanity)
def tearDown(self): if self.problems: self.p2.DeleteProblems(self.problems) self.problems = list() def _bunch_of_new_problems(self, upper_limit): self.problems = list() for i in range(0, upper_limit): problem_path = create_problem(self, self.p2, wait=True) self.problems.append(problem_path) def test_new_problem_time_limit(self): self.assertRaisesProblems2Exception( "Too many problems have been recently created", self._bunch_of_new_problems, 11) self.p2.DeleteProblems(self.problems) time.sleep(16) self.assertRaisesProblems2Exception( "Too many problems have been recently created", self._bunch_of_new_problems, 3) self.assertGreaterEqual(len(self.problems), 1, "The limit has been restored") if __name__ == "__main__": abrt_p2_testing.main(TestNewProblemTimeLimit)
"type": "abrt-problems2-sanity"} task_path = self.p2.NewProblem(description, 0x1) self.assertRaisesProblems2Exception( "Failed to create new " "problem directory: Failed to save data of passed file " "descriptor", wait_for_task_new_problem, self, self.bus, task_path) os.write(wp, b"Epic success!") os.close(wp) wp = -1 task_path = self.p2.NewProblem(description, 0x1) self.p2_entry_path = wait_for_task_new_problem(self, self.bus, task_path) entry = Problems2Entry(self.bus, self.p2_entry_path) data = entry.ReadElements(["pipe"], 0x0) self.assertIn("pipe", data) self.assertEqual(data["pipe"], "Epic success!") finally: os.close(rp) if wp != -1: os.close(wp) if __name__ == "__main__": abrt_p2_testing.main(TestNewProblemSanity)
p2_entry = Problems2Entry(self.bus, self.p2_entry_root_path) self.assertEqual("Application has been killed", p2_entry.getproperty("Reason"), "Properties are accessible") def test_foreign_problem_not_accessible(self): p = self.p2.GetProblems(0, dict()) self.assertNotEqual(0, len(p), "no problems") self.assertIn(self.p2_entry_path, p, "missing our problem") self.assertNotIn(self.p2_entry_root_path, p, "accessible private problem") self.assertRaisesDBusError(DBUS_ERROR_ACCESS_DENIED_READ, self.p2.GetProblemData, self.p2_entry_root_path) self.assertRaisesDBusError(DBUS_ERROR_ACCESS_DENIED_DELETE, self.p2.DeleteProblems, [self.p2_entry_root_path]) p2_entry = Problems2Entry(self.bus, self.p2_entry_root_path) self.assertRaisesDBusError(DBUS_ERROR_ACCESS_DENIED_READ, p2_entry.getproperty, "Reason") if __name__ == "__main__": abrt_p2_testing.main(TestForeignProblems)
wait=True) time.sleep(30) uuid, duphash = create_problem(self, self.p2, bus=self.bus, description=description, wait=False) self.loop_counter += 1 self.wait_for_signals(["Crash"]) self.assertEqual(len(self.crash_signal_occurrences), 2, "Duplicate Crash signal wasn't emitted") self.p2_entry_path = self.crash_signal_occurrences[1][0] self.assertEqual(origin, self.p2_entry_path, "Crash signal was emitted with wrong UID") self.assertEqual(os.geteuid(), self.crash_signal_occurrences[1][1], "Crash signal was emitted with wrong UID") p2e = Problems2Entry(self.root_bus, self.p2_entry_path) self.assertEqual(uuid, p2e.getproperty("UUID")) self.assertEqual(duphash, p2e.getproperty("Duphash")) self.assertEqual(2, p2e.getproperty("Count")) if __name__ == "__main__": abrt_p2_testing.main(TestCrashSanity)
for path, bus in task_paths: tasks.append(Problems2Task(bus, path)) for i in range(0, 60): for t in tasks: status = t.getproperty("Status") if status == 4: results, code = t.Finish() self.assertIn("Error.Message", results) self.assertRegexpMatches( results["Error.Message"], "Failed to create new problem " "directory: Problem data is " "too big") tasks.remove(t) elif not status == 1: self.fail("Unexpected task status: %s" % (str(status))) if not tasks: break time.sleep(1) self.assertFalse(tasks) for _, _, _, huge_file in buses: huge_file.close() if __name__ == "__main__": abrt_p2_testing.main(TestConcurency)
self.p2.GetProblemData, "/org/freedesktop/Problems2/Entry/FAKE") self.assertRaisesDBusError(DBUS_ERROR_ACCESS_DENIED_READ, self.p2.GetProblemData, self.p2_entry_root_path) p = self.p2.GetProblemData(self.p2_entry_path) expected = { "analyzer" : (10, len("problems2testsuite_analyzer"), "problems2testsuite_analyzer"), "type" : (10, len("problems2testsuite_type"), "problems2testsuite_type"), "reason" : (22, len("Application has been killed"), "Application has been killed"), "backtrace" : (6, len("die()"), "die()"), "executable" : (10, len("/usr/bin/foo"), "/usr/bin/foo"), "hugetext" : (73, os.path.getsize("/tmp/hugetext"), "/var/spool/abrt/[^/]+/hugetext"), "binary" : (9, os.path.getsize("/usr/bin/true"), "/var/spool/abrt/[^/]+/binary"), } for k, v in expected.items(): if self.assertIn(k, p): print("Missing %s" % (k)) continue g = p[k] self.assertRegexpMatches(g[2], v[2], "invalid contents of '%s'" % (k)) self.assertEqual(v[1], g[1], "invalid length '%s'" % (k)) self.assertEqual(v[0], g[0], "invalid flags %s" % (k)) if __name__ == "__main__": abrt_p2_testing.main(TestGetProblemDataSanity)
if self.p2_entry_duplicate_path: self.p2.DeleteProblems([self.p2_entry_duplicate_path]) def test_duplicates(self): description = { "analyzer": "problems2testsuite_analyzer", "reason": "Application has been killed", "backtrace": "die()", "duphash": "NEW_PROBLEM_DUPLICATES", "uuid": "NEW_PROBLEM_DUPLICATES", "executable": "/usr/bin/true", "type": "abrt-problems2-dupes" } task_path = self.p2.NewProblem(description, 0x1) self.p2_entry_path = wait_for_task_new_problem(self, self.bus, task_path) task_duplicate_path = self.p2.NewProblem(description, 0x1) self.p2_entry_duplicate_path = wait_for_task_new_problem( self, self.bus, task_duplicate_path) self.assertEqual(self.p2_entry_path, self.p2_entry_duplicate_path) self.p2_entry_duplicate_path = None if __name__ == "__main__": abrt_p2_testing.main(TestDuplicates)