Skip to content
This repository has been archived by the owner on Apr 6, 2021. It is now read-only.

Artifact types #24

Merged
merged 3 commits into from
Sep 28, 2015
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
44 changes: 44 additions & 0 deletions lib/shanty/artifact.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
require 'uri'
require 'pathname'

module Shanty
# Public: Contain information on an artifact published by a project
class Artifact
attr_reader :file_extension, :plugin, :uri

# Public: Initialise an artifact instance
#
# file_extension - The extension of the artifact
# plugin - The plugin publishing the artifact
# uri - The URI to the object
#
# Fails if the URI is not absolute or
# the mime type is not valid
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like this last bit of the documentation may not be valid still.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

def initialize(file_extension, plugin, uri)
@file_extension = file_extension
@plugin = plugin
@uri = uri
validate_uri
end

def local?
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will need to add docs for this method.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

@uri.scheme == 'file'
end

def to_local_path
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Docs for this method, will need to mention the raise in the format described by the TomDoc spec (see http://tomdoc.org/, § "The Returns/Raises").

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

return @uri.path if local?
fail 'URI is not a local resource'
end

def to_s
@uri.to_s
end

private

def validate_uri
fail 'Scheme not present on URI' unless @uri.absolute?
fail 'URI is not absolute' if @uri.path.nil?
end
end
end
4 changes: 4 additions & 0 deletions lib/shanty/plugin.rb
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,10 @@ def projects
end
end

def artifacts(*)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suspect this should actually be def artifacts(_) as it should only ever take one project to return the artifacts for at a time.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

[]
end

def with_graph(graph)
callbacks = self.class.instance_variable_get(:@with_graph_callbacks)
return [] if callbacks.nil? || callbacks.empty?
Expand Down
14 changes: 14 additions & 0 deletions lib/shanty/plugins/rubygem_plugin.rb
Original file line number Diff line number Diff line change
@@ -1,14 +1,28 @@
require 'shanty/plugin'
require 'shanty/artifact'

module Shanty
# Public: Rubygem plugin for buildin gems.
class RubygemPlugin < Plugin
ARTIFACT_EXTENSION = 'gem'

tags :rubygem
projects '**/*.gemspec'
subscribe :build, :build_gem

def build_gem
system 'gem build *.gemspec'
end

def artifacts(project)
Dir[File.join(project.path, '*.gemspec')].flat_map do |file|
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Use project_tree.glob instead.

gemspec = Gem::Specification.load(file)
Artifact.new(
ARTIFACT_EXTENSION,
'rubygem',
URI("file://#{project.path}/#{gemspec.name}-#{gemspec.version}.#{ARTIFACT_EXTENSION}")
)
end
end
end
end
19 changes: 10 additions & 9 deletions lib/shanty/project.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ class Project
include ActsAsGraphVertex
include Env

attr_accessor :name, :path, :tags, :options
attr_accessor :artifacts, :name, :path, :tags, :options

# Multiton or Flyweight pattern - only allow once instance per unique path.
#
Expand Down Expand Up @@ -40,6 +40,7 @@ def initialize(path)
@path = path

@name = File.basename(path)
@artifacts = []
@plugins = []
@tags = []
@options = {}
Expand All @@ -61,6 +62,14 @@ def all_tags
(@tags + @plugins.flat_map { |plugin| plugin.class.tags }).map(&:to_sym).uniq
end

# Public: The artifacts published by this project and any artifacts published
# by any plugins operating on this project.
#
# Returns an Array of Artifacts representing published binaries
def all_artifacts
(@artifacts + @plugins.flat_map { |plugin| plugin.artifacts(project) }).uniq
end

def publish(name, *args)
@plugins.each do |plugin|
next unless plugin.subscribed?(name)
Expand All @@ -69,14 +78,6 @@ def publish(name, *args)
end
end

# Public: The absolute paths to the artifacts that would be created by this
# project when built, if any. This is expected to be overriden in subclasses.
#
# Returns an Array of Strings representing the absolute paths to the artifacts.
def artifact_paths
[]
end

# Public: Overriden String conversion method to return a simplified
# representation of this instance that doesn't include the cyclic
# parent/children attributes as defined by the ActsAsGraphVertex mixin.
Expand Down
40 changes: 40 additions & 0 deletions spec/lib/shanty/artifact_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
require 'shanty/artifact'

# All classes referenced belong to the shanty project
module Shanty
RSpec.describe(Artifact) do
subject { Artifact.new('html', 'test', uri) }

describe('#localfile') do
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm going to slightly reorder and rename these describe blocks as these should actually be real method names, eg. describe('#local?') or describe('.some_class_method').

let(:uri) { URI('file:///nic/kim/cage.html') }

it('works with a local file') do
expect(subject.local?).to be(true)
expect(subject.to_local_path).to eql('/nic/kim/cage.html')
end
end

describe('#noscheme') do
let(:uri) { URI('kim/cage.html') }
it('fails if there is no scheme present in the URI') do
expect { subject }.to raise_error('Scheme not present on URI')
end
end

describe('#notabsolute') do
let(:uri) { URI('file:kim/cage.html') }
it('fails if the URI is not an absolute path') do
expect { subject }.to raise_error('URI is not absolute')
end
end

describe('#remotefile') do
let(:uri) { URI('http://www.nic.com/kim/cage.html') }

it('fails when converting to a local path if the resource is not local') do
expect(subject.local?).to be(false)
expect { subject.to_local_path }.to raise_error('URI is not a local resource')
end
end
end
end
13 changes: 13 additions & 0 deletions spec/lib/shanty/plugins/rubygem_plugin_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -25,5 +25,18 @@ module Shanty
subject.build_gem
end
end

describe('#artifacts') do
it('lists the project artifacts') do
path = File.join(File.dirname(__FILE__), '..', '..', '..', '..')
result = subject.artifacts(Project.new(path))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You should change the:

include_context('basics')

above to

include_context('graph')

And then modify these two lines to:

FileUtils.write(File.join(project_path, 'foo.gemspec'), 'gemspec contents here')
result = subject.artifacts(project_path)

Adding the require 'fileutils' at the top.

Reasoning here is that we've elsewhere stopped testing using example projects in Shanty itself and have moved to making a temporary folder with more testable mocks. It avoids lots of weird relative path nonsense which makes moving things around a total pain.


expect(result.length).to eql(1)
expect(File.dirname(result.first.to_local_path)).to eql(path)
expect(result.first.file_extension).to eql('gem')
expect(result.first.local?).to be true
expect(result.first.uri.scheme).to eql('file')
end
end
end
end
6 changes: 3 additions & 3 deletions spec/lib/shanty/project_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -84,9 +84,9 @@ module Shanty
end
end

describe('#artifact_paths') do
it('defaults the paths to an empty array') do
expect(subject.artifact_paths).to eql([])
describe('#all_artifacts') do
it('defaults the artifacts to an empty array') do
expect(subject.all_artifacts).to eql([])
end
end

Expand Down