Begin refactoring classes used by add-grammar

This commit is contained in:
Alhadis
2018-04-12 19:01:10 +10:00
parent d2f2f91a89
commit 4fadaf80e0

View File

@@ -3,39 +3,85 @@
require "optparse" require "optparse"
require "open3" require "open3"
class GrammarRepo
# Whitelist of trusted hosting providers
HOSTS = Regexp.union %w[github.com bitbucket.org gitlab.com]
# Public: Define a repository source by upstream URL.
#
# url - an HTTPS, HTTP, or SSH address accepted by git-remote(1)
# Only domains listed in HOSTS are accepted; unrecognised
# hostnames or invalid URLs will raise an ArgumentError.
#
# Assumption: Repo URLs will never include subdomains.
# We only check for a possible `www`, nothing else.
#
# module_path - path of submodule as registered in `.gitmodules`
# Omit this unless grammar is being replaced.
def initialize(url, module_path = nil)
if https? url
@host = $1.downcase
@user = $2
@repo = $3.sub /\.git$/, ""
elsif ssh?(url) || shorthand?(url)
@host = $1.downcase
@user = $2
@repo = $3
elsif implicit_shorthand? url
@host = "github.com"
@user = $1
@repo = $2
else
raise ArgumentError, "Unsupported URL: #{url}"
end
end
# Match a well-formed HTTP or HTTPS address
def https?(url)
nil unless url =~ /
^ (?<protocol> https? ://)?
(?<userauth> [^@.]+ @ )?
(?<subdomain> www \. )?
(?<hostname> #{HOSTS} )
\/ (?<user> [^\/]+ )
\/ (?<repo> [^\/]+ ) /xi
end
# Match an SSH address starting with `git@`
def ssh?(url)
nil unless url =~ /
^ git@
(?<hostname> #{HOSTS}) :
(?<user> [^\/]+) \/
(?<repo> [^\/]+) \.git $/xi
end
# Match `provider:user/repo`
def shorthand?(url)
nil unless url =~ /
^ (?<hostname> #{HOSTS}) : \/?
(?<user> [^\/]+) \/
(?<repo> [^\/]+) \/? $ /xi
end
# Match `user/repo` shorthand, assumed to be GitHub
def implicit_shorthand?(url)
nil unless url =~ /
^ \/? (?<user>[^\/]+)
\/ (?<repo>[^\/]+)
\/? $/xi
end
end
class GrammarGuardian
ROOT = File.expand_path("../../", __FILE__) ROOT = File.expand_path("../../", __FILE__)
def initialize
# Break a repository URL into its separate components # Track each change so we can roll back after a failed command
def parse_url(input) @changes = Hash.new
hosts = "github\.com|bitbucket\.org|gitlab\.com"
# HTTPS/HTTP link pointing to recognised hosts
if input =~ /^(?:https?:\/\/)?(?:[^.@]+@)?(?:www\.)?(#{hosts})\/([^\/]+)\/([^\/]+)/i
{ host: $1.downcase(), user: $2, repo: $3.sub(/\.git$/, "") }
# SSH
elsif input =~ /^git@(#{hosts}):([^\/]+)\/([^\/]+)\.git$/i
{ host: $1.downcase(), user: $2, repo: $3 }
# provider:user/repo
elsif input =~ /^(github|bitbucket|gitlab):\/?([^\/]+)\/([^\/]+)\/?$/i
{ host: $1.downcase(), user: $2, repo: $3 }
# user/repo - Common GitHub shorthand
elsif input =~ /^\/?([^\/]+)\/([^\/]+)\/?$/
{ host: "github.com", user: $1, repo: $2 }
else
raise "Unsupported URL: #{input}"
end
end
# Isolate the vendor-name component of a submodule path
def parse_submodule(name)
name =~ /^(?:.*(?:vendor\/)?grammars\/)?([^\/]+)/i
path = "vendor/grammars/#{$1}"
unless File.exist?("#{ROOT}/" + path)
warn "Submodule '#{path}' does not exist. Aborting."
exit 1
end
path
end end
# Print debugging feedback to STDOUT if running with --verbose # Print debugging feedback to STDOUT if running with --verbose
@@ -54,6 +100,19 @@ def command(*args)
exit 1 exit 1
end end
end end
end
# Isolate the vendor-name component of a submodule path
def parse_submodule(name)
name =~ /^(?:.*(?:vendor\/)?grammars\/)?([^\/]+)/i
path = "vendor/grammars/#{$1}"
unless File.exist?("#{ROOT}/" + path)
warn "Submodule '#{path}' does not exist. Aborting."
exit 1
end
path
end
usage = """Usage: usage = """Usage:
#{$0} [-v|--verbose] [--replace grammar] url #{$0} [-v|--verbose] [--replace grammar] url