jakimowicz-longurl 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/VERSION.yml ADDED
@@ -0,0 +1,4 @@
1
+ ---
2
+ :patch: 1
3
+ :major: 0
4
+ :minor: 0
data/bin/longurl ADDED
@@ -0,0 +1,15 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "rubygems"
4
+ require "longurl"
5
+
6
+ def usage
7
+ puts "Usage: #$0 <url>"
8
+ exit(-1)
9
+ end
10
+
11
+ if ARGV.size < 1
12
+ usage
13
+ end
14
+
15
+ puts LongURL.expand(ARGV[0])
data/lib/longurl.rb ADDED
@@ -0,0 +1,51 @@
1
+ # Copyright (c) 2009 by Fabien Jakimowicz (fabien@jakimowicz.com)
2
+ #
3
+ # Please see the LICENSE file for licensing.
4
+
5
+ require 'longurl/constants'
6
+ require 'longurl/exceptions'
7
+ require 'longurl/service'
8
+ require 'longurl/direct'
9
+
10
+ module LongURL
11
+
12
+ class << self
13
+
14
+ # Expand given <tt>:url</tt> to a longest one.
15
+ # First, expand will try to expand url using longurl.org service.
16
+ # Then, it will try to direct follow redirections on the given url and returns final one.
17
+ # === Options
18
+ # * <tt>:try_unsupported</tt> : use longurl.org to resolve the address, even if it is not a supported service
19
+ # * <tt>:direct_resolution</tt> : fetch url and follow redirection to find the final destination
20
+ # === Types
21
+ # <tt>url</tt> is expected to be a String and returns a String with the url.
22
+ # === Examples
23
+ # # simple expands
24
+ # LongURL.expand("http://tinyurl.com/1c2") # => "http://www.google.com"
25
+ # LongURL.expand("http://tinyurl.com/blnhsg") # => "http://www.google.com/search?q=number+of+horns+on+a+unicorn&ie=UTF-8"
26
+ # LongURL.expand("http://is.gd/iUKg") # => "http://fabien.jakimowicz.com"
27
+ #
28
+ # # not expandable urls, without any http call
29
+ # LongURL.expand("http://www.linuxfr.org") # => "http://www.linuxfr.org"
30
+ #
31
+ # # not expandable urls, calling longurl.org only
32
+ # LongURL.expand("http://www.linuxfr.org", :try_unsupported => true) # => "http://www.linuxfr.org/pub"
33
+ #
34
+ # # not expandable urls, direct resolution only
35
+ # LongURL.expand("http://www.linuxfr.org", :direct_resolution => true) # => "http://www.linuxfr.org/pub"
36
+ #
37
+ # # not expandable urls, longurl.org and direct resolution
38
+ # LongURL.expand("http://www.linuxfr.org",
39
+ # :try_unsupported => true, :direct_resolution => true) # => "http://www.linuxfr.org/pub"
40
+ # === Exceptions
41
+ # * LongURL::InvalidURL : will occurs if given url is nil, empty or invalid
42
+ # * LongURL::UnknownError : an unknown error occurs
43
+ def expand(url, options = {})
44
+ @@service ||= Service.new
45
+ options[:try_unsupported] ? @@service.query(url) : @@service.query_supported_service_only(url)
46
+ rescue UnsupportedService
47
+ options[:direct_resolution] ? Direct.follow_redirections(url) : url
48
+ end
49
+ end
50
+
51
+ end
@@ -0,0 +1,6 @@
1
+ require "uri"
2
+
3
+ module LongURL
4
+ EndPoint = URI.parse("http://api.longurl.org/v1/expand")
5
+ ServiceEndPoint = URI.parse("http://api.longurl.org/v1/services")
6
+ end
@@ -0,0 +1,15 @@
1
+ require 'uri'
2
+ require "net/http"
3
+
4
+ module LongURL
5
+ module Direct
6
+ def self.follow_redirections(orig)
7
+ uri = URI.parse(orig)
8
+ Net::HTTP.start(uri.host, uri.port) do |http|
9
+ answer = http.get(uri.path.empty? ? '/' : uri.path)
10
+ dest = answer['Location']
11
+ (dest && dest[0, 7] == 'http://' && follow_redirections(dest)) || orig
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,13 @@
1
+ module LongURL
2
+ # Raised by LongURL::Service class if longurl.org service returns unsupported service error.
3
+ class UnsupportedService < Exception
4
+ end
5
+
6
+ # Raised by LongURL::Service class if longurl.org service returns a not supported answer.
7
+ class UnknownError < Exception
8
+ end
9
+
10
+ # Raised by LongURL::Service if supplied url is invalid (nil, empty, ...)
11
+ class InvalidURL < Exception
12
+ end
13
+ end
@@ -0,0 +1,66 @@
1
+ require "net/http"
2
+ require "cgi"
3
+ require "uri"
4
+ require "rubygems"
5
+ require "json"
6
+ require "longurl/constants"
7
+ require "longurl/exceptions"
8
+
9
+ module LongURL
10
+
11
+ class Service
12
+
13
+ def initialize
14
+ @@supported_services = fetch_supported_services
15
+ end
16
+
17
+ def query_supported_service_only(url)
18
+ check url
19
+ raise LongURL::UnsupportedService unless service_supported?(url)
20
+ query url
21
+ end
22
+
23
+ def query(url)
24
+ escaped_url = check_and_escape(url)
25
+ Net::HTTP.start(EndPoint.host, EndPoint.port) do |http|
26
+ handle_response http.get("#{EndPoint.path}?format=json&url=#{escaped_url}")
27
+ end
28
+ end
29
+
30
+ def service_supported?(url)
31
+ @@supported_services.include? URI.parse(url).host.downcase
32
+ end
33
+
34
+ def check(url)
35
+ raise LongURL::InvalidURL if url.nil? or url.empty?
36
+ end
37
+
38
+ protected
39
+
40
+ def check_and_escape(url)
41
+ check url
42
+ CGI.escape url
43
+ end
44
+
45
+ def fetch_supported_services
46
+ Net::HTTP.start(ServiceEndPoint.host, ServiceEndPoint.port) do |http|
47
+ response = http.get("#{ServiceEndPoint.path}?format=json")
48
+ parsed = JSON.parse(response.body)
49
+ parsed.values.flatten
50
+ end
51
+ end
52
+
53
+ def handle_response(response)
54
+ parsed = JSON.parse(response.body)
55
+ if parsed['long_url']
56
+ parsed['long_url']
57
+ elsif parsed['message'] # Error
58
+ raise LongURL::UnsupportedService if parsed['messages']['message'] == 'Unsupported service.'
59
+ else
60
+ raise LongURL::UnknownError
61
+ end
62
+ end
63
+
64
+ end
65
+
66
+ end
@@ -0,0 +1,47 @@
1
+ # tc_service.rb
2
+ #
3
+ # Created by Vincent Foley on 2005-06-01
4
+
5
+ $test_lib_dir = File.join(File.dirname(__FILE__), "..", "lib")
6
+ $:.unshift($test_lib_dir)
7
+
8
+ require "test/unit"
9
+ require "longurl/exceptions"
10
+ require "longurl/service"
11
+
12
+ class TestService < Test::Unit::TestCase
13
+
14
+ ShortToLong = {:tiny_url => {
15
+ "http://tinyurl.com/cnuw9a" => "http://fabien.jakimowicz.com",
16
+ "http://tinyurl.com/blnhsg" => "http://www.google.com/search?q=number+of+horns+on+a+unicorn&ie=UTF-8"
17
+ },
18
+ :is_gd => {
19
+ "http://is.gd/iUKg" => "http://fabien.jakimowicz.com",
20
+ "http://is.gd/iYCo" => "http://www.google.com/search?q=number+of+horns+on+a+unicorn&ie=UTF-8"
21
+ }
22
+ }
23
+
24
+ def setup
25
+ @service = LongURL::Service.new
26
+ end
27
+
28
+ def test_query_should_raise_invalid_url_if_url_is_nil
29
+ assert_raise(LongURL::InvalidURL) { @service.query(nil) }
30
+ end
31
+
32
+ def test_query_should_raise_invalid_url_if_url_is_empty
33
+ assert_raise(LongURL::InvalidURL) { @service.query('') }
34
+ end
35
+
36
+ def test_query_should_returns_given_url_if_not_shorten_url
37
+ assert_equal "http://www.google.com", @service.query("http://www.google.com")
38
+ end
39
+
40
+ def test_query_should_returns_expanded_url_for_tiny_url
41
+ ShortToLong[:tiny_url].each {|short, long| assert_equal long, @service.query(short)}
42
+ end
43
+
44
+ def test_query_should_returns_expanded_url_for_is_gd
45
+ ShortToLong[:is_gd].each {|short, long| assert_equal long, @service.query(short)}
46
+ end
47
+ end
metadata ADDED
@@ -0,0 +1,70 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: jakimowicz-longurl
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Fabien Jakimowicz
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2009-02-10 00:00:00 -08:00
13
+ default_executable: longurl
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: json
17
+ version_requirement:
18
+ version_requirements: !ruby/object:Gem::Requirement
19
+ requirements:
20
+ - - ">="
21
+ - !ruby/object:Gem::Version
22
+ version: "0"
23
+ version:
24
+ description: LongURL expands short urls (tinyurl, is.gd, ...) to original ones, using on LongURL.org, internal resolution or direct resolution
25
+ email: fabien@jakimowicz.com
26
+ executables:
27
+ - longurl
28
+ extensions: []
29
+
30
+ extra_rdoc_files: []
31
+
32
+ files:
33
+ - VERSION.yml
34
+ - bin/longurl
35
+ - lib/longurl
36
+ - lib/longurl/constants.rb
37
+ - lib/longurl/direct.rb
38
+ - lib/longurl/exceptions.rb
39
+ - lib/longurl/service.rb
40
+ - lib/longurl.rb
41
+ - test/service_test.rb
42
+ has_rdoc: true
43
+ homepage: http://longurl.rubyforge.org
44
+ post_install_message:
45
+ rdoc_options:
46
+ - --inline-source
47
+ - --charset=UTF-8
48
+ require_paths:
49
+ - lib
50
+ required_ruby_version: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: "0"
55
+ version:
56
+ required_rubygems_version: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: "0"
61
+ version:
62
+ requirements: []
63
+
64
+ rubyforge_project: longurl
65
+ rubygems_version: 1.2.0
66
+ signing_key:
67
+ specification_version: 2
68
+ summary: LongURL expands shorten urls (tinyurl, is.gd, ...)
69
+ test_files: []
70
+