require File.dirname(__FILE__) + '/spec_helper' def expected_helpers { "type" => "random", "version" => "1.0", "html" => "<em>Hello world!</em>", "url" => "http://foo.com/bar", }.freeze end def expected_skipped { "fields" => "hello", "__id__" => 1234, "provider" => "oohEmbed", "to_s" => "random string", }.freeze end def all_expected expected_helpers.merge(expected_skipped).freeze end describe OEmbed::Response do include OEmbedSpecHelper let(:flickr) { flickr = OEmbed::Provider.new("http://www.flickr.com/services/oembed/") flickr << "http://*.flickr.com/*" flickr } let(:skitch) { OEmbed::Provider.new("https://skitch.com/oembed") } let(:qik) { qik = OEmbed::Provider.new("http://qik.com/api/oembed.{format}", format: :xml) qik << "http://qik.com/video/*" qik << "http://qik.com/*" qik } let(:viddler) { viddler = OEmbed::Provider.new("http://lab.viddler.com/services/oembed/", format: :json) viddler << "http://*.viddler.com/*" viddler } let(:new_res) { OEmbed::Response.new(valid_response(:object), OEmbed::Providers::OohEmbed) } let(:default_res) { OEmbed::Response.create_for(valid_response(:json), @flickr, example_url(:flickr), :json) } let(:xml_res) { OEmbed::Response.create_for(valid_response(:xml), @qik, example_url(:qik), :xml) } let(:json_res) { OEmbed::Response.create_for(valid_response(:json), @viddler, example_url(:viddler), :json) } describe "#initialize" do it "should parse the data into fields" do # We need to compare keys & values separately because we don't expect all # non-string values to be recognized correctly. expect(new_res.fields.keys).to eq(valid_response(:object).keys) expect(new_res.fields.values.map{|v|v.to_s}).to eq(valid_response(:object).values.map{|v|v.to_s}) expect(default_res.fields.keys).to eq(valid_response(:object).keys) expect(default_res.fields.values.map{|v|v.to_s}).to eq(valid_response(:object).values.map{|v|v.to_s}) expect(xml_res.fields.keys).to eq(valid_response(:object).keys) expect(xml_res.fields.values.map{|v|v.to_s}).to eq(valid_response(:object).values.map{|v|v.to_s}) expect(json_res.fields.keys).to eq(valid_response(:object).keys) expect(json_res.fields.values.map{|v|v.to_s}).to eq(valid_response(:object).values.map{|v|v.to_s}) end it "should set the provider" do expect(new_res.provider).to eq(OEmbed::Providers::OohEmbed) expect(default_res.provider).to eq(@flickr) expect(xml_res.provider).to eq(@qik) expect(json_res.provider).to eq(@viddler) end it "should set the format" do expect(new_res.format).to be_nil expect(default_res.format.to_s).to eq('json') expect(xml_res.format.to_s).to eq('xml') expect(json_res.format.to_s).to eq('json') end it "should set the request_url" do expect(new_res.request_url).to be_nil expect(default_res.request_url.to_s).to eq(example_url(:flickr)) expect(xml_res.request_url.to_s).to eq(example_url(:qik)) expect(json_res.request_url.to_s).to eq(example_url(:viddler)) end end describe "create_for" do it "should only allow JSON or XML" do expect { OEmbed::Response.create_for(valid_response(:json), flickr, example_url(:flickr), :json) }.not_to raise_error expect { OEmbed::Response.create_for(valid_response(:xml), flickr, example_url(:flickr), :xml) }.not_to raise_error expect { OEmbed::Response.create_for(valid_response(:yml), flickr, example_url(:flickr), :yml) }.to raise_error(OEmbed::FormatNotSupported) end it "should not parse the incorrect format" do expect { OEmbed::Response.create_for(valid_response(:object), example_url(:flickr), flickr, :json) }.to raise_error(OEmbed::ParseError) expect { OEmbed::Response.create_for(valid_response(:xml), example_url(:flickr), viddler, :json) }.to raise_error(OEmbed::ParseError) expect { OEmbed::Response.create_for(valid_response(:json), example_url(:flickr), viddler, :xml) }.to raise_error(OEmbed::ParseError) end end it "should access the XML data through #field" do expect(xml_res.field(:type)).to eq("photo") expect(xml_res.field(:version)).to eq("1.0") expect(xml_res.field(:fields)).to eq("hello") expect(xml_res.field(:__id__)).to eq("1234") end it "should access the JSON data through #field" do expect(json_res.field(:type)).to eq("photo") expect(json_res.field(:version)).to eq("1.0") expect(json_res.field(:fields)).to eq("hello") expect(json_res.field(:__id__)).to eq("1234") end describe "#define_methods!" do context "with automagic" do all_expected.each do |method, value| before do @local_res = OEmbed::Response.new(all_expected, OEmbed::Providers::OohEmbed) end it "should define the #{method} method" do expect(@local_res).to respond_to(method) end end expected_helpers.each do |method, value| it "should define #{method} to return #{value.inspect}" do expect(@local_res.send(method)).to eq(value) end end expected_skipped.each do |method, value| it "should NOT override #{method} to not return #{value.inspect}" do expect(@local_res.send(method)).to_not eq(value) end end end it "should protect most already defined methods" do expect(Object.new).to respond_to('__id__') expect(Object.new).to respond_to('to_s') expect(all_expected.keys).to include('__id__') expect(all_expected.keys).to include('to_s') local_res = OEmbed::Response.new(all_expected, OEmbed::Providers::OohEmbed) expect(local_res.__id__).to_not eq(local_res.field('__id__')) expect(local_res.to_s).to_not eq(local_res.field('to_s')) end it "should not protect already defined methods that are specifically overridable" do class Object def version "two point oh" end end expect(Object.new).to respond_to('version') expect(String.new).to respond_to('version') expect(all_expected.keys).to include('version') expect(all_expected['version']).to_not eq(String.new.version) local_res = OEmbed::Response.new(all_expected, OEmbed::Providers::OohEmbed) expect(local_res.version).to eq(local_res.field('version')) expect(local_res.version).to_not eq(String.new.version) end end describe "OEmbed::Response::Photo" do describe "#html" do it "should include the title, if given" do response = OEmbed::Response.create_for(example_body(:flickr), example_url(:flickr), flickr, :json) expect(response).to respond_to(:title) expect(response.title).to_not be_empty expect(response.html).to_not be_nil expect(response.html).to match(/alt='#{response.title}'/) end it "should work just fine, without a title" do response = OEmbed::Response.create_for(example_body(:skitch), example_url(:skitch), skitch, :json) expect(response).to_not respond_to(:title) expect(response.html).to_not be_nil expect(response.html).to match(/alt=''/) end end end end