def _normalize_svn_file_content(self, repository, contents, path, revision): """Post-process a file pertaining to a Subversion repository. This is common code that handles collapsing keywords for files fetched from or diffed against a Subversion repository. Args: repository (reviewboard.scmtools.models.Repository): The repository the content is for. contents (bytes): The file content to normalize. path (unicode): The path to the file. revision (unicode): The revision of the file. Returns: bytes: The resulting file. """ if has_expanded_svn_keywords(contents): try: props = self._api_get_svn_props(repository, path, revision) except URLError: props = None if props and 'svn:keywords' in props: contents = collapse_svn_keywords( contents, props['svn:keywords'].encode('utf-8')) return contents
def test_collapse_svn_keywords(self): """Testing collapse_svn_keywords""" keyword_test_data = [ (b'Id', b'/* $Id: test2.c 3 2014-08-04 22:55:09Z david $ */', b'/* $Id$ */'), (b'id', b'/* $Id: test2.c 3 2014-08-04 22:55:09Z david $ */', b'/* $Id$ */'), (b'id', b'/* $id: test2.c 3 2014-08-04 22:55:09Z david $ */', b'/* $id$ */'), (b'Id', b'/* $id: test2.c 3 2014-08-04 22:55:09Z david $ */', b'/* $id$ */') ] for keyword, data, result in keyword_test_data: self.assertEqual(collapse_svn_keywords(data, keyword), result)
def _get_file_data(self, normpath, normrev): data = self.client.cat(normpath, normrev) if has_expanded_svn_keywords(data): # Find out if this file has any keyword expansion set. # If it does, collapse these keywords. This is because SVN # will return the file expanded to us, which would break patching. keywords = self.client.propget('svn:keywords', normpath, normrev, recurse=True) if normpath in keywords: data = collapse_svn_keywords(data, force_bytes(keywords[normpath])) return data
def normalize_patch(self, patch, filename, revision=HEAD): """ If using Subversion, we need not only contract keywords in file, but also in the patch. Otherwise, if a file with expanded keyword somehow ends up in the repository (e.g. by first checking in a file without svn:keywords and then setting svn:keywords in the repository), RB won't be able to apply a patch to such file. """ if revision != PRE_CREATION and has_expanded_svn_keywords(patch): keywords = self.client.get_keywords(filename, revision) if keywords: return collapse_svn_keywords(patch, force_bytes(keywords)) return patch
def get_file(self, path, revision=HEAD): """Return the contents of a given file at the given revision. Args: path (unicode): The path to the file. revision (unicode or reviewboard.scmtools.core.Revision, optional): The revision of the file to fetch. Returns: bytes: The file contents. Raises: reviewboard.scmtools.errors.FileNotFoundError: The file could not be found in the repository. """ if not path: raise FileNotFoundError(path, revision) revnum = self._normalize_revision(revision) path = self.normalize_path(path) data = io.BytesIO() try: self.client.cat(path, data, revnum) except SubversionException as e: raise FileNotFoundError(e) contents = data.getvalue() if has_expanded_svn_keywords(contents): keywords = self.get_keywords(path, revision) if keywords: contents = collapse_svn_keywords(contents, keywords) return contents