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
rubocops/cask: Disallow protocol in cask URL verified stanza #14886
Changes from 1 commit
79db987
f4a0bc7
4791224
4e06756
d995afc
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
# typed: true | ||
# frozen_string_literal: true | ||
|
||
require "forwardable" | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Not sure what this does, I copied and pasted from other cops. 😳 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it's meaningless without any use of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I thought so, but it's in a few cops that don't make use of |
||
|
||
module RuboCop | ||
module Cop | ||
module Cask | ||
# This cop checks that a cask's `url` stanza is formatted correctly. | ||
# | ||
# @example | ||
# # bad | ||
# url "https://example.com/foo.dmg", | ||
# verified: "https://example.com" | ||
# | ||
# | ||
# # good | ||
# url "https://example.com/foo.dmg", | ||
# verified: "example.com" | ||
# | ||
class Url < Base | ||
extend AutoCorrector | ||
extend Forwardable | ||
include OnUrlStanza | ||
|
||
def on_url_stanza(stanza) | ||
return if stanza.stanza_node.block_type? | ||
|
||
hash_node = stanza.stanza_node.last_argument | ||
return unless hash_node.hash_type? | ||
|
||
hash_node.each_pair do |key_node, value_node| | ||
next unless key_node.source == "verified" | ||
next unless value_node.str_type? | ||
next unless value_node.source.start_with?("\"https:/", "\"http:/") | ||
|
||
add_offense( | ||
value_node.source_range, | ||
message: "Verified URL parameter value should not start with https:// or http://.", | ||
) do |corrector| | ||
corrector.replace(value_node.source_range, value_node.source.gsub(%r{^"https?://}, "\"")) | ||
end | ||
end | ||
end | ||
end | ||
end | ||
end | ||
end |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
# typed: false | ||
# frozen_string_literal: true | ||
|
||
require "rubocops/rubocop-cask" | ||
require "test/rubocops/cask/shared_examples/cask_cop" | ||
|
||
describe RuboCop::Cop::Cask::Url do | ||
include CaskCop | ||
|
||
subject(:cop) { described_class.new } | ||
|
||
context "when url 'verified' value does not start with a protocol" do | ||
let(:source) do | ||
<<~CASK | ||
cask "foo" do | ||
url "https://example.com/download/foo-v1.2.0.dmg", | ||
verified: "example.com" | ||
end | ||
CASK | ||
end | ||
|
||
include_examples "does not report any offenses" | ||
end | ||
|
||
context "when url 'verified' value starts with a protocol" do | ||
let(:source) do | ||
<<~CASK | ||
cask "foo" do | ||
url "https://example.com/download/foo-v1.2.0.dmg", | ||
verified: "https://example.com" | ||
end | ||
CASK | ||
end | ||
|
||
let(:expected_offenses) do | ||
[{ | ||
message: "Verified URL parameter value should not start with https:// or http://.", | ||
severity: :convention, | ||
line: 3, | ||
column: 14, | ||
source: "verified: \"https://example.com\"", | ||
}] | ||
end | ||
|
||
include_examples "reports offenses" | ||
end | ||
end |
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.
Sorbet doesn't run successfully. Need to read up on https://sorbet.org/docs/requires-ancestor.
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.
Reading https://blog.appsignal.com/2021/01/13/using-mixins-and-modules-in-your-ruby-on-rails-application.html for a general overview of mixins, and https://sorbet.org/docs/requires-ancestor, I do not understand what it wants me to do. As the person who introduced this
requires_ancestor
thing, @dduugg can you shed any light (either here or in Slack)? Have I taken a wrong approach here somewhere?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.
This code means that any module that includes
RuboCop::Cop::Cask::OnUrlStanza
must subclassRuboCop::Cop::Cask::UrlLegacyCommaSeparators
. This makes the methods defined in the latter available in the former. (In this specific case,OnUrlStanza
makes use ofon_url_stanza
, the lone method defined inUrlLegacyCommaSeparators
.)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.
Hmmm, so if we now have
RuboCop::Cop::Cask::Url
andRuboCop::Cop::Cask::UrlLegacyCommaSeparators
cops that have theon_url_stanza
method , which one should inherit from which? They're separate cops.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.
I figured it out!