Come visualizzare i commit di un utente specifico nel registro svn?


161

Come visualizzare i commit di un utente specifico in svn? Non ho trovato alcun interruttore per quello per il registro svn.


10
Utilizzare l' --searchopzione con Subversion 1.8 o client più recente.
bahrep,

Risposte:


258

Puoi usare questo:

svn log | sed -n '/USERNAME/,/-----$/ p' 

Ti mostrerà ogni commit fatto dall'utente specificato (USERNAME).

AGGIORNARE

Come suggerito da @bahrep, sovversione 1.8 viene fornito con --searchun'opzione.


6
Questa soluzione è perfetta Vorrei capire cosa sta facendo, ma non sono stato in grado di trovare nulla nella documentazione di sed che lo spieghi. Qualcuno ha qualche informazione sul perché funziona?
Matt Hulse,

1
+1 Funziona anche per me. Come vi, su distribuzioni Unix / Linux sed è forse più onnipresente di Python - e quindi non è necessario preoccuparsi dell'installazione.
therobyouknow,

10
@MattHulse funziona perché usa sed per abbinare tutto tra due espressioni regolari specificate (il nome utente e i trattini), quindi gli dice di stamparlo (il p).
Gijs,

5
@therobyouknow No, non è necessario esibirsi svn logsu una copia funzionante. Puoi anche specificare il tuo repository, ad es svn log https://your-svn-repo.
MBober,

4
Non c'è più bisogno di farlo. Utilizzare Subversion 1.8 o client più recente che supporti l' --searchopzione.
bahrep,

101

Con Subversion 1.8 o successivo:

svn log --search johnsmith77 -l 50

Oltre alle corrispondenze dell'autore, questo mostrerà anche commit SVN che contengono quel nome utente nel messaggio di commit, cosa che non dovrebbe accadere se il tuo nome utente non è una parola comune.

Questo -l 50limiterà la ricerca alle ultime 50 voci.

--search ARG

Filtra i messaggi di registro per mostrare solo quelli che corrispondono al modello di ricerca ARG.

I messaggi di registro vengono visualizzati solo se il modello di ricerca fornito corrisponde a qualsiasi autore, data, testo del messaggio di registro (a meno che non --quietvenga utilizzato) o, se --verboseviene fornita anche l' opzione, un percorso modificato.

Se --searchvengono fornite più opzioni, viene visualizzato un messaggio di registro se corrisponde a uno dei modelli di ricerca forniti.

Se --limitutilizzato, limita il numero di messaggi di registro cercati, anziché limitare l'output a un determinato numero di messaggi di registro corrispondenti.

http://svnbook.red-bean.com/en/1.8/svn.ref.svn.html#svn.ref.svn.sw.search



se si desidera cercare più di un autore, svn log --search foo --search bar -l 30. If multiple --search options are provided, a log message is shown if it matches any of the provided search patterns.
zhuguowei,

Questa soluzione potrebbe essere usata anche con l'argomento --diff (per mostrare il codice modificato)
joro

Un modo per filtrare le apparenze nei messaggi di commit, se il nome utente è una parola comune (parte di)?
Tor Klingberg,

17

svn non include opzioni integrate per questo. Ha svn log --xmlun'opzione per permetterti di analizzare da solo l'output e ottenere le parti interessanti.

Puoi scrivere uno script per analizzarlo, ad esempio, in Python 2.6:

import sys
from xml.etree.ElementTree import iterparse, dump

author = sys.argv[1]
iparse = iterparse(sys.stdin, ['start', 'end'])

for event, elem in iparse:
    if event == 'start' and elem.tag == 'log':
        logNode = elem
        break

logentries = (elem for event, elem in iparse
                   if event == 'end' and elem.tag == 'logentry')

for logentry in logentries:
    if logentry.find('author').text == author:
        dump(logentry)
    logNode.remove(logentry)

Se si salva quanto sopra come svnLogStripByAuthor.py, è possibile chiamarlo come:

svn log --xml other-options | svnLogStripByAuthor.py user

Ecco perché ho aggiunto anche il tag 'bash'.
Mimrock,

Potresti scrivere uno script di utilità per analizzarlo - vedi il mio esempio
Avi

Non ho installato Python, ma mentre il mio problema è risolto in modo non correlato, suppongo che la tua soluzione funzioni, grazie!
Mimrock,

3
La magia è potente. Python è Bash.
n611x007,

13

Dal momento che tutti sembrano essere inclini a Linux (et al): ecco l'equivalente di Windows:

svn log [SVNPath]|find "USERNAME"

Grazie! Un client utilizza Windows, quindi è stato di grande aiuto. Questo è un sistema gestito, non ho i diritti di amministratore e non posso installare cygwin / perl / qualunque ...
n13

8
svn log | grep user

funziona per la maggior parte.

O per essere più accurati:

svn log | egrep 'r[0-9]+ \| user \|'

Grazie, ma non riesco a vedere i messaggi di commit in quel modo.
Mimrock,

@mimrock True. Si potrebbe grep -Aper visualizzare il contesto, ma questo numero è statico mentre il messaggio di commit è di lunghezza variabile. Potresti fare una soluzione con sed o simili, ma questo è uno sforzo. : P
Moinudin,

Funziona anche con Windows, se installi GIT Extensions ( code.google.com/p/gitextensions ) e avvii un prompt dei comandi di GIT Bash.
Contango,

1
@marcog Per la completa completezza, prendi quell'elenco di revisioni e fai un'altra chiamata solo con loro: | awk '{ print "-" $1 }' | xargs svn log
Izkata,

5

Mentre la soluzione di yvoyer funziona bene, qui c'è uno che fa uso dell'output XML di SVN, analizzandolo con xmlstarlet.

svn log --xml | xmlstarlet sel -t -m 'log/logentry' \
  --if "author = '<AUTHOR>'" \
  -v "concat('Revision ', @revision, ' ', date)" -n -v msg -n -n

Da qui è possibile accedere a query XML più avanzate.


3

Ecco la mia soluzione usando xslt. Sfortunatamente, xsltproc non è un processore di streaming, quindi devi dare un limite al registro. Esempio di utilizzo:

svn log -v --xml --limit=500  | xsltproc --stringparam author yonran /path/to/svnLogFilter.xslt  - | xsltproc /path/to/svnLogText.xslt  - | less

svnLogFilter.xslt

<!--
svnLogFilter.xslt

Usage: (note: use double dashes; I can't do double dashes in a XML comment)
svn log -xml | xsltproc -stringparam author yonran svnLogFilter.xslt -
-->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
  <xsl:param name="author" select="''"/>
  <xsl:strip-space elements="log"/>
  <xsl:variable name="uppercase" select="'ABCDEFGHIJKLMNOPQRSTUVWXYZ'"/>
  <xsl:variable name="lowercase" select="'abcdefghijklmnopqrstuvwxyz'"/>
  <xsl:variable name="lowercaseAuthor" select="translate($author, $uppercase, $lowercase)"/>

<xsl:template match="/log">
  <xsl:copy>
    <xsl:apply-templates name="entrymatcher"/>
  </xsl:copy>
</xsl:template>

<xsl:template name="entrymatcher" match="logentry">
  <xsl:variable name="lowercaseChangeAuthor" select="translate(author, $uppercase, $lowercase)"/>
  <xsl:choose>
    <xsl:when test="contains($lowercaseChangeAuthor, $lowercaseAuthor)">
      <xsl:call-template name="insideentry"/>
    </xsl:when>
    <!--Filter out-->
    <xsl:otherwise/>
  </xsl:choose>
</xsl:template>


<xsl:template name="insideentry" match="@*|node()">
  <xsl:copy>
    <xsl:apply-templates select="@*|node()"/>
  </xsl:copy>
</xsl:template>

</xsl:stylesheet>

svnLogText.xslt

<!--
svnLogText.xslt

Usage: (note: use double dashes; I can't do double dashes in a XML comment)
svn log -xml -limit=1000 | xsltproc svnLogText.xslt -
-->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
  <xsl:param name="author" select="''"/>
  <xsl:param name="xml" select="false()"/>
  <xsl:output method="text"/>

<xsl:template match="/log">
  <xsl:apply-templates name="entrymatcher"/>
  <xsl:text>------------------------------------------------------------------------&#xa;</xsl:text>
</xsl:template>

<xsl:template name="entrymatcher" match="logentry">
  <xsl:text>------------------------------------------------------------------------&#xa;</xsl:text>
  <xsl:text>r</xsl:text><xsl:value-of select="@revision"/>
  <xsl:text> | </xsl:text>
  <xsl:value-of select="author"/>
  <xsl:text> | </xsl:text>
  <xsl:value-of select="date"/>
  <xsl:text>&#xa;&#xa;</xsl:text>
  <xsl:if test="paths">
    <xsl:text>Changed paths:&#xa;</xsl:text>
    <xsl:for-each select="paths/path">
      <xsl:text>   </xsl:text>
      <xsl:value-of select="@action"/>
      <xsl:text> </xsl:text>
      <xsl:value-of select="."/>
      <xsl:text>&#xa;</xsl:text>
    </xsl:for-each>
  </xsl:if>
  <xsl:text>&#xa;</xsl:text>
  <xsl:value-of select="msg"/>
  <xsl:text>&#xa;</xsl:text>
</xsl:template>

</xsl:stylesheet>


1

È possibile utilizzare Perl per filtrare il registro in base al nome utente e mantenere i messaggi di commit. Basta impostare la variabile $ / che decide cosa costituisce una "linea" in Perl. Se si imposta questo come separatore delle voci del registro SVN, Perl leggerà un record alla volta e quindi si dovrebbe essere in grado di abbinare il nome utente nell'intero record. Vedi sotto:

svn log | perl -ne 'BEGIN{$/="------------------------------------------------------------------------"} print if /USERNAME/'

Questo funziona anche se vuoi trovare un sacco di risultati di log in base al nome di un file!
Walmik,

1

Per ottenere le differenze con il check-in.

Ottieni i numeri di revisione in un file:

svn log | sed -n '/USERNAME/,/-----$/ p'| grep "^r" 

Ora leggi il file ed esegui diff per ogni revisione:

while read p; do   svn log -v"$p" --diff ; done < Revisions.txt 

0

Avevo scritto una sceneggiatura di Python:

#!/usr/bin/python
# coding:utf-8

import sys

argv_len = len(sys.argv)


def help():
    print 'Filter svnlog by user or date!       '
    print 'USEAGE: svnlog [ARGs]                '
    print 'ARGs:                                '
    print '    -n[=name]:                       '
    print '      filter by the special [=name]\n'
    print '    -t[=date]:                       '
    print '      filter by the special [=date]  '
    print 'EXP:                                 '
    print '1. Filter ruikye\'s commit log       \n'
    print '     svn log -l 50 | svnlog -n=ruikye\n'


if not argv_len - 1:
    help()
    quit()

author = ''
date = ''

for index in range(1, argv_len):
    argv = sys.argv[index]
    if argv.startswith('-n='):
        author = argv.replace('-n=', '')
    elif argv.startswith('-t='):
        date = argv.replace('-t=', '')
    else:
        help()
        quit()

if author == '' and date == '':
    help()
    quit()


SPLIT_LINE =
    '------------------------------------------------------------------------'
src = ''.join(sys.stdin.readlines()).replace('\n\n', '\n')
lines = src.split(SPLIT_LINE)

for line in lines:
    if author in line and date in line:
        print SPLIT_LINE, line

if len(lines):
    print SPLIT_LINE

e usa:

$ mv svnlog.py svnlog          

$ chmod a+x svnlog             

$ cd /usr/local/bin
$ ln -s ~/mycmd/svnlog filter 

$ svn log | filter -n=ruikye -t=2015-03-04

La risposta esistente che utilizza XML e la analizza correttamente sarà più solida e flessibile.
Tripleee
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.