forked from caldwell/jenkins-sparkle-appcast-plugin
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Initial version (works on test data)
- Loading branch information
Showing
7 changed files
with
240 additions
and
0 deletions.
There are no files selected for viewing
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
*~ | ||
work |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
jruby-1.7.0 |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
source :rubygems | ||
|
||
gem "jenkins-plugin-runtime", "~> 0.2.3" | ||
gem "builder" | ||
gem "mime-types" | ||
|
||
group :development do | ||
gem "jpi" | ||
end |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
GEM | ||
remote: http://rubygems.org/ | ||
specs: | ||
builder (3.1.4) | ||
jenkins-plugin-runtime (0.2.3) | ||
json | ||
slop (~> 3.0.2) | ||
jenkins-war (1.475) | ||
jpi (0.3.8) | ||
bundler | ||
jenkins-plugin-runtime (~> 0.2.3) | ||
jenkins-war (> 1.427) | ||
rubyzip | ||
thor | ||
json (1.7.6) | ||
json (1.7.6-java) | ||
mime-types (1.19) | ||
rubyzip (0.9.9) | ||
slop (3.0.4) | ||
thor (0.16.0) | ||
|
||
PLATFORMS | ||
java | ||
ruby | ||
|
||
DEPENDENCIES | ||
builder | ||
jenkins-plugin-runtime (~> 0.2.3) | ||
jpi | ||
mime-types |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,123 @@ | ||
require 'java' | ||
require 'builder' | ||
require 'pathname' | ||
require 'fileutils' | ||
require 'time' | ||
require 'mime/types' | ||
|
||
# Grab the good builds and the changelogs from the bad builds (so the good | ||
# build that follows a bad build gets the bad build's changelog appended to | ||
# its own). | ||
def get_builds(latest_build) | ||
b=latest_build | ||
builds=[] | ||
c=[] | ||
begin | ||
c += b.getChangeSet.getItems.map { |c| c.getMsg } | ||
if b.getResult.to_s == 'SUCCESS' | ||
builds.push({ :build => b, :changes => c}) | ||
c=[] | ||
end | ||
end while (b=b.getPreviousBuild) #getPreviousSuccessfulBuild | ||
builds | ||
end | ||
|
||
# One line per change entry right now. Consider moving to markdown. | ||
def format_changelog(changes) | ||
changes.map {|c| c+"\n" }.join('') | ||
end | ||
|
||
# The mime-types gem doesn't have x-apple-diskimage by default. Consider giving them a pull request. | ||
MIME::Types.add(MIME::Type.from_hash('Content-Type' => 'application/x-apple-diskimage', | ||
'Content-Transfer-Encoding' => '8bit', | ||
'Extensions' => ['dmg'])) | ||
|
||
class Sparkle_appcastPublisher < Jenkins::Tasks::Publisher | ||
|
||
display_name "Publish Sparkle Appcast (RSS)" | ||
|
||
attr_reader :url_base, :output_directory, :author, :title, :description, :rss_filename | ||
|
||
# Invoked with the form parameters when this extension point | ||
# is created from a configuration screen. | ||
def initialize(attrs = {}) | ||
attrs.each { |k, v| v = nil if v == ""; instance_variable_set "@#{k}", v } | ||
@output_directory = Pathname.new(attrs["output_directory"]) if attrs["output_directory"] | ||
end | ||
|
||
## | ||
# Runs before the build begins | ||
# | ||
# @param [Jenkins::Model::Build] build the build which will begin | ||
# @param [Jenkins::Model::Listener] listener the listener for this build. | ||
def prebuild(build, listener) | ||
# do any setup that needs to be done before this build runs. | ||
end | ||
|
||
## | ||
# Runs the step over the given build and reports the progress to the listener. | ||
# | ||
# @param [Jenkins::Model::Build] build on which to run this step | ||
# @param [Jenkins::Launcher] launcher the launcher that can run code on the node running this build | ||
# @param [Jenkins::Model::Listener] listener the listener for this build. | ||
def perform(build_ruby, launcher, listener) | ||
build = build_ruby.native | ||
unless build.getResult.to_s == 'SUCCESS' | ||
listener.info "Not writing Appcast file for failed build." | ||
return | ||
end | ||
|
||
project_name = build.project.getDisplayName | ||
builds = get_builds(build) | ||
|
||
@rss_filename ||= project_name + ".rss" | ||
|
||
# Build symlink tree and keep track of URLs and filenames | ||
builds.each do |b| | ||
build = b[:build] | ||
version_dir = project_name + "-" + build.number.to_s | ||
raise "Can't build appcast #{@rss_filename}: Too many artifacts" if build.getArtifacts.size > 1 | ||
first_artifact = build.getArtifacts.first.getFile | ||
b[:file] = @output_directory + version_dir + first_artifact.getName | ||
FileUtils.mkdir_p @output_directory + version_dir | ||
FileUtils.ln_sf first_artifact.getAbsolutePath, b[:file] | ||
b[:url] = "#{@url_base}/#{version_dir}/#{first_artifact.getName}" | ||
end | ||
|
||
rss = Builder::XmlMarkup.new(:indent => 2) | ||
rss.instruct! | ||
rss_s = rss.rss("version" => "2.0", | ||
"xmlns:content" => "http://purl.org/rss/1.0/modules/content/", | ||
"xmlns:dc" => "http://purl.org/dc/elements/1.1/", | ||
"xmlns:sparkle" => "http://www.andymatuschak.org/xml-namespaces/sparkle", | ||
) { | ||
rss.channel { | ||
rss.author @author || "Jenkins" | ||
rss.updated Time.now.to_s | ||
rss.link "#{@url_base}/#{@rss_filename}" | ||
rss.title @title || "#{project_name} Versions" | ||
rss.description @description || "#{project_name} Versions" | ||
|
||
builds.each do |b| | ||
rss.item { | ||
rss.link b[:url] | ||
rss.title "#{project_name} #{b[:build].number} Released" | ||
rss.updated File.mtime(b[:file]) | ||
rss.enclosure("url" => b[:url], | ||
"type" => MIME::Types.type_for(b[:file].to_s).last || "application/octet-stream", | ||
"length" => File.size(b[:file]), | ||
"sparkle:version" => b[:build].number) | ||
rss.pubDate File.ctime(b[:file]) | ||
rss.dc(:date, File.ctime(b[:file]).iso8601) | ||
rss.description { rss.cdata! format_changelog(b[:changes]) } | ||
} | ||
end | ||
} | ||
} | ||
|
||
listener.info "Writing Appcast file \"#{@output_directory + @rss_filename}\"..." | ||
File.open(@output_directory + @rss_filename, "w") { |f| f.write(rss_s) } | ||
|
||
end | ||
|
||
end |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
Jenkins::Plugin::Specification.new do |plugin| | ||
plugin.name = "sparkle-appcast" | ||
plugin.display_name = "Sparkle Appcast (RSS) Plugin" | ||
plugin.version = '0.1.0' | ||
plugin.description = 'Publishes an Appcast (RSS) Feed for use with the Sparkle auto-update library' | ||
|
||
# You should create a wiki-page for your plugin when you publish it, see | ||
# https://wiki.jenkins-ci.org/display/JENKINS/Hosting+Plugins#HostingPlugins-AddingaWikipage | ||
# This line makes sure it's listed in your POM. | ||
plugin.url = 'https://wiki.jenkins-ci.org/display/JENKINS/Sparkle+Appcast+Plugin' | ||
|
||
# The first argument is your user name for jenkins-ci.org. | ||
plugin.developed_by "david", "David Caldwell <[email protected]>" | ||
|
||
# This specifies where your code is hosted. | ||
# Alternatives include: | ||
# :git => 'git://repo.or.cz/sparkle-appcast-plugin.git' | ||
# :svn => 'https://svn.jenkins-ci.org/trunk/hudson/plugins/sparkle-appcast-plugin' | ||
plugin.uses_repository :github => 'caldwell/jenkins-sparkle-appcast-plugin' | ||
|
||
# This is a required dependency for every ruby plugin. | ||
plugin.depends_on 'ruby-runtime', '0.10' | ||
|
||
# This is a sample dependency for a Jenkins plugin, 'git'. | ||
#plugin.depends_on 'git', '1.1.11' | ||
end |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
<% | ||
f = taglib("/lib/form") | ||
f.block do | ||
%> | ||
|
||
<table style="margin-left: 30px;"> | ||
<% | ||
f.entry :title => 'Output Directory', | ||
:field => :output_directory, | ||
:description => 'Where to build the symlink tree and appcast rss file.' do | ||
f.textbox :clazz => 'required', :default => '' | ||
end | ||
|
||
f.entry :title => 'URL Base', | ||
:field => :url_base, | ||
:description => 'Where the feed url will be (eg. "http://example.com/some_directory")' do | ||
f.textbox :clazz => 'required', :default => 'http://example.com/some_directory' | ||
end | ||
|
||
f.entry :title => 'Appcast Filename', | ||
:field => :rss_filename, | ||
:description => 'Filename for the generated Appcast (if left blank it will use the project name plus ".rss"")' do | ||
f.textbox :clazz => 'optional', :default => '' | ||
end | ||
|
||
f.entry :title => 'RSS Author', | ||
:field => :author, | ||
:description => 'Author field in the Appcast RSS. Not shown by Sparkle.' do | ||
f.textbox :clazz => 'optional', :default => '' | ||
end | ||
|
||
f.entry :title => 'RSS Title', | ||
:field => :title, | ||
:description => 'Title field in the Appcast RSS. Not shown by Sparkle.' do | ||
f.textbox :clazz => 'optional', :default => '' | ||
end | ||
|
||
f.entry :title => 'RSS Description', | ||
:field => :description, | ||
:description => 'Description field in the Appcast RSS. Not shown by Sparkle.' do | ||
f.textbox :clazz => 'optional', :default => '' | ||
end | ||
|
||
%> | ||
</table> | ||
|
||
<% | ||
end | ||
%> |