-
Notifications
You must be signed in to change notification settings - Fork 26
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Bob Corsaro
committed
Jan 20, 2011
1 parent
d4be3ff
commit dbd768b
Showing
12 changed files
with
303 additions
and
7 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,4 @@ | ||
Gemfile.lock | ||
embedly.gemspec | ||
pkg/ | ||
|
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 @@ | ||
rvm 1.9.2@embedly |
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
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,11 @@ | ||
#!/usr/bin/env ruby | ||
$:.unshift(File.expand_path('../../lib', __FILE__)) | ||
%w{embedly json}.each {|l| require l} | ||
|
||
Embedly::VERSION | ||
urls = ARGV | ||
api = Embedly::API.new :endpoint => 'http://localhost:8001' | ||
urls.each do |url| | ||
obj = api.objectify :url => url | ||
puts JSON.pretty_generate(obj.marshal_dump) | ||
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,11 @@ | ||
#!/usr/bin/env ruby | ||
$:.unshift(File.expand_path('../../lib', __FILE__)) | ||
%w{embedly json}.each {|l| require l} | ||
|
||
Embedly::VERSION | ||
urls = ARGV | ||
api = Embedly::API.new | ||
urls.each do |url| | ||
obj = api.oembed :url => url | ||
puts JSON.pretty_generate(obj.marshal_dump) | ||
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,11 @@ | ||
#!/usr/bin/env ruby | ||
$:.unshift(File.expand_path('../../lib', __FILE__)) | ||
%w{embedly json}.each {|l| require l} | ||
|
||
Embedly::VERSION | ||
urls = ARGV | ||
api = Embedly::API.new :endpoint => 'http://localhost:8001' | ||
urls.each do |url| | ||
obj = api.preview :url => url | ||
puts JSON.pretty_generate(obj.marshal_dump) | ||
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 @@ | ||
default: features |
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,61 @@ | ||
Feature: OEmbed | ||
|
||
As an embedly user | ||
I want to call the the embedly api | ||
Because I want and oembed for a specific url | ||
|
||
Scenario Outline: Get the provider_url | ||
Given an embedly endpoint | ||
When oembed is called with the <url> URL | ||
Then the provider_url should be <provider_url> | ||
|
||
Examples: | ||
| url | provider_url | | ||
| http://www.scribd.com/doc/13994900/Easter | http://www.scribd.com/ | | ||
| http://www.scribd.com/doc/28452730/Easter-Cards | http://www.scribd.com/ | | ||
| http://www.youtube.com/watch?v=Zk7dDekYej0 | http://www.youtube.com/ | | ||
| http://tweetphoto.com/14784358 | http://plixi.com | | ||
|
||
|
||
Scenario Outline: Get the provider_url with force flag | ||
Given an embedly endpoint | ||
When oembed is called with the <url> URL and force flag | ||
Then the provider_url should be <provider_url> | ||
|
||
Examples: | ||
| url | provider_url | | ||
| http://www.youtube.com/watch?v=Zk7dDekYej0 | http://www.youtube.com/ | | ||
|
||
|
||
Scenario Outline: Get multiple provider_urls | ||
Given an embedly endpoint | ||
When oembed is called with the <urls> URLs | ||
Then provider_url should be <provider_urls> | ||
|
||
Examples: | ||
| urls | provider_urls | | ||
| http://www.scribd.com/doc/13994900/Easter,http://www.scribd.com/doc/28452730/Easter-Cards | http://www.scribd.com/,http://www.scribd.com/ | | ||
| http://www.youtube.com/watch?v=Zk7dDekYej0,http://plixi.com/p/16044847 | http://www.youtube.com/,http://plixi.com | | ||
|
||
|
||
Scenario Outline: Get the provider_url with pro | ||
Given an embedly endpoint with 3ea4fc74fd6d11df84894040444cdc60 key | ||
When oembed is called with the <url> URL | ||
Then the provider_url should be <provider_url> | ||
|
||
Examples: | ||
| url | provider_url | | ||
| http://blog.embed.ly/bob | http://posterous.com | | ||
| http://blog.doki-pen.org/cassandra-rules | http://posterous.com | | ||
|
||
|
||
Scenario Outline: Attempt to get 404 URL | ||
Given an embedly endpoint | ||
When oembed is called with the <url> URLs | ||
Then type should be error | ||
And error_code should be 404 | ||
|
||
Examples: | ||
| url | | ||
| http://www.youtube.com/this/is/a/bad/url | | ||
|
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 @@ | ||
$:.unshift(File.expand_path('../../../lib',__FILE__)) | ||
require 'embedly' | ||
|
||
Given /an embedly endpoint( [^\s]+)?( with ([^\s]+) key)?$/ do |endpoint, _, key| | ||
opts = {} | ||
opts[:endpoint] = endpoint | ||
opts[:key] = key | ||
@api = Embedly::API.new opts | ||
end | ||
|
||
When /oembed is called with the (.*) URLs?( and ([^\s]+) flag)?$/ do |urls, _, flag| | ||
urls = urls.split(',') | ||
opts = {} | ||
if urls.size == 1 | ||
opts[:url] = urls.first | ||
else | ||
opts[:urls] = urls | ||
end | ||
opts[flag.to_sym] = true if flag | ||
@result = @api.oembed opts | ||
end | ||
|
||
Then /([^\s]+) should be ([^\s]+)/ do |key, value| | ||
if @result.is_a?Array | ||
@result.collect{|o| puts o.provider_url; puts key; puts o.send(key); o.send(key).to_s}.join(',').should == value | ||
else | ||
@result.send(key).to_s.should == value | ||
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,14 @@ | ||
require 'logger' | ||
|
||
module Embedly | ||
VERSION = File.read(File.expand_path('../../VERSION', __FILE__)) | ||
|
||
def self.logger(name) | ||
@_loggers ||= {} | ||
@_loggers[name] ||= Logger.new(STDOUT) | ||
@_loggers[name].level = Logger::ERROR | ||
@_loggers[name] | ||
end | ||
end | ||
|
||
require 'embedly/api' |
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,141 @@ | ||
require 'net/http' | ||
require 'json' | ||
require 'ostruct' | ||
|
||
# = Embedly::API = | ||
# | ||
# Performs api calls to embedly. | ||
# | ||
# You won't find methods. We are using method_missing and passing the method | ||
# name to apicall. | ||
# | ||
# == Parameters == | ||
# :+endpoint+: Hostname of embedly server. Defaults to api.embed.ly if no key | ||
# is provided, pro.embed.ly if key is provided. | ||
# :+key+: Your pro.embed.ly api key. | ||
# | ||
# == Currently Supported Methods == | ||
# | ||
# * +oembed+ | ||
# * +objectify+ | ||
# * +preview+ _pro-only_ | ||
# | ||
# Call parameters should be passed as the opts parameter. If set, key will | ||
# automatically be added to the query string of the call, so no need to set it. | ||
# | ||
# This API _would_ be future compatible, if not for the version. In order to | ||
# add support for a new method, you will need to add a version to the | ||
# api_version hash. Here is an example. | ||
# | ||
# api = Embedly::API.new | ||
# api.api_version['new_method'] = 3 | ||
# api.new_method :arg1 => '1', :arg2 => '2' | ||
# | ||
class Embedly::API | ||
attr_reader :key, :endpoint, :api_version | ||
|
||
# = Parameters = | ||
# :+endpoint+: Hostname of embedly server. Defaults to api.embed.ly if no key | ||
# is provided, pro.embed.ly if key is provided. | ||
# :+key+: Your pro.embed.ly api key. | ||
def initialize opts={} | ||
@key = opts[:key] | ||
if @key | ||
@endpoint = opts[:endpoint] || 'pro.embed.ly' | ||
else | ||
@endpoint = opts[:endpoint] || 'api.embed.ly' | ||
end | ||
@api_versions = Hash.new('1').merge!({'objectify' => '2'}) | ||
end | ||
|
||
# Normalizes url and urls parameters and calls the endpoint. url OR urls | ||
# must be present | ||
# | ||
# == Options == | ||
# :+url+: _(optional)_ A single url | ||
# :+urls+: _(optional)_ An array of urls | ||
# :+action+: The method that should be called. ex. oembed, objectify, preview | ||
# :+version+: The api version number. | ||
# _others_: All other parameters are used as query strings. | ||
def apicall opts | ||
opts[:urls] ||= [] | ||
opts[:urls] << opts[:url] if opts[:url] | ||
|
||
raise 'must pass urls' if opts[:urls].size == 0 | ||
|
||
if opts[:urls].size == 1 | ||
params = {:url => opts[:urls].first} | ||
else | ||
params = {:urls => opts[:urls]} | ||
end | ||
|
||
params[:key] = key if key | ||
params.merge!opts.select{|k,_| not [:url, :urls, :action, :version].index k} | ||
|
||
path = "/#{opts[:version]}/#{opts[:action]}?#{q params}" | ||
logger.debug { "calling http://#{endpoint}#{path}" } | ||
http = Net::HTTP.new(endpoint) | ||
request = Net::HTTP::Get.new(path) | ||
response = http.request(request) | ||
|
||
# passing url vs. urls causes different things to happen on errors (like a | ||
# 404 for the URL). using the url parameter returns a non 200 error code | ||
# in the response. Using urls causes an error json object to be returned, | ||
# but the main call will still be status 200. Below, we try to canonize as | ||
# best we can but it should really be changed server side. | ||
if response.code.to_i == 200 | ||
logger.debug { response.body } | ||
# [].flatten is to be sure we have an array | ||
objs = [JSON.parse(response.body)].flatten.collect {|o| OpenStruct.new(o)} | ||
else | ||
objs = OpenStruct.new :type => 'error', :error_code => response.code.to_i | ||
end | ||
|
||
if objs.size == 1 | ||
objs.first | ||
else | ||
objs | ||
end | ||
end | ||
|
||
private | ||
# Performs api call based on method name | ||
# | ||
# == Currently supported == | ||
# | ||
# * +oembed+ | ||
# * +objectify+ | ||
# * +preview+ _pro-only_ | ||
# | ||
def method_missing(name, *args, &block) | ||
opts = args[0] | ||
opts[:action] = name | ||
opts[:version] = @api_versions[name] | ||
apicall opts | ||
end | ||
|
||
# Escapes url parameters | ||
# TODO: move to utils | ||
def escape s | ||
s.to_s.gsub(/([^ a-zA-Z0-9_.-]+)/u) do | ||
'%'+$1.unpack('H2'*$1.bytesize).join('%').upcase | ||
end.tr(' ', '+') | ||
end | ||
|
||
# Creates query string | ||
# TODO: move to utils | ||
def q params | ||
params.collect do |k,v| | ||
if v.is_a?Array | ||
"#{k.to_s}=#{v.collect{|i|escape(i)}.join(',')}" | ||
else | ||
"#{k.to_s}=#{escape(v)}" | ||
end | ||
end.join('&') | ||
end | ||
|
||
def logger | ||
@logger ||= Embedly.logger('API') | ||
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 |
---|---|---|
@@ -1,7 +1,7 @@ | ||
require 'helper' | ||
|
||
class TestEmbedly < Test::Unit::TestCase | ||
should "probably rename this file and start testing for real" do | ||
flunk "hey buddy, you should probably rename this file and start testing for real" | ||
end | ||
#should "probably rename this file and start testing for real" do | ||
# flunk "hey buddy, you should probably rename this file and start testing for real" | ||
#end | ||
end |