Skip to content
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

Bsfy 214 #1269

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 30 additions & 0 deletions lib/travis/api/v3/models/scan_result.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@

module Travis::API::V3
class Models::ScanResult
attr_reader :id, :log_id, :job_id, :owner_id, :owner_type, :created_at, :formatted_content, :issues_found, :archived, :purged_at, :token, :token_created_at,
:job_number, :build_id, :build_number, :job_finished_at, :commit_sha, :commit_compare_url, :commit_branch, :repository_id

def initialize(attributes = {})
@id = attributes.fetch('id')
@log_id = attributes.fetch('log_id')
@job_id = attributes.fetch('job_id')
@owner_id = attributes.fetch('owner_id')
@owner_type = attributes.fetch('owner_type')
@created_at = attributes.fetch('created_at')
@formatted_content = attributes.fetch('formatted_content')
@issues_found = attributes.fetch('issues_found')
@archived = attributes.fetch('archived')
@purged_at = attributes.fetch('purged_at')
@token = attributes.fetch('token')
@token_created_at = attributes.fetch('token_created_at')
@job_number = attributes.fetch('job_number')
@build_id = attributes.fetch('build_id')
@build_number = attributes.fetch('build_number')
@job_finished_at = attributes.fetch('job_finished_at')
@commit_sha = attributes.fetch('commit_sha')
@commit_compare_url = attributes.fetch('commit_compare_url')
@commit_branch = attributes.fetch('commit_branch')
@repository_id = attributes.fetch('repository_id')
end
end
end
32 changes: 32 additions & 0 deletions lib/travis/api/v3/models/scanner_collection.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# frozen_string_literal: true

module Travis::API::V3
class Models::ScannerCollection
def initialize(collection, total_count)
@collection = collection
@total_count = total_count
end

def count(*)
@total_count
end

def limit(*)
self
end

def offset(*)
self
end

def map
return @collection.map unless block_given?

@collection.map { |x| yield x }
end

def to_sql
"scanner_query:#{Time.now.to_i}"
end
end
end
4 changes: 4 additions & 0 deletions lib/travis/api/v3/permissions/repository.rb
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@ def create_request?
write?
end

def check_scan_results?
write?
end

def admin?
access_control.adminable? object
end
Expand Down
15 changes: 15 additions & 0 deletions lib/travis/api/v3/queries/scan_result.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
module Travis::API::V3
class Queries::ScanResult < RemoteQuery
params :id

def find
scanner_client.get_scan_result(id)
end

private

def scanner_client
@_scanner_client ||= ScannerClient.new(nil)
end
end
end
22 changes: 22 additions & 0 deletions lib/travis/api/v3/queries/scan_results.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
module Travis::API::V3
class Queries::ScanResults < Query
params :repository_id, :offset, :limit

def all
# Reset the scan status on viewing the reports
Repository.find(repository_id).update!(scan_failed_at: nil)

page = (offset.to_i / limit.to_i) + 1
scanner_client(repository_id).scan_results(
page.to_s,
limit
)
end

private

def scanner_client(repository_id)
@_scanner_client ||= ScannerClient.new(repository_id)
end
end
end
6 changes: 3 additions & 3 deletions lib/travis/api/v3/renderer/repository.rb
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
module Travis::API::V3
class Renderer::Repository < ModelRenderer
representation(:minimal, :id, :name, :slug)
representation(:standard, :id, :name, :slug, :description, :github_id, :vcs_id, :vcs_type, :github_language, :active, :private, :owner, :owner_name, :vcs_name, :default_branch, :starred, :managed_by_installation, :active_on_org, :migration_status, :history_migration_status, :shared, :config_validation, :server_type)
representation(:experimental, :id, :name, :slug, :description, :vcs_id, :vcs_type, :github_id, :github_language, :active, :private, :owner, :default_branch, :starred, :current_build, :last_started_build, :next_build_number, :server_type)
representation(:internal, :id, :name, :slug, :github_id, :vcs_id, :vcs_type, :active, :private, :owner, :default_branch, :private_key, :token, :user_settings, :server_type)
representation(:standard, :id, :name, :slug, :description, :github_id, :vcs_id, :vcs_type, :github_language, :active, :private, :owner, :owner_name, :vcs_name, :default_branch, :starred, :managed_by_installation, :active_on_org, :migration_status, :history_migration_status, :shared, :config_validation, :server_type, :scan_failed_at)
representation(:experimental, :id, :name, :slug, :description, :vcs_id, :vcs_type, :github_id, :github_language, :active, :private, :owner, :default_branch, :starred, :current_build, :last_started_build, :next_build_number, :server_type, :scan_failed_at)
representation(:internal, :id, :name, :slug, :github_id, :vcs_id, :vcs_type, :active, :private, :owner, :default_branch, :private_key, :token, :user_settings, :server_type, :scan_failed_at)
representation(:additional, :allow_migration)

hidden_representations(:experimental, :internal)
Expand Down
27 changes: 27 additions & 0 deletions lib/travis/api/v3/renderer/scan_result.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
module Travis::API::V3
class Renderer::ScanResult < ModelRenderer
representation(:minimal, :id, :created_at, :formatted_content, :issues_found, :job_id, :build_id, :job_number, :build_number, :job_finished_at,
:commit_sha, :commit_compare_url, :commit_branch, :build_created_by)
representation(:standard, *representations[:minimal])

def build_created_by
job = Travis::API::V3::Models::Job.find(model.job_id)
build = Travis::API::V3::Models::Build.find(job.source_id)
return nil unless creator = build.sender
{
'@type' => build.sender_type.downcase,
'@href' => created_by_href(creator),
'@representation' => 'minimal'.freeze,
'id' => creator.id,
'login' => creator.login
}
end

private def created_by_href(creator)
case creator
when V3::Models::Organization then Renderer.href(:organization, script_name: script_name, id: creator.id)
when V3::Models::User then Renderer.href(:user, script_name: script_name, id: creator.id)
end
end
end
end
6 changes: 6 additions & 0 deletions lib/travis/api/v3/renderer/scan_results.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
module Travis::API::V3
class Renderer::ScanResults < CollectionRenderer
type :scan_results
collection_key :scan_results
end
end
10 changes: 10 additions & 0 deletions lib/travis/api/v3/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -283,6 +283,16 @@ module Routes
end
end

resource :scan_results do
route '/scan_results'
get :all
end

resource :scan_result do
route '/scan_result/{scan_result.id}'
get :find
end

resource :user do
capture id: :digit
route '/user/{user.id}'
Expand Down
84 changes: 84 additions & 0 deletions lib/travis/api/v3/scanner_client.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@

# frozen_string_literal: true

module Travis::API::V3
class ScannerClient
class ConfigurationError < StandardError; end

def initialize(repository_id)
@repository_id = repository_id
end

def scan_results(page, limit)
query_string = query_string_from_params(
repository_id: @repository_id,
limit: limit,
page: page || '1',
)
response = connection.get("/scan_results?#{query_string}")

handle_errors_and_respond(response) do |body|
scan_results = body['scan_results'].map do |scan_result|
Travis::API::V3::Models::ScanResult.new(scan_result)
end

Travis::API::V3::Models::ScannerCollection.new(scan_results, body.fetch('total_count', 0))
end
end

def get_scan_result(id)
response = connection.get("/scan_results/#{id}")
handle_errors_and_respond(response) do |body|
Travis::API::V3::Models::ScanResult.new(body.fetch('scan_result'))
end
end

private

def handle_errors_and_respond(response)
case response.status
when 200, 201
yield(response.body) if block_given?
when 202
true
when 204
true
when 400
raise Travis::API::V3::ClientError, response.body&.fetch('error', '')
when 403
raise Travis::API::V3::InsufficientAccess, response.body&.fetch('rejection_code', '')
when 404
raise Travis::API::V3::NotFound, response.body&.fetch('error', '')
when 422
raise Travis::API::V3::UnprocessableEntity, response.body&.fetch('error', '')
else
raise Travis::API::V3::ServerError, 'Scanner API failed'
end
end

def connection(timeout: 20)
@connection ||= Faraday.new(url: scanner_url, ssl: { ca_path: '/usr/lib/ssl/certs' }) do |conn|
conn.headers[:Authorization] = "Token token=\"#{scanner_token}\""
conn.headers['Content-Type'] = 'application/json'
conn.request :json
conn.response :json
conn.options[:open_timeout] = timeout
conn.options[:timeout] = timeout
conn.use OpenCensus::Trace::Integrations::FaradayMiddleware if Travis::Api::App::Middleware::OpenCensus.enabled?
conn.adapter :net_http
end
end

def scanner_url
Travis.config.scanner.url || raise(ConfigurationError, 'No Scanner API URL configured!')
end

def scanner_token
Travis.config.scanner.token || raise(ConfigurationError, 'No Scanner Auth Token configured!')
end

def query_string_from_params(params)
params.delete_if { |_, v| v.nil? || v.empty? }.to_query
end
end
end
2 changes: 2 additions & 0 deletions lib/travis/api/v3/services.rb
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@ module Services
Leads = Module.new { extend Services }
Lint = Module.new { extend Services }
Log = Module.new { extend Services }
ScanResult = Module.new { extend Services }
ScanResults = Module.new { extend Services }
Messages = Module.new { extend Services }
Organization = Module.new { extend Services }
Organizations = Module.new { extend Services }
Expand Down
19 changes: 19 additions & 0 deletions lib/travis/api/v3/services/scan_result/find.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
module Travis::API::V3
class Services::ScanResult::Find < Service
params :id

def run!
raise LoginRequired unless access_control.full_access_or_logged_in?
scan_result = query(:scan_result).find

repository = Travis::API::V3::Models::Repository.find(scan_result.repository_id)
check_access(repository)

result scan_result
end

def check_access(repository)
access_control.permissions(repository).check_scan_results!
end
end
end
19 changes: 19 additions & 0 deletions lib/travis/api/v3/services/scan_results/all.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
module Travis::API::V3
class Services::ScanResults::All < Service
params :repository_id
paginate

def run!
raise LoginRequired unless access_control.full_access_or_logged_in?

repository = Travis::API::V3::Models::Repository.find(params['repository_id'])
check_access(repository)

result query(:scan_results).all
end

def check_access(repository)
access_control.permissions(repository).check_scan_results!
end
end
end
Loading