cosm-rb 0.0.5 → 0.0.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. data/lib/cosm-rb.rb +1 -0
  2. data/lib/cosm-rb/datapoint.rb +3 -2
  3. data/lib/cosm-rb/datastream.rb +4 -3
  4. data/lib/cosm-rb/exceptions.rb +5 -0
  5. data/lib/cosm-rb/feed.rb +4 -3
  6. data/lib/cosm-rb/key.rb +3 -2
  7. data/lib/cosm-rb/parsers/csv/datastream_defaults.rb +9 -3
  8. data/lib/cosm-rb/parsers/csv/feed_defaults.rb +13 -6
  9. data/lib/cosm-rb/parsers/json/datapoint_defaults.rb +5 -1
  10. data/lib/cosm-rb/parsers/json/datastream_defaults.rb +11 -6
  11. data/lib/cosm-rb/parsers/json/feed_defaults.rb +9 -3
  12. data/lib/cosm-rb/parsers/json/key_defaults.rb +6 -1
  13. data/lib/cosm-rb/parsers/json/search_result_defaults.rb +7 -1
  14. data/lib/cosm-rb/parsers/json/trigger_defaults.rb +5 -1
  15. data/lib/cosm-rb/parsers/xml/datapoint_defaults.rb +16 -10
  16. data/lib/cosm-rb/parsers/xml/datastream_defaults.rb +12 -6
  17. data/lib/cosm-rb/parsers/xml/feed_defaults.rb +18 -12
  18. data/lib/cosm-rb/parsers/xml/key_defaults.rb +31 -25
  19. data/lib/cosm-rb/parsers/xml/trigger_defaults.rb +17 -11
  20. data/lib/cosm-rb/search_result.rb +1 -1
  21. data/lib/cosm-rb/trigger.rb +3 -2
  22. data/lib/cosm-rb/version.rb +1 -1
  23. data/spec/cosm-rb/datapoint_spec.rb +18 -0
  24. data/spec/cosm-rb/datastream_spec.rb +43 -0
  25. data/spec/cosm-rb/feed_spec.rb +44 -0
  26. data/spec/cosm-rb/key_spec.rb +20 -0
  27. data/spec/cosm-rb/parsers/csv/datastream_defaults_spec.rb +9 -4
  28. data/spec/cosm-rb/parsers/csv/feed_defaults_spec.rb +35 -0
  29. data/spec/cosm-rb/parsers/json/datapoint_defaults_spec.rb +6 -0
  30. data/spec/cosm-rb/parsers/json/datastream_defaults_spec.rb +33 -10
  31. data/spec/cosm-rb/parsers/json/feed_defaults_spec.rb +6 -1
  32. data/spec/cosm-rb/parsers/json/key_defaults_spec.rb +6 -0
  33. data/spec/cosm-rb/parsers/json/search_result_defaults_spec.rb +6 -0
  34. data/spec/cosm-rb/parsers/json/trigger_defaults_spec.rb +6 -0
  35. data/spec/cosm-rb/parsers/xml/datastream_defaults_spec.rb +6 -0
  36. data/spec/cosm-rb/parsers/xml/feed_defaults_spec.rb +77 -2
  37. data/spec/cosm-rb/parsers/xml/key_defaults_spec.rb +6 -0
  38. data/spec/cosm-rb/parsers/xml/trigger_defaults_spec.rb +6 -0
  39. data/spec/cosm-rb/trigger_spec.rb +40 -0
  40. data/spec/support/datastream_helper.rb +25 -1
  41. metadata +5 -4
@@ -14,6 +14,7 @@ require 'cosm-rb/base'
14
14
  require 'cosm-rb/validations'
15
15
  require 'cosm-rb/object_extensions'
16
16
  require 'cosm-rb/nil_content'
17
+ require 'cosm-rb/exceptions'
17
18
  require 'cosm-rb/string_extensions'
18
19
  require 'cosm-rb/array_extensions'
19
20
  require 'cosm-rb/hash_extensions'
@@ -25,10 +25,11 @@ module Cosm
25
25
  return pass
26
26
  end
27
27
 
28
- def initialize(input = {})
28
+ def initialize(input = {}, format = nil)
29
+ raise InvalidFormatError, "Unknown format specified, currently we can only parse JSON or XML." unless [nil,:json,:xml].include?(format)
29
30
  if input.is_a? Hash
30
31
  self.attributes = input
31
- elsif input.strip[0...1].to_s == "{"
32
+ elsif format == :json || (format.nil? && input.strip[0...1].to_s == "{")
32
33
  self.attributes = from_json(input)
33
34
  else
34
35
  self.attributes = from_xml(input)
@@ -59,12 +59,13 @@ module Cosm
59
59
  return pass
60
60
  end
61
61
 
62
- def initialize(input = {})
62
+ def initialize(input = {}, format = nil)
63
+ raise InvalidFormatError, "Unknown format specified, currently we can only parse JSON, XML or CSV." unless [nil,:json,:xml,:csv].include?(format)
63
64
  if input.is_a? Hash
64
65
  self.attributes = input
65
- elsif input.strip[0...1].to_s == "{"
66
+ elsif format == :json || (format.nil? && input.strip[0...1].to_s == "{")
66
67
  self.attributes = from_json(input)
67
- elsif input.strip[0...1].to_s == "<"
68
+ elsif format == :xml || (format.nil? && input.strip[0...1].to_s == "<")
68
69
  self.attributes = from_xml(input)
69
70
  else
70
71
  self.attributes = from_csv(input)
@@ -0,0 +1,5 @@
1
+ module Cosm
2
+ class Error < StandardError; end
3
+ class InvalidFormatError < Error; end
4
+ class ParserError < Error; end
5
+ end
@@ -38,12 +38,13 @@ module Cosm
38
38
  return pass
39
39
  end
40
40
 
41
- def initialize(input = {}, csv_version = nil)
41
+ def initialize(input = {}, csv_version = nil, format = nil)
42
+ raise InvalidFormatError, "Unknown format specified, currently we can only parse JSON, XML or CSV." unless [nil,:json,:xml,:csv].include?(format)
42
43
  if input.is_a?(Hash)
43
44
  self.attributes = input
44
- elsif input.strip[0...1].to_s == "{"
45
+ elsif format == :json || (format.nil? && input.strip[0...1].to_s == "{")
45
46
  self.attributes = from_json(input)
46
- elsif input.strip[0...5].to_s == "<?xml" || input.strip[0...5].to_s == "<eeml"
47
+ elsif format == :xml || (format.nil? && input.strip[0...5].to_s == "<?xml" || input.strip[0...5].to_s == "<eeml")
47
48
  self.attributes = from_xml(input)
48
49
  else
49
50
  self.attributes = from_csv(input, csv_version)
@@ -33,10 +33,11 @@ module Cosm
33
33
  end
34
34
 
35
35
  # Build an instance from either a Hash, a JSON string, or an XML document
36
- def initialize(input = {})
36
+ def initialize(input = {}, format = nil)
37
+ raise InvalidFormatError, "Unknown format specified, currently we can only parse JSON or XML." unless [nil,:json,:xml].include?(format)
37
38
  if input.is_a?(Hash)
38
39
  self.attributes = input
39
- elsif input.strip[0...1].to_s == "{"
40
+ elsif format == :json || (format.nil? && input.strip[0...1].to_s == "{")
40
41
  self.attributes = from_json(input)
41
42
  else
42
43
  self.attributes = from_xml(input)
@@ -3,14 +3,20 @@ module Cosm
3
3
  module CSV
4
4
  module DatastreamDefaults
5
5
  def from_csv(csv, csv_version = nil)
6
- rows = Cosm::CSV.parse(csv.strip)
6
+ begin
7
+ rows = Cosm::CSV.parse(csv.strip)
8
+ rescue Exception => e
9
+ # this might be a FasterCSV or CSV exception depending on whether
10
+ # we are running under 1.8.x or 1.9.x
11
+ raise InvalidCSVError, e.message
12
+ end
7
13
  raise InvalidCSVError, "CSV is invalid. Can only construct a Cosm::Datastream object from a single row of data" if rows.size > 1
8
14
  row = rows.first
9
15
  raise InvalidCSVError, "CSV is invalid. Too many fields; must only be a single value, or a timestamp and a value" if row.size > 2
10
16
  if row.size == 2
11
- return { "updated" => row[0], "current_value" => row[1].to_s }
17
+ return { "updated" => row[0].to_s.strip, "current_value" => row[1].to_s.strip }
12
18
  else
13
- return { "current_value" => row[0].to_s }
19
+ return { "current_value" => row[0].to_s.strip }
14
20
  end
15
21
  end
16
22
  end
@@ -1,12 +1,18 @@
1
1
  module Cosm
2
2
  module Parsers
3
3
  module CSV
4
- class UnknownVersionError < StandardError ; end
5
- class InvalidCSVError < StandardError ; end
4
+ class UnknownVersionError < Cosm::ParserError ; end
5
+ class InvalidCSVError < Cosm::ParserError ; end
6
6
 
7
7
  module FeedDefaults
8
8
  def from_csv(csv, csv_version = nil)
9
- rows = Cosm::CSV.parse(csv.strip)
9
+ begin
10
+ rows = Cosm::CSV.parse(csv.strip)
11
+ rescue Exception => e
12
+ # this might be a FasterCSV or CSV exception depending on whether
13
+ # we are running under 1.8.x or 1.9.x
14
+ raise InvalidCSVError, e.message
15
+ end
10
16
  version = detect_version(rows, csv_version)
11
17
  hash = Hash.new
12
18
  if version == :v2
@@ -14,14 +20,15 @@ module Cosm
14
20
  hash["datastreams"] = rows.collect {|row|
15
21
  timestamp = {}
16
22
  if row.size == 3
17
- timestamp["updated"] = row[1]
23
+ timestamp["updated"] = row[1].strip
18
24
  end
19
- { "id" => row.first.to_s, "current_value" => row.last.to_s }.merge(timestamp)
25
+ { "id" => row.first.to_s.strip, "current_value" => row.last.to_s.strip }.merge(timestamp)
20
26
  }
21
27
  elsif version == :v1
28
+ raise InvalidCSVError, "CSV is invalid. Currently we can only accept CSV for your most recent set of values. You have submitted 2 rows of data." if rows.size > 1
22
29
  hash["datastreams"] = []
23
30
  rows.first.each_with_index do |current_value, stream_id|
24
- hash["datastreams"] << { "id" => stream_id.to_s, "current_value" => current_value }
31
+ hash["datastreams"] << { "id" => stream_id.to_s.strip, "current_value" => current_value.to_s.strip }
25
32
  end
26
33
  end
27
34
  hash["csv_version"] = version
@@ -3,7 +3,11 @@ module Cosm
3
3
  module JSON
4
4
  module DatapointDefaults
5
5
  def from_json(json)
6
- ::JSON.parse(json)
6
+ begin
7
+ ::JSON.parse(json)
8
+ rescue ::JSON::ParserError => e
9
+ raise InvalidJSONError, e.message
10
+ end
7
11
  end
8
12
  end
9
13
  end
@@ -3,12 +3,17 @@ module Cosm
3
3
  module JSON
4
4
  module DatastreamDefaults
5
5
  def from_json(json)
6
- hash = ::JSON.parse(json)
6
+ begin
7
+ hash = ::JSON.parse(json)
8
+ rescue ::JSON::ParserError => e
9
+ raise InvalidJSONError, e.message
10
+ end
11
+ raise InvalidJSONError, "JSON doesn't appear to be a hash" unless hash.is_a?(Hash)
7
12
  case hash['version']
8
- when '1.0.0'
9
- transform_1_0_0(hash)
10
- when '0.6-alpha', nil
13
+ when '0.6-alpha'
11
14
  transform_0_6_alpha(hash)
15
+ when '1.0.0', nil
16
+ transform_1_0_0(hash)
12
17
  end
13
18
  end
14
19
 
@@ -19,7 +24,7 @@ module Cosm
19
24
  hash["id"] = hash.delete("id")
20
25
  hash["updated"] = hash.delete("at")
21
26
  hash["current_value"] = hash.delete("current_value")
22
- hash["tags"] = hash["tags"].join(',') if hash["tags"]
27
+ hash["tags"] = join_tags(hash["tags"])
23
28
  if unit = hash.delete('unit')
24
29
  hash['unit_type'] = unit['type']
25
30
  hash['unit_symbol'] = unit['symbol']
@@ -37,7 +42,7 @@ module Cosm
37
42
  hash["max_value"] = hash["values"].first.delete("max_value")
38
43
  hash["min_value"] = hash["values"].first.delete("min_value")
39
44
  end
40
- hash["tags"] = hash["tags"].join(',') if hash["tags"]
45
+ hash["tags"] = join_tags(hash["tags"])
41
46
  if unit = hash.delete('unit')
42
47
  hash['unit_type'] = unit['type']
43
48
  hash['unit_symbol'] = unit['symbol']
@@ -1,17 +1,23 @@
1
1
  module Cosm
2
2
  module Parsers
3
3
  module JSON
4
+ class InvalidJSONError < Cosm::ParserError; end
4
5
  module FeedDefaults
5
6
 
6
7
  include Cosm::Helpers
7
8
 
8
9
  def from_json(json)
9
- hash = ::JSON.parse(json)
10
+ begin
11
+ hash = ::JSON.parse(json)
12
+ rescue ::JSON::ParserError => e
13
+ raise InvalidJSONError, e.message
14
+ end
15
+ raise InvalidJSONError, "JSON doesn't appear to be a hash" unless hash.is_a?(Hash)
10
16
  case hash['version']
11
- when '1.0.0'
12
- transform_1_0_0(hash)
13
17
  when '0.6-alpha', '0.6'
14
18
  transform_0_6_alpha(hash)
19
+ else
20
+ transform_1_0_0(hash)
15
21
  end
16
22
  end
17
23
 
@@ -3,7 +3,12 @@ module Cosm
3
3
  module JSON
4
4
  module KeyDefaults
5
5
  def from_json(json)
6
- hash = ::JSON.parse(json)["key"]
6
+ begin
7
+ hash = ::JSON.parse(json)["key"]
8
+ rescue ::JSON::ParserError => e
9
+ raise InvalidJSONError, e.message
10
+ end
11
+ raise InvalidJSONError, "JSON doesn't appear to be a hash" unless hash.is_a?(Hash)
7
12
  hash["id"] = hash.delete("id")
8
13
  hash["key"] = hash.delete("api_key")
9
14
  hash
@@ -5,7 +5,13 @@ module Cosm
5
5
  include FeedDefaults
6
6
 
7
7
  def from_json(json)
8
- hash = ::JSON.parse(json)
8
+ begin
9
+ hash = ::JSON.parse(json)
10
+ rescue ::JSON::ParserError => e
11
+ raise InvalidJSONError, e.message
12
+ end
13
+ raise InvalidJSONError, "JSON doesn't appear to be a hash" unless hash.is_a?(Hash)
14
+
9
15
  hash['results'] = hash['results'].collect do |feed|
10
16
  transform_1_0_0(feed)
11
17
  end
@@ -3,7 +3,11 @@ module Cosm
3
3
  module JSON
4
4
  module TriggerDefaults
5
5
  def from_json(json)
6
- ::JSON.parse(json)
6
+ begin
7
+ ::JSON.parse(json)
8
+ rescue ::JSON::ParserError => e
9
+ raise InvalidJSONError, e.message
10
+ end
7
11
  end
8
12
  end
9
13
  end
@@ -3,16 +3,22 @@ module Cosm
3
3
  module XML
4
4
  module DatapointDefaults
5
5
  def from_xml(xml)
6
- xml = Nokogiri.parse(xml)
7
- hash = {}
8
- environment = xml.at_xpath("//xmlns:environment")
9
- raise InvalidXMLError, "Missing 'environment' node from base node" if environment.nil?
10
- data = environment.at_xpath("xmlns:data")
11
- datapoint = data.at_xpath("xmlns:datapoints")
12
- value = datapoint.at_xpath("xmlns:value")
13
- hash["value"] = value.content
14
- hash["at"] = value.attributes["at"].value
15
- hash
6
+ begin
7
+ xml = Nokogiri::XML(xml) do |config|
8
+ config.strict.nonet
9
+ end
10
+ hash = {}
11
+ environment = xml.at_xpath("//xmlns:environment")
12
+ raise InvalidXMLError, "Missing 'environment' node from base node" if environment.nil?
13
+ data = environment.at_xpath("xmlns:data")
14
+ datapoint = data.at_xpath("xmlns:datapoints")
15
+ value = datapoint.at_xpath("xmlns:value")
16
+ hash["value"] = value.content
17
+ hash["at"] = value.attributes["at"].value
18
+ hash
19
+ rescue Nokogiri::SyntaxError => e
20
+ raise InvalidXMLError, e.message
21
+ end
16
22
  end
17
23
  end
18
24
  end
@@ -3,12 +3,18 @@ module Cosm
3
3
  module XML
4
4
  module DatastreamDefaults
5
5
  def from_xml(xml)
6
- xml = Nokogiri.parse(xml)
7
- case xml.root.attributes["version"].value
8
- when "0.5.1"
9
- transform_0_5_1(xml)
10
- else # "5"
11
- transform_5(xml)
6
+ begin
7
+ xml = Nokogiri::XML(xml) do |config|
8
+ config.strict.nonet
9
+ end
10
+ case xml.root.attributes["version"].value
11
+ when "5"
12
+ transform_5(xml)
13
+ else
14
+ transform_0_5_1(xml)
15
+ end
16
+ rescue Nokogiri::SyntaxError => e
17
+ raise InvalidXMLError, e.message
12
18
  end
13
19
  end
14
20
 
@@ -1,15 +1,21 @@
1
1
  module Cosm
2
2
  module Parsers
3
3
  module XML
4
- class InvalidXMLError < StandardError; end
4
+ class InvalidXMLError < Cosm::ParserError; end
5
5
  module FeedDefaults
6
6
  def from_xml(xml)
7
- xml = Nokogiri.parse(xml)
8
- case xml.root.attributes["version"].value
9
- when "0.5.1"
10
- transform_0_5_1(xml)
11
- else
12
- transform_5(xml)
7
+ begin
8
+ xml = Nokogiri::XML(xml) do |config|
9
+ config.strict.nonet
10
+ end
11
+ case xml.root.attributes["version"].value
12
+ when "5"
13
+ transform_5(xml)
14
+ else
15
+ transform_0_5_1(xml)
16
+ end
17
+ rescue Nokogiri::SyntaxError => e
18
+ raise InvalidXMLError, e.message
13
19
  end
14
20
  end
15
21
 
@@ -31,7 +37,7 @@ module Cosm
31
37
  hash["email"] = strip(environment.at_xpath("xmlns:email").content)
32
38
  hash["private"] = strip(environment.at_xpath("xmlns:private").content)
33
39
  if (tags = environment.xpath("xmlns:tag").collect { |t| t.content.strip }).any?
34
- hash["tags"] = Cosm::CSV.generate_line(tags.sort{|a,b| a.downcase <=> b.downcase}).strip
40
+ hash["tags"] = Cosm::CSV.generate_line(tags.delete_if { |v| v.to_s.strip == "" }.sort{ |a,b| a.downcase <=> b.downcase}).strip
35
41
  end
36
42
  location = environment.at_xpath("xmlns:location")
37
43
  if location
@@ -68,7 +74,7 @@ module Cosm
68
74
  unit_hash = {}
69
75
  end
70
76
  if (tags = datastream.xpath("xmlns:tag").collect { |t| t.content.strip }).any?
71
- tags_hash = { "tags" => Cosm::CSV.generate_line(tags.sort { |a, b| a.downcase <=> b.downcase }).strip }
77
+ tags_hash = { "tags" => Cosm::CSV.generate_line(tags.delete_if { |v| v.strip.to_s == "" }.sort { |a, b| a.downcase <=> b.downcase }).strip }
72
78
  else
73
79
  tags_hash = {}
74
80
  end
@@ -125,7 +131,7 @@ module Cosm
125
131
  unit_hash = {}
126
132
  end
127
133
  if (tags = datastream.xpath("xmlns:tag").collect { |t| t.content.strip }).any?
128
- tags_hash = { "tags" => Cosm::CSV.generate_line(tags.sort { |a, b| a.downcase <=> b.downcase }).strip }
134
+ tags_hash = { "tags" => Cosm::CSV.generate_line(tags.delete_if { |v| v.to_s.strip == "" }.sort { |a, b| a.downcase <=> b.downcase }).strip }
129
135
  else
130
136
  tags_hash = {}
131
137
  end
@@ -133,8 +139,8 @@ module Cosm
133
139
  "id" => datastream.attributes["id"].value,
134
140
  "current_value" => strip(current_value.content),
135
141
  "updated" => environment.attributes["updated"].value,
136
- "min_value" => current_value.attributes["minValue"].value,
137
- "max_value" => current_value.attributes["maxValue"].value,
142
+ "min_value" => (current_value.nil? ? "" : current_value.attributes["minValue"].value),
143
+ "max_value" => (current_value.nil? ? "" : current_value.attributes["maxValue"].value),
138
144
  }.merge(unit_hash).merge(tags_hash)
139
145
  end
140
146
  hash
@@ -3,35 +3,41 @@ module Cosm
3
3
  module XML
4
4
  module KeyDefaults
5
5
  def from_xml(xml)
6
- xml = Nokogiri.parse(xml)
7
- hash = {}
8
- hash["id"] = xml.at_xpath("//id").content if xml.at_xpath("//id")
9
- hash["expires_at"] = xml.at_xpath("//expires-at").content if xml.at_xpath("//expires-at")
10
- hash["key"] = xml.at_xpath("//api-key").content if xml.at_xpath("//api-key")
11
- hash["label"] = xml.at_xpath("//label").content if xml.at_xpath("//label")
12
- hash["user"] = xml.at_xpath("//user").content if xml.at_xpath("//user")
13
- hash["private_access"] = xml.at_xpath("//private-access").content if xml.at_xpath("//private-access")
6
+ begin
7
+ xml = Nokogiri::XML(xml) do |config|
8
+ config.strict.nonet
9
+ end
10
+ hash = {}
11
+ hash["id"] = xml.at_xpath("//id").content if xml.at_xpath("//id")
12
+ hash["expires_at"] = xml.at_xpath("//expires-at").content if xml.at_xpath("//expires-at")
13
+ hash["key"] = xml.at_xpath("//api-key").content if xml.at_xpath("//api-key")
14
+ hash["label"] = xml.at_xpath("//label").content if xml.at_xpath("//label")
15
+ hash["user"] = xml.at_xpath("//user").content if xml.at_xpath("//user")
16
+ hash["private_access"] = xml.at_xpath("//private-access").content if xml.at_xpath("//private-access")
14
17
 
15
- hash["permissions"] = xml.xpath("//key/permissions/permission").collect { |permission|
16
- access_methods = permission.xpath("access-methods/access-method").collect { |method|
17
- method.content.to_s.downcase
18
- }
19
- resources = permission.xpath("resources/resource").collect { |resource|
20
- { "feed_id" => resource.at_xpath("feed-id").content,
21
- "datastream_id" => resource.at_xpath("datastream-id").content,
22
- "datastream_trigger_id" => resource.at_xpath("datastream-trigger-id").content
18
+ hash["permissions"] = xml.xpath("//key/permissions/permission").collect { |permission|
19
+ access_methods = permission.xpath("access-methods/access-method").collect { |method|
20
+ method.content.to_s.downcase
21
+ }
22
+ resources = permission.xpath("resources/resource").collect { |resource|
23
+ { "feed_id" => resource.at_xpath("feed-id").content,
24
+ "datastream_id" => resource.at_xpath("datastream-id").content,
25
+ "datastream_trigger_id" => resource.at_xpath("datastream-trigger-id").content
26
+ }.delete_if_nil_value
27
+ }
28
+ {
29
+ "referer" => permission.at_xpath("referer").content,
30
+ "source_ip" => permission.at_xpath("source-ip").content,
31
+ "private_access" => permission.at_xpath("private-access").content,
32
+ "access_methods" => access_methods,
33
+ "resources" => resources
23
34
  }.delete_if_nil_value
24
35
  }
25
- {
26
- "referer" => permission.at_xpath("referer").content,
27
- "source_ip" => permission.at_xpath("source-ip").content,
28
- "private_access" => permission.at_xpath("private-access").content,
29
- "access_methods" => access_methods,
30
- "resources" => resources
31
- }.delete_if_nil_value
32
- }
33
36
 
34
- hash
37
+ hash
38
+ rescue Nokogiri::SyntaxError => e
39
+ raise InvalidXMLError, e.message
40
+ end
35
41
  end
36
42
  end
37
43
  end
@@ -3,17 +3,23 @@ module Cosm
3
3
  module XML
4
4
  module TriggerDefaults
5
5
  def from_xml(xml)
6
- xml = Nokogiri.parse(xml)
7
- hash = {}
8
- hash["id"] = xml.at_xpath("//id").content if xml.at_xpath("//id")
9
- hash["url"] = xml.at_xpath("//url").content if xml.at_xpath("//url")
10
- hash["trigger_type"] = xml.at_xpath("//trigger-type").content if xml.at_xpath("//trigger-type")
11
- hash["threshold_value"] = xml.at_xpath("//threshold-value").content if xml.at_xpath("//threshold-value")
12
- hash["notified_at"] = xml.at_xpath("//notified-at").content if xml.at_xpath("//notified-at")
13
- hash["user"] = xml.at_xpath("//user").content if xml.at_xpath("//user")
14
- hash["environment_id"] = xml.at_xpath("//environment-id").content if xml.at_xpath("//environment-id")
15
- hash["stream_id"] = xml.at_xpath("//stream-id").content if xml.at_xpath("//stream-id")
16
- hash
6
+ begin
7
+ xml = Nokogiri::XML(xml) do |config|
8
+ config.strict.nonet
9
+ end
10
+ hash = {}
11
+ hash["id"] = xml.at_xpath("//id").content if xml.at_xpath("//id")
12
+ hash["url"] = xml.at_xpath("//url").content if xml.at_xpath("//url")
13
+ hash["trigger_type"] = xml.at_xpath("//trigger-type").content if xml.at_xpath("//trigger-type")
14
+ hash["threshold_value"] = xml.at_xpath("//threshold-value").content if xml.at_xpath("//threshold-value")
15
+ hash["notified_at"] = xml.at_xpath("//notified-at").content if xml.at_xpath("//notified-at")
16
+ hash["user"] = xml.at_xpath("//user").content if xml.at_xpath("//user")
17
+ hash["environment_id"] = xml.at_xpath("//environment-id").content if xml.at_xpath("//environment-id")
18
+ hash["stream_id"] = xml.at_xpath("//stream-id").content if xml.at_xpath("//stream-id")
19
+ hash
20
+ rescue Nokogiri::SyntaxError => e
21
+ raise InvalidXMLError, e.message
22
+ end
17
23
  end
18
24
  end
19
25
  end
@@ -12,7 +12,7 @@ module Cosm
12
12
  def initialize(input = {})
13
13
  if input.is_a?(Hash)
14
14
  self.attributes = input
15
- elsif input.strip[0...1].to_s == "{"
15
+ else
16
16
  self.attributes = from_json(input)
17
17
  end
18
18
  end
@@ -25,10 +25,11 @@ module Cosm
25
25
  return pass
26
26
  end
27
27
 
28
- def initialize(input = {})
28
+ def initialize(input = {}, format = nil)
29
+ raise InvalidFormatError, "Unknown format specified, currently we can only parse JSON or XML." unless [nil,:json,:xml].include?(format)
29
30
  if input.is_a?(Hash)
30
31
  self.attributes = input
31
- elsif input.strip[0...1].to_s == "{"
32
+ elsif format == :json || (format.nil? && input.strip[0...1].to_s == "{")
32
33
  self.attributes = from_json(input)
33
34
  else
34
35
  self.attributes = from_xml(input)
@@ -1,3 +1,3 @@
1
1
  module Cosm #:nodoc:
2
- VERSION = '0.0.5'
2
+ VERSION = '0.0.8'
3
3
  end
@@ -42,6 +42,24 @@ describe Cosm::Datapoint do
42
42
  datapoint = Cosm::Datapoint.new(datapoint_as_(:hash))
43
43
  datapoint.value.should == "2000"
44
44
  end
45
+
46
+ it "should raise known exception if passed json but told xml" do
47
+ expect {
48
+ Cosm::Datapoint.new(datapoint_as_(:json), :xml)
49
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
50
+ end
51
+
52
+ it "should raise known exception if passed xml but told json" do
53
+ expect {
54
+ Cosm::Datapoint.new(datapoint_as_(:xml), :json)
55
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
56
+ end
57
+
58
+ it "should raise known exception if given unknown format" do
59
+ expect {
60
+ Cosm::Datapoint.new(datapoint_as_(:json), :msgpack)
61
+ }.to raise_error(Cosm::InvalidFormatError)
62
+ end
45
63
  end
46
64
 
47
65
  describe "#attributes" do
@@ -117,6 +117,49 @@ describe Cosm::Datastream do
117
117
  end
118
118
  end
119
119
  end
120
+
121
+ it "should raise known exception if passed json but told xml" do
122
+ expect {
123
+ Cosm::Datastream.new(datastream_as_(:json), :xml)
124
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
125
+ end
126
+
127
+ it "should raise known exception if passed csv but told xml" do
128
+ expect {
129
+ Cosm::Datastream.new(datastream_as_(:csv), :xml)
130
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
131
+ end
132
+
133
+ it "should raise known exception if passed xml but told json" do
134
+ expect {
135
+ Cosm::Datastream.new(datastream_as_(:xml), :json)
136
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
137
+ end
138
+
139
+ it "should raise known exception if passed csv but told json" do
140
+ expect {
141
+ Cosm::Datastream.new(datastream_as_(:csv), :json)
142
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
143
+ end
144
+
145
+ it "should raise known exception if passed json but told csv" do
146
+ expect {
147
+ Cosm::Datastream.new(datastream_as_(:json), :csv)
148
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
149
+ end
150
+
151
+ it "should raise known exception if passed xml but told csv" do
152
+ expect {
153
+ Cosm::Datastream.new(datastream_as_(:xml), :csv)
154
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
155
+ end
156
+
157
+ it "should raise known exception if told some format we don't accept" do
158
+ expect {
159
+ Cosm::Datastream.new(datastream_as_(:xml), :html)
160
+ }.to raise_error(Cosm::InvalidFormatError)
161
+ end
162
+
120
163
  end
121
164
 
122
165
  describe "#attributes" do
@@ -92,6 +92,50 @@ describe Cosm::Feed do
92
92
  end
93
93
  end
94
94
  end
95
+
96
+ context "specifying format" do
97
+ it "should raise known exception if told xml but given csv" do
98
+ expect {
99
+ Cosm::Feed.new(feed_as_(:csv), :v2, :xml)
100
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
101
+ end
102
+
103
+ it "should raise known exception if told xml but given json" do
104
+ expect {
105
+ Cosm::Feed.new(feed_as_(:json), nil, :xml)
106
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
107
+ end
108
+
109
+ it "should raise known exception if told json but given xml" do
110
+ expect {
111
+ Cosm::Feed.new(feed_as_(:xml), nil, :json)
112
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
113
+ end
114
+
115
+ it "should raise known exception if told json but given csv" do
116
+ expect {
117
+ Cosm::Feed.new(feed_as_(:csv), nil, :json)
118
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
119
+ end
120
+
121
+ it "should raise known exception if told csv but given xml" do
122
+ expect {
123
+ Cosm::Feed.new(feed_as_(:xml), :v2, :csv)
124
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
125
+ end
126
+
127
+ it "should raise known exception if told csv but given json" do
128
+ expect {
129
+ Cosm::Feed.new(feed_as_(:json), :v2, :csv)
130
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
131
+ end
132
+
133
+ it "should raise known exception if told format is something unknown" do
134
+ expect {
135
+ Cosm::Feed.new(feed_as_(:json), :v2, :msgpack)
136
+ }.to raise_error(Cosm::InvalidFormatError)
137
+ end
138
+ end
95
139
  end
96
140
 
97
141
  describe "#attributes" do
@@ -71,6 +71,26 @@ describe Cosm::Key do
71
71
  key = Cosm::Key.new(key_as_(:hash))
72
72
  key.permissions.first.access_methods.should == ["get", "put", "post", "delete"]
73
73
  end
74
+
75
+ context "specifying format" do
76
+ it "should raise known exception if told xml but given json" do
77
+ expect {
78
+ Cosm::Key.new(key_as_(:json), :xml)
79
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
80
+ end
81
+
82
+ it "should raise known exception if told json but given xml" do
83
+ expect {
84
+ Cosm::Key.new(key_as_(:xml), :json)
85
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
86
+ end
87
+
88
+ it "should raise known exception if given unknown format" do
89
+ expect {
90
+ Cosm::Key.new(key_as_(:xml), :gif)
91
+ }.to raise_error(Cosm::InvalidFormatError)
92
+ end
93
+ end
74
94
  end
75
95
 
76
96
  describe "#attributes" do
@@ -9,11 +9,10 @@ describe "default datastream csv parser" do
9
9
  end
10
10
 
11
11
  it "should capture timestamp if present" do
12
- timestamp = Time.now.iso8601(6)
13
- csv = "#{timestamp},123"
12
+ csv = datastream_as_(:csv, :version => "timestamped")
14
13
  datastream = Cosm::Datastream.new(csv)
15
- datastream.updated.should == timestamp
16
- datastream.current_value.should == "123"
14
+ datastream.updated.should == "2011-02-16T16:21:01.834174Z"
15
+ datastream.current_value.should == "14"
17
16
  end
18
17
 
19
18
  it "should raise error if passed more than a single row" do
@@ -29,6 +28,12 @@ describe "default datastream csv parser" do
29
28
  Cosm::Datastream.new(csv)
30
29
  }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
31
30
  end
31
+
32
+ it "should raise exception if passed garbage csv" do
33
+ expect {
34
+ Cosm::Datastream.new("badly, \"quoted", :csv)
35
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
36
+ end
32
37
  end
33
38
  end
34
39
 
@@ -48,6 +48,41 @@ CSV
48
48
  Cosm::Feed.new(csv)
49
49
  }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
50
50
  end
51
+
52
+ it "should raise an error if passed more than one row when we state it's v1" do
53
+ csv =<<-CSV
54
+ This,2
55
+ Wrong,3
56
+ CSV
57
+
58
+ expect {
59
+ Cosm::Feed.new(csv, :v1)
60
+ }.to raise_error(Cosm::Parsers::CSV::InvalidCSVError)
61
+ end
62
+
63
+ context "unwanted whitespace" do
64
+ it "should strip whitespace from v2" do
65
+ dodgy_csv = <<-CSV
66
+ 0, 00035
67
+ stream1, 0012
68
+ 2, 2012-08-02T14:11:14Z ," red car "
69
+ CSV
70
+ good_csv = <<-CSV
71
+ 0,00035
72
+ stream1,0012
73
+ 2,2012-08-02T14:11:14Z,red car
74
+ CSV
75
+ feed = Cosm::Feed.new(dodgy_csv)
76
+ feed.should fully_represent_feed(:csv_v2, good_csv)
77
+ end
78
+
79
+ it "should strip whitespace from v1" do
80
+ dodgy_csv = %Q{ 00035 , 0012," red car"}
81
+ good_csv = "00035,0012,red car"
82
+ feed = Cosm::Feed.new(dodgy_csv)
83
+ feed.should fully_represent_feed(:csv_v1, good_csv)
84
+ end
85
+ end
51
86
  end
52
87
  end
53
88
 
@@ -12,4 +12,10 @@ describe "default datapoint json parser" do
12
12
  attributes["at"].should == json["at"]
13
13
  attributes["value"].should == json["value"]
14
14
  end
15
+
16
+ it "should raise known exeception if passed garbage as json" do
17
+ expect {
18
+ Cosm::Datapoint.new("This is not\nJSON", :json)
19
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
20
+ end
15
21
  end
@@ -1,24 +1,39 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe "default datastream json parser" do
4
+ include Cosm::Helpers
5
+
4
6
  before(:each) do
5
7
  @datastream = Cosm::Datastream.new(datastream_as_(:json))
6
8
  end
7
9
 
8
- it "should default to v1 API if no version is sent" do
9
- @json = datastream_as_(:json, :version => "0.6-alpha", :except => [:version])
10
- attributes = {}
11
- lambda {attributes = @datastream.from_json(@json)}.should_not raise_error
10
+ it "should default to v2 if no version is present" do
11
+ @json = datastream_as_(:json, :version => "1.0.0", :except => [:version])
12
+ attributes = @datastream.from_json(@json)
12
13
  json = JSON.parse(@json)
13
14
  attributes["id"].should == json["id"]
14
- attributes["updated"].should == json["values"].first["recorded_at"]
15
- attributes["current_value"].should == json["values"].first["value"]
16
- attributes["max_value"].should == json["values"].first["max_value"]
17
- attributes["min_value"].should == json["values"].first["min_value"]
18
- attributes["tags"].should == json["tags"].join(',')
15
+ attributes["updated"].should == json["at"]
16
+ attributes["current_value"].should == json["current_value"]
17
+ attributes["max_value"].should == json["max_value"]
18
+ attributes["min_value"].should == json["min_value"]
19
+ attributes["tags"].should == join_tags(json["tags"])
19
20
  attributes["unit_type"].should == json["unit"]["type"]
20
21
  attributes["unit_label"].should == json["unit"]["label"]
21
22
  attributes["unit_symbol"].should == json["unit"]["symbol"]
23
+ at_least_one_datapoint = false
24
+ attributes["datapoints"].each do |point|
25
+ at_least_one_datapoint = true
26
+ dp = json["datapoints"].detect {|dp| dp["at"] == point["at"]}
27
+ point["value"].should == dp["value"]
28
+ point["at"].should == dp["at"]
29
+ end
30
+ at_least_one_datapoint.should be_true
31
+ end
32
+
33
+ it "should raise known exception if passed garbage as JSON" do
34
+ expect {
35
+ Cosm::Datastream.new("This is not json", :json)
36
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
22
37
  end
23
38
 
24
39
  context "1.0.0 (used by API v2)" do
@@ -31,7 +46,7 @@ describe "default datastream json parser" do
31
46
  attributes["current_value"].should == json["current_value"]
32
47
  attributes["max_value"].should == json["max_value"]
33
48
  attributes["min_value"].should == json["min_value"]
34
- attributes["tags"].should == json["tags"].join(',')
49
+ attributes["tags"].should == join_tags(json["tags"])
35
50
  attributes["unit_type"].should == json["unit"]["type"]
36
51
  attributes["unit_label"].should == json["unit"]["label"]
37
52
  attributes["unit_symbol"].should == json["unit"]["symbol"]
@@ -49,6 +64,14 @@ describe "default datastream json parser" do
49
64
  @json = datastream_as_(:json, :except => [:tags])
50
65
  lambda {@datastream.from_json(@json)}.should_not raise_error
51
66
  end
67
+
68
+ it "should capture timestamp" do
69
+ @json = datastream_as_(:json, :version => "1.0.0-minimal_timestamp")
70
+ attributes = @datastream.from_json(@json)
71
+ json = JSON.parse(@json)
72
+ attributes["updated"].should_not be_nil
73
+ attributes["updated"].should == json["at"]
74
+ end
52
75
  end
53
76
 
54
77
  context "0.6-alpha (used by API v1)" do
@@ -29,11 +29,16 @@ describe "default feed json parser" do
29
29
  end
30
30
 
31
31
  it "should capture empty fields if present" do
32
- json = "{\"version\":\"1.0.0\",\"description\":\"\",\"feed\":\"\",\"location\":{\"name\":\"\"}}"
32
+ json = "{\"version\":\"1.0.0\",\"description\":\"\",\"feed\":\"\",\"location\":{\"name\":\"\"},\"tags\":[],\"datastreams\":[{\"unit\":{\"label\":\"\",\"symbol\":\"\"},\"tags\":[]}]}"
33
33
  feed = Cosm::Feed.new(json)
34
34
  feed.description.should == ""
35
35
  feed.feed.should == ""
36
36
  feed.location_name.should == ""
37
+ feed.tags.should == ""
38
+ feed.datastreams.size.should == 1
39
+ feed.datastreams[0].unit_label.should == ""
40
+ feed.datastreams[0].unit_symbol.should == ""
41
+ feed.datastreams[0].tags.should == ""
37
42
  end
38
43
  end
39
44
  end
@@ -5,4 +5,10 @@ describe "default key json parser" do
5
5
  @json = key_as_(:json)
6
6
  Cosm::Key.new(@json).should fully_represent_key(:json, @json)
7
7
  end
8
+
9
+ it "should raise known exception if passed garbage as json" do
10
+ expect {
11
+ Cosm::Key.new("this ain't json", :json)
12
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
13
+ end
8
14
  end
@@ -7,6 +7,12 @@ describe "default search result json parser" do
7
7
  search_result = Cosm::SearchResult.new(json)
8
8
  search_result.should fully_represent_search_result(:json, json)
9
9
  end
10
+
11
+ it "should raise known exception if passed garbage as json" do
12
+ expect {
13
+ Cosm::SearchResult.new("Guess what, not JSON!")
14
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
15
+ end
10
16
  end
11
17
  end
12
18
 
@@ -13,4 +13,10 @@ describe "default trigger json parser" do
13
13
  attributes[key].should == json[key]
14
14
  end
15
15
  end
16
+
17
+ it "should raise known exception if passed garbage as json" do
18
+ expect {
19
+ Cosm::Trigger.new("This is not JSON", :json)
20
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
21
+ end
16
22
  end
@@ -59,5 +59,11 @@ describe "default datastream xml parser" do
59
59
  Cosm::Datastream.new(@xml).should fully_represent_datastream(:xml, @xml)
60
60
  end
61
61
  end
62
+
63
+ it "should raise exception if passed garbage as XML" do
64
+ expect {
65
+ Cosm::Datastream.new("This is not xml", :xml)
66
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
67
+ end
62
68
  end
63
69
 
@@ -27,6 +27,25 @@ describe "default feed xml parser" do
27
27
  Cosm::Feed.new(@xml).should fully_represent_feed(:xml, @xml)
28
28
  end
29
29
 
30
+ it "should handle present but empty tags" do
31
+ xml = <<-EOXML
32
+ <?xml version="1.0" encoding="UTF-8"?>
33
+ <eeml xmlns="http://www.eeml.org/xsd/0.5.1" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="0.5.1" xsi:schemaLocation="http://www.eeml.org/xsd/005 http://www.eeml.org/xsd/005/005.xsd">
34
+ <environment>
35
+ <title>ohai</title>
36
+ <tag></tag>
37
+ <data id="123">
38
+ <tag></tag>
39
+ </data>
40
+ </environment>
41
+ </eeml>
42
+ EOXML
43
+
44
+ feed = Cosm::Feed.new(xml)
45
+ feed.tags.should == ""
46
+ feed.datastreams.first.tags.should == ""
47
+ end
48
+
30
49
  it "should gracefully handle 0.5.1 xml missing the base environment node" do
31
50
  xml = <<-EOXML
32
51
  <?xml version="1.0" encoding="UTF-8"?>
@@ -58,7 +77,6 @@ EOXML
58
77
  feed.datastreams.size.should == 1
59
78
  feed.datastreams.first.tags.should == "freakin lasers,humidity,Temperature"
60
79
  end
61
-
62
80
  end
63
81
 
64
82
  context "5 (used by API v1)" do
@@ -92,8 +110,25 @@ EOXML
92
110
  feed = Cosm::Feed.new(@xml)
93
111
  Cosm::Feed.new(@xml).should fully_represent_feed(:xml, @xml)
94
112
  end
113
+
114
+ it "should handle present but empty tags" do
115
+ xml = <<-EOXML
116
+ <?xml version="1.0" encoding="UTF-8"?>
117
+ <eeml xmlns="http://www.eeml.org/xsd/005" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="5" xsi:schemaLocation="http://www.eeml.org/xsd/005 http://www.eeml.org/xsd/005/005.xsd">
118
+ <environment>
119
+ <title>ohai</title>
120
+ <data id="123">
121
+ <tag></tag>
122
+ </data>
123
+ </environment>
124
+ </eeml>
125
+ EOXML
126
+
127
+ feed = Cosm::Feed.new(xml)
128
+ feed.datastreams.first.tags.should == ""
129
+ end
95
130
 
96
- it "should gracefully handle 0.5.1 xml missing the base environment node" do
131
+ it "should gracefully handle 5 xml missing the base environment node" do
97
132
  xml = <<-EOXML
98
133
  <?xml version="1.0" encoding="UTF-8"?>
99
134
  <eeml xmlns="http://www.eeml.org/xsd/005" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="5" xsi:schemaLocation="http://www.eeml.org/xsd/005 http://www.eeml.org/xsd/005/005.xsd">
@@ -131,5 +166,45 @@ EOXML
131
166
  datastream.unit_label.should == "celsius"
132
167
  end
133
168
  end
169
+
170
+ context "garbage input" do
171
+ it "should not propogate nokogiri error for invalid xml" do
172
+ xml = <<-EOXML
173
+ <?xml version="1.0" encoding="UTF-8"?>
174
+ <rss version="2.0">
175
+ <channel>
176
+ <title>Skype Statistics</title>
177
+ <description>Statistics From Skype</description>
178
+ <link>http://www.skype.com/</link>
179
+ <lastBuildDate>Thu, 02 Aug 2012 13:50:01 +0000</lastBuildDate>
180
+ <image>
181
+ <url>http://www.skype.com/i/logos/skype.png</url>
182
+ <title>Skype</title>
183
+ <link>http://www.skype.com/</link>
184
+ <description>Statistics From Skype</description>
185
+ </image>
186
+ <ttl>60</ttl>
187
+ <item>
188
+ <title>Total Skype Downloads</title>
189
+ <link>http://www.skype.com/</link>
190
+ <description>2992280145</description>
191
+ <pubDate>Thu, 02 Aug 2012 13:50:01 +0000</pubDate>
192
+ <guid>Total Skype Downloads Thu, 02 Aug 2012 13:50:01 +0000</guid>
193
+ </item>
194
+ <item>
195
+ <title>Users Online Now</title>
196
+ <link>http://www.skype.com/</link>
197
+ <description>39393244</description>
198
+ <pubDate>Thu, 02 Aug 2012 13:50:01 +0000</pubDate>
199
+ <guid>Users Online Now Thu, 02 Aug 2012 13:50:01 +0000</guid>
200
+ </item>
201
+ </channel>
202
+ </rss>
203
+ EOXML
204
+ expect {
205
+ Cosm::Feed.new(xml)
206
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
207
+ end
208
+ end
134
209
  end
135
210
 
@@ -12,5 +12,11 @@ describe "default key xml parser" do
12
12
  Cosm::Key.new(@xml).should fully_represent_key(:xml, @xml)
13
13
  end
14
14
  end
15
+
16
+ it "should raise known exception if passed garbage as xml" do
17
+ expect {
18
+ Cosm::Key.new("This is not XML", :xml)
19
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
20
+ end
15
21
  end
16
22
 
@@ -12,5 +12,11 @@ describe "default trigger xml parser" do
12
12
  Cosm::Trigger.new(@xml).should fully_represent_trigger(:xml, @xml)
13
13
  end
14
14
  end
15
+
16
+ it "should raise known exception if passed garbage as xml" do
17
+ expect {
18
+ Cosm::Trigger.new("This is not XML", :xml)
19
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
20
+ end
15
21
  end
16
22
 
@@ -42,6 +42,46 @@ describe Cosm::Trigger do
42
42
  trigger = Cosm::Trigger.new(trigger_as_(:hash))
43
43
  trigger.url.should == "http://www.postbin.org/zc9sca"
44
44
  end
45
+
46
+ context "specifying format explicitly" do
47
+ it "should raise known exception if passed json but told xml" do
48
+ expect {
49
+ Cosm::Trigger.new(trigger_as_(:json), :xml)
50
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
51
+ end
52
+
53
+ it "should raise known exception if passed xml but told json" do
54
+ expect {
55
+ Cosm::Trigger.new(trigger_as_(:json), :xml)
56
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
57
+ end
58
+
59
+ it "should raise known exception if passed unknown format" do
60
+ expect {
61
+ Cosm::Trigger.new(trigger_as_(:json), :png)
62
+ }.to raise_error(Cosm::InvalidFormatError)
63
+ end
64
+ end
65
+
66
+ context "specifying format" do
67
+ it "should raise known exception if told xml but given json" do
68
+ expect {
69
+ Cosm::Trigger.new(trigger_as_(:json), :xml)
70
+ }.to raise_error(Cosm::Parsers::XML::InvalidXMLError)
71
+ end
72
+
73
+ it "should raise known exception if told json but given xml" do
74
+ expect {
75
+ Cosm::Trigger.new(trigger_as_(:xml), :json)
76
+ }.to raise_error(Cosm::Parsers::JSON::InvalidJSONError)
77
+ end
78
+
79
+ it "should raise known exception if given unknown format" do
80
+ expect {
81
+ Cosm::Trigger.new(trigger_as_(:xml), :gif)
82
+ }.to raise_error(Cosm::InvalidFormatError)
83
+ end
84
+ end
45
85
  end
46
86
 
47
87
  describe "#attributes" do
@@ -31,7 +31,7 @@ def datastream_as_(format, options = {})
31
31
  when 'xml'
32
32
  data = datastream_as_xml(options[:version] || "0.5.1", options[:except_node])
33
33
  when 'csv'
34
- data = '14'
34
+ data = datastream_as_csv(options[:version] || "plain")
35
35
  end
36
36
 
37
37
  # Add extra options we passed
@@ -94,6 +94,21 @@ def datastream_as_json(version)
94
94
  },
95
95
  'version' => '1.0.0'
96
96
  }
97
+ when "1.0.0-minimal"
98
+ {
99
+ "current_value" => "294",
100
+ "max_value" => "697.0",
101
+ "min_value" => "0.0",
102
+ "id" => "1"
103
+ }
104
+ when "1.0.0-minimal_timestamp"
105
+ {
106
+ "current_value" => "294",
107
+ "max_value" => "697.0",
108
+ "min_value" => "0.0",
109
+ "id" => "1",
110
+ "at" => "2011-03-02T16:00:18.416500Z"
111
+ }
97
112
  when "0.6-alpha"
98
113
  {
99
114
  "tags" => ["humidity"],
@@ -298,3 +313,12 @@ XML
298
313
  raise "Datastream as XML #{version} not implemented"
299
314
  end
300
315
  end
316
+
317
+ def datastream_as_csv(version)
318
+ case version
319
+ when "timestamped"
320
+ return "2011-02-16T16:21:01.834174Z,14"
321
+ else
322
+ return "14"
323
+ end
324
+ end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cosm-rb
3
3
  version: !ruby/object:Gem::Version
4
- hash: 21
4
+ hash: 15
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 0
9
- - 5
10
- version: 0.0.5
9
+ - 8
10
+ version: 0.0.8
11
11
  platform: ruby
12
12
  authors:
13
13
  - Paul Bellamy
@@ -17,7 +17,7 @@ autorequire:
17
17
  bindir: bin
18
18
  cert_chain: []
19
19
 
20
- date: 2012-07-10 00:00:00 Z
20
+ date: 2012-08-03 00:00:00 Z
21
21
  dependencies:
22
22
  - !ruby/object:Gem::Dependency
23
23
  version_requirements: &id001 !ruby/object:Gem::Requirement
@@ -179,6 +179,7 @@ files:
179
179
  - lib/cosm-rb/client.rb
180
180
  - lib/cosm-rb/datapoint.rb
181
181
  - lib/cosm-rb/datastream.rb
182
+ - lib/cosm-rb/exceptions.rb
182
183
  - lib/cosm-rb/feed.rb
183
184
  - lib/cosm-rb/hash_extensions.rb
184
185
  - lib/cosm-rb/helpers.rb