git-p4: Support usage of perforce client spec
When syncing, git-p4 will only download files that are included in the active perforce client spec. This does not change the default behaviour - it requires that the user either supplies the command line argument --use-client-spec, or sets the git config option p4.useclientspec to "true". Signed-off-by: Tor Arvid Lund <torarvid@gmail.com> Signed-off-by: Simon Hausmann <simon@lst.de>
Tor Arvid Lund committed
Feb 18, 2008 at 15:22 UTC
3a70cdfa42199e16d2d047c286431c4274d65b1a
1 file changed
+42
-8
contrib/fast-import/git-p4
+42
-8
@@ -745,7 +745,9 @@ class P4Sync(Command):
745
help="Import into refs/heads/ , not refs/remotes"),
746
optparse.make_option("--max-changes", dest="maxChanges"),
747
optparse.make_option("--keep-path", dest="keepRepoPath", action='store_true',
748
- help="Keep entire BRANCH/DIR/SUBDIR prefix during import")
748
+ help="Keep entire BRANCH/DIR/SUBDIR prefix during import"),
749
+ optparse.make_option("--use-client-spec", dest="useClientSpec", action='store_true',
750
+ help="Only sync files that are included in the Perforce Client Spec")
751
]
752
self.description = """Imports from Perforce into a git repository.\n
753
example:
@@ -772,6 +774,8 @@ class P4Sync(Command):
774
self.depotPaths = None
775
self.p4BranchesInGit = []
776
self.cloneExclude = []
777
+ self.useClientSpec = False
778
+ self.clientSpecDirs = []
779
780
if gitConfig("git-p4.syncFromOrigin") == "false":
781
self.syncWithOrigin = False
@@ -846,11 +850,21 @@ class P4Sync(Command):
850
851
## Should move this out, doesn't use SELF.
852
def readP4Files(self, files):
853
+ for f in files:
854
+ for val in self.clientSpecDirs:
855
+ if f['path'].startswith(val[0]):
856
+ if val[1] > 0:
857
+ f['include'] = True
858
+ else:
859
+ f['include'] = False
860
+ break
861
+
862
files = [f for f in files
850
- if f['action'] != 'delete']
863
+ if f['action'] != 'delete' and
864
+ (f.has_key('include') == False or f['include'] == True)]
865
866
if not files:
853
- return
867
+ return []
868
869
filedata = p4CmdList('-x - print',
870
stdin='\n'.join(['%s#%s' % (f['path'], f['rev'])
@@ -885,6 +899,7 @@ class P4Sync(Command):
899
for f in files:
900
assert not f.has_key('data')
901
f['data'] = contents[f['path']]
902
+ return files
903
904
def commit(self, details, files, branch, branchPrefixes, parent = ""):
905
epoch = details["time"]
@@ -901,11 +916,7 @@ class P4Sync(Command):
916
new_files.append (f)
917
else:
918
sys.stderr.write("Ignoring file outside of prefix: %s\n" % path)
904
- files = new_files
905
- self.readP4Files(files)
906
-
907
-
908
-
919
+ files = self.readP4Files(new_files)
920
921
self.gitStream.write("commit %s\n" % branch)
922
# gitStream.write("mark :%s\n" % details["change"])
@@ -1320,6 +1331,26 @@ class P4Sync(Command):
1331
print self.gitError.read()
1332
1333
1334
+ def getClientSpec(self):
1335
+ specList = p4CmdList( "client -o" )
1336
+ temp = {}
1337
+ for entry in specList:
1338
+ for k,v in entry.iteritems():
1339
+ if k.startswith("View"):
1340
+ if v.startswith('"'):
1341
+ start = 1
1342
+ else:
1343
+ start = 0
1344
+ index = v.find("...")
1345
+ v = v[start:index]
1346
+ if v.startswith("-"):
1347
+ v = v[1:]
1348
+ temp[v] = -len(v)
1349
+ else:
1350
+ temp[v] = len(v)
1351
+ self.clientSpecDirs = temp.items()
1352
+ self.clientSpecDirs.sort( lambda x, y: abs( y[1] ) - abs( x[1] ) )
1353
+
1354
def run(self, args):
1355
self.depotPaths = []
1356
self.changeRange = ""
@@ -1352,6 +1383,9 @@ class P4Sync(Command):
1383
if not gitBranchExists(self.refPrefix + "HEAD") and self.importIntoRemotes and gitBranchExists(self.branch):
1384
system("git symbolic-ref %sHEAD %s" % (self.refPrefix, self.branch))
1385
1386
+ if self.useClientSpec or gitConfig("p4.useclientspec") == "true":
1387
+ self.getClientSpec()
1388
+
1389
# TODO: should always look at previous commits,
1390
# merge with previous imports, if possible.
1391
if args == []: