SearchCases.py 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. # Copyright 2015-2017 Espressif Systems (Shanghai) PTE LTD
  2. #
  3. # Licensed under the Apache License, Version 2.0 (the "License");
  4. # you may not use this file except in compliance with the License.
  5. # You may obtain a copy of the License at
  6. #
  7. # http:#www.apache.org/licenses/LICENSE-2.0
  8. #
  9. # Unless required by applicable law or agreed to in writing, software
  10. # distributed under the License is distributed on an "AS IS" BASIS,
  11. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. # See the License for the specific language governing permissions and
  13. # limitations under the License.
  14. """ search test cases from a given file or path """
  15. import os
  16. import fnmatch
  17. import types
  18. import copy
  19. # TODO: add a function to use suitable import lib for python2 and python3
  20. import imp
  21. class Search(object):
  22. TEST_CASE_FILE_PATTERN = "*_test.py"
  23. @classmethod
  24. def _search_cases_from_file(cls, file_name):
  25. """ get test cases from test case .py file """
  26. print("Try to get cases from: " + file_name)
  27. test_functions = []
  28. try:
  29. # TODO: add a function to use suitable import lib for python2 and python3
  30. mod = imp.load_source(str(hash(file_name)), file_name)
  31. for func in [mod.__getattribute__(x) for x in dir(mod)
  32. if isinstance(mod.__getattribute__(x), types.FunctionType)]:
  33. try:
  34. # test method decorator will add test_method attribute to test function
  35. if func.test_method:
  36. test_functions.append(func)
  37. except AttributeError:
  38. continue
  39. except ImportError as e:
  40. print("ImportError: \r\n\tFile:" + file_name + "\r\n\tError:" + str(e))
  41. for i, test_function in enumerate(test_functions):
  42. print("\t{}. ".format(i+1) + test_function.case_info["name"])
  43. return test_functions
  44. @classmethod
  45. def _search_test_case_files(cls, test_case, file_pattern):
  46. """ search all test case files recursively of a path """
  47. if not os.path.exists(test_case):
  48. raise OSError("test case path not exist")
  49. if os.path.isdir(test_case):
  50. test_case_files = []
  51. for root, _, file_names in os.walk(test_case):
  52. for filename in fnmatch.filter(file_names, file_pattern):
  53. test_case_files.append(os.path.join(root, filename))
  54. else:
  55. test_case_files = [test_case]
  56. return test_case_files
  57. @classmethod
  58. def replicate_case(cls, case):
  59. """
  60. Replicate cases according to its filter values.
  61. If one case has specified filter chip=(ESP32, ESP32C),
  62. it will create 2 cases, one for ESP32 and on for ESP32C.
  63. Once the cases are replicated, it's easy to filter those we want to execute.
  64. :param case: the original case
  65. :return: a list of replicated cases
  66. """
  67. replicate_config = []
  68. for key in case.case_info:
  69. if isinstance(case.case_info[key], (list, tuple)):
  70. replicate_config.append(key)
  71. def _replicate_for_key(case_list, replicate_key, replicate_list):
  72. case_out = []
  73. for _case in case_list:
  74. for value in replicate_list:
  75. new_case = copy.deepcopy(_case)
  76. new_case.case_info[replicate_key] = value
  77. case_out.append(new_case)
  78. return case_out
  79. replicated_cases = [case]
  80. for key in replicate_config:
  81. replicated_cases = _replicate_for_key(replicated_cases, key, case.case_info[key])
  82. return replicated_cases
  83. @classmethod
  84. def search_test_cases(cls, test_case):
  85. """
  86. search all test cases from a folder or file, and then do case replicate.
  87. :param test_case: test case file(s) path
  88. :return: a list of replicated test methods
  89. """
  90. test_case_files = cls._search_test_case_files(test_case, cls.TEST_CASE_FILE_PATTERN)
  91. test_cases = []
  92. for test_case_file in test_case_files:
  93. test_cases += cls._search_cases_from_file(test_case_file)
  94. # handle replicate cases
  95. test_case_out = []
  96. for case in test_cases:
  97. test_case_out += cls.replicate_case(case)
  98. return test_case_out