-
Notifications
You must be signed in to change notification settings - Fork 2.2k
Baseline implementation #5475
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Baseline implementation #5475
Conversation
Generated by 🚫 Danger |
@SimplyDanny and @jpsim - would love to get some feedback on this ... |
d683fc0
to
d1dce64
Compare
1ea4217
to
795d71c
Compare
f593be5
to
b2df4d2
Compare
65ec039
to
65d9b72
Compare
3dd0245
to
e2628cb
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very good idea to store and compare the violating line for more context. To increase precision even further, could this theoretically be extended to the violating line itself plus the previous and the subsequent line? Not sure what the benefit of this would be though ...
Tests/SwiftLintFrameworkTests/Resources/BaselineFixtures/BaselineExample.swift
Outdated
Show resolved
Hide resolved
e2628cb
to
09eee8c
Compare
So we could definitely store more context, and that would definitely improve accuracy in some situations. But having more context would mean that a change in the preceding or following line would then show up as "new", at least on the basis of exact equality. The same is true for the line the violation is on of course - someone could change whitespace there, but still leave the violation, and that would fail our equality test. We could try to filter intelligently for preceding and following line changes, but I think the line the violation is on is going to work well for most cases (one can always construct a pathological set of violations that will fool whichever algorithm you use). If this does turn out to be a problem in practice, we can always update it later. |
I swapped saving the dictionaries of baseline violations, keyed on file, to saving a sorted array of baseline violations - 2834540 So exactly identical baselines should also now be identical on disk. |
I've added a |
I think I've addressed everything so far, but let me know if I've missed anything ... |
I kept the open points as "unresolved" and added a few more comments. |
Very eager to see it :) |
fbddaf0
to
329bd5e
Compare
Co-authored-by: Danny Mösch <danny.moesch@icloud.com>
Co-authored-by: Danny Mösch <danny.moesch@icloud.com>
Co-authored-by: Danny Mösch <danny.moesch@icloud.com>
Co-authored-by: Danny Mösch <danny.moesch@icloud.com>
185ddf8
to
994fd94
Compare
This is a very good implementation to start with and collect some feedback for. Having it as an incubation allows us to further enhance it if that's required. Thanks a lot, @mildm8nnered, for picking up and refining previous PRs! |
Thank you for all your help and feedback @SimplyDanny We may be able to close these old baseline PRs now: |
Hello @mildm8nnered , First of all great job. So here is my commands:
But I still have the violations output. Could you tell me what I am wrong ? |
So you need to use the same config file to generate the baseline that you will use when using it to filter violations. I would have expected your commands to be:
and
Please let us know if this does not fix it for you. |
Inspired by #3421 and its predecessors.
Adds a new baseline capability to SwiftLint, in the form of two new options to the lint and analyze commands.
This may be helpful for people who have large numbers of pre-existing violations in their codebase, that they cannot easily fix, and do not want to suppress individually.
This should allow rules to be enabled, and existing violations be ignored, but any new violations detected.
Usage:
For example:
swiftlint --baseline /path/to/baselinefile --write-baseline /path/to/baselinefile
Will read the existing baseline from
baselinefile
, and also write the full set of detected violations back to the same file.If the baseline cannot be read, that is a fatal error, unless you've also specified the same file with
--write-baseline
(so that you can use that invocation, and still have it work first time around).In practice, in CI, I expect that you would probably keep a current baseline from your main branch, and then compare feature branches against that baseline.
Baseline Comparisons
A baseline is a dictionary, keyed on relative file path, whose values are the array of
StyleViolation
's in each file, and additionally the text of the line of source code that triggered the violation. Storing the text means that violations can still be matched, even if they have been moved around in the source file, changing their line numbers.On disk, the baseline is actually stored as a sorted array, so that identical baselines will have identical on-disk representations.
When filtering detected violations according to the baseline, we first compare for exact equality between the detected and baseline violations, including line numbers.
If the sets of violations are not exactly equal, then we remove any violations that are exactly identical (again including line numbers).
We then group the violations by rule, and then again by the original source code text. For each detected violation, if the baseline does not contain a matching violation of the same rule, with the same reason, and text, then the detected violation is reported. If the detected violations contain multiple violations of the same rule, with the same reason and text, then all those violations are reported, even if the baseline contains a match, as we cannot tell which of the violations map to which of the baseline violations.
It may be the case that the user fixed one violation of a rule, but introduced a completely new violation of that rule, with the same text, elsewhere, or fixed two existing violations, but added a new one. In the current implementation, as long as the number of violations of that rule (additionally matching on the reason and text) did not increase, we will ignore them.
Threshold Violations
Currently threshold violations are not filtered or stored in the baseline, and are calculated against the filtered violations.
Inspecting a Baseline
There is also a new command -
baseline
This uses the existing reporters to report the violations contained in the baseline (
--reporter summary
can be useful with the following commands, to get an overview without having to wade through individual violations).For example, to inspect a baseline:
swiftlint baseline report Baseline.json
To see what new violations have been introduced, you can run:
swiftlint baseline compare Baseline.json --other-baseline NewBaseline.json
This will produce the same output as:
swiftlint lint --baseline Baseline.json
To see what violations have been fixed, simply reverse the baselines
swiftlint baseline compare NewBaseline.json --other-baseline Baseline.json