class RubyForge
def add_file(group_name, package_name, release_name, userfile)
def add_file(group_name, package_name, release_name, userfile) type_id = @userconfig["type_id"] group_id = lookup "group", group_name package_id = lookup "package", package_name release_id = (Integer === release_name) ? release_name : lookup("release", package_name)[release_name] url = "/releases/#{release_id}/files.js" userfile = open userfile, 'rb' type_id ||= userfile.path[%r|\.[^\./]+$|] type_id = (lookup "type", type_id rescue lookup "type", ".oth") processor_id = @userconfig["processor_id"] processor_id ||= "Any" processor_id = lookup "processor", processor_id form = { "file[filename]" => File.basename(userfile.path), "file[processor_id]" => processor_id, "file[type_id]" => type_id, "contents" => userfile.read } run url, form end
def add_release(group_id, package_id, release_name, *files)
def add_release(group_id, package_id, release_name, *files) group_id = lookup "group", group_id package_id = lookup "package", package_id release_date = @userconfig["release_date"] release_notes = @userconfig["release_notes"] release_changes = @userconfig["release_changes"] preformatted = @userconfig["preformatted"] release_date ||= Time.now.strftime("%Y-%m-%d %H:%M") release_notes = IO::read(release_notes) if test(?e, release_notes) if release_notes release_changes = IO::read(release_changes) if test(?e, release_changes) if release_changes preformatted = preformatted ? 1 : 0 form = { "release[name]" => release_name, "release[release_date]" => release_date, "release[notes]" => release_notes, "release[changes]" => release_changes, "release[preformatted]" => preformatted, } url = "/packages/#{package_id}/releases" json = run url, form release_id = JSON.parse(json)["release_id"].to_i rescue nil unless release_id then puts json if $DEBUG raise "Couldn't get release_id, upload failed?" end # FIXME #raise "Invalid package_id #{package_id}" if html[/Invalid package_id/] #raise "You have already released this version." if html[/That filename already exists in this project/] files.each do |file| add_file(group_id, package_id, release_id, file) end package_name = @autoconfig["package_ids"].invert[package_id] raise "unknown package name for #{package_id}" if package_name.nil? @autoconfig["release_ids"][package_name] ||= {} @autoconfig["release_ids"][package_name][release_name] = release_id save_autoconfig release_id end
def client
def client return @client if @client @client = RubyForge::Client::new ENV["HTTP_PROXY"] @client.debug_dev = STDERR if ENV["RUBYFORGE_DEBUG"] || ENV["DEBUG"] || $DEBUG @client end
def configure opts = {}
def configure opts = {} user_path = CONFIG_F dir, file = File.split(user_path) @userconfig = if test(?e, user_path) then YAML.load_file(user_path) else CONFIG end.merge(opts) @autoconfig_path = File.join(dir, file.sub(/^user/, 'auto')) @autoconfig = if test(?e, @autoconfig_path) then YAML.load_file(@autoconfig_path) else CONFIG["rubyforge"].dup end @autoconfig["type_ids"] = CONFIG['rubyforge']['type_ids'].dup raise "no <username>" unless @userconfig["username"] raise "no <password>" unless @userconfig["password"] self end
def create_package(group_id, package_name)
def create_package(group_id, package_name) page = "/groups/#{group_id}/packages" group_id = lookup "group", group_id is_private = @userconfig["is_private"] is_public = is_private ? 0 : 1 form = { "package[name]" => package_name, "package[is_public]" => is_public } run page, form group_name = @autoconfig["group_ids"].invert[group_id] scrape_project(group_name) end
def delete_package(group_id, package_id)
def delete_package(group_id, package_id) group_id = lookup "group", group_id package_id = lookup "package", package_id package_name = @autoconfig["package_ids"].invert[package_id] @autoconfig["package_ids"].delete package_name @autoconfig["release_ids"].delete package_name save_autoconfig url = "/packages/#{package_id}" run url, {"_method" => "delete"} end
def force
def force @userconfig['force'] end
def get_via_rest_api(path)
def get_via_rest_api(path) url = "#{self.uri}#{path}" puts "Hitting REST API: #{url}" if $DEBUG JSON.parse(client.get_content(url, {}, {}, @userconfig)) end
def initialize(userconfig=nil, autoconfig=nil, opts=nil)
def initialize(userconfig=nil, autoconfig=nil, opts=nil) # def initialize(userconfig=CONFIG_F, opts={}) @userconfig, @autoconfig = userconfig, autoconfig @autoconfig ||= CONFIG["rubyforge"].dup @userconfig.merge! opts if opts @client = nil @uri = nil end
def login ; end
def login ; end
def logout ; end
def logout ; end
def lookup(type, val) # :nodoc:
def lookup(type, val) # :nodoc: unless Fixnum === val then key = val.to_s val = @autoconfig["#{type}_ids"][key] raise "no <#{type}_id> configured for <#{ key }>" unless val end val end
def post_news(group_id, subject, body)
def post_news(group_id, subject, body) # TODO - what was the post_changes parameter for? form = { "news_byte[summary]" => subject, "news_byte[details]" => body } group_id = lookup "group", group_id url = "/groups/#{group_id}/news_bytes" run url, form end
def run(page, form, extheader={}) # :nodoc:
def run(page, form, extheader={}) # :nodoc: uri = self.uri + page puts "client.post_content #{uri.inspect}, #{form.inspect}, #{extheader.inspect}" if $DEBUG response = client.post_content uri, form, extheader, @userconfig puts response if $DEBUG response end
def save_autoconfig
def save_autoconfig File.open(@autoconfig_path, "w") do |file| YAML.dump @autoconfig, file end end
def scrape_config
def scrape_config username = @userconfig['username'] %w(group package processor release).each do |type| @autoconfig["#{type}_ids"].clear if @autoconfig["#{type}_ids"] end json = get_via_rest_api "/users/#{username}/groups.js" projects = json.collect {|group| group['group']['unix_group_name'] } puts "Fetching #{projects.size} projects" projects.each do |project| scrape_project(project) end end
def scrape_project(project)
def scrape_project(project) data = { "group_ids" => {}, "package_ids" => {}, "processor_ids" => Hash.new { |h,k| h[k] = {} }, "release_ids" => Hash.new { |h,k| h[k] = {} }, } unless data["group_ids"].has_key? project then json = get_via_rest_api "/groups/#{project}.js" group_id = json["group"]["group_id"].to_i data["group_ids"][project] = group_id end # Get project's packages json = get_via_rest_api "/groups/#{project}/packages.js" json.each do |package| data["package_ids"][package["package"]["name"]] = package["package"]["package_id"] # Get releases for this package json = get_via_rest_api "/packages/#{package["package"]["package_id"]}/releases.js" json.each do |release| data["release_ids"][package["package"]["name"]][release["name"]] = release["release_id"] end end # Get processor ids if @autoconfig['processor_ids'].nil? || @autoconfig['processor_ids'].empty? puts "Fetching processor ids" if $DEBUG json = get_via_rest_api "/processors.js" json.each do |processor| data["processor_ids"][processor["processor"]["name"]] = processor["processor"]["processor_id"] end end data.each do |key, val| @autoconfig[key] ||= {} @autoconfig[key].merge! val end save_autoconfig end
def setup
def setup FileUtils::mkdir_p RUBYFORGE_D, :mode => 0700 unless test ?d, RUBYFORGE_D test ?e, CONFIG_F and FileUtils::mv CONFIG_F, "#{CONFIG_F}.bak" config = CONFIG.dup config.delete "rubyforge" open(CONFIG_F, "w") { |f| f.write YAML.dump(config) } edit = (ENV["EDITOR"] || ENV["EDIT"] || "vi") + " '#{CONFIG_F}'" system edit or puts "edit '#{CONFIG_F}'" end
def uri
def uri uri = @userconfig['uri'] abort "Using new REST api, but uri isn't api.rubyforge.org. n `rubyforge setup` and fix please" if uri =~ /rubyforge.org/ and uri !~ /api.rubyforge.org/ @uri ||= URI.parse uri end