Don't flag color components of Color and NSColor initializers - #6841
Open
lechuckcaptain wants to merge 1 commit into
Open
Don't flag color components of Color and NSColor initializers#6841lechuckcaptain wants to merge 1 commit into
Color and NSColor initializers#6841lechuckcaptain wants to merge 1 commit into
Conversation
Generated by 🚫 Danger |
lechuckcaptain
force-pushed
the
no-magic-numbers-colour-initializers
branch
2 times, most recently
from
July 28, 2026 21:47
77d5564 to
a317a2a
Compare
`no_magic_numbers` already exempts the component arguments of a `UIColor` initializer, but the check hardcoded that single type name, so SwiftUI's `Color` and AppKit's `NSColor` got no exemption at all. Recognise all three, and accept the `opacity` label alongside `alpha`, since SwiftUI spells it differently. AppKit encodes the color space in the label of the first component, so cover the `calibratedRed`, `deviceRed`, `srgbRed`, `calibratedWhite`, `deviceWhite`, `genericGamma22White`, `calibratedHue` and `deviceHue` variants as well as the `deviceCyan:magenta:yellow:black:alpha:` components. Recognising the type name alone would have left the first component of such a call reported while the rest were not. The exemption also required the literal to be the *immediate* argument, so `UIColor(red: 0.6, ...)` was exempt while `UIColor(red: 0x19 / 255, ...)` was not: there the literal's parent is the division, not the labelled argument. Walk up through arithmetic, parentheses and numeric conversions to find the enclosing argument instead, and bail out on anything else so an exemption granted for one argument cannot leak past it. That boundary is what keeps the existing manual bit-packing example `Int(r * 255) << 16` flagged, and `Color(...).opacity(0.42)` too, since in neither case is the literal inside a color initializer's argument list. Every literal remains judged by its own label, so an unrecognised label is exempted for nothing but itself: `UIColor(rgb: 0x33373A, alpha: 0.16)` keeps reporting the `rgb:` value while exempting `alpha:`, which is a color component whatever its sibling happens to be.
lechuckcaptain
force-pushed
the
no-magic-numbers-colour-initializers
branch
from
August 4, 2026 16:05
a317a2a to
14d590a
Compare
lechuckcaptain
marked this pull request as ready for review
August 4, 2026 20:57
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
no_magic_numbersexempts the color-component arguments of aUIColorinitializer, but thecheck hardcoded that one type name, so SwiftUI's
Colorand AppKit'sNSColorgot no exemptionat all. All three are now recognised, and the
opacitylabel is accepted alongsidealpha.alone was not enough:
NSColor(srgbRed: 0.1, green: 0.42, blue: 0.7, alpha: 1)would have hadits last three components exempted and the first still reported. The
calibratedRed,deviceRed,srgbRed,calibratedWhite,deviceWhite,genericGamma22White,calibratedHueand
deviceHuevariants are covered too, as are the CMYK components ofdeviceCyan:magenta:yellow:black:alpha:.UIColor(red: 0.6, …)was exempt while
UIColor(red: 0x19 / 255, …)was not. The enclosing argument is now found bywalking up through arithmetic, parentheses and numeric conversions, bailing out on anything else
so an exemption cannot leak past the argument it was granted for.
Every literal is still judged by its own label, so an unrecognised label is exempted for nothing but
itself: in Wire's
UIColor(rgb: 0x33373A, alpha: 0.16)thergb:value stays reported whilealpha:is exempt, since0.16is a color component whatever its sibling happens to be. There isa triggering example pinning that.
Validation
swift test --filter NoMagicNumbersRuleGeneratedTestspasses, as do theRuleDocumentation,DefaultRuleConfiguration,RuleNameConsistencyandExamplesuites. No existing example wasedited, reordered or removed; the manual bit-packing example
Int(r * 255) << 16andColor.primary.opacity(isAnimate ? 0.1 : 1.5)still trigger.swift run swiftlint --strictclean on the changed file.