0

I am going to sync perforce files through perforce API. I expect output about each file operation. Something like what we see as output from p4 cmd:

  • //depot/file.txt#1 - updating X:\file.txt
  • //depot/file.txt#2 - deleted as X:\file.txt

Here is my perforce api code to sync files:

var repository = new P4.Repository(new P4.Server(new P4.ServerAddress("server:111111")));
repository.Connection.UserName = "me";
repository.Connection.Connect(new P4.Options());
repository.Connection.Login("password");
repository.Connection.Client = repository.GetClient("client");
var syncFlags = new P4.Options(P4.SyncFilesCmdFlags.Force, 100);
var clientPath = new P4.ClientPath(@"X:\File.txt");

IList<P4.FileSpec> results = repository.Connection.Client.SyncFiles(syncFlags, new[] { new P4.FileSpec(clientPath, new P4.Revision(1)) });
P4.VersionSpec downloadedVersion = results.First().Version; // This is #1 as expected

results = repository.Connection.Client.SyncFiles(syncFlags, new[] { new P4.FileSpec(clientPath, new P4.Revision(2)) });
downloadedVersion = results.First().Version; // This is #2 as expected

results = repository.Connection.Client.SyncFiles(syncFlags, new[] { new P4.FileSpec(clientPath, new P4.Revision(0)) });
downloadedVersion = results.First().Version; // File is really deleted and I hoped for #0, but it's #2!

How can I get information that the file is deleted? I tried to use SyncFiles output for that, but the information is not correct for deleted files. Is there any other way?

jing
  • 1,919
  • 2
  • 20
  • 39
  • Note that 'sync file#0' is not precisely the same as syncing a file that has been explicitly deleted with a delete revision. Also, perhaps 'new P4.Revision(0)' is not having the effects you expect. Look at your server's command log (the P4LOG file on the server) and see what actual 'p4 sync' commands are being recorded at the server. In particular, does the server register that final command as 'p4 sync' or as 'p4 sync#0'? – Bryan Pendleton Feb 11 '15 at 14:26
  • Thanks a lot for comment. Unfortunately I don't have permission and possibility to see P4LOG file on my server. But I see that P4.Revision(0) really deletes file in my client and P4.Revision(1) adds it. So it works. Note that P4.Revision(0) is not the only usage I expect. My app can sync to label without my file, in that case the file needs to be deleted, too. I used revision(0) as the simplest example. I hoped I can attach my "OnStatusChanged+=P4.something" and listen to output or so. But I didn't find anything. – jing Feb 11 '15 at 15:17
  • Perhaps, since you're going to be developing tools like this, you should set up your own test server to develop your tools against. It's quite easy to set up a test Perforce server on your own workstation. – Bryan Pendleton Feb 11 '15 at 17:32

2 Answers2

2

Here is solution I found:

repository.Connection.TaggedOutputReceived += Connection_TaggedOutputReceived;


static void Connection_TaggedOutputReceived(uint cmdId, int ObjId, P4.TaggedObject t)
{
    string action, oldAction, haveRevStr, depotFile;

    t.TryGetValue("action", out action);
    t.TryGetValue("oldAction", out oldAction);
    t.TryGetValue("haveRev", out haveRevStr);
    t.TryGetValue("depotFile", out depotFile);

    if (haveRevStr == null || haveRevStr == "none")
        haveRevStr = string.Empty;
    else
        haveRevStr = "#" + haveRevStr;

    if (string.IsNullOrEmpty(oldAction))
        oldAction = string.Empty;
    else
        oldAction = oldAction + " ";

    if (depotFile != null && action != null)
        Console.Out.WriteLine("{0}{1} - {2}{3}", depotFile, haveRevStr, oldAction, action);
}

... the repository.Connection contains also other interesting delegates to hook: .CommandEcho, .Errorreceived, .InfoResultReceived, .TextResultsReceived

jing
  • 1,919
  • 2
  • 20
  • 39
1

The Client.SyncFiles function gives you a tidy list of which files were affected, but not the rest of the output of the sync command. If you just want to figure out whether the file was deleted or not, statting the clientFile on the local machine should do the trick.

If you want the full output, using the P4Server interface is a better bet:

https://www.perforce.com/manuals/p4api.net/p4api.net_reference/html/M_Perforce_P4_P4Server_RunCommand.htm

If you call RunCommand() with "tagged" set to true it should give you all the data you'd get from "p4 -Ztag (command)", with the results accessible through GetTaggedOutput(). Running it without the "tagged" option will give you the formatted message you'd see as an end user, accessible through GetInfoMessages().

Norman Morse
  • 105
  • 1
  • 5
Samwise
  • 68,105
  • 3
  • 30
  • 44