You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by ju...@apache.org on 2012/05/31 19:30:17 UTC

svn commit: r1344825 - in /subversion/trunk/tools/dev/mergegraph: mergegraph.py save_as_sh.py

Author: julianfoad
Date: Thu May 31 17:30:17 2012
New Revision: 1344825

URL: http://svn.apache.org/viewvc?rev=1344825&view=rev
Log:
Teach the 'mergegraph' tool to write a sequence of 'svn' commands that will
create the scenario described in the graph.

* tools/dev/mergegraph/mergegraph.py
  (MergeDot): If the format is 'sh', use 'save_as_sh.py' to write a '.sh'
    file.

* tools/dev/mergegraph/save_as_sh.py
  New file.

Added:
    subversion/trunk/tools/dev/mergegraph/save_as_sh.py   (with props)
Modified:
    subversion/trunk/tools/dev/mergegraph/mergegraph.py

Modified: subversion/trunk/tools/dev/mergegraph/mergegraph.py
URL: http://svn.apache.org/viewvc/subversion/trunk/tools/dev/mergegraph/mergegraph.py?rev=1344825&r1=1344824&r2=1344825&view=diff
==============================================================================
--- subversion/trunk/tools/dev/mergegraph/mergegraph.py (original)
+++ subversion/trunk/tools/dev/mergegraph/mergegraph.py Thu May 31 17:30:17 2012
@@ -301,4 +301,8 @@ class MergeDot(MergeGraph, pydot.Dot):
        according to the given format."""
     if not filename:
       filename = graph.basename + '.' + format
-    pydot.Dot.write(graph, filename, format=format)
+    if format == 'sh':
+      import save_as_sh
+      save_as_sh.write_sh_file(graph, filename)
+    else:
+      pydot.Dot.write(graph, filename, format=format)

Added: subversion/trunk/tools/dev/mergegraph/save_as_sh.py
URL: http://svn.apache.org/viewvc/subversion/trunk/tools/dev/mergegraph/save_as_sh.py?rev=1344825&view=auto
==============================================================================
--- subversion/trunk/tools/dev/mergegraph/save_as_sh.py (added)
+++ subversion/trunk/tools/dev/mergegraph/save_as_sh.py Thu May 31 17:30:17 2012
@@ -0,0 +1,128 @@
+#!/usr/bin/env python
+
+# ====================================================================
+#    Licensed to the Apache Software Foundation (ASF) under one
+#    or more contributor license agreements.  See the NOTICE file
+#    distributed with this work for additional information
+#    regarding copyright ownership.  The ASF licenses this file
+#    to you under the Apache License, Version 2.0 (the
+#    "License"); you may not use this file except in compliance
+#    with the License.  You may obtain a copy of the License at
+#
+#      http://www.apache.org/licenses/LICENSE-2.0
+#
+#    Unless required by applicable law or agreed to in writing,
+#    software distributed under the License is distributed on an
+#    "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+#    KIND, either express or implied.  See the License for the
+#    specific language governing permissions and limitations
+#    under the License.
+# ====================================================================
+
+
+# This module writes a sequence of 'svn' commands to a file, that when
+# run will perform the branching and merging described by a given MergeDot
+# graph description object.
+
+
+def shebang_line(out):
+  print >> out, '#!/bin/sh'
+
+def command(out, cmd, *args):
+  """Write the shell command CMD with the arguments ARGS to the file-like
+     object OUT."""
+  print >> out, ' '.join((cmd,) + args)
+
+def svn(out, subcmd, *args):
+  """Write an svn command with the given subcommand and arguments.  Write
+     to the file-like object OUT."""
+  command(out, 'svn', subcmd, *args)
+
+def comment(out, text):
+  """Write the comment TEXT to the file-like object OUT."""
+  print >> out, '#', text
+
+def write_recipe(graph, out):
+  """Write out a sequence of svn commands that will execute the branching
+     and merging shown in GRAPH.  Write to the file-like object OUT."""
+  revs = {}  # keyed by revnum
+
+  def node_branch(node_name):
+    """Extract branch name from a node name.
+       ### TODO: multi-char names."""
+    return node_name[:1]
+
+  def node_url(node_name):
+    """Extract the URL (in command-line repo-relative URL syntax) from a
+       node name."""
+    return '^/' + node_branch(node_name)
+
+  def node_rev(node_name):
+    """Extract revnum (as an integer) from a node name.
+       ### TODO: multi-char names."""
+    return int(node_name[1:]) + 1
+
+  def add(node_name, action, *args):
+    """Add the tuple (ACTION, (ARGS)) to the list REVS[REVNUM]."""
+    revnum = node_rev(node_name)
+    if not revnum in revs:
+      revs[revnum] = []
+    revs[revnum].append((action, args))
+
+  for br, orig, r1, head in graph.branches:
+    if orig:
+      add(br + str(r1), 'copy', orig, br)
+    else:
+      add(br + str(r1), 'mkproj', br)
+
+  for base_node, src_node, tgt_node, kind in graph.merges:
+    add(tgt_node, 'merge', src_node, tgt_node, kind)
+
+  for node_name in graph.changes:
+    # Originally the 'changes' list could have entries that overlapped with
+    # merges. We must either disallow that or filter out such changes here.
+    #if not node_name in revs:
+    add(node_name, 'modify', node_name)
+
+  # Execute the actions for each revision in turn.
+  for r in sorted(revs.keys()):
+    comment(out, 'start r' + str(r))
+    for action, params in revs[r]:
+      #comment(out, '(' + action + ' ' + params + ')')
+      if action == 'mkproj':
+        (br,) = params
+        svn(out, 'mkdir', br, br + '/created_in_' + br)
+      elif action == 'copy':
+        (orig, br) = params
+        svn(out, 'copy', '-r' + str(node_rev(orig)), node_branch(orig), br)
+      elif action == 'modify':
+        (node_name,) = params
+        svn(out, 'mkdir', node_branch(node_name) + '/new_in_' + node_name)
+      elif action == 'merge':
+        (src_node, tgt_node, kind) = params
+        assert node_rev(tgt_node) == r
+        svn(out, 'update')
+        if kind == 'cherry':
+          svn(out, 'merge',
+              '-c' + str(node_rev(src_node)), node_url(src_node),
+              node_branch(tgt_node))
+        elif kind.startswith('reint'):
+          svn(out, 'merge', '--reintegrate',
+              node_url(src_node) + '@' + str(node_rev(src_node)),
+              node_branch(tgt_node))
+        else:
+          svn(out, 'merge',
+              node_url(src_node) + '@' + str(node_rev(src_node)),
+              node_branch(tgt_node))
+      else:
+        raise 'unknown action: %s' % action
+    svn(out, 'commit', '-m', 'r' + str(r))
+
+def write_sh_file(graph, filename):
+  """Write a file containing a sequence of 'svn' commands that when run will
+     perform the branching and merging described by the MergeDot object
+     GRAPH.  Write to a new file named FILENAME."""
+  out_stream = open(filename, 'w')
+  shebang_line(out_stream)
+  write_recipe(graph, out_stream)
+  out_stream.close()

Propchange: subversion/trunk/tools/dev/mergegraph/save_as_sh.py
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: subversion/trunk/tools/dev/mergegraph/save_as_sh.py
------------------------------------------------------------------------------
    svn:mime-type = text/x-python



Re: svn commit: r1344825 - in /subversion/trunk/tools/dev/mergegraph: mergegraph.py save_as_sh.py

Posted by Greg Stein <gs...@gmail.com>.
On May 31, 2012 4:45 PM, "Julian Foad" <ju...@btopenworld.com> wrote:
>
> I (Julian Foad) wrote:
>
> > Greg Stein wrote:
> >>>  +def command(out, cmd, *args):
> >>>  +  """Write the shell command CMD with the arguments ARGS to the
file-like
> >>>  +     object OUT."""
> >> Please review my earlier comments about standard docstring formatting
in
> >> Python. More specifically, PEP 8. (Google it)
> >
> > OK, r1344888 for 'most
> > importantly, the """ that ends a multiline docstring should be
> > on a line by itself [...]'.  Anything further will have to wait till
another
> > day.
>
> Let me add a few more words here.  I support efforts to both standardize
and raise the usefulness of doc strings.  I just haven't yet spent the time
to read PEP 257 (being the relevant one) in full, digest it into my
Python-commenting brain-space, decide what subset of its suggestions are
appropriate for us to use in scripts like these, and go back and change
them.

Not a problem. As long as we move towards the PEP styles in time. I
consider using the standardized docstrings as being similar to the doxygen
rules (and what we've established for internal docstrings).

Thx,
-g

Re: svn commit: r1344825 - in /subversion/trunk/tools/dev/mergegraph: mergegraph.py save_as_sh.py

Posted by Julian Foad <ju...@btopenworld.com>.
I (Julian Foad) wrote:

> Greg Stein wrote:
>>>  +def command(out, cmd, *args):
>>>  +  """Write the shell command CMD with the arguments ARGS to the file-like
>>>  +     object OUT."""
>> Please review my earlier comments about standard docstring formatting in 
>> Python. More specifically, PEP 8. (Google it)
> 
> OK, r1344888 for 'most
> importantly, the """ that ends a multiline docstring should be
> on a line by itself [...]'.  Anything further will have to wait till another 
> day.

Let me add a few more words here.  I support efforts to both standardize and raise the usefulness of doc strings.  I just haven't yet spent the time to read PEP 257 (being the relevant one) in full, digest it into my Python-commenting brain-space, decide what subset of its suggestions are appropriate for us to use in scripts like these, and go back and change them.

- Julian

Re: svn commit: r1344825 - in /subversion/trunk/tools/dev/mergegraph: mergegraph.py save_as_sh.py

Posted by Julian Foad <ju...@btopenworld.com>.
Greg Stein wrote:

>On May 31, 2012 1:30 PM, <ju...@apache.org> wrote:
>>...
>> +++ subversion/trunk/tools/dev/mergegraph/save_as_sh.py Thu May 31 17:30:17 2012
>>...
>> +def command(out, cmd, *args):
>> +  """Write the shell command CMD with the arguments ARGS to the file-like
>> +     object OUT."""
>Please review my earlier comments about standard docstring formatting in Python. More specifically, PEP 8. (Google it)


OK, r1344888 for 'most
importantly, the """ that ends a multiline docstring should be
on a line by itself [...]'.  Anything further will have to wait till another day.


>> +def write_recipe(graph, out):
>> +  """Write out a sequence of svn commands that will execute the branching
>> +     and merging shown in GRAPH.  Write to the file-like object OUT."""
>> +  revs = {}  # keyed by revnum
>> +
>> +  def node_branch(node_name):
>> +    """Extract branch name from a node name.
>> +       ### TODO: multi-char names."""
>> +    return node_name[:1]
>> +
>> +  def node_url(node_name):
>> +    """Extract the URL (in command-line repo-relative URL syntax) from a
>> +       node name."""
>> +    return '^/' + node_branch(node_name)
>> +
>> +  def node_rev(node_name):
>> +    """Extract revnum (as an integer) from a node name.
>> +       ### TODO: multi-char names."""
>> +    return int(node_name[1:]) + 1
>> +
>> +  def add(node_name, action, *args):
>> +    """Add the tuple (ACTION, (ARGS)) to the list REVS[REVNUM]."""
>> +    revnum = node_rev(node_name)
>> +    if not revnum in revs:
>> +      revs[revnum] = []
>> +    revs[revnum].append((action, args))
> There is no need to embed these functions. It makes write_recipe() less clear to have this clutter in here.


OK.  1344885.


>> +        raise 'unknown action: %s' % action
> This form of exception is deprecated. Please raise an instance of Exception (or of a subclass).


Agreed.  1344885.


- Julian


Re: svn commit: r1344825 - in /subversion/trunk/tools/dev/mergegraph: mergegraph.py save_as_sh.py

Posted by Greg Stein <gs...@gmail.com>.
On May 31, 2012 1:30 PM, <ju...@apache.org> wrote:
>...
> +++ subversion/trunk/tools/dev/mergegraph/save_as_sh.py Thu May 31
17:30:17 2012
>...
> +def command(out, cmd, *args):
> +  """Write the shell command CMD with the arguments ARGS to the file-like
> +     object OUT."""

Please review my earlier comments about standard docstring formatting in
Python. More specifically, PEP 8. (Google it)

>...
> +def write_recipe(graph, out):
> +  """Write out a sequence of svn commands that will execute the branching
> +     and merging shown in GRAPH.  Write to the file-like object OUT."""
> +  revs = {}  # keyed by revnum
> +
> +  def node_branch(node_name):
> +    """Extract branch name from a node name.
> +       ### TODO: multi-char names."""
> +    return node_name[:1]
> +
> +  def node_url(node_name):
> +    """Extract the URL (in command-line repo-relative URL syntax) from a
> +       node name."""
> +    return '^/' + node_branch(node_name)
> +
> +  def node_rev(node_name):
> +    """Extract revnum (as an integer) from a node name.
> +       ### TODO: multi-char names."""
> +    return int(node_name[1:]) + 1
> +
> +  def add(node_name, action, *args):
> +    """Add the tuple (ACTION, (ARGS)) to the list REVS[REVNUM]."""
> +    revnum = node_rev(node_name)
> +    if not revnum in revs:
> +      revs[revnum] = []
> +    revs[revnum].append((action, args))

There is no need to embed these functions. It makes write_recipe() less
clear to have this clutter in here.

>...
> +        raise 'unknown action: %s' % action

This form of exception is deprecated. Please raise an instance of Exception
(or of a subclass).

>...

Cheers,
-g