summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorShawn O. Pearce <sop@google.com>2009-04-17 21:03:32 -0700
committerShawn O. Pearce <sop@google.com>2009-04-17 21:03:45 -0700
commitc12c360f89d4d1cc0a0ad80c4ea0785f84be1848 (patch)
tree7e875709a4270e681f7335b7a3171b14b2d8e313
parentfbcde472cadfc8319016faca90cb5b57f7a00ee4 (diff)
downloadgit-repo-c12c360f89d4d1cc0a0ad80c4ea0785f84be1848.tar.gz
Pickle parsed git config files
We now cache the output of `git config --list` for each of our GitConfig instances in a Python pickle file. These can be read back in using only the Python interpreter at a much faster rate than we can fork+exec the git config process. If the corresponding git config file has a newer modification timestamp than the pickle file, we delete the pickle file and regenerate it. This ensures that any edits made by the user will be taken into account the next time we consult the file. This reduces the time for a no-op repo sync from 0.847s to 0.269s. Signed-off-by: Shawn O. Pearce <sop@google.com>
-rw-r--r--git_config.py38
1 files changed, 38 insertions, 0 deletions
diff --git a/git_config.py b/git_config.py
index 9b63417e..c87d5bed 100644
--- a/git_config.py
+++ b/git_config.py
@@ -13,6 +13,7 @@
13# See the License for the specific language governing permissions and 13# See the License for the specific language governing permissions and
14# limitations under the License. 14# limitations under the License.
15 15
16import cPickle
16import os 17import os
17import re 18import re
18import sys 19import sys
@@ -57,6 +58,9 @@ class GitConfig(object):
57 self._cache_dict = None 58 self._cache_dict = None
58 self._remotes = {} 59 self._remotes = {}
59 self._branches = {} 60 self._branches = {}
61 self._pickle = os.path.join(
62 os.path.dirname(self.file),
63 '.repopickle_' + os.path.basename(self.file))
60 64
61 def Has(self, name, include_defaults = True): 65 def Has(self, name, include_defaults = True):
62 """Return true if this configuration file has the key. 66 """Return true if this configuration file has the key.
@@ -170,6 +174,40 @@ class GitConfig(object):
170 return self._cache_dict 174 return self._cache_dict
171 175
172 def _Read(self): 176 def _Read(self):
177 d = self._ReadPickle()
178 if d is None:
179 d = self._ReadGit()
180 self._SavePickle(d)
181 return d
182
183 def _ReadPickle(self):
184 try:
185 if os.path.getmtime(self._pickle) \
186 <= os.path.getmtime(self.file):
187 os.remove(self._pickle)
188 return None
189 except OSError:
190 return None
191 try:
192 return cPickle.load(open(self._pickle, 'r'))
193 except IOError:
194 os.remove(self._pickle)
195 return None
196 except cPickle.PickleError:
197 os.remove(self._pickle)
198 return None
199
200 def _SavePickle(self, cache):
201 try:
202 cPickle.dump(cache,
203 open(self._pickle, 'w'),
204 cPickle.HIGHEST_PROTOCOL)
205 except IOError:
206 os.remove(self._pickle)
207 except cPickle.PickleError:
208 os.remove(self._pickle)
209
210 def _ReadGit(self):
173 d = self._do('--null', '--list') 211 d = self._do('--null', '--list')
174 c = {} 212 c = {}
175 while d: 213 while d: