replace a library in perforce - version-control

I need to replace a library in a perforce depot. The library is checked in in the form of source files which are all managed by perforce.
Now the problem is that in the new version of the library there may be
unchanged files
changed files
new files and
some files may have been deleted
Of course I can just mark the whole source tree for delete, submit, copy the new version of the library to the directory in question, mark for add and submit again, but that would create a short interval of time in which no one should synchronize in order to not break his next build -- maybe that's the best option but I'd like to know whether there is a better approach.
A second solution is to copy the new version of the library to some other directory, update all references in order to reflect the new location, and then just delete the old library and mark the new one for add. This can be done in one change list. The unpleasant and error prone part here is to update the references. Also a change in the directory names is not really desired.
Does anyone know a way to do this in one step with one changelist? I experimented with a single file example. It actually is possible to mark a file for delete and then immediately create a file with the same name and mark that for add. If you do that and submit, then the result is exactly what I want for that single file. This procedure, however, seems to require touching each file manually. I could not figure out how to do that for a whole directory or directory tree.

One possibility is to use p4 reconcile to do the majority of the work, using a process such as:
In your workspace, remove the current copy of the source tree entirely: rm -rf top-directory-name (or del /s /q if you're on Windows).
copy the entire new copy of the source tree for the library into that location.
Run p4 reconcile and let it figure out what files to open for add, for edit, and for delete. CAREFULLY inspect the results by looking closely at p4 opened, p4 diff, etc.
Submit the new changelist.

Related

How to recover Perforce history on a moved directory

I have a branch on Perforce, where I changes the directory structure of the project using Rename/Move command.
During merging back to the mainstream, Something went wrong that caused Perforce to think of the new structure as a whole-new directories.
Subsequently, the history of the files in the new directory structure is totally unrelated to the history of the same files before changing the structure.
Is there anyway to recover this situation ? Or ask Perforce to append the old history with the new history ?
Something went wrong that caused Perforce to think of the new structure as a whole-new directories.
Usually if this happens it means someone didn't use the "rename/move" command and used some other method to rename instead (i.e. they did something that adds the new directory as a new set of files independent of the originals rather than an atomic rename of an existing set of files). It's impossible for me to say how to "recover" without seeing what the history of the files looks like now so I can reverse-engineer what the "something went wrong" was.
I'd recommend either posting on the Perforce forums or contacting Perforce technical support so that somebody with expertise can wheedle the necessary data out of you (I can intuit that this will require an amount of back and forth that stackoverflow frowns on -- "what were the branches you were merging from and to", "okay, now run THIS command to see the history of that branch and send me the output," "okay, which of these five merge operations I can see in the history is the one you're talking about,") and propose a solution.
From another answer:
So, for a file a/b/c, you can look at the by using the -i option where appropriate. For example, p4 filelog -li a/b/c.
This is not necessary if files are renamed via the "move/rename" command, so if you need to use "filelog -i" to see file history, the files were definitely renamed by some other method. (The "p4 move" command was added in 2009 so long-time Perforce users will sometimes use other workflows.)

Sharing unopened files rather than getting local copy of everything

I'd like to know if there are any revision control systems such that, when user checks-out/gets/creates a workarea, it will create symbolic links for the files, rather than a local copy of everything. Once we "edit" a file, then it will replace the symbolic link with a local copy.
To make it more clear, let's say we have a repository like this:
proj/
data/
big_data.csv
src/
script.py
Users are mostly working on script.py, but data folder is huge in size. If every user keeps a local copy of big_data.csv, it consumes lots of disk space. If the revision control system keeps a copy of every version of every file, then all we need is a link to it. Users don't need to hold a local copy, unless they have to edit that file.
proj/
data/
#big_data.csv -> /depot/proj/data/big_data.csv#5
src/
script.py
So which revision control tools have a feature like this? Is it possible to get something similar in perforce?
Thanks!
You can have a symlink checked into a Perforce depot, and it can point wherever you like (I assume in this case you'd have a read-only shared network filer that the file lives on), but when you p4 edit it you'll just be editing where the symlink points.
I can envision a way you'd set this up in Perforce with streams (you could do it with classic branches and template clients too, but streams make it a lot easier).
You'd have one stream (let's call it dw) where big_data is the actual file, and one stream (let's call it dr) where big_data is the symlink, and big_data is specified as an isolate Path so that changes won't merge between the two.
There's a background script (maybe a change-commit trigger on dw/big_data) that writes each revision of dw/big_data to the filer as a unique read-only file, and then edits and submits dr/big_data to create a symlink revision that points to the filer revision. Hence a user syncing dr/big_data will get (via symlink) the matching revision of dw/big_data. dr/big_data is made read-only (via p4 protect) to all normal users to make sure nobody accidentally edits it; it needs to be strictly managed by the script that ties it to the filer.
So users who don't want to edit big_data use the dr stream; they can sync big_data to whatever revision they want, and it behaves normally, but they can't edit it. Other files in the stream (e.g. script.py) are normal files and they can edit them normally.
If a user wants to edit big_data, they do p4 switch dw and everything resyncs (for most of the files this is probably a no-op) and now big_data is a normal editable file. When they submit a new revision to it, the trigger fires and a second later there's a matching dr/big_data symlink, so users in the dr branch will see the change when they sync. (The one symlink rev per revision is so that you still get the benefits of versioning; big_data ONLY updates when you sync to the new symlink rev. If you didn't want this behavior you could just ignore keeping the file in Perforce and symlink straight to the filer and edit it there directly, but I assume you want actual version control on it.) Once they're done editing, they're free to p4 switch dr and go back to the read-only symlink (the head revision of which will now reference the revision they just submitted).
Whether dr is a parent of dw or vice versa, and how this fits into the rest of your codeline hierarchy, is left as an exercise for the reader -- it depends on whether you need to make edits to big_data in more than one codeline or whether having a linear "master" history of it is sufficient.

How to recover files that were moved to a single file?

I tried to move multiple files into a folder, but there was a mistake in my matlab code that I didn't create the folder. Now all the files were moved to a single file which cannot be opened or edited. How to recover these files?
Example of the mistake:
a=strcat('C:\Users\foldername'); % name and directory of the folder
fname=a;
% mkdir(fname); % so this command wasn't executed...
movefile('file1',fname);
movefile('file2',fname);
So now file1 and file2 were merged in file 'fname', instead of in the folder named 'fname'. How to get file1 and file2 back?
Thanks in advance!
Unfortunately, the odds may be stacked against you getting back any of the files, except for the last one. The reason why is because movefile doesn't append to an existing destination file, it overwrites it. The following will give you back your last file (by simply renaming fname):
movefile(fname, 'file2');
If you're lucky, your operating system will have options for you to restore previous versions of your files/folders. Your best bet may be to check and see if the folder containing your original files has any previous versions you can open/restore to get previous versions of 'file1' and 'file2'. For example, on my Windows machine I can right click on my default MATLAB folder, select "Properties", then select the "Previous Versions" tab, and I see this:
You can see there are a few versions I could open and copy files from if I've inadvertently deleted or overwritten anything recently. Good luck!

Mercurial/Kiln how can I get a deleted file without affecting my other files?

I have a file that was deleted a few changesets ago. As you can imagine, the other files in my project have changed since then. How can I get back that file (it's actually 2 files) without reverting all the other source files?
Use hg revert for just that file:
hg revert -r REV path/to/deleted/file
From the help for hg revert
If a file has been deleted, it is restored. If the executable mode of a file was changed, it is reset.
If names are given, all files matching the names are reverted. If no arguments are given, no files are reverted.
Another approach to this is to use the Kiln website. You can search for a changeset by changeset id, or just use a date search, .e.g. date:2011-10-01..2011-10-31
That will then give you a list of changesets, click the one that will show the version of the code you want to recover, and then if you click the Browse files at [changeset id] link on the right hand side you will then get a list of the folders and files at that point in time.
You can then just add new files to your project and cut and paste the code back into those new files.
Admittedly this isn't as nice an approach for recovering a whole file, but it's handy if you only want to recover part of the code, or if someone has subsequently added a new file with the name of the old file.

Same file in multiple changelists in perforce

Is there any way to have the same file be a part of multiples changelists in perforce? With that I mean that from the set of changed lines in the file one subset will belong to a changelist, while the other subset will belong to a second changelist.
Bonus question: If perforce does not support this, then which Source Control Systems, if any, do?
To answer the bonus question: GIT allows for per-line changelists.
For a comparison between the two view this question: GIT vs. Perforce- Two VCS will enter... one will leave.
The same copy of the file? No, unfortunately this isn't possible.
Another way to do this without branching is create additional workspaces (clients). Unless you really know what you're doing, be sure to set a different root directory in each of your workspaces. To save time (and disk), don't bother syncing the whole depot in the new workspace.
Sometimes, I'll have two copies of a depot (using two workspaces); one which contains work-in-progress and one which I keep unmodified. If I need to make a quickie change on a file that's heavily modified in my WIP workspace, I can use the 'virgin' workspace to make the change and submit it.
If you are using p4 server 2009.2, there is a workaround to do it. You can shelve a particular file and the diff is stored on the server. After shelving you may want to revert the file to its original version and then work it on in another change-list.
I know this is not a way you wanted it but it is quite easy to create another workspace/client and then sync the code. The later exercise becomes more tedious when you have volumes of code that goes into another application.
For more info read:
http://blog.perforce.com/blog/?p=1872
http://www.perforce.com/perforce/doc.current/manuals/cmdref/shelve.html
You could make a copy of the file with all of the changes, revert, edit the file copy one set of changes into the file, submit, edit, copy the next set of changes, submit, edit, etc...
Bonus answer: I found this feature in Rational Team Concert (http://www-03.ibm.com/software/products/en/rtc/). You can have the same file in many changesets. If you want to add File1 to Changeset1 and Changeset2, you must complete Changeset1 first. This allows you to add File 2 to Changeset2 but then a dependency between changesets is created, so you can not deliver Changeset2 without delivering Changeset1 too. Moreover you can not make changes to a complete changeset.