From 2f6d5c75fc1fece5fc10cc7c45ad59cf6b820d64 Mon Sep 17 00:00:00 2001 From: Christoph Helma Date: Wed, 7 Mar 2012 17:13:48 +0000 Subject: error and dataset tests added, wait_for_task moved to URI.to_object --- lib/error.rb | 10 ++++--- lib/opentox.rb | 20 +++++++------ lib/overwrite.rb | 27 +++++++++++++++-- lib/rest-client-wrapper.rb | 73 +++++++++++++--------------------------------- test/dataset.rb | 57 ++++++++++++++++++++++++++++++++++++ test/error.rb | 35 ++++++++++++++++++++++ 6 files changed, 154 insertions(+), 68 deletions(-) create mode 100644 test/dataset.rb create mode 100644 test/error.rb diff --git a/lib/error.rb b/lib/error.rb index b65651f..2033c1e 100644 --- a/lib/error.rb +++ b/lib/error.rb @@ -5,7 +5,9 @@ class RuntimeError attr_accessor :report, :http_code def initialize message super message + self.set_backtrace message.backtrace if message.is_a? Exception @http_code ||= 500 + puts self.class @report = OpenTox::ErrorReport.create self $logger.error "\n"+@report.to_turtle end @@ -77,9 +79,10 @@ module OpenTox errorDetails += "REST paramenters:\n#{error.request.args.inspect}" end error.respond_to?(:http_code) ? statusCode = error.http_code : statusCode = 500 + puts error.inspect if error.respond_to? :response - statusCode = error.response.code - message = error.body + statusCode = error.response.code if error.response + message = error.response.body end statusCode = error.http_code if error.respond_to? :http_code report.rdf << [subject, RDF::OT.statusCode, statusCode ] @@ -87,7 +90,6 @@ module OpenTox # TODO: remove kludge for old task services report.http_code = statusCode report.rdf << [subject, RDF::OT.message , message ] - errorDetails += "\nBacktrace:\n" + error.backtrace.short_backtrace if error.respond_to?(:backtrace) and error.backtrace report.rdf << [subject, RDF::OT.errorDetails, errorDetails ] # TODO Error cause @@ -139,7 +141,7 @@ module Kernel raise stderr.strip if !status.success? return stdout rescue Exception - internal_server_error "'#{cmd}' failed with: '#{$!.message}'" + internal_server_error $! end alias_method :system!, :system diff --git a/lib/opentox.rb b/lib/opentox.rb index 566c458..9ba64bd 100644 --- a/lib/opentox.rb +++ b/lib/opentox.rb @@ -70,8 +70,7 @@ module OpenTox def delete headers={} headers[:subjectid] ||= @subjectid - headers[:accept] ||= 'application/rdf+xml' - @response = RestClientWrapper.delete(@uri.to_s,:subjectid => @subjectid) + @response = RestClientWrapper.delete(@uri.to_s,nil,nil,headers) end # class methods @@ -82,23 +81,26 @@ module OpenTox subjectid ? eval("#{self}.new(\"#{uri}\", #{subjectid})") : eval("#{self}.new(\"#{uri}\")") end - def from_file service_uri, file, subjectid=nil - RestClientWrapper.post(service_uri, :file => File.new(file), :subjectid => subjectid).chomp.to_object + def from_file service_uri, filename, subjectid=nil + file = File.new filename + uri = RestClientWrapper.post(service_uri, {:file => file}, {:subjectid => subjectid, :content_type => file.mime_type, :accept => "text/uri-list"}) + puts uri end def all service_uri, subjectid=nil - uris = RestClientWrapper.get(service_uri, nil, {:accept => 'text/uri-list'}).split("\n").compact + uris = RestClientWrapper.get(service_uri, {}, :accept => 'text/uri-list').split("\n").compact uris.collect{|uri| subjectid ? eval("#{self}.new(\"#{uri}\", #{subjectid})") : eval("#{self}.new(\"#{uri}\")")} end end - # create default classes - SERVICES.each do |s| - eval "class #{s} + # create default OpenTox classes + SERVICES.each do |klass| + c = Class.new do include OpenTox extend OpenTox::ClassMethods - end" + end + OpenTox.const_set klass,c end end diff --git a/lib/overwrite.rb b/lib/overwrite.rb index f0dcda9..c7a1d43 100644 --- a/lib/overwrite.rb +++ b/lib/overwrite.rb @@ -23,8 +23,13 @@ module URI end def self.accessible? uri, subjectid=nil - Net::HTTP.get_response(URI.parse(uri)) - true + if URI.task? uri + # just ry to get a response, valid tasks may return codes > 400 + Net::HTTP.get_response(URI.parse(uri)) + true + else + Net::HTTP.get_response(URI.parse(uri)).code.to_i < 400 + end rescue false end @@ -36,5 +41,23 @@ module URI false end + def self.to_object uri, wait=true + + # TODO add waiting task + if task? uri and wait + t = OpenTox::Task.new(uri) + t.wait + uri = t.resultURI + end + + klass = + subjectid ? eval("#{self}.new(\"#{uri}\", #{subjectid})") : eval("#{self}.new(\"#{uri}\")") + end + end +class File + def mime_type + `file -ib #{self.path}`.chomp + end +end diff --git a/lib/rest-client-wrapper.rb b/lib/rest-client-wrapper.rb index 64c7d7e..e594729 100644 --- a/lib/rest-client-wrapper.rb +++ b/lib/rest-client-wrapper.rb @@ -13,7 +13,7 @@ module OpenTox # @param [optional,OpenTox::Task] waiting_task (can be a OpenTox::Subtask as well), progress is updated accordingly # @param [wait,Boolean] Set to false to NOT wait for task if result is a task # @return [RestClient::Response] REST call response - [:head,:get,:post,:put,:dealete].each do |method| + [:head,:get,:post,:put,:delete].each do |method| define_singleton_method method do |uri,payload={},headers={},waiting_task=nil, wait=true| @@ -25,64 +25,40 @@ module OpenTox args[:payload] = payload headers.each{ |k,v| headers.delete(k) if v==nil } if headers #remove keys with empty values, as this can cause problems args[:headers] = headers - @request = RestClient::Request.new(args) # check input bad_request_error "Invalid URI: '#{uri}'" unless URI.valid? uri - bad_request_error "Unreachable URI: '#{uri}'" unless URI.accessible? uri + not_found_error "URI '#{uri}' not found." unless URI.accessible? uri bad_request_error "Headers are not a hash: #{headers.inspect}" unless headers==nil or headers.is_a?(Hash) # make sure that no header parameters are set in the payload [:accept,:content_type,:subjectid].each do |header| bad_request_error "#{header} should be submitted in the headers" if payload and payload.is_a?(Hash) and payload[header] end - bad_request_error "waiting_task is not 'nil', OpenTox::SubTask or OpenTox::Task: #{waiting_task.class}" unless waiting_task.nil? or waiting_task.is_a?(OpenTox::Task) or waiting_task.is_a?(OpenTox::SubTask) + #bad_request_error "waiting_task is not 'nil', OpenTox::SubTask or OpenTox::Task: #{waiting_task.class}" unless waiting_task.nil? or waiting_task.is_a?(OpenTox::Task) or waiting_task.is_a?(OpenTox::SubTask) - - begin - @response = @request.execute do |response, request, result| - # ignore error codes from Task services (may contain eg 500 which causes exceptions in RestClient and RDF::Reader - rest_error "Response code is #{response.code}" unless response.code < 400 or URI.task? uri - return response - end - - return @response if @response.code==200 or !wait + # perform request + @request = RestClient::Request.new(args) + #begin + # do not throw RestClient exceptions in order to create a @response object (needed for error reports) in every case + @response = @request.execute { |response, request, result| return response } + # ignore error codes from Task services (may return error codes >= 400 according to API, which causes exceptions in RestClient and RDF::Reader) + raise OpenTox::RestCallError.new @request, @response, "Response code is #{@response.code}." unless @response.code < 400 or URI.task? uri + #return @response if @response.code==200 or !wait # wait for task - while @response.code==201 or @response.code==202 - @response = wait_for_task(@response, uri, waiting_task) - end - return @response + #while @response.code==201 or @response.code==202 + #@response = wait_for_task(@response, uri, waiting_task) + #end + @response - rescue - rest_error $!.message - end -=begin - rescue RestClient::RequestTimeout - raise OpenTox::Error @request, @response, $!.message - #received_error ex.message, 408, nil, {:rest_uri => uri, :headers => headers, :payload => payload} - rescue Errno::ETIMEDOUT - raise OpenTox::Error @request, @response, $!.message - #received_error ex.message, 408, nil, {:rest_uri => uri, :headers => headers, :payload => payload} - rescue Errno::ECONNREFUSED - raise OpenTox::Error $!.message - #received_error ex.message, 500, nil, {:rest_uri => uri, :headers => headers, :payload => payload} - rescue RestClient::ExceptionWithResponse - # error comming from a different webservice, - received_error ex.http_body, ex.http_code, ex.response.net_http_res.content_type, {:rest_uri => uri, :headers => headers, :payload => payload} - #rescue OpenTox::RestCallError => ex - # already a rest-error, probably comes from wait_for_task, just pass through - #raise ex - #rescue => ex - # some internal error occuring in rest-client-wrapper, just pass through - #raise ex - end -=end + #rescue + #rest_error $!.message + #end end end +=begin def wait_for_task( response, base_uri, waiting_task=nil ) - #TODO remove TUM hack - # @response.headers[:content_type] = "text/uri-list" if base_uri =~/tu-muenchen/ and @response.headers[:content_type] == "application/x-www-form-urlencoded;charset=UTF-8" task = nil case @response.headers[:content_type] @@ -97,7 +73,6 @@ module OpenTox rest_error "Unknown content-type for task : '"+@response.headers[:content_type].to_s+"'"+" base-uri: "+base_uri.to_s+" content: "+@response[0..200].to_s end - #LOGGER.debug "result is a task '"+task.uri.to_s+"', wait for completion" task.wait waiting_task unless task.completed? # maybe task was cancelled / error if task.errorReport @@ -111,18 +86,10 @@ module OpenTox end def self.rest_error message + puts message raise OpenTox::RestCallError.new @request, @response, message end -=begin - def self.bad_request_error message - raise OpenTox::Error.new message - end - - def self.not_found_error message - raise OpenTox::NotFoundError.new message - end - def self.received_error( body, code, content_type=nil, params=nil ) # try to parse body TODO diff --git a/test/dataset.rb b/test/dataset.rb new file mode 100644 index 0000000..13012bd --- /dev/null +++ b/test/dataset.rb @@ -0,0 +1,57 @@ +require 'test/unit' +$LOAD_PATH << File.join(File.dirname(__FILE__),'..','lib') +require File.join File.dirname(__FILE__),'..','lib','opentox-client.rb' + +class DatasetTest < Test::Unit::TestCase + +=begin + def test_post_get_delete + service_uri = "http://ot-dev.in-silico.ch/dataset" + dataset = OpenTox::Dataset.create service_uri + assert_match /#{service_uri}/, dataset.uri.to_s + puts dataset.uri + puts dataset.class + puts dataset.to_yaml + metadata = dataset.metadata + puts dataset.class + assert_equal RDF::OT.Dataset, metadata[RDF.type] + assert_equal dataset.uri, metadata[RDF::XSD.anyURI] + dataset.delete + end + def test_all + datasets = OpenTox::Dataset.all "http://ot-dev.in-silico.ch/dataset" + assert_equal OpenTox::Dataset, datasets.first.class + end + + def test_create + d = OpenTox::Dataset.create "http://ot-dev.in-silico.ch/dataset" + assert_equal OpenTox::Dataset, d.class + puts d.delete + assert_raise OpenTox::NotFoundError do + puts d.get(:accept => 'application/x-yaml') + end + end +=end + + def test_create_from_file + d = OpenTox::Dataset.from_file "http://ot-dev.in-silico.ch/dataset", "data/EPAFHM.mini.csv" + assert_equal OpenTox::Dataset, d.class + puts d.inspect + + end + +=begin + def test_save + d = OpenTox::Dataset.create "http://ot-dev.in-silico.ch/dataset" + d.metadata + d.metadata[RDF::DC.title] = "test" + d.save + # TODO: save does not work with datasets + #puts d.response.code.inspect + #assert_equal "test", d.metadata[RDF::DC.title] # should reload metadata + d.delete + end +=end + + +end diff --git a/test/error.rb b/test/error.rb new file mode 100644 index 0000000..af5db52 --- /dev/null +++ b/test/error.rb @@ -0,0 +1,35 @@ +require 'test/unit' +$LOAD_PATH << File.join(File.dirname(__FILE__),'..','lib') +require File.join File.dirname(__FILE__),'..','lib','opentox-client.rb' + +class ErrorTest < Test::Unit::TestCase + + def test_bad_request + object = OpenTox::Feature.new "http://this-is-a/fantasy/url" + assert_raise OpenTox::BadRequestError do + response = object.get + end + end + + def test_error_methods + assert_raise OpenTox::NotFoundError do + not_found_error "This is a test" + end + end + + def test_exception + assert_raise Exception do + raise Exception.new "Basic Exception" + end + end + + def test_backtick + assert_raise OpenTox::InternalServerError do + `this call will not work` + end + assert_raise OpenTox::InternalServerError do + `ls inexisting_directory` + end + end + +end -- cgit v1.2.3