views:

2015

answers:

6

I would like to write some scripts in python that do some automated changes to source code. If the script determines it needs to change the file I would like to first check it out of perforce. I don't care about checking in because I will always want to build and test first.

+3  A: 

Here's what I came up with:

import os

def CreateNewChangeList(description):
    "Create a new changelist and returns the changelist number as a string"
    p4in, p4out = os.popen2("p4 changelist -i")
    p4in.write("change: new\n")
    p4in.write("description: " + description)
    p4in.close()
    changelist = p4out.readline().split()[1]
    return changelist

def OpenFileForEdit(file, changelist = ""):
    "Open a file for edit, if a changelist is passed in then open it in that list"
    cmd = "p4 edit "
    if changelist:
        cmd += " -c " + changelist + " "
    ret = os.popen(cmd + file).readline().strip()
    if not ret.endswith("opened for edit"):
        print "Couldn't open", file, "for edit:"
        print ret
        raise ValueError
Matt Price
Seems silly to use os.popen() calls when you can use the native API/tools supported by Perforce.
Nick Stinemates
Using the p4 module ties you to a specific version of the perforce C++ API if I remember correctly. Using the command line is backwards compatible, easy, and if you change the command to p4 -G edit, it will return the objects as marshalled python dictionary objects.
grieve
Using the command line p4 is easier to configure too
justinhj
+1  A: 

You may want to check out the P4Python module. It's available on the perforce site and it makes things very simple.

Nithin
+11  A: 

Perforce has Python wrappers around their C/C++ tools, available in binary form for Windows, and source for other platforms:

http://www.perforce.com/perforce/loadsupp.html#api

You will find their documentation of the scripting API to be helpful:

http://www.perforce.com/perforce/doc.current/manuals/p4script/p4script.pdf

Use of the Python API is quite similar to the command-line client:

PythonWin 2.5.1 (r251:54863, May  1 2007, 17:47:05) [MSC v.1310 32 bit (Intel)] on win32.
Portions Copyright 1994-2006 Mark Hammond - see 'Help/About PythonWin' for further copyright information.
>>> import P4
>>> p4 = P4.P4()
>>> p4.connect() # connect to the default server, with the default clientspec
>>> desc = {"Description": "My new changelist description",
...         "Change": "new"
...         }
>>> p4.input = desc
>>> p4.run("changelist", "-i")
['Change 2579505 created.']
>>>

I'll verify it from the command line:

P:\>p4 changelist -o 2579505
# A Perforce Change Specification.
#
#  Change:      The change number. 'new' on a new changelist.
#  Date:        The date this specification was last modified.
#  Client:      The client on which the changelist was created.  Read-only.
#  User:        The user who created the changelist.
#  Status:      Either 'pending' or 'submitted'. Read-only.
#  Description: Comments about the changelist.  Required.
#  Jobs:        What opened jobs are to be closed by this changelist.
#               You may delete jobs from this list.  (New changelists only.)
#  Files:       What opened files from the default changelist are to be added
#               to this changelist.  You may delete files from this list.
#               (New changelists only.)

Change: 2579505

Date:   2008/10/08 13:57:02

Client: MYCOMPUTER-DT

User:   myusername

Status: pending

Description:
        My new changelist description
Troy J. Farrell
+2  A: 

Perforce's P4 Python module mentioned in another answer is the way to go, but if installing this module isn't an option you can use the -G flag to help parse p4.exe output:

p4 [ options ] command [ arg ... ]
    options:
            -c client -C charset -d dir -H host -G -L language
            -p port -P pass -s -Q charset -u user -x file
    The -G flag causes all output (and batch input for form commands
    with -i) to be formatted as marshalled Python dictionary objects.
Syeberman
+1  A: 

Building from p4python source requires downloading and extracting the p4 api recommended for that version. For example, if building the Windows XP x86 version of P4Python 2008.2 for activepython 2.5:

  • download and extract both the p4python and p4api
  • fixup the setup.cfg for p4python to point to the p4api directory.

To open files for edit (do a checkout), on the command line, see 'p4 help open'.

You can check out files without making a changelist if you add the file to the default changelist, but it's a good idea to make a changelist first.

P4Python doesn't currently compile for activepython 2.6 without visual studio 2008; the provided libs are built with 2005 or 2003. Forcing p4python to build against mingw is nearly impossible, even with pexports of python26.dll and reimp/reassembly of the provided .lib files into .a files.

In that case, you'll probably rather use subprocess, and return p4 results as marshalled python objects. You can write your own command wrapper that takes an arg array, constructs and runs the commands, and returns the results dictionary.

You might try changing everything, testing, and on success, opening the files that are different with something equivalent to 'p4 diff -se //...'

Epu
A: 

I think second answer above has its limitation, the granularity does not fully wrapped in OO. e.g. hard coded global options of p4.