Skip to content

Commit

Permalink
first commit
Browse files Browse the repository at this point in the history
  • Loading branch information
aterreno committed Dec 25, 2011
0 parents commit cf69204
Show file tree
Hide file tree
Showing 8 changed files with 165 additions and 0 deletions.
1 change: 1 addition & 0 deletions .rbenv-version
@@ -0,0 +1 @@
1.9.2-p290
5 changes: 5 additions & 0 deletions Gemfile
@@ -0,0 +1,5 @@
source :rubygems

gem 'rack-raw-upload'
gem 'sinatra'
gem "haml"
23 changes: 23 additions & 0 deletions Gemfile.lock
@@ -0,0 +1,23 @@
GEM
remote: http://rubygems.org/
specs:
haml (3.1.4)
json (1.6.4)
rack (1.3.5)
rack-protection (1.1.4)
rack
rack-raw-upload (1.0.11)
json
sinatra (1.3.1)
rack (~> 1.3, >= 1.3.4)
rack-protection (~> 1.1, >= 1.1.2)
tilt (~> 1.3, >= 1.3.3)
tilt (1.3.3)

PLATFORMS
ruby

DEPENDENCIES
haml
rack-raw-upload
sinatra
6 changes: 6 additions & 0 deletions config.ru
@@ -0,0 +1,6 @@
require 'bundler'
Bundler.require
require './superupload'

use Rack::RawUpload
run Sinatra::Application
65 changes: 65 additions & 0 deletions lib/rack/raw_upload.rb
@@ -0,0 +1,65 @@
module Rack
class RawUpload

def initialize(app, opts = {})
@app = app
@paths = opts[:paths]
@paths = [@paths] if @paths.kind_of?(String)
end

def call(env)
raw_file_post?(env) ? convert_and_pass_on(env) : @app.call(env)
end

def upload_path?(request_path)
return true if @paths.nil?

@paths.any? do |candidate|
literal_path_match?(request_path, candidate) || wildcard_path_match?(request_path, candidate)
end
end


private

def convert_and_pass_on(env)
tempfile = Tempfile.new('raw-upload.')
tempfile << env['rack.input'].read
tempfile.flush
tempfile.rewind
fake_file = {
:filename => env['HTTP_X_FILE_NAME'],
:type => 'application/octet-stream',
:tempfile => tempfile,
}
env['rack.request.form_input'] = env['rack.input']
env['rack.request.form_hash'] ||= {}
env['rack.request.query_hash'] ||= {}
env['rack.request.form_hash']['file'] = fake_file
env['rack.request.query_hash']['file'] = fake_file
if query_params = env['HTTP_X_QUERY_PARAMS']
require 'json'
params = JSON.parse(query_params)
env['rack.request.form_hash'].merge!(params)
env['rack.request.query_hash'].merge!(params)
end
@app.call(env)
end

def raw_file_post?(env)
upload_path?(env['PATH_INFO']) &&
env['REQUEST_METHOD'] == 'POST' &&
env['CONTENT_TYPE'] == 'application/octet-stream'
end

def literal_path_match?(request_path, candidate)
candidate == request_path
end

def wildcard_path_match?(request_path, candidate)
return false unless candidate.include?('*')
regexp = '^' + candidate.gsub('.', '\.').gsub('*', '[^/]*') + '$'
!! (Regexp.new(regexp) =~ request_path)
end
end
end
44 changes: 44 additions & 0 deletions public/superupload.js
@@ -0,0 +1,44 @@
$(document).ready(function() {
document.getElementById('the-file').onchange = function () {
var fileInput = document.getElementById('the-file');
var file = fileInput.files[0];

var xhr = new XMLHttpRequest();
xhr.upload.addEventListener('loadstart', onloadstartHandler, false);
xhr.upload.addEventListener('progress', onprogressHandler, false);
xhr.upload.addEventListener('load', onloadHandler, false);
xhr.addEventListener('readystatechange', onreadystatechangeHandler, false);
xhr.open('POST', '/', true);
xhr.setRequestHeader("Content-Type", "application/octet-stream");
xhr.setRequestHeader("X-File-Name", file.name);
xhr.send(file); // Simple!

function onloadstartHandler(evt) {
$('#upload-status').html('Upload started!');
}

function onloadHandler(evt) {
$('#upload-status').html('Upload successful!');
}

function onprogressHandler(evt) {
var percent = evt.loaded/evt.total*100;
$('#progress').html('Progress: ' + percent.toFixed(2) + '%');
}

function onreadystatechangeHandler(evt) {
var status = null;

try {
status = evt.target.status;
}
catch(e) {
return;
}

if (status == '200' && evt.target.responseText) {
$('#result').html('<p>The server saw it as:</p><pre>' + evt.target.responseText + '</pre>');
}
}
}
});
9 changes: 9 additions & 0 deletions superupload.rb
@@ -0,0 +1,9 @@
require 'json'

get '/' do
haml :index
end

post '/' do
JSON.generate(params[:file])
end
12 changes: 12 additions & 0 deletions views/index.haml
@@ -0,0 +1,12 @@
!!!
%html{:lang => "en"}
%head
%meta{:charset => "utf-8"}
%title Superupload
%script{:src => "http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"}
%script{:src => "/superupload.js"}
%body
%input#the-file{:name => "file", :type => "file"}
%p#upload-status
%p#progress
#result

0 comments on commit cf69204

Please sign in to comment.