Skip to content

Instantly share code, notes, and snippets.

@lsegal
Forked from anonymous/config.ru
Last active August 29, 2015 13:58
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save lsegal/10222857 to your computer and use it in GitHub Desktop.
Save lsegal/10222857 to your computer and use it in GitHub Desktop.
require_relative 'boot'
db = Sequel.connect(ENV['DATABASE_URL'])
Urls.attach_db(db[:urls])
run UrlShortener
require 'sinatra/base'
require 'uri'
require_relative 'urls'
class UrlShortener < Sinatra::Application
INVALID_URL_ERROR = 'Please+enter+a+valid+URL'
get '/' do
error = params[:error]
url_to_shorten = params[:url]
erb :index, :locals => {:error => error, :url_to_shorten => url_to_shorten}
end
post '/shorten' do
url_to_shorten = params[:url]
if url_to_shorten.empty? || url_to_shorten.split(' ').count > 1 || !is_valid_url?(url_to_shorten) || url_to_shorten.nil?
redirect "/?url=#{url_to_shorten}&error=#{INVALID_URL_ERROR}"
else
begin
id = Urls.create(url_to_shorten)
redirect to("/#{id}?stats=true")
rescue Sequel::AlreadyExistsError
redirect "/?url=#{url_to_shorten}&error=This+already+exists"
end
end
end
get '/:id' do
stats = params[:stats] == 'true'
id = params[:id]
url_container = Urls.find(id)
new_url = "#{request.base_url}/#{id}"
if stats
erb :stats, :locals => {url_container: url_container, new_url: new_url} #{:original_url => original_url, :, :views => views}
else
url_container.increase_views
redirect original_url
end
end
private
def is_valid_url?(url_to_shorten)
url = false
if url_to_shorten.empty? || url_to_shorten.split(' ').count > 1 || url_to_shorten.nil?
elsif url_to_shorten
if url_to_shorten =~ /^#{URI::regexp}$/
url = true
end
url
end
end
end
class Urls
class << self
attr_accessor :db
def attach_db(db)
@db = db
end
def create(url, vanity_name = nil)
if vanity_name
@db.insert(url: url, vanity_name: vanity_name)
vanity_name
else
# wrap in a transaction
id = @db.insert(url: url)
@db.where(id: id).update(vanity_name: id.to_s)
id.to_s
end
end
def find(id)
new(@db.where(vanity_name: id))
end
end
attr_accessor :id, :stats, :url, :vanity_name
def initialize(record)
@record = record
data = record.first
@id = data[:id]
@stats = data[:stats]
@url = data[:url]
@vanity_name = data[:vanity_name]
end
def increase_views
@record.update(:stats => Sequel.+(:stats,1))
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment