##// END OF EJS Templates
fix race condition in profiledir creation.
James Porter -
Show More
@@ -24,6 +24,7 b' Authors:'
24 import os
24 import os
25 import shutil
25 import shutil
26 import errno
26 import errno
27 import time
27
28
28 from IPython.config.configurable import LoggingConfigurable
29 from IPython.config.configurable import LoggingConfigurable
29 from IPython.utils.path import get_ipython_package_dir, expand_path
30 from IPython.utils.path import get_ipython_package_dir, expand_path
@@ -79,9 +80,17 b' class ProfileDir(LoggingConfigurable):'
79 if self._location_isset:
80 if self._location_isset:
80 raise RuntimeError("Cannot set profile location more than once.")
81 raise RuntimeError("Cannot set profile location more than once.")
81 self._location_isset = True
82 self._location_isset = True
82 if not os.path.isdir(new):
83 num_tries = 0
83 os.makedirs(new)
84 max_tries = 5
84
85 while not os.path.isdir(new):
86 try:
87 os.makedirs(new)
88 except OSError:
89 if num_tries > max_tries:
90 raise
91 num_tries += 1
92 time.sleep(0.5)
93
85 # ensure config files exist:
94 # ensure config files exist:
86 self.security_dir = os.path.join(new, self.security_dir_name)
95 self.security_dir = os.path.join(new, self.security_dir_name)
87 self.log_dir = os.path.join(new, self.log_dir_name)
96 self.log_dir = os.path.join(new, self.log_dir_name)
@@ -92,12 +101,12 b' class ProfileDir(LoggingConfigurable):'
92
101
93 def _log_dir_changed(self, name, old, new):
102 def _log_dir_changed(self, name, old, new):
94 self.check_log_dir()
103 self.check_log_dir()
95
104
96 def _mkdir(self, path, mode=None):
105 def _mkdir(self, path, mode=None):
97 """ensure a directory exists at a given path
106 """ensure a directory exists at a given path
98
107
99 This is a version of os.mkdir, with the following differences:
108 This is a version of os.mkdir, with the following differences:
100
109
101 - returns True if it created the directory, False otherwise
110 - returns True if it created the directory, False otherwise
102 - ignores EEXIST, protecting against race conditions where
111 - ignores EEXIST, protecting against race conditions where
103 the dir may have been created in between the check and
112 the dir may have been created in between the check and
@@ -124,7 +133,7 b' class ProfileDir(LoggingConfigurable):'
124 return False
133 return False
125 else:
134 else:
126 raise
135 raise
127
136
128 return True
137 return True
129
138
130 def check_log_dir(self):
139 def check_log_dir(self):
@@ -270,5 +279,3 b' class ProfileDir(LoggingConfigurable):'
270 if not os.path.isdir(profile_dir):
279 if not os.path.isdir(profile_dir):
271 raise ProfileDirError('Profile directory not found: %s' % profile_dir)
280 raise ProfileDirError('Profile directory not found: %s' % profile_dir)
272 return cls(location=profile_dir, config=config)
281 return cls(location=profile_dir, config=config)
273
274
General Comments 0
You need to be logged in to leave comments. Login now