Show More
@@ -35,6 +35,7 b' from . import (' | |||||
35 | pycompat, |
|
35 | pycompat, | |
36 | revsetlang, |
|
36 | revsetlang, | |
37 | similar, |
|
37 | similar, | |
|
38 | url, | |||
38 | util, |
|
39 | util, | |
39 | ) |
|
40 | ) | |
40 |
|
41 | |||
@@ -1016,6 +1017,56 b' class filecache(object):' | |||||
1016 | except KeyError: |
|
1017 | except KeyError: | |
1017 | raise AttributeError(self.name) |
|
1018 | raise AttributeError(self.name) | |
1018 |
|
1019 | |||
|
1020 | def extdatasource(repo, source): | |||
|
1021 | """Gather a map of rev -> value dict from the specified source | |||
|
1022 | ||||
|
1023 | A source spec is treated as a URL, with a special case shell: type | |||
|
1024 | for parsing the output from a shell command. | |||
|
1025 | ||||
|
1026 | The data is parsed as a series of newline-separated records where | |||
|
1027 | each record is a revision specifier optionally followed by a space | |||
|
1028 | and a freeform string value. If the revision is known locally, it | |||
|
1029 | is converted to a rev, otherwise the record is skipped. | |||
|
1030 | ||||
|
1031 | Note that both key and value are treated as UTF-8 and converted to | |||
|
1032 | the local encoding. This allows uniformity between local and | |||
|
1033 | remote data sources. | |||
|
1034 | """ | |||
|
1035 | ||||
|
1036 | spec = repo.ui.config("extdata", source) | |||
|
1037 | if not spec: | |||
|
1038 | raise error.Abort(_("unknown extdata source '%s'") % source) | |||
|
1039 | ||||
|
1040 | data = {} | |||
|
1041 | if spec.startswith("shell:"): | |||
|
1042 | # external commands should be run relative to the repo root | |||
|
1043 | cmd = spec[6:] | |||
|
1044 | cwd = os.getcwd() | |||
|
1045 | os.chdir(repo.root) | |||
|
1046 | try: | |||
|
1047 | src = util.popen(cmd) | |||
|
1048 | finally: | |||
|
1049 | os.chdir(cwd) | |||
|
1050 | else: | |||
|
1051 | # treat as a URL or file | |||
|
1052 | src = url.open(repo.ui, spec) | |||
|
1053 | ||||
|
1054 | try: | |||
|
1055 | for l in src.readlines(): | |||
|
1056 | if " " in l: | |||
|
1057 | k, v = l.strip().split(" ", 1) | |||
|
1058 | else: | |||
|
1059 | k, v = l.strip(), "" | |||
|
1060 | ||||
|
1061 | k = encoding.tolocal(k) | |||
|
1062 | if k in repo: | |||
|
1063 | # we ignore data for nodes that don't exist locally | |||
|
1064 | data[repo[k].rev()] = encoding.tolocal(v) | |||
|
1065 | finally: | |||
|
1066 | src.close() | |||
|
1067 | ||||
|
1068 | return data | |||
|
1069 | ||||
1019 | def _locksub(repo, lock, envvar, cmd, environ=None, *args, **kwargs): |
|
1070 | def _locksub(repo, lock, envvar, cmd, environ=None, *args, **kwargs): | |
1020 | if lock is None: |
|
1071 | if lock is None: | |
1021 | raise error.LockInheritanceContractViolation( |
|
1072 | raise error.LockInheritanceContractViolation( |
General Comments 0
You need to be logged in to leave comments.
Login now