# http://www.fsf.org/licensing/licenses/gpl.html
#
+# Needed for the default implementation of get_page_data.
+require 'net/http'
+
+# Necessary in a lot of subclasses; plus, we need it
+# to parse the server name out of our URL.
+require 'uri'
+
+# Needed to download.. things.
+require 'net/http'
+
# This class keeps track of all its subclasses
# We use this to loop through every "website" in an
# attempt to determine to which site a URL belongs.
class Website
+
+ protected;
+
+ @url = nil
+
+
def self.inherited(subclass)
if superclass.respond_to? :inherited
superclass.inherited(subclass)
@subclasses << subclass
end
- def self.subclasses
- @subclasses
+
+ def server
+ # Get the HTTP server portion of our URI
+ uri = URI.parse(@url)
+ return uri.host
end
- # This should be overridden in any class that wants
- # to claim ownership of a URL.
- def self.owns_url?(url)
- return false
+
+
+ def get_page_data(url)
+ # A naive implementation that just grabs the
+ # data from a page.
+ uri = URI.parse(url)
+
+ response = Net::HTTP.start(uri.host, uri.port) do |http|
+ http.get(uri.request_uri)
+ end
+
+ return response.body
end
- # Same here. We want to default to nil unless overridden.
- def get_video_url(url)
+
+
+ public;
+
+ def initialize(url)
+ @url = url
+ end
+
+
+ def self.create(url)
+ # Factory method returning an instance of
+ # the appropriate subclass.
+
+ # Check the URL against each website's class.
+ # The class will know whether or not the URL
+ # "belongs" to its website.
+ @subclasses.each do |w|
+ if w.owns_url?(url)
+ return w.new(url)
+ end
+ end
+
+ # If nothing matched, we don't return an instance
+ # of anything.
return nil
end
+
+
+ # Abstract definition. Each subclass of Website
+ # should support it on its own.
+ def self.owns_url?(url)
+ raise NotImplementedError
+ end
+
+
+ # Same here. Abstract.
+ def get_video_url()
+ raise NotImplementedError
+ end
+
+
+ # The website class should be responsible for determining the
+ # video's filename. By default, we can take the last component
+ # of the video URL, but in some cases, subclasses will want
+ # to override this behavior.
+ def get_video_filename()
+ # Use whatever comes after the final front slash.
+ return get_video_url().split('/').pop()
+ end
+
end