annotate hgext/fix.py @ 45073:54009f8c3e25

fix: obtain base paths before starting workers This moves calculation of base paths to before work is dispatched. While this does mean that copy tracing will be serialized instead of parallel, it is necessary to be able to prefetch the base contents in a batch, which will likely be more efficient. Differential Revision: https://phab.mercurial-scm.org/D8722
author Rodrigo Damazio Bovendorp <rdamazio@google.com>
date Thu, 09 Jul 2020 20:45:35 -0700
parents b7808443ed6a
children 797ef6f8295e
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
1 # fix - rewrite file content in changesets and working copy
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
2 #
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
3 # Copyright 2018 Google LLC.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
4 #
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
5 # This software may be used and distributed according to the terms of the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
6 # GNU General Public License version 2 or any later version.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
7 """rewrite file content in changesets or working copy (EXPERIMENTAL)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
8
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
9 Provides a command that runs configured tools on the contents of modified files,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
10 writing back any fixes to the working copy or replacing changesets.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
11
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
12 Here is an example configuration that causes :hg:`fix` to apply automatic
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
13 formatting fixes to modified lines in C++ code::
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
14
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
15 [fix]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
16 clang-format:command=clang-format --assume-filename={rootpath}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
17 clang-format:linerange=--lines={first}:{last}
40533
2ecf5c24d0cd fix: rename :fileset subconfig to :pattern
Danny Hooper <hooper@google.com>
parents: 40532
diff changeset
18 clang-format:pattern=set:**.cpp or **.hpp
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
19
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
20 The :command suboption forms the first part of the shell command that will be
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
21 used to fix a file. The content of the file is passed on standard input, and the
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
22 fixed file content is expected on standard output. Any output on standard error
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
23 will be displayed as a warning. If the exit status is not zero, the file will
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
24 not be affected. A placeholder warning is displayed if there is a non-zero exit
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
25 status but no standard error output. Some values may be substituted into the
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
26 command::
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
27
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
28 {rootpath} The path of the file being fixed, relative to the repo root
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
29 {basename} The name of the file being fixed, without the directory path
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
30
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
31 If the :linerange suboption is set, the tool will only be run if there are
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
32 changed lines in a file. The value of this suboption is appended to the shell
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
33 command once for every range of changed lines in the file. Some values may be
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
34 substituted into the command::
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
35
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
36 {first} The 1-based line number of the first line in the modified range
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
37 {last} The 1-based line number of the last line in the modified range
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
38
42756
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
39 Deleted sections of a file will be ignored by :linerange, because there is no
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
40 corresponding line range in the version being fixed.
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
41
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
42 By default, tools that set :linerange will only be executed if there is at least
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
43 one changed line range. This is meant to prevent accidents like running a code
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
44 formatter in such a way that it unexpectedly reformats the whole file. If such a
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
45 tool needs to operate on unchanged files, it should set the :skipclean suboption
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
46 to false.
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
47
40533
2ecf5c24d0cd fix: rename :fileset subconfig to :pattern
Danny Hooper <hooper@google.com>
parents: 40532
diff changeset
48 The :pattern suboption determines which files will be passed through each
43227
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
49 configured tool. See :hg:`help patterns` for possible values. However, all
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
50 patterns are relative to the repo root, even if that text says they are relative
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
51 to the current working directory. If there are file arguments to :hg:`fix`, the
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
52 intersection of these patterns is used.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
53
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
54 There is also a configurable limit for the maximum size of file that will be
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
55 processed by :hg:`fix`::
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
56
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
57 [fix]
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
58 maxfilesize = 2MB
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
59
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
60 Normally, execution of configured tools will continue after a failure (indicated
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
61 by a non-zero exit status). It can also be configured to abort after the first
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
62 such failure, so that no files will be affected if any tool fails. This abort
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
63 will also cause :hg:`fix` to exit with a non-zero status::
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
64
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
65 [fix]
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
66 failure = abort
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
67
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
68 When multiple tools are configured to affect a file, they execute in an order
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
69 defined by the :priority suboption. The priority suboption has a default value
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
70 of zero for each tool. Tools are executed in order of descending priority. The
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
71 execution order of tools with equal priority is unspecified. For example, you
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
72 could use the 'sort' and 'head' utilities to keep only the 10 smallest numbers
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
73 in a text file by ensuring that 'sort' runs before 'head'::
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
74
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
75 [fix]
41126
d8f5c615e811 tests: use more portable flags in test-fix.t
Danny Hooper <hooper@google.com>
parents: 40570
diff changeset
76 sort:command = sort -n
d8f5c615e811 tests: use more portable flags in test-fix.t
Danny Hooper <hooper@google.com>
parents: 40570
diff changeset
77 head:command = head -n 10
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
78 sort:pattern = numbers.txt
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
79 head:pattern = numbers.txt
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
80 sort:priority = 2
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
81 head:priority = 1
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
82
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
83 To account for changes made by each tool, the line numbers used for incremental
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
84 formatting are recomputed before executing the next tool. So, each tool may see
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
85 different values for the arguments added by the :linerange suboption.
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
86
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
87 Each fixer tool is allowed to return some metadata in addition to the fixed file
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
88 content. The metadata must be placed before the file content on stdout,
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
89 separated from the file content by a zero byte. The metadata is parsed as a JSON
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
90 value (so, it should be UTF-8 encoded and contain no zero bytes). A fixer tool
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
91 is expected to produce this metadata encoding if and only if the :metadata
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
92 suboption is true::
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
93
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
94 [fix]
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
95 tool:command = tool --prepend-json-metadata
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
96 tool:metadata = true
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
97
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
98 The metadata values are passed to hooks, which can be used to print summaries or
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
99 perform other post-fixing work. The supported hooks are::
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
100
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
101 "postfixfile"
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
102 Run once for each file in each revision where any fixer tools made changes
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
103 to the file content. Provides "$HG_REV" and "$HG_PATH" to identify the file,
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
104 and "$HG_METADATA" with a map of fixer names to metadata values from fixer
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
105 tools that affected the file. Fixer tools that didn't affect the file have a
44048
61881b170140 fix: fix grammar/typos in hg help -e fix
timeless <timeless@mozdev.org>
parents: 43380
diff changeset
106 value of None. Only fixer tools that executed are present in the metadata.
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
107
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
108 "postfix"
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
109 Run once after all files and revisions have been handled. Provides
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
110 "$HG_REPLACEMENTS" with information about what revisions were created and
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
111 made obsolete. Provides a boolean "$HG_WDIRWRITTEN" to indicate whether any
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
112 files in the working copy were updated. Provides a list "$HG_METADATA"
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
113 mapping fixer tool names to lists of metadata values returned from
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
114 executions that modified a file. This aggregates the same metadata
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
115 previously passed to the "postfixfile" hook.
42673
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
116
44048
61881b170140 fix: fix grammar/typos in hg help -e fix
timeless <timeless@mozdev.org>
parents: 43380
diff changeset
117 Fixer tools are run in the repository's root directory. This allows them to read
42673
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
118 configuration files from the working copy, or even write to the working copy.
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
119 The working copy is not updated to match the revision being fixed. In fact,
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
120 several revisions may be fixed in parallel. Writes to the working copy are not
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
121 amended into the revision being fixed; fixer tools should always write fixed
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
122 file content back to stdout as documented above.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
123 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
124
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
125 from __future__ import absolute_import
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
126
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
127 import collections
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
128 import itertools
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
129 import os
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
130 import re
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
131 import subprocess
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
132
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
133 from mercurial.i18n import _
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
134 from mercurial.node import nullrev
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
135 from mercurial.node import wdirrev
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
136
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
137 from mercurial.utils import procutil
39826
c31ce080eb75 py3: convert arguments, cwd and env to native strings when spawning subprocess
Matt Harbison <matt_harbison@yahoo.com>
parents: 38967
diff changeset
138
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
139 from mercurial import (
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
140 cmdutil,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
141 context,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
142 copies,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
143 error,
43227
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
144 match as matchmod,
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
145 mdiff,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
146 merge,
44856
b7808443ed6a mergestate: split out merge state handling code from main merge module
Augie Fackler <augie@google.com>
parents: 44575
diff changeset
147 mergestate as mergestatemod,
37618
1edf3738e000 fix: port most of the way to python 3
Augie Fackler <augie@google.com>
parents: 37595
diff changeset
148 pycompat,
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
149 registrar,
43936
699d6be3820a fix: use rewriteutil.precheck() instead of reimplementing it
Martin von Zweigbergk <martinvonz@google.com>
parents: 43897
diff changeset
150 rewriteutil,
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
151 scmutil,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
152 util,
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
153 worker,
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
154 )
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
155
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
156 # Note for extension authors: ONLY specify testedwith = 'ships-with-hg-core' for
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
157 # extensions which SHIP WITH MERCURIAL. Non-mainline extensions should
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
158 # be specifying the version(s) of Mercurial they are tested with, or
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
159 # leave the attribute unspecified.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
160 testedwith = b'ships-with-hg-core'
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
161
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
162 cmdtable = {}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
163 command = registrar.command(cmdtable)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
164
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
165 configtable = {}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
166 configitem = registrar.configitem(configtable)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
167
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
168 # Register the suboptions allowed for each configured fixer, and default values.
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
169 FIXER_ATTRS = {
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
170 b'command': None,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
171 b'linerange': None,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
172 b'pattern': None,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
173 b'priority': 0,
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
174 b'metadata': False,
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
175 b'skipclean': True,
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
176 b'enabled': True,
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
177 }
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
178
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
179 for key, default in FIXER_ATTRS.items():
43217
5cb3e6f4e069 fix: fix registration of config item defaults
Martin von Zweigbergk <martinvonz@google.com>
parents: 43193
diff changeset
180 configitem(b'fix', b'.*:%s$' % key, default=default, generic=True)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
181
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
182 # A good default size allows most source code files to be fixed, but avoids
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
183 # letting fixer tools choke on huge inputs, which could be surprising to the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
184 # user.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
185 configitem(b'fix', b'maxfilesize', default=b'2MB')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
186
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
187 # Allow fix commands to exit non-zero if an executed fixer tool exits non-zero.
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
188 # This helps users do shell scripts that stop when a fixer tool signals a
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
189 # problem.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
190 configitem(b'fix', b'failure', default=b'continue')
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
191
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
192
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
193 def checktoolfailureaction(ui, message, hint=None):
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
194 """Abort with 'message' if fix.failure=abort"""
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
195 action = ui.config(b'fix', b'failure')
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
196 if action not in (b'continue', b'abort'):
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
197 raise error.Abort(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
198 _(b'unknown fix.failure action: %s') % (action,),
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
199 hint=_(b'use "continue" or "abort"'),
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
200 )
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
201 if action == b'abort':
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
202 raise error.Abort(message, hint=hint)
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
203
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
204
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
205 allopt = (b'', b'all', False, _(b'fix all non-public non-obsolete revisions'))
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
206 baseopt = (
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
207 b'',
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
208 b'base',
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
209 [],
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
210 _(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
211 b'revisions to diff against (overrides automatic '
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
212 b'selection, and applies to every revision being '
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
213 b'fixed)'
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
214 ),
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
215 _(b'REV'),
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
216 )
44575
a6ef1e8e2f6d fix: mark -r as advanced
Martin von Zweigbergk <martinvonz@google.com>
parents: 44574
diff changeset
217 revopt = (b'r', b'rev', [], _(b'revisions to fix (ADVANCED)'), _(b'REV'))
44574
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
218 sourceopt = (
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
219 b's',
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
220 b'source',
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
221 [],
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
222 _(b'fix the specified revisions and their descendants'),
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
223 _(b'REV'),
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
224 )
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
225 wdiropt = (b'w', b'working-dir', False, _(b'fix the working directory'))
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
226 wholeopt = (b'', b'whole', False, _(b'always fix every line of a file'))
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
227 usage = _(b'[OPTION]... [FILE]...')
38949
b0c591950e51 fix: pull out flag definitions to make them re-usable from extensions
Danny Hooper <hooper@google.com>
parents: 38860
diff changeset
228
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
229
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
230 @command(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
231 b'fix',
44574
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
232 [allopt, baseopt, revopt, sourceopt, wdiropt, wholeopt],
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
233 usage,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
234 helpcategory=command.CATEGORY_FILE_CONTENTS,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
235 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
236 def fix(ui, repo, *pats, **opts):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
237 """rewrite file content in changesets or working directory
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
238
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
239 Runs any configured tools to fix the content of files. Only affects files
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
240 with changes, unless file arguments are provided. Only affects changed lines
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
241 of files, unless the --whole flag is used. Some tools may always affect the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
242 whole file regardless of --whole.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
243
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
244 If revisions are specified with --rev, those revisions will be checked, and
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
245 they may be replaced with new revisions that have fixed file content. It is
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
246 desirable to specify all descendants of each specified revision, so that the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
247 fixes propagate to the descendants. If all descendants are fixed at the same
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
248 time, no merging, rebasing, or evolution will be required.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
249
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
250 If --working-dir is used, files with uncommitted changes in the working copy
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
251 will be fixed. If the checked-out revision is also fixed, the working
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
252 directory will update to the replacement revision.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
253
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
254 When determining what lines of each file to fix at each revision, the whole
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
255 set of revisions being fixed is considered, so that fixes to earlier
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
256 revisions are not forgotten in later ones. The --base flag can be used to
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
257 override this default behavior, though it is not usually desirable to do so.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
258 """
37618
1edf3738e000 fix: port most of the way to python 3
Augie Fackler <augie@google.com>
parents: 37595
diff changeset
259 opts = pycompat.byteskwargs(opts)
44574
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
260 cmdutil.check_at_most_one_arg(opts, b'all', b'source', b'rev')
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
261 cmdutil.check_incompatible_arguments(
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
262 opts, b'working_dir', [b'all', b'source']
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
263 )
44573
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
264
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
265 with repo.wlock(), repo.lock(), repo.transaction(b'fix'):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
266 revstofix = getrevstofix(ui, repo, opts)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
267 basectxs = getbasectxs(repo, opts, revstofix)
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
268 workqueue, numitems = getworkqueue(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
269 ui, repo, pats, opts, revstofix, basectxs
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
270 )
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
271 basepaths = getbasepaths(repo, opts, workqueue, basectxs)
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
272 fixers = getfixers(ui)
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
273
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
274 # There are no data dependencies between the workers fixing each file
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
275 # revision, so we can use all available parallelism.
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
276 def getfixes(items):
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
277 for rev, path in items:
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
278 ctx = repo[rev]
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
279 olddata = ctx[path].data()
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
280 metadata, newdata = fixfile(
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
281 ui, repo, opts, fixers, ctx, path, basepaths, basectxs[rev]
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
282 )
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
283 # Don't waste memory/time passing unchanged content back, but
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
284 # produce one result per item either way.
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
285 yield (
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
286 rev,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
287 path,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
288 metadata,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
289 newdata if newdata != olddata else None,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
290 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
291
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
292 results = worker.worker(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
293 ui, 1.0, getfixes, tuple(), workqueue, threadsafe=False
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
294 )
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
295
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
296 # We have to hold on to the data for each successor revision in memory
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
297 # until all its parents are committed. We ensure this by committing and
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
298 # freeing memory for the revisions in some topological order. This
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
299 # leaves a little bit of memory efficiency on the table, but also makes
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
300 # the tests deterministic. It might also be considered a feature since
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
301 # it makes the results more easily reproducible.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
302 filedata = collections.defaultdict(dict)
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
303 aggregatemetadata = collections.defaultdict(list)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
304 replacements = {}
38950
35bc4b6e132d fix: correctly set wdirwritten given that the dict item is deleted
Danny Hooper <hooper@google.com>
parents: 38949
diff changeset
305 wdirwritten = False
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
306 commitorder = sorted(revstofix, reverse=True)
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
307 with ui.makeprogress(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
308 topic=_(b'fixing'), unit=_(b'files'), total=sum(numitems.values())
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
309 ) as progress:
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
310 for rev, path, filerevmetadata, newdata in results:
38537
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
311 progress.increment(item=path)
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
312 for fixername, fixermetadata in filerevmetadata.items():
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
313 aggregatemetadata[fixername].append(fixermetadata)
38537
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
314 if newdata is not None:
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
315 filedata[rev][path] = newdata
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
316 hookargs = {
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
317 b'rev': rev,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
318 b'path': path,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
319 b'metadata': filerevmetadata,
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
320 }
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
321 repo.hook(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
322 b'postfixfile',
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
323 throw=False,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
324 **pycompat.strkwargs(hookargs)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
325 )
38537
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
326 numitems[rev] -= 1
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
327 # Apply the fixes for this and any other revisions that are
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
328 # ready and sitting at the front of the queue. Using a loop here
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
329 # prevents the queue from being blocked by the first revision to
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
330 # be ready out of order.
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
331 while commitorder and not numitems[commitorder[-1]]:
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
332 rev = commitorder.pop()
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
333 ctx = repo[rev]
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
334 if rev == wdirrev:
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
335 writeworkingdir(repo, ctx, filedata[rev], replacements)
38950
35bc4b6e132d fix: correctly set wdirwritten given that the dict item is deleted
Danny Hooper <hooper@google.com>
parents: 38949
diff changeset
336 wdirwritten = bool(filedata[rev])
38537
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
337 else:
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
338 replacerev(ui, repo, ctx, filedata[rev], replacements)
a3be09e277e9 fix: add progress bar for number of file revisions processed
Danny Hooper <hooper@google.com>
parents: 38536
diff changeset
339 del filedata[rev]
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
340
38950
35bc4b6e132d fix: correctly set wdirwritten given that the dict item is deleted
Danny Hooper <hooper@google.com>
parents: 38949
diff changeset
341 cleanup(repo, replacements, wdirwritten)
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
342 hookargs = {
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
343 b'replacements': replacements,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
344 b'wdirwritten': wdirwritten,
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
345 b'metadata': aggregatemetadata,
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
346 }
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
347 repo.hook(b'postfix', throw=True, **pycompat.strkwargs(hookargs))
38811
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
348
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
349
38811
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
350 def cleanup(repo, replacements, wdirwritten):
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
351 """Calls scmutil.cleanupnodes() with the given replacements.
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
352
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
353 "replacements" is a dict from nodeid to nodeid, with one key and one value
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
354 for every revision that was affected by fixing. This is slightly different
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
355 from cleanupnodes().
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
356
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
357 "wdirwritten" is a bool which tells whether the working copy was affected by
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
358 fixing, since it has no entry in "replacements".
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
359
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
360 Useful as a hook point for extending "hg fix" with output summarizing the
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
361 effects of the command, though we choose not to output anything here.
64535d43c103 fix: add a monkey-patchable point after all new revisions have been committed
Danny Hooper <hooper@google.com>
parents: 38770
diff changeset
362 """
43105
649d3ac37a12 py3: define and use pycompat.iteritems() for hgext/
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43087
diff changeset
363 replacements = {
649d3ac37a12 py3: define and use pycompat.iteritems() for hgext/
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43087
diff changeset
364 prec: [succ] for prec, succ in pycompat.iteritems(replacements)
649d3ac37a12 py3: define and use pycompat.iteritems() for hgext/
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43087
diff changeset
365 }
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
366 scmutil.cleanupnodes(repo, replacements, b'fix', fixphase=True)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
367
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
368
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
369 def getworkqueue(ui, repo, pats, opts, revstofix, basectxs):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
370 """"Constructs the list of files to be fixed at specific revisions
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
371
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
372 It is up to the caller how to consume the work items, and the only
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
373 dependence between them is that replacement revisions must be committed in
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
374 topological order. Each work item represents a file in the working copy or
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
375 in some revision that should be fixed and written back to the working copy
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
376 or into a replacement revision.
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
377
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
378 Work items for the same revision are grouped together, so that a worker
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
379 pool starting with the first N items in parallel is likely to finish the
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
380 first revision's work before other revisions. This can allow us to write
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
381 the result to disk and reduce memory footprint. At time of writing, the
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
382 partition strategy in worker.py seems favorable to this. We also sort the
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
383 items by ascending revision number to match the order in which we commit
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
384 the fixes later.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
385 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
386 workqueue = []
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
387 numitems = collections.defaultdict(int)
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
388 maxfilesize = ui.configbytes(b'fix', b'maxfilesize')
38536
5ffe2041d427 fix: use a worker pool to parallelize running tools
Danny Hooper <hooper@google.com>
parents: 38423
diff changeset
389 for rev in sorted(revstofix):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
390 fixctx = repo[rev]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
391 match = scmutil.match(fixctx, pats, opts)
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
392 for path in sorted(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
393 pathstofix(ui, repo, pats, opts, match, basectxs[rev], fixctx)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
394 ):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
395 fctx = fixctx[path]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
396 if fctx.islink():
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
397 continue
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
398 if fctx.size() > maxfilesize:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
399 ui.warn(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
400 _(b'ignoring file larger than %s: %s\n')
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
401 % (util.bytecount(maxfilesize), path)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
402 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
403 continue
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
404 workqueue.append((rev, path))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
405 numitems[rev] += 1
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
406 return workqueue, numitems
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
407
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
408
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
409 def getrevstofix(ui, repo, opts):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
410 """Returns the set of revision numbers that should be fixed"""
44573
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
411 if opts[b'all']:
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
412 revs = repo.revs(b'(not public() and not obsolete()) or wdir()')
44574
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
413 elif opts[b'source']:
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
414 source_revs = scmutil.revrange(repo, opts[b'source'])
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
415 revs = set(repo.revs(b'%ld::', source_revs))
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
416 if wdirrev in source_revs:
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
417 # `wdir()::` is currently empty, so manually add wdir
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
418 revs.add(wdirrev)
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
419 if repo[b'.'].rev() in revs:
5205b46bd887 fix: add a -s option to format a revision and its descendants
Martin von Zweigbergk <martinvonz@google.com>
parents: 44573
diff changeset
420 revs.add(wdirrev)
44573
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
421 else:
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
422 revs = set(scmutil.revrange(repo, opts[b'rev']))
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
423 if opts.get(b'working_dir'):
9f5e94bbc606 fix: move handling of --all into getrevstofix() for consistency
Martin von Zweigbergk <martinvonz@google.com>
parents: 44561
diff changeset
424 revs.add(wdirrev)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
425 for rev in revs:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
426 checkfixablectx(ui, repo, repo[rev])
44561
368f85c5dfc0 fix: refactor getrevstofix() to define revisions first, then validate them
Martin von Zweigbergk <martinvonz@google.com>
parents: 44560
diff changeset
427 # Allow fixing only wdir() even if there's an unfinished operation
368f85c5dfc0 fix: refactor getrevstofix() to define revisions first, then validate them
Martin von Zweigbergk <martinvonz@google.com>
parents: 44560
diff changeset
428 if not (len(revs) == 1 and wdirrev in revs):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
429 cmdutil.checkunfinished(repo)
43936
699d6be3820a fix: use rewriteutil.precheck() instead of reimplementing it
Martin von Zweigbergk <martinvonz@google.com>
parents: 43897
diff changeset
430 rewriteutil.precheck(repo, revs, b'fix')
44856
b7808443ed6a mergestate: split out merge state handling code from main merge module
Augie Fackler <augie@google.com>
parents: 44575
diff changeset
431 if wdirrev in revs and list(
b7808443ed6a mergestate: split out merge state handling code from main merge module
Augie Fackler <augie@google.com>
parents: 44575
diff changeset
432 mergestatemod.mergestate.read(repo).unresolved()
b7808443ed6a mergestate: split out merge state handling code from main merge module
Augie Fackler <augie@google.com>
parents: 44575
diff changeset
433 ):
44561
368f85c5dfc0 fix: refactor getrevstofix() to define revisions first, then validate them
Martin von Zweigbergk <martinvonz@google.com>
parents: 44560
diff changeset
434 raise error.Abort(b'unresolved conflicts', hint=b"use 'hg resolve'")
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
435 if not revs:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
436 raise error.Abort(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
437 b'no changesets specified', hint=b'use --rev or --working-dir'
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
438 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
439 return revs
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
440
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
441
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
442 def checkfixablectx(ui, repo, ctx):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
443 """Aborts if the revision shouldn't be replaced with a fixed one."""
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
444 if ctx.obsolete():
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
445 # It would be better to actually check if the revision has a successor.
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
446 allowdivergence = ui.configbool(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
447 b'experimental', b'evolution.allowdivergence'
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
448 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
449 if not allowdivergence:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
450 raise error.Abort(
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
451 b'fixing obsolete revision could cause divergence'
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
452 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
453
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
454
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
455 def pathstofix(ui, repo, pats, opts, match, basectxs, fixctx):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
456 """Returns the set of files that should be fixed in a context
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
457
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
458 The result depends on the base contexts; we include any file that has
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
459 changed relative to any of the base contexts. Base contexts should be
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
460 ancestors of the context being fixed.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
461 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
462 files = set()
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
463 for basectx in basectxs:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
464 stat = basectx.status(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
465 fixctx, match=match, listclean=bool(pats), listunknown=bool(pats)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
466 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
467 files.update(
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
468 set(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
469 itertools.chain(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
470 stat.added, stat.modified, stat.clean, stat.unknown
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
471 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
472 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
473 )
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
474 return files
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
475
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
476
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
477 def lineranges(opts, path, basepaths, basectxs, fixctx, content2):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
478 """Returns the set of line ranges that should be fixed in a file
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
479
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
480 Of the form [(10, 20), (30, 40)].
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
481
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
482 This depends on the given base contexts; we must consider lines that have
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
483 changed versus any of the base contexts, and whether the file has been
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
484 renamed versus any of them.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
485
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
486 Another way to understand this is that we exclude line ranges that are
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
487 common to the file in all base contexts.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
488 """
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
489 if opts.get(b'whole'):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
490 # Return a range containing all lines. Rely on the diff implementation's
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
491 # idea of how many lines are in the file, instead of reimplementing it.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
492 return difflineranges(b'', content2)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
493
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
494 rangeslist = []
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
495 for basectx in basectxs:
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
496 basepath = basepaths.get((basectx.rev(), fixctx.rev(), path), path)
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
497
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
498 if basepath in basectx:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
499 content1 = basectx[basepath].data()
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
500 else:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
501 content1 = b''
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
502 rangeslist.extend(difflineranges(content1, content2))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
503 return unionranges(rangeslist)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
504
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
505
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
506 def getbasepaths(repo, opts, workqueue, basectxs):
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
507 if opts.get(b'whole'):
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
508 # Base paths will never be fetched for line range determination.
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
509 return {}
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
510
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
511 basepaths = {}
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
512 for rev, path in workqueue:
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
513 fixctx = repo[rev]
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
514 for basectx in basectxs[rev]:
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
515 basepath = copies.pathcopies(basectx, fixctx).get(path, path)
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
516 if basepath in basectx:
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
517 basepaths[(basectx.rev(), fixctx.rev(), path)] = basepath
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
518 return basepaths
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
519
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
520
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
521 def unionranges(rangeslist):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
522 """Return the union of some closed intervals
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
523
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
524 >>> unionranges([])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
525 []
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
526 >>> unionranges([(1, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
527 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
528 >>> unionranges([(1, 100), (1, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
529 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
530 >>> unionranges([(1, 100), (2, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
531 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
532 >>> unionranges([(1, 99), (1, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
533 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
534 >>> unionranges([(1, 100), (40, 60)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
535 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
536 >>> unionranges([(1, 49), (50, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
537 [(1, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
538 >>> unionranges([(1, 48), (50, 100)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
539 [(1, 48), (50, 100)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
540 >>> unionranges([(1, 2), (3, 4), (5, 6)])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
541 [(1, 6)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
542 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
543 rangeslist = sorted(set(rangeslist))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
544 unioned = []
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
545 if rangeslist:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
546 unioned, rangeslist = [rangeslist[0]], rangeslist[1:]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
547 for a, b in rangeslist:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
548 c, d = unioned[-1]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
549 if a > d + 1:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
550 unioned.append((a, b))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
551 else:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
552 unioned[-1] = (c, max(b, d))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
553 return unioned
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
554
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
555
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
556 def difflineranges(content1, content2):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
557 """Return list of line number ranges in content2 that differ from content1.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
558
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
559 Line numbers are 1-based. The numbers are the first and last line contained
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
560 in the range. Single-line ranges have the same line number for the first and
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
561 last line. Excludes any empty ranges that result from lines that are only
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
562 present in content1. Relies on mdiff's idea of where the line endings are in
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
563 the string.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
564
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
565 >>> from mercurial import pycompat
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
566 >>> lines = lambda s: b'\\n'.join([c for c in pycompat.iterbytestr(s)])
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
567 >>> difflineranges2 = lambda a, b: difflineranges(lines(a), lines(b))
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
568 >>> difflineranges2(b'', b'')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
569 []
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
570 >>> difflineranges2(b'a', b'')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
571 []
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
572 >>> difflineranges2(b'', b'A')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
573 [(1, 1)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
574 >>> difflineranges2(b'a', b'a')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
575 []
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
576 >>> difflineranges2(b'a', b'A')
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
577 [(1, 1)]
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
578 >>> difflineranges2(b'ab', b'')
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
579 []
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
580 >>> difflineranges2(b'', b'AB')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
581 [(1, 2)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
582 >>> difflineranges2(b'abc', b'ac')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
583 []
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
584 >>> difflineranges2(b'ab', b'aCb')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
585 [(2, 2)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
586 >>> difflineranges2(b'abc', b'aBc')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
587 [(2, 2)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
588 >>> difflineranges2(b'ab', b'AB')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
589 [(1, 2)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
590 >>> difflineranges2(b'abcde', b'aBcDe')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
591 [(2, 2), (4, 4)]
37213
893ff8c3bc57 py3: fix fix doctests to be bytes-safe
Yuya Nishihara <yuya@tcha.org>
parents: 37207
diff changeset
592 >>> difflineranges2(b'abcde', b'aBCDe')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
593 [(2, 4)]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
594 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
595 ranges = []
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
596 for lines, kind in mdiff.allblocks(content1, content2):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
597 firstline, lastline = lines[2:4]
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
598 if kind == b'!' and firstline != lastline:
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
599 ranges.append((firstline + 1, lastline))
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
600 return ranges
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
601
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
602
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
603 def getbasectxs(repo, opts, revstofix):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
604 """Returns a map of the base contexts for each revision
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
605
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
606 The base contexts determine which lines are considered modified when we
38590
f068495a1c28 fix: add test case that shows why --whole with --base is useful
Danny Hooper <hooper@google.com>
parents: 38537
diff changeset
607 attempt to fix just the modified lines in a file. It also determines which
f068495a1c28 fix: add test case that shows why --whole with --base is useful
Danny Hooper <hooper@google.com>
parents: 38537
diff changeset
608 files we attempt to fix, so it is important to compute this even when
f068495a1c28 fix: add test case that shows why --whole with --base is useful
Danny Hooper <hooper@google.com>
parents: 38537
diff changeset
609 --whole is used.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
610 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
611 # The --base flag overrides the usual logic, and we give every revision
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
612 # exactly the set of baserevs that the user specified.
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
613 if opts.get(b'base'):
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
614 baserevs = set(scmutil.revrange(repo, opts.get(b'base')))
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
615 if not baserevs:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
616 baserevs = {nullrev}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
617 basectxs = {repo[rev] for rev in baserevs}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
618 return {rev: basectxs for rev in revstofix}
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
619
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
620 # Proceed in topological order so that we can easily determine each
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
621 # revision's baserevs by looking at its parents and their baserevs.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
622 basectxs = collections.defaultdict(set)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
623 for rev in sorted(revstofix):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
624 ctx = repo[rev]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
625 for pctx in ctx.parents():
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
626 if pctx.rev() in basectxs:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
627 basectxs[rev].update(basectxs[pctx.rev()])
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
628 else:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
629 basectxs[rev].add(pctx)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
630 return basectxs
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
631
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
632
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
633 def fixfile(ui, repo, opts, fixers, fixctx, path, basepaths, basectxs):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
634 """Run any configured fixers that should affect the file in this context
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
635
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
636 Returns the file content that results from applying the fixers in some order
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
637 starting with the file's content in the fixctx. Fixers that support line
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
638 ranges will affect lines that have changed relative to any of the basectxs
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
639 (i.e. they will only avoid lines that are common to all basectxs).
38967
a009589cd32a fix: determine fixer tool failure by exit code instead of stderr
Danny Hooper <hooper@google.com>
parents: 38950
diff changeset
640
a009589cd32a fix: determine fixer tool failure by exit code instead of stderr
Danny Hooper <hooper@google.com>
parents: 38950
diff changeset
641 A fixer tool's stdout will become the file's new content if and only if it
42673
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
642 exits with code zero. The fixer tool's working directory is the repository's
74b4cd091e0d fix: run fixer tools in the repo root as cwd so they can use the working copy
Danny Hooper <hooper@google.com>
parents: 42655
diff changeset
643 root.
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
644 """
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
645 metadata = {}
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
646 newdata = fixctx[path].data()
43105
649d3ac37a12 py3: define and use pycompat.iteritems() for hgext/
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43087
diff changeset
647 for fixername, fixer in pycompat.iteritems(fixers):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
648 if fixer.affects(opts, fixctx, path):
45073
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
649 ranges = lineranges(
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
650 opts, path, basepaths, basectxs, fixctx, newdata
54009f8c3e25 fix: obtain base paths before starting workers
Rodrigo Damazio Bovendorp <rdamazio@google.com>
parents: 44856
diff changeset
651 )
42758
e9f503074044 fix: pass line ranges as value instead of callback
Danny Hooper <hooper@google.com>
parents: 42757
diff changeset
652 command = fixer.command(ui, path, ranges)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
653 if command is None:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
654 continue
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
655 ui.debug(b'subprocess: %s\n' % (command,))
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
656 proc = subprocess.Popen(
39836
f1d6021453c2 py3: remove a couple of superfluous calls to pycompat.rapply()
Matt Harbison <matt_harbison@yahoo.com>
parents: 39826
diff changeset
657 procutil.tonativestr(command),
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
658 shell=True,
43193
2d1f9880af1b py3: convert cwd to native string when running `fix`
Matt Harbison <matt_harbison@yahoo.com>
parents: 43117
diff changeset
659 cwd=procutil.tonativestr(repo.root),
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
660 stdin=subprocess.PIPE,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
661 stdout=subprocess.PIPE,
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
662 stderr=subprocess.PIPE,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
663 )
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
664 stdout, stderr = proc.communicate(newdata)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
665 if stderr:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
666 showstderr(ui, fixctx.rev(), fixername, stderr)
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
667 newerdata = stdout
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
668 if fixer.shouldoutputmetadata():
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
669 try:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
670 metadatajson, newerdata = stdout.split(b'\0', 1)
43380
579672b347d2 py3: define and use json.loads polyfill
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43227
diff changeset
671 metadata[fixername] = pycompat.json_loads(metadatajson)
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
672 except ValueError:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
673 ui.warn(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
674 _(b'ignored invalid output from fixer tool: %s\n')
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
675 % (fixername,)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
676 )
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
677 continue
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
678 else:
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
679 metadata[fixername] = None
38967
a009589cd32a fix: determine fixer tool failure by exit code instead of stderr
Danny Hooper <hooper@google.com>
parents: 38950
diff changeset
680 if proc.returncode == 0:
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
681 newdata = newerdata
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
682 else:
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
683 if not stderr:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
684 message = _(b'exited with status %d\n') % (proc.returncode,)
40532
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
685 showstderr(ui, fixctx.rev(), fixername, message)
93bab80993f4 fix: add a config to abort when a fixer tool fails
Danny Hooper <hooper@google.com>
parents: 40431
diff changeset
686 checktoolfailureaction(
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
687 ui,
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
688 _(b'no fixes will be applied'),
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
689 hint=_(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
690 b'use --config fix.failure=continue to apply any '
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
691 b'successful fixes anyway'
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
692 ),
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
693 )
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
694 return metadata, newdata
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
695
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
696
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
697 def showstderr(ui, rev, fixername, stderr):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
698 """Writes the lines of the stderr string as warnings on the ui
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
699
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
700 Uses the revision number and fixername to give more context to each line of
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
701 the error message. Doesn't include file names, since those take up a lot of
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
702 space and would tend to be included in the error message if they were
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
703 relevant.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
704 """
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
705 for line in re.split(b'[\r\n]+', stderr):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
706 if line:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
707 ui.warn(b'[')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
708 if rev is None:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
709 ui.warn(_(b'wdir'), label=b'evolve.rev')
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
710 else:
43501
b2f95f9d3588 fix: replace str() by b'%d' for formatting integer
Martin von Zweigbergk <martinvonz@google.com>
parents: 43380
diff changeset
711 ui.warn(b'%d' % rev, label=b'evolve.rev')
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
712 ui.warn(b'] %s: %s\n' % (fixername, line))
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
713
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
714
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
715 def writeworkingdir(repo, ctx, filedata, replacements):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
716 """Write new content to the working copy and check out the new p1 if any
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
717
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
718 We check out a new revision if and only if we fixed something in both the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
719 working directory and its parent revision. This avoids the need for a full
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
720 update/merge, and means that the working directory simply isn't affected
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
721 unless the --working-dir flag is given.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
722
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
723 Directly updates the dirstate for the affected files.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
724 """
43105
649d3ac37a12 py3: define and use pycompat.iteritems() for hgext/
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43087
diff changeset
725 for path, data in pycompat.iteritems(filedata):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
726 fctx = ctx[path]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
727 fctx.write(data, fctx.flags())
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
728 if repo.dirstate[path] == b'n':
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
729 repo.dirstate.normallookup(path)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
730
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
731 oldparentnodes = repo.dirstate.parents()
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
732 newparentnodes = [replacements.get(n, n) for n in oldparentnodes]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
733 if newparentnodes != oldparentnodes:
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
734 repo.setparents(*newparentnodes)
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
735
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
736
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
737 def replacerev(ui, repo, ctx, filedata, replacements):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
738 """Commit a new revision like the given one, but with file content changes
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
739
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
740 "ctx" is the original revision to be replaced by a modified one.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
741
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
742 "filedata" is a dict that maps paths to their new file content. All other
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
743 paths will be recreated from the original revision without changes.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
744 "filedata" may contain paths that didn't exist in the original revision;
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
745 they will be added.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
746
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
747 "replacements" is a dict that maps a single node to a single node, and it is
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
748 updated to indicate the original revision is replaced by the newly created
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
749 one. No entry is added if the replacement's node already exists.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
750
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
751 The new revision has the same parents as the old one, unless those parents
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
752 have already been replaced, in which case those replacements are the parents
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
753 of this new revision. Thus, if revisions are replaced in topological order,
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
754 there is no need to rebase them into the original topology later.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
755 """
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
756
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
757 p1rev, p2rev = repo.changelog.parentrevs(ctx.rev())
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
758 p1ctx, p2ctx = repo[p1rev], repo[p2rev]
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
759 newp1node = replacements.get(p1ctx.node(), p1ctx.node())
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
760 newp2node = replacements.get(p2ctx.node(), p2ctx.node())
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
761
40570
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
762 # We don't want to create a revision that has no changes from the original,
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
763 # but we should if the original revision's parent has been replaced.
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
764 # Otherwise, we would produce an orphan that needs no actual human
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
765 # intervention to evolve. We can't rely on commit() to avoid creating the
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
766 # un-needed revision because the extra field added below produces a new hash
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
767 # regardless of file content changes.
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
768 if (
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
769 not filedata
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
770 and p1ctx.node() not in replacements
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
771 and p2ctx.node() not in replacements
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
772 ):
40570
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
773 return
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
774
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
775 extra = ctx.extra().copy()
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
776 extra[b'fix_source'] = ctx.hex()
40570
ad71c792a8d8 fix: add extra field to fixed revisions to avoid creating obsolescence cycles
Danny Hooper <hooper@google.com>
parents: 40566
diff changeset
777
43962
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
778 wctx = context.overlayworkingctx(repo)
44092
833210fbd900 graftcopies: remove `skip` and `repo` arguments
Martin von Zweigbergk <martinvonz@google.com>
parents: 44090
diff changeset
779 wctx.setbase(repo[newp1node])
44271
c791ed6a2154 merge: introduce a revert_to() for that use-case
Martin von Zweigbergk <martinvonz@google.com>
parents: 44129
diff changeset
780 merge.revert_to(ctx, wc=wctx)
44092
833210fbd900 graftcopies: remove `skip` and `repo` arguments
Martin von Zweigbergk <martinvonz@google.com>
parents: 44090
diff changeset
781 copies.graftcopies(wctx, ctx, ctx.p1())
43962
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
782
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
783 for path in filedata.keys():
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
784 fctx = ctx[path]
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
785 copysource = fctx.copysource()
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
786 wctx.write(path, filedata[path], flags=fctx.flags())
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
787 if copysource:
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
788 wctx.markcopied(path, copysource)
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
789
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
790 memctx = wctx.tomemctx(
38423
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
791 text=ctx.description(),
43962
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
792 branch=ctx.branch(),
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
793 extra=extra,
38423
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
794 date=ctx.date(),
43962
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
795 parents=(newp1node, newp2node),
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
796 user=ctx.user(),
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
797 )
43962
eebdd6709868 fix: fix handling of merge commits by using overlayworkingctx
Kyle Lippincott <spectral@google.com>
parents: 43936
diff changeset
798
38423
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
799 sucnode = memctx.commit()
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
800 prenode = ctx.node()
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
801 if prenode == sucnode:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
802 ui.debug(b'node %s already existed\n' % (ctx.hex()))
38423
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
803 else:
32fba6fe893d scmutil: make cleanupnodes optionally also fix the phase
Martin von Zweigbergk <martinvonz@google.com>
parents: 38420
diff changeset
804 replacements[ctx.node()] = sucnode
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
805
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
806
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
807 def getfixers(ui):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
808 """Returns a map of configured fixer tools indexed by their names
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
809
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
810 Each value is a Fixer object with methods that implement the behavior of the
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
811 fixer's config suboptions. Does not validate the config values.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
812 """
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
813 fixers = {}
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
814 for name in fixernames(ui):
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
815 enabled = ui.configbool(b'fix', name + b':enabled')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
816 command = ui.config(b'fix', name + b':command')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
817 pattern = ui.config(b'fix', name + b':pattern')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
818 linerange = ui.config(b'fix', name + b':linerange')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
819 priority = ui.configint(b'fix', name + b':priority')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
820 metadata = ui.configbool(b'fix', name + b':metadata')
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
821 skipclean = ui.configbool(b'fix', name + b':skipclean')
42655
2987d015aba4 fix: ignore fixer tool configurations that are missing patterns
Danny Hooper <hooper@google.com>
parents: 42653
diff changeset
822 # Don't use a fixer if it has no pattern configured. It would be
2987d015aba4 fix: ignore fixer tool configurations that are missing patterns
Danny Hooper <hooper@google.com>
parents: 42653
diff changeset
823 # dangerous to let it affect all files. It would be pointless to let it
2987d015aba4 fix: ignore fixer tool configurations that are missing patterns
Danny Hooper <hooper@google.com>
parents: 42653
diff changeset
824 # affect no files. There is no reasonable subset of files to use as the
2987d015aba4 fix: ignore fixer tool configurations that are missing patterns
Danny Hooper <hooper@google.com>
parents: 42653
diff changeset
825 # default.
43220
d3d1a3afe7aa fix: warn when a fixer doesn't have a configured command
Martin von Zweigbergk <martinvonz@google.com>
parents: 43219
diff changeset
826 if command is None:
d3d1a3afe7aa fix: warn when a fixer doesn't have a configured command
Martin von Zweigbergk <martinvonz@google.com>
parents: 43219
diff changeset
827 ui.warn(
d3d1a3afe7aa fix: warn when a fixer doesn't have a configured command
Martin von Zweigbergk <martinvonz@google.com>
parents: 43219
diff changeset
828 _(b'fixer tool has no command configuration: %s\n') % (name,)
d3d1a3afe7aa fix: warn when a fixer doesn't have a configured command
Martin von Zweigbergk <martinvonz@google.com>
parents: 43219
diff changeset
829 )
d3d1a3afe7aa fix: warn when a fixer doesn't have a configured command
Martin von Zweigbergk <martinvonz@google.com>
parents: 43219
diff changeset
830 elif pattern is None:
42655
2987d015aba4 fix: ignore fixer tool configurations that are missing patterns
Danny Hooper <hooper@google.com>
parents: 42653
diff changeset
831 ui.warn(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
832 _(b'fixer tool has no pattern configuration: %s\n') % (name,)
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
833 )
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
834 elif not enabled:
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
835 ui.debug(b'ignoring disabled fixer tool: %s\n' % (name,))
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
836 else:
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
837 fixers[name] = Fixer(
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
838 command, pattern, linerange, priority, metadata, skipclean
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
839 )
40566
b9557567cc3f fix: add suboption for configuring execution order of tools
Danny Hooper <hooper@google.com>
parents: 40533
diff changeset
840 return collections.OrderedDict(
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
841 sorted(fixers.items(), key=lambda item: item[1]._priority, reverse=True)
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
842 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
843
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
844
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
845 def fixernames(ui):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
846 """Returns the names of [fix] config options that have suboptions"""
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
847 names = set()
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
848 for k, v in ui.configitems(b'fix'):
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
849 if b':' in k:
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
850 names.add(k.split(b':', 1)[0])
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
851 return names
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
852
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
853
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
854 class Fixer(object):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
855 """Wraps the raw config values for a fixer with methods"""
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
856
43219
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
857 def __init__(
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
858 self, command, pattern, linerange, priority, metadata, skipclean
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
859 ):
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
860 self._command = command
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
861 self._pattern = pattern
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
862 self._linerange = linerange
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
863 self._priority = priority
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
864 self._metadata = metadata
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
865 self._skipclean = skipclean
0101db49606f fix: make Fixer initialization more explicit for clarity
Martin von Zweigbergk <martinvonz@google.com>
parents: 43218
diff changeset
866
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
867 def affects(self, opts, fixctx, path):
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
868 """Should this fixer run on the file at the given path and context?"""
43227
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
869 repo = fixctx.repo()
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
870 matcher = matchmod.match(
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
871 repo.root, repo.root, [self._pattern], ctx=fixctx
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
872 )
f02d3c0eed18 fix: match patterns relative to root
Martin von Zweigbergk <martinvonz@google.com>
parents: 43221
diff changeset
873 return matcher(path)
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
874
42194
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
875 def shouldoutputmetadata(self):
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
876 """Should the stdout of this fixer start with JSON and a null byte?"""
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
877 return self._metadata
0da689a60163 fix: allow fixer tools to return metadata in addition to the file content
Danny Hooper <hooper@google.com>
parents: 42009
diff changeset
878
42758
e9f503074044 fix: pass line ranges as value instead of callback
Danny Hooper <hooper@google.com>
parents: 42757
diff changeset
879 def command(self, ui, path, ranges):
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
880 """A shell command to use to invoke this fixer on the given file/lines
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
881
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
882 May return None if there is no appropriate command to run for the given
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
883 parameters.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
884 """
37774
d6970628b95f fix: use templater to substitute values in command string
Yuya Nishihara <yuya@tcha.org>
parents: 37618
diff changeset
885 expand = cmdutil.rendercommandtemplate
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
886 parts = [
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
887 expand(
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
888 ui,
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
889 self._command,
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
890 {b'rootpath': path, b'basename': os.path.basename(path)},
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
891 )
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
892 ]
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
893 if self._linerange:
42756
ed0da6e0d6ee fix: allow tools to use :linerange, but also run if a file is unchanged
Danny Hooper <hooper@google.com>
parents: 42673
diff changeset
894 if self._skipclean and not ranges:
37183
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
895 # No line ranges to fix, so don't run the fixer.
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
896 return None
ded5ea279a93 fix: new extension for automatically modifying file contents
Danny Hooper <hooper@google.com>
parents:
diff changeset
897 for first, last in ranges:
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
898 parts.append(
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
899 expand(
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
900 ui, self._linerange, {b'first': first, b'last': last}
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
901 )
43076
2372284d9457 formatting: blacken the codebase
Augie Fackler <augie@google.com>
parents: 43058
diff changeset
902 )
43077
687b865b95ad formatting: byteify all mercurial/ and hgext/ string literals
Augie Fackler <augie@google.com>
parents: 43076
diff changeset
903 return b' '.join(parts)