Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1""" 

2@file 

3@brief Helper for the setup. 

4""" 

5import os 

6import sys 

7import shlex 

8import subprocess 

9from ..loghelper import noLOG, run_cmd 

10from ..loghelper.run_cmd import get_interpreter_path 

11from .open_script_file import open_script 

12 

13 

14def call_setup_hook_cmd(folder, module_name, function_name="_setup_hook", 

15 additional_paths=None, interpreter_path=None, 

16 check=True, **args): 

17 """ 

18 Prepares the command line to call function 

19 @see fn _setup_hook for a specific module. 

20 

21 @param folder folder which contains the setup 

22 @param module_name module name 

23 @param function_name function to call by default 

24 @param additional_paths additional_paths to add to *sys.path* before call the function 

25 @param args additional parameter (dictionary) 

26 @param interpreter_path to use a different interpreter than the current one 

27 @param check check existence of filename 

28 @return stdout, stderr 

29 

30 The function expects to find file ``__init__.py`` in 

31 ``<folder>/src/<module_name>``. 

32 

33 .. versionadded:: 1.9 

34 Parameter *check* was added. 

35 """ 

36 this = os.path.abspath(os.path.dirname(__file__)) 

37 this = os.path.normpath(os.path.join(this, "..", "..")) 

38 src = os.path.abspath(os.path.join(folder, "src")) 

39 if check and not os.path.exists(src): 

40 src = os.path.abspath(folder) 

41 if check and not os.path.exists(src): 

42 raise FileNotFoundError( # pragma: no cover 

43 "Unable to find folder '{}'.".format(folder)) 

44 if additional_paths is None: 

45 additional_paths = [src, this] 

46 else: 

47 additional_paths = [src, this] + additional_paths 

48 

49 if args is None or len(args) == 0: 

50 str_args = "" 

51 else: 

52 typstr = str 

53 str_args = "**" + typstr(args) 

54 

55 code = ["import sys", ] 

56 code.extend(["sys.path.append('{0}')".format( 

57 d.replace("\\", "/")) for d in additional_paths]) 

58 code.extend(["from {0} import {1}".format(module_name, function_name), 

59 "{0}({1})".format(function_name, str_args), 

60 "sys.exit(0)"]) 

61 code = ";".join(code) 

62 

63 if interpreter_path is None: 

64 interpreter_path = get_interpreter_path() 

65 

66 cmd = [interpreter_path, "-c", '"{0}"'.format(code)] 

67 cmd = " ".join(cmd) 

68 return cmd, code 

69 

70 

71def call_setup_hook(folder, module_name, fLOG=noLOG, must_be=False, 

72 function_name="_setup_hook", use_print=False, 

73 force_call=False, additional_paths=None, 

74 **args): 

75 """ 

76 Calls function @see fn _setup_hook for a specific module, 

77 it is called in a separate process. 

78 

79 @param folder folder which contains the setup 

80 @param module_name module name 

81 @param fLOG logging function 

82 @param must_be raises an exception if @see fn _setup_hook is not found 

83 @param function_name function to call by default 

84 @param use_print use print to display information 

85 @param force_call use *subprocess.call* instead of @see fn run_cmd 

86 @param additional_paths additional_paths to add to *sys.path* before call the function 

87 @param args additional parameter (dictionary) 

88 @return stdout, stderr 

89 

90 The function expects to find file ``__init__.py`` in 

91 ``<folder>/src/<module_name>``. 

92 """ 

93 cmd, code = call_setup_hook_cmd(folder=folder, module_name=module_name, 

94 function_name=function_name, 

95 additional_paths=additional_paths, **args) 

96 if use_print: # pragma: no cover 

97 print("CODE:\n", code) 

98 print("CMD:\n", cmd) 

99 

100 fLOG("[call_setup_hook] calls _setup_hook from", module_name) 

101 if not force_call and sys.platform.startswith("win"): 

102 out, err = run_cmd( # pragma: no cover 

103 cmd, wait=True, fLOG=fLOG, log_error=False) 

104 exit = 0 # pragma: no cover 

105 else: 

106 if use_print: # pragma: no cover 

107 print("subprocess.call", cmd) 

108 if not sys.platform.startswith("win"): 

109 args = shlex.split(cmd) 

110 else: 

111 args = cmd # pragma: no cover 

112 exit = subprocess.call(args) 

113 out = "linux" 

114 err = "" 

115 

116 if exit != 0: 

117 src = os.path.abspath(os.path.join(folder, "src")) 

118 if not os.path.exists(src): # pragma: no cover 

119 src = os.path.abspath(folder) 

120 if not os.path.exists(src): 

121 raise FileNotFoundError( # pragma: no cover 

122 "Unable to find folder '{}'.".format(folder)) 

123 init = os.path.join(src, module_name, "__init__.py") 

124 with open_script(init, "r") as f: 

125 content = f.read() 

126 sdef = 'def {0}'.format(function_name) 

127 if sdef not in content: 

128 exit = 0 

129 err = "ImportError: cannot import name '{0}'".format( 

130 function_name) 

131 fLOG("[call_setup_hook] end of call _setup_hook") 

132 

133 if use_print: # pragma: no cover 

134 print("OUT:\n", out) 

135 if err: 

136 if "cannot import name '_setup_hook'" in err: 

137 fLOG("[call_setup_hook] _setup_hook was not found.") 

138 else: 

139 print("[pyqerror]\n", err) 

140 

141 def error(): 

142 mes = ("**CMD:\n{3}\n**CODE:\n{0}\n**OUT:\n{1}\n**[pyqerror]" 

143 "\n{2}\nexit={4}").format( # pragma: no cover 

144 code.replace(";", "\n"), out, err, cmd, exit) 

145 return mes # pragma: no cover 

146 

147 if not must_be and ( 

148 "ImportError: cannot import name '{0}'".format(function_name) in err or 

149 "ImportError: cannot import name {0}".format(function_name) in err): 

150 # no _setup_hook 

151 return out, "no {0}".format(function_name) 

152 if "Error while finding spec " in err: 

153 raise Exception(error()) # pragma: no cover 

154 if "ImportError: No module named" in err: 

155 raise Exception(error()) # pragma: no cover 

156 if exit != 0: 

157 raise Exception(error()) # pragma: no cover 

158 out = "CMD: {0}\n---\n{1}".format(cmd, out) 

159 return out, err