1 | #!/usr/bin/python3
|
---|
2 | # License: CC0
|
---|
3 |
|
---|
4 | """
|
---|
5 | Helper script to replace "@since xxx" in Javadoc by the upcoming revision
|
---|
6 | number.
|
---|
7 |
|
---|
8 | Will retrieve the current revision number from the server. It runs over all
|
---|
9 | modified and added .java files and replaces xxx in "since xxx" by the revision
|
---|
10 | number that is to be expected for the next commit.
|
---|
11 | """
|
---|
12 |
|
---|
13 | import xml.etree.ElementTree as ElementTree
|
---|
14 | import subprocess
|
---|
15 | import re
|
---|
16 | import sys
|
---|
17 |
|
---|
18 | revision = None
|
---|
19 |
|
---|
20 |
|
---|
21 | def main() -> None:
|
---|
22 | """
|
---|
23 | Do the main work of the script.
|
---|
24 | :return: Nothing
|
---|
25 | """
|
---|
26 | args = sys.argv
|
---|
27 | svn_status = subprocess.check_output("svn status --xml".split(" "))
|
---|
28 | tree = ElementTree.fromstring(svn_status)
|
---|
29 | rev = get_revision()
|
---|
30 | if len(args) == 2:
|
---|
31 | for change_set in tree.findall("./changelist"):
|
---|
32 | if (
|
---|
33 | "name" in change_set.attrib
|
---|
34 | and change_set.attrib["name"] == args[1]
|
---|
35 | ):
|
---|
36 | for el in change_set.findall("./entry"):
|
---|
37 | write_xxx(rev, el)
|
---|
38 | elif len(args) > 2:
|
---|
39 | raise ValueError(
|
---|
40 | "Too many args: only one changelist should be passed at a time, "
|
---|
41 | "or none at all "
|
---|
42 | )
|
---|
43 | else:
|
---|
44 | for el in tree.findall("./target/entry"):
|
---|
45 | write_xxx(rev, el)
|
---|
46 |
|
---|
47 |
|
---|
48 | def write_xxx(rev: int, el: ElementTree.Element) -> None:
|
---|
49 | """
|
---|
50 | Write a revision to a changed file
|
---|
51 | :param rev: The revision to write
|
---|
52 | :param el: The element containing the path to the file to update
|
---|
53 | :return: Nothing
|
---|
54 | """
|
---|
55 | if el.find("wc-status").get("item") not in ["added", "modified"]:
|
---|
56 | return
|
---|
57 | path = el.get("path")
|
---|
58 | if not path.endswith(".java"):
|
---|
59 | return
|
---|
60 | with open(path, "r") as f:
|
---|
61 | old_text = f.read()
|
---|
62 | new_text = re.sub("since xxx", lambda _: "since {}".format(rev), old_text)
|
---|
63 | if old_text != new_text:
|
---|
64 | print(
|
---|
65 | "replacing 'since xxx' with 'since {}' in '{}'".format(rev, path)
|
---|
66 | )
|
---|
67 | with open(path, "w") as f:
|
---|
68 | f.write(new_text)
|
---|
69 |
|
---|
70 |
|
---|
71 | def get_revision() -> int:
|
---|
72 | """
|
---|
73 | Get the next revision
|
---|
74 | :return: The current revision + 1
|
---|
75 | """
|
---|
76 | global revision
|
---|
77 | if revision is not None:
|
---|
78 | return revision
|
---|
79 | svn_info_local = subprocess.check_output("svn info --xml".split(" "))
|
---|
80 | rep_url = ElementTree.fromstring(svn_info_local).findtext(
|
---|
81 | "./entry/repository/root"
|
---|
82 | )
|
---|
83 | svn_info_server = subprocess.check_output(
|
---|
84 | "svn info --xml".split(" ") + [rep_url]
|
---|
85 | )
|
---|
86 | revision = (
|
---|
87 | int(
|
---|
88 | ElementTree.fromstring(svn_info_server)
|
---|
89 | .find("./entry")
|
---|
90 | .get("revision")
|
---|
91 | )
|
---|
92 | + 1
|
---|
93 | )
|
---|
94 | return revision
|
---|
95 |
|
---|
96 |
|
---|
97 | if __name__ == "__main__":
|
---|
98 | main()
|
---|