Commits
Pam Ford authored 3c867cb1b94 Merge
1 1 | ######################################################################################################################## |
2 2 | ############################################ Imports ############################################# |
3 3 | ######################################################################################################################## |
4 - | |
5 4 | import argparse |
6 5 | import os |
7 6 | import shutil |
8 7 | import sys |
9 8 | import traceback |
10 9 | import subprocess |
11 10 | import unittest |
12 11 | import json |
13 12 | import datetime |
14 13 | import platform |
15 14 | |
16 - | |
17 - | default_timeout = 1800 |
18 - | sys.path.insert(0,'') |
19 - | |
20 15 | ######################################################################################################################## |
21 16 | ###################################### Imports / Constants ####################################### |
22 17 | ######################################################################################################################## |
23 18 | |
19 + | default_timeout = 1800 |
20 + | sys.path.insert(0,'') |
21 + | |
24 22 | # mem mode variables |
25 23 | HAVE_MEMTEST=True |
26 24 | MEM = 0 |
27 25 | try: |
28 26 | import memTest |
29 27 | except ImportError: |
30 28 | HAVE_MEMTEST = False |
31 29 | |
32 30 | # cov mode variables |
33 31 | HAVE_COVTEST=True |
80 78 | |
81 79 | # Use Nose attribute Functionality |
82 80 | RUN_SUBTEST = False |
83 81 | |
84 82 | # Dry run of Tests |
85 83 | DRY_RUN = False |
86 84 | |
87 85 | ######################################################################################################################## |
88 86 | ########################################### Functions ############################################ |
89 87 | ######################################################################################################################## |
88 + | # At the moment, this needs to be a sep function due to repr and escape characters, try/ except for osx |
89 + | def write_conftest_linux(filepath): |
90 + | string = """ |
91 + | import pytest |
92 + | import inspect |
93 + | import os |
94 + | |
95 + | @pytest.mark.trylast |
96 + | def pytest_configure(config): |
97 + | terminal_reporter = config.pluginmanager.getplugin('terminalreporter') |
98 + | config.pluginmanager.register(TestDescriptionPlugin(terminal_reporter), 'testdescription') |
99 + | |
100 + | class TestDescriptionPlugin: |
101 + | |
102 + | def __init__(self, terminal_reporter): |
103 + | self.terminal_reporter = terminal_reporter |
104 + | self.desc = None |
105 + | self.funcn = None |
106 + | |
107 + | def pytest_runtest_protocol(self, item): |
108 + | #from pprint import pprint |
109 + | #d = item.__dict__ |
110 + | #pprint(d, indent=2) |
111 + | self.desc = inspect.getdoc(item.obj) |
112 + | #print(item._nodeid) |
113 + | self.funcn = item._nodeid |
114 + | |
115 + | @pytest.hookimpl(hookwrapper=True, tryfirst=True) |
116 + | def pytest_runtest_logstart(self, nodeid, location): |
117 + | #print("Verbosity Level: {}".format(self.terminal_reporter.verbosity)) |
118 + | if self.terminal_reporter.verbosity == 0: |
119 + | yield |
120 + | self.terminal_reporter.write(f'\\n{self.funcn} \\n') |
121 + | else: |
122 + | self.terminal_reporter.write('\\n') |
123 + | yield |
124 + | if self.desc: |
125 + | self.terminal_reporter.write(f'\\n{self.desc} \\n') |
126 + | else: |
127 + | self.terminal_reporter.write(f'\\n') |
128 + | |
129 + | @pytest.hookimpl(hookwrapper=True) |
130 + | def pytest_runtest_makereport(item, call): |
131 + | outcome = yield |
132 + | report = outcome.get_result() |
133 + | #print(dir(report)) |
134 + | report.start = call.start |
135 + | report.stop = call.stop |
136 + | if report.when=='teardown': |
137 + | filepath = os.path.join(os.getcwd(),'short_summary.log') |
138 + | |
139 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
140 + | file_obj.write("{} {}\\n".format(report.outcome.upper(), report.nodeid,)) |
141 + | file_obj.close() |
142 + | |
143 + | @pytest.hookimpl(hookwrapper=True) |
144 + | def pytest_runtest_makereport(item, call): |
145 + | outcome = yield |
146 + | report = outcome.get_result() |
147 + | if report.when=='call': |
148 + | filepath = os.path.join(os.getcwd(),'short_summary.log') |
149 + | # write short summary to file |
150 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
151 + | file_obj.write("{} {}\\n".format(report.outcome.upper(), report.nodeid)) |
152 + | file_obj.close() |
153 + | |
154 + | # Write not pass to Textfile |
155 + | if report.outcome != 'passed': |
156 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
157 + | file_obj.write("\\tDuration: {}s\\n".format(round(report.duration,5))) |
158 + | file_obj.write("\\tMessage : {}\\n".format(report.longrepr.reprcrash.message)) |
159 + | file_obj.close() |
160 + | filepath = os.path.join(os.path.abspath(os.path.join(os.path.dirname( __file__ ), '..')),'summary_of_failed.log') |
161 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
162 + | file_obj.write("{} {}\\n".format(report.outcome.upper(), report.nodeid)) |
163 + | file_obj.write("\\tDuration: {}s\\n".format(round(report.duration,5))) |
164 + | file_obj.write("\\tMessage : {}\\n".format(report.longrepr.reprcrash.message)) |
165 + | file_obj.close() |
166 + | """ |
167 + | file_obj = open(filepath,'w') |
168 + | file_obj.write(string) |
169 + | file_obj.close() |
170 + | |
171 + | # At the moment, this needs to be a sep function due to repr and escape characters, try/ except for osx |
172 + | def write_conftest_osx(filepath): |
173 + | string = """ |
174 + | import pytest |
175 + | import inspect |
176 + | import os |
177 + | |
178 + | @pytest.mark.trylast |
179 + | def pytest_configure(config): |
180 + | terminal_reporter = config.pluginmanager.getplugin('terminalreporter') |
181 + | try: |
182 + | config.pluginmanager.unregister(TestDescriptionPlugin(terminal_reporter), 'testdescription') |
183 + | except: |
184 + | pass |
185 + | config.pluginmanager.register(TestDescriptionPlugin(terminal_reporter), 'testdescription') |
186 + | |
187 + | class TestDescriptionPlugin: |
188 + | |
189 + | def __init__(self, terminal_reporter): |
190 + | self.terminal_reporter = terminal_reporter |
191 + | self.desc = None |
192 + | self.funcn = None |
193 + | |
194 + | def pytest_runtest_protocol(self, item): |
195 + | #from pprint import pprint |
196 + | #d = item.__dict__ |
197 + | #pprint(d, indent=2) |
198 + | self.desc = inspect.getdoc(item.obj) |
199 + | #print(item._nodeid) |
200 + | self.funcn = item._nodeid |
201 + | |
202 + | @pytest.hookimpl(hookwrapper=True, tryfirst=True) |
203 + | def pytest_runtest_logstart(self, nodeid, location): |
204 + | #print("Verbosity Level: {}".format(self.terminal_reporter.verbosity)) |
205 + | if self.terminal_reporter.verbosity == 0: |
206 + | yield |
207 + | self.terminal_reporter.write(f'\\n{self.funcn} \\n') |
208 + | else: |
209 + | self.terminal_reporter.write('\\n') |
210 + | yield |
211 + | if self.desc: |
212 + | self.terminal_reporter.write(f'\\n{self.desc} \\n') |
213 + | else: |
214 + | self.terminal_reporter.write(f'\\n') |
215 + | |
216 + | @pytest.hookimpl(hookwrapper=True) |
217 + | def pytest_runtest_makereport(item, call): |
218 + | outcome = yield |
219 + | report = outcome.get_result() |
220 + | if report.when=='call': |
221 + | filepath = os.path.join(os.getcwd(),'short_summary.log') |
222 + | # write short summary to file |
223 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
224 + | file_obj.write("{} {}\\n".format(report.outcome.upper(), report.nodeid)) |
225 + | file_obj.close() |
226 + | |
227 + | # Write not pass to Textfile |
228 + | if report.outcome != 'passed': |
229 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
230 + | file_obj.write("\\tDuration: {}s\\n".format(round(report.duration,5))) |
231 + | file_obj.write("\\tMessage : {}\\n".format(report.longrepr.reprcrash.message)) |
232 + | file_obj.close() |
233 + | filepath = os.path.join(os.path.abspath(os.path.join(os.path.dirname( __file__ ), '..')),'summary_of_failed.log') |
234 + | file_obj = open(filepath, 'a' if os.path.isfile(filepath) else 'w') |
235 + | file_obj.write("{} {}\\n".format(report.outcome.upper(), report.nodeid)) |
236 + | file_obj.write("\\tDuration: {}s\\n".format(round(report.duration,5))) |
237 + | file_obj.write("\\tMessage : {}\\n".format(report.longrepr.reprcrash.message)) |
238 + | file_obj.close() |
239 + | """ |
240 + | file_obj = open(filepath,'w') |
241 + | file_obj.write(string) |
242 + | file_obj.close() |
90 243 | |
91 244 | class casa_test: |
92 245 | def __init__(self, |
93 246 | name, |
94 247 | path, |
95 248 | test_group=None, |
96 249 | test_type=None, |
97 250 | maintainer=None, |
98 251 | email=None, |
99 252 | options=None, |
239 392 | ## Almatasks |
240 393 | |
241 394 | os.chdir(os.path.dirname(os.getcwd())) |
242 395 | os.makedirs("almatasks") |
243 396 | os.chdir("almatasks") |
244 397 | subprocess.call(["git","init", "--quiet"]) |
245 398 | subprocess.call(["git","remote","add","-f","origin", "https://open-bitbucket.nrao.edu/scm/casa/almatasks.git"], stdout=FNULL, stderr=subprocess.STDOUT) |
246 399 | subprocess.call(["git","config","core.sparseCheckout","true"]) |
247 400 | print("tests/tasks", file=open(".git/info/sparse-checkout", "a")) |
248 401 | subprocess.call(['git','pull','--quiet','origin','master']) |
402 + | |
403 + | ## casaviewer |
404 + | |
249 405 | os.chdir(os.path.dirname(os.getcwd())) |
406 + | os.makedirs("casaviewer") |
407 + | os.chdir("casaviewer") |
408 + | subprocess.call(["git","init", "--quiet"]) |
409 + | subprocess.call(["git","remote","add","-f","origin", "https://open-bitbucket.nrao.edu/scm/casa/casaviewer.git"], stdout=FNULL, stderr=subprocess.STDOUT) |
410 + | subprocess.call(["git","config","core.sparseCheckout","true"]) |
411 + | print("tests/tasks", file=open(".git/info/sparse-checkout", "a")) |
412 + | subprocess.call(['git','pull','--quiet','origin','master']) |
250 413 | |
414 + | ## casampi |
251 415 | |
416 + | os.chdir(os.path.dirname(os.getcwd())) |
417 + | os.makedirs("casampi") |
418 + | os.chdir("casampi") |
419 + | subprocess.call(["git","init", "--quiet"]) |
420 + | subprocess.call(["git","remote","add","-f","origin", "https://open-bitbucket.nrao.edu/scm/casa/casampi.git"], stdout=FNULL, stderr=subprocess.STDOUT) |
421 + | subprocess.call(["git","config","core.sparseCheckout","true"]) |
422 + | print("src/casampi/tests", file=open(".git/info/sparse-checkout", "a")) |
423 + | subprocess.call(['git','pull','--quiet','origin','master']) |
424 + | |
425 + | os.chdir(os.path.dirname(os.getcwd())) |
252 426 | os.chdir(cwd) |
253 427 | |
254 428 | def git_fetch_casa_tests_branch(path, branch): |
255 429 | |
256 430 | cwd = os.getcwd() |
257 431 | if os.path.exists(path): |
258 432 | try: |
259 433 | os.rmdir(path) |
260 434 | except: |
261 435 | shutil.rmtree(path) |
450 624 | # Copy Tests to Working Directory |
451 625 | os.makedirs(workdir) |
452 626 | |
453 627 | if RUN_ALL: |
454 628 | print("Gathering All Tests") |
455 629 | git_fetch_casa_tests( workpath + 'casa6') |
456 630 | os.makedirs(workdir + "all/") |
457 631 | gather_all_tests(workpath +'casa6/', workdir + "all/") |
458 632 | gather_all_tests(workpath +'casaplotms/', workdir + "all/") |
459 633 | gather_all_tests(workpath +'almatasks/', workdir + "all/") |
634 + | gather_all_tests(workpath +'casaviewer/', workdir + "all/") |
635 + | gather_all_tests(workpath +'casampi/', workdir + "all/") |
460 636 | cmd = [ workdir ] |
461 637 | cmd = ["--continue-on-collection-errors"] + cmd |
462 - | if verbose: |
463 - | cmd = ["--verbose"] + cmd |
638 + | cmd = ["--verbose"] + ["-ra"] + cmd |
464 639 | |
465 640 | |
466 641 | if DRY_RUN: |
467 642 | cmd = ["--collect-only"] + cmd |
468 643 | |
469 644 | if not os.path.isdir(workpath + '/xml/all/'): |
470 645 | os.makedirs(workpath + '/xml/all/') |
471 646 | xmlfile = workpath + '/xml/all/nose.xml' |
472 647 | |
473 648 | ######### |
477 652 | # PytestDeprecationWarning: The 'junit_family' # default value will change to 'xunit2' in pytest 6.0. |
478 653 | # Add 'junit_family=xunit1' to your pytest.ini file to keep the current format in future versions of pytest and silence this warning. |
479 654 | # _issue_warning_captured(deprecated.JUNIT_XML_DEFAULT_FAMILY, config.hook, 2) |
480 655 | ######### |
481 656 | cmd = ["--junitxml={}".format(xmlfile)] + ["-s"] + cmd |
482 657 | |
483 658 | if len(os.listdir(workdir + "all/")) == 0: |
484 659 | print("No Tests to Run") |
485 660 | else: |
486 661 | print("Running Command: pytest {}".format(cmd)) |
662 + | conf_name = os.path.join(os.getcwd(),"conftest.py") |
663 + | if platform.system() == 'Darwin': |
664 + | write_conftest_osx(conf_name) |
665 + | else: |
666 + | write_conftest_linux(conf_name) |
487 667 | pytest.main(cmd) |
668 + | os.remove(conf_name) |
488 669 | |
489 670 | else: |
490 671 | print("Tests: {}".format(testnames)) |
491 672 | gittest = True |
492 673 | |
493 674 | for testname in testnames: |
494 675 | cmd = [] |
495 676 | |
496 677 | # Copy Test To nosedir Directory if in cwd |
497 678 | if testname.startswith("test"): |
533 714 | # gather_all_tests(workpath +'almatasks/', workdir + "tests/") |
534 715 | gittest = False |
535 716 | |
536 717 | else: |
537 718 | print("Fetching Tests From Git Main Since No Local Test is Given") |
538 719 | git_fetch_casa_tests( workpath + 'casa6/') |
539 720 | os.makedirs(workdir + "tests/") |
540 721 | gather_all_tests(workpath +'casa6/', workdir + "tests/") |
541 722 | gather_all_tests(workpath +'casaplotms/', workdir + "tests/") |
542 723 | gather_all_tests(workpath +'almatasks/', workdir + "tests/") |
724 + | gather_all_tests(workpath +'casaviewer/', workdir + "tests/") |
725 + | gather_all_tests(workpath +'casampi/', workdir + "tests/") |
543 726 | gittest = False |
544 727 | |
545 728 | if test.endswith(".py"): |
546 729 | try: |
547 730 | print("Copying: {} to {}".format(test, workdir + "{}/".format(test if not test.endswith(".py") else test[:-3]))) |
548 731 | shutil.copy2(test, workdir + "{}/".format(test if not test.endswith(".py") else test[:-3])) |
549 732 | except: |
550 733 | traceback.print_exc() |
551 734 | else: |
552 735 | try: |
553 736 | print("Copying: {} to {}".format(workdir + "tests/",test), workdir + "{}/".format(test if not test.endswith(".py") else test[:-3])) |
554 737 | shutil.copy2("{}{}.py".format(workdir + "tests/",test), workdir + "{}/".format(test if not test.endswith(".py") else test[:-3])) |
555 738 | except: |
556 739 | traceback.print_exc() |
557 740 | |
558 741 | # https://docs.pytest.org/en/stable/usage.html |
559 - | if verbose: |
560 - | cmd = ["--verbose"] + ["--tb=long"] + cmd |
561 - | elif not verbose: |
562 - | cmd = ["-ra"] + ["--tb=short"] + cmd |
563 - | #cmd = ["-ra"] + ["--tb=long"] + cmd |
742 + | |
743 + | cmd = ["--verbose"] + ["-ra"] + ["--tb=short"] + cmd |
564 744 | |
565 745 | if DRY_RUN: |
566 746 | cmd = ["--collect-only"] + cmd |
567 747 | |
568 748 | if not os.path.isdir(workpath + '/xml/{}/'.format(test if not test.endswith(".py") else test[:-3])): |
569 749 | os.makedirs(workpath + '/xml/{}/'.format(test if not test.endswith(".py") else test[:-3])) |
570 750 | xmlfile = workpath + 'xml/{}/nose.xml'.format(test if not test.endswith(".py") else test[:-3]) |
571 751 | |
572 752 | ######### |
573 753 | #============================================================ warnings summary ===================================================== |
582 762 | #print("Work Path: {}".format(workpath)) |
583 763 | if len(os.listdir(workpath)) < 1: # If only the XML dir was created |
584 764 | print("No Tests to Run") |
585 765 | sys.exit() |
586 766 | else: |
587 767 | |
588 768 | myworkdir = os.getcwd() |
589 769 | os.chdir("{}".format(workdir + "{}/".format(test if not test.endswith(".py") else test[:-3]))) |
590 770 | print("Test Directory: {}".format(os.getcwd())) |
591 771 | print("Running Command: pytest {}".format(cmd)) |
772 + | conf_name = os.path.join(os.getcwd(),"conftest.py") |
773 + | if platform.system() == 'Darwin': |
774 + | write_conftest_osx(conf_name) |
775 + | else: |
776 + | write_conftest_linux(conf_name) |
592 777 | pytest.main(cmd) |
778 + | os.remove(conf_name) |
593 779 | os.chdir(myworkdir) |
594 780 | |
595 781 | ################################################## |
596 782 | ########## Real Path ########## |
597 783 | ################################################## |
598 784 | # Copy Test To nosedir Directory assuming it's in another location |
599 785 | elif testname.startswith("/"): |
600 786 | testpath = testname.split("[")[0] |
601 787 | cmd = [] |
602 788 | dirname = testname.split("/")[-1] |
626 812 | # Set up Test Working Directory |
627 813 | if not os.path.exists(workdir + "{}/".format(dirname)): |
628 814 | print("Setting Working Directory: {}".format(workdir + "{}/".format(dirname))) |
629 815 | os.makedirs(workdir + "{}/".format(dirname)) |
630 816 | cmd = [ workdir + "{}/".format(dirname) ] + cmd |
631 817 | try: |
632 818 | shutil.copy2(testpath, workdir + "{}/".format(dirname)) |
633 819 | except: |
634 820 | traceback.print_exc() |
635 821 | |
636 - | if verbose: |
637 - | cmd = ["--verbose"] + ["--tb=long"] + cmd |
638 - | elif not verbose: |
639 - | cmd = ["-ra"] + ["--tb=short"] + cmd |
640 - | #cmd = ["-ra"] + ["--tb=long"] + cmd |
641 - | |
822 + | cmd = ["--verbose"] + ["-ra"] + ["--tb=short"] + cmd |
642 823 | |
643 824 | if DRY_RUN: |
644 825 | cmd = ["--collect-only"] + cmd |
645 826 | |
646 827 | if not os.path.isdir(workpath + '/xml/{}/'.format(dirname)): |
647 828 | os.makedirs(workpath + '/xml/{}/'.format(dirname)) |
648 829 | xmlfile = workpath + 'xml/{}/nose.xml'.format(dirname) |
649 830 | |
650 831 | ######### |
651 832 | #============================================================ warnings summary ===================================================== |
659 840 | #print("Running Command: pytest {}".format(cmd)) |
660 841 | #print("Work Path: {}".format(workpath)) |
661 842 | if len(os.listdir(workpath)) < 1: # If only the XML dir was created |
662 843 | print("No Tests to Run") |
663 844 | sys.exit() |
664 845 | else: |
665 846 | myworkdir = os.getcwd() |
666 847 | os.chdir(workdir + "{}/".format(dirname)) |
667 848 | print("Test Directory: {}".format(os.getcwd())) |
668 849 | print("Running Command: pytest {}".format(cmd)) |
850 + | conf_name = os.path.join(os.getcwd(),"conftest.py") |
851 + | if platform.system() == 'Darwin': |
852 + | write_conftest_osx(conf_name) |
853 + | else: |
854 + | write_conftest_linux(conf_name) |
669 855 | pytest.main(cmd) |
856 + | os.remove(conf_name) |
670 857 | os.chdir(myworkdir) |
671 858 | os.chdir(cwd) |
672 859 | |
673 860 | if not HAVE_PYTEST: |
674 861 | print("Missing Pytest") |
675 862 | |
676 863 | |
677 864 | ######################################################################################################################## |
678 865 | ####################################### Run Bamboo Option ######################################## |
679 866 | ######################################################################################################################## |