magickly 1.0.0 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/Gemfile CHANGED
@@ -6,6 +6,7 @@ source 'http://rubygems.org'
6
6
  gem 'sinatra', '~> 1.2.1', :require => 'sinatra/base'
7
7
  gem 'rack-cache', :require => 'rack/cache'
8
8
  gem 'dragonfly', '~> 0.8.2'
9
+ gem 'addressable', '~> 2.2', :require => 'addressable/uri'
9
10
 
10
11
  gem 'haml', '~> 3.0.25'
11
12
  gem 'httparty', '~> 0.7.3'
@@ -23,6 +24,6 @@ group :development, :test do
23
24
  gem 'rspec', '~> 2.4'
24
25
  gem 'webmock', '~> 1.6'
25
26
  gem 'imagesize', '~> 0.1'
26
- #gem 'ruby-debug19', :platforms => :ruby_19
27
- #gem 'ruby-debug', :platforms => :ruby_18
27
+ gem 'ruby-debug19', :platforms => :ruby_19
28
+ gem 'ruby-debug', :platforms => :ruby_18
28
29
  end
@@ -3,6 +3,8 @@ GEM
3
3
  specs:
4
4
  activesupport (3.0.5)
5
5
  addressable (2.2.4)
6
+ archive-tar-minitar (0.5.2)
7
+ columnize (0.3.2)
6
8
  crack (0.1.8)
7
9
  diff-lcs (1.1.2)
8
10
  dragonfly (0.8.2)
@@ -16,6 +18,9 @@ GEM
16
18
  bundler (~> 1.0.0)
17
19
  git (>= 1.2.5)
18
20
  rake
21
+ linecache (0.43)
22
+ linecache19 (0.5.12)
23
+ ruby_core_source (>= 0.1.4)
19
24
  rack (1.2.2)
20
25
  rack-cache (1.0)
21
26
  rack (>= 0.4)
@@ -31,6 +36,21 @@ GEM
31
36
  rspec-expectations (2.5.0)
32
37
  diff-lcs (~> 1.1.2)
33
38
  rspec-mocks (2.5.0)
39
+ ruby-debug (0.10.4)
40
+ columnize (>= 0.1)
41
+ ruby-debug-base (~> 0.10.4.0)
42
+ ruby-debug-base (0.10.4)
43
+ linecache (>= 0.3)
44
+ ruby-debug-base19 (0.11.25)
45
+ columnize (>= 0.3.1)
46
+ linecache19 (>= 0.5.11)
47
+ ruby_core_source (>= 0.1.4)
48
+ ruby-debug19 (0.11.6)
49
+ columnize (>= 0.3.1)
50
+ linecache19 (>= 0.5.11)
51
+ ruby-debug-base19 (>= 0.11.19)
52
+ ruby_core_source (0.1.5)
53
+ archive-tar-minitar (>= 0.5.2)
34
54
  sinatra (1.2.1)
35
55
  rack (~> 1.1)
36
56
  tilt (< 2.0, >= 1.2.2)
@@ -44,6 +64,7 @@ PLATFORMS
44
64
 
45
65
  DEPENDENCIES
46
66
  activesupport (>= 2.0.0)
67
+ addressable (~> 2.2)
47
68
  dragonfly (~> 0.8.2)
48
69
  haml (~> 3.0.25)
49
70
  httparty (~> 0.7.3)
@@ -53,5 +74,7 @@ DEPENDENCIES
53
74
  rack-test
54
75
  rcov
55
76
  rspec (~> 2.4)
77
+ ruby-debug
78
+ ruby-debug19
56
79
  sinatra (~> 1.2.1)
57
80
  webmock (~> 1.6)
@@ -0,0 +1,8 @@
1
+ # 1.1.0
2
+
3
+ * make underlying Dragonfly application accessible for external configuration
4
+ * major refactoring: namespacing inside of Magickly module (should be entirely backwards compatible)
5
+
6
+ # 1.0.0
7
+
8
+ * initial release
data/README.md CHANGED
@@ -2,34 +2,68 @@
2
2
 
3
3
  A service for image manipulation - built as a simple wrapper of Imagemagick which handles caching, c/o the [Dragonfly](http://markevans.github.com/dragonfly/) gem.
4
4
 
5
- ## Usage
5
+ Say the base URL is the hosted version of this app, [magickly.heroku.com](http://magickly.heroku.com). The image URL is appended to the query string as a `src=`, followed by any of the supported operations below. Multiple operations can be combined, and will be applied in order.
6
6
 
7
- Say the base URL is the hosted version of this app, [magickly.heroku.com](http://magickly.heroku.com). The image URL is appended to the query string as a `src=`, followed by any of the supported imagemagick operations. For example, you could get a 100x100 thumbnail of [the imagemagick logo](http://upload.wikimedia.org/wikipedia/commons/0/0d/Imagemagick-logo.png) like so:
7
+ ## Parameters
8
8
 
9
- [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/0/0d/Imagemagick-logo.png&resize=100x100](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/0/0d/Imagemagick-logo.png&resize=100x100)
9
+ *See the [Dragonfly documentation](http://markevans.github.com/dragonfly/file.Processing.html#ImageMagickProcessor) for more details about the permitted* `geometry` *values.*
10
10
 
11
- ### Parameters (required)
11
+ ### src=*url* (required)
12
12
 
13
- **src** - the URL of the original image
13
+ The URL of the original image.
14
14
 
15
- ### Parameters (optional):
15
+ ### flip=true
16
16
 
17
- See the [imagemagick command line params documentation](http://www.imagemagick.org/script/command-line-options.php) for details about allowed values.
17
+ ![flipped imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flip=true)
18
18
 
19
- **crop**
19
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flip=true](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flip=true)
20
20
 
21
- **flip**
21
+ ### flop=true
22
22
 
23
- **flop**
23
+ ![flopped imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flop=true)
24
24
 
25
- **greyscale**
25
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flop=true](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&flop=true)
26
26
 
27
- **resize**
27
+ ### greyscale=true
28
28
 
29
- **rotate**
29
+ ![flopped imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&greyscale=true)
30
30
 
31
- **thumb**
31
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&greyscale=true](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&greyscale=true)
32
32
 
33
+ ### resize=*geometry*
34
+
35
+ ![resized imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&resize=100x100)
36
+
37
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&resize=100x100](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&resize=100x100)
38
+
39
+ ### rotate=*degrees*
40
+
41
+ ![rotated imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&rotate=45)
42
+
43
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&rotate=45](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&rotate=45)
44
+
45
+ ### thumb=*geometry*
46
+
47
+ ![thumbnail of imagemagick logo](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&thumb=200x100%23)
48
+
49
+ [http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&thumb=200x100%23](http://magickly.heroku.com/?src=http://upload.wikimedia.org/wikipedia/commons/thumb/0/0d/Imagemagick-logo.png/200px-Imagemagick-logo.png&thumb=200x100%23)
50
+
51
+ (note: the `%23` in the geometry string above is an encoded '`#`', which tells Dragonfly to fill the dimensions and crop)
52
+
53
+ ## Customization
54
+
55
+ In addition to the available listed above, custom "shortcuts" can be created to perform arbitrary imagemagick operations. For example, to create a shortcut called `resize_with_blur`:
56
+
57
+ # somewhere in your app configuration, i.e. config/initializers/magickly.rb for a Rails 3 app
58
+ Magickly.dragonfly.configure do |c|
59
+ c.job :resize_with_blur do |size|
60
+ process :convert, "-filter Gaussian -resize #{size}"
61
+ end
62
+ end
63
+
64
+ which can then be used with the query string `?src=...&resize_with_blur=200x`. Note that magickly will pass the value of the query param to the block as a single string.
65
+
66
+ See the [Dragonfly documentation](http://markevans.github.com/dragonfly/file.GeneralUsage.html#Shortcuts) for more info on "shortcuts".
33
67
 
34
68
  ## Installation
35
69
 
@@ -47,13 +81,13 @@ The app can be accessed at [http://localhost:4567](http://localhost:4567)
47
81
 
48
82
  ### B. Use as an endpoint in another Rack app
49
83
 
50
- As an example, to have magickly accessible at `/images` in a Rails app:
84
+ As an example, to have magickly accessible at `/magickly` in a Rails app:
51
85
 
52
86
  # Gemfile
53
87
  gem 'magickly', '~> 0.1'
54
88
 
55
89
  # config/routes.rb
56
- match '/magickly', :to => MagicklyApp, :anchor => false
90
+ match '/magickly', :to => Magickly::App, :anchor => false
57
91
 
58
92
  For more info, see [Rails Routing from the Outside In](http://guides.rubyonrails.org/routing.html#routing-to-rack-applications) or Michael Raidel's [Mount Rails apps in Rails 3](http://inductor.induktiv.at/blog/2010/05/23/mount-rack-apps-in-rails-3/).
59
93
 
@@ -67,7 +101,7 @@ For more info, see [Rails Routing from the Outside In](http://guides.rubyonrails
67
101
  * Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.
68
102
  * Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.
69
103
 
70
- ## Copyright
104
+ ## Credits
105
+
106
+ Created by [Aidan Feldman](http://www.aidanfeldman.com) at [Jux.com](http://www.jux.com). Thanks to [Mark Evans](https://github.com/markevans) for all his hard work on [Dragonfly](http://markevans.github.com/dragonfly/).
71
107
 
72
- Copyright (c) 2011 Aidan Feldman. See LICENSE.txt for
73
- further details.
data/Rakefile CHANGED
@@ -15,8 +15,8 @@ Jeweler::Tasks.new do |gem|
15
15
  gem.name = "magickly"
16
16
  gem.homepage = "http://github.com/afeld/magickly"
17
17
  gem.license = "MIT"
18
- gem.summary = %Q{Imagemagick as a service}
19
- gem.description = %Q{A simple wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.}
18
+ gem.summary = %Q{image manipulation as a (plugin-able) service}
19
+ gem.description = %Q{A service for image manipulation - built as an extensible wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.}
20
20
  gem.email = "aidan.feldman@gmail.com"
21
21
  gem.authors = ["Aidan Feldman"]
22
22
  gem.executables = ['magickly']
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.0.0
1
+ 1.1.0
@@ -9,4 +9,4 @@ rescue LoadError => e
9
9
  require 'magickly'
10
10
  end
11
11
 
12
- MagicklyApp.run!
12
+ Magickly::App.run!
data/config.ru CHANGED
@@ -3,4 +3,4 @@ require 'bundler'
3
3
  Bundler.require
4
4
 
5
5
  require File.join(File.dirname(__FILE__), 'lib', 'magickly')
6
- run MagicklyApp
6
+ run Magickly::App
@@ -2,7 +2,6 @@ require 'httparty'
2
2
 
3
3
  module Dragonfly
4
4
  module DataStorage
5
-
6
5
  #class Forbidden < StandardError; end
7
6
 
8
7
  class RemoteDataStore
@@ -4,66 +4,51 @@ require 'active_support/ordered_hash'
4
4
  require 'sinatra/base'
5
5
  require 'dragonfly'
6
6
  require File.expand_path(File.join(File.dirname(__FILE__), 'dragonfly', 'data_storage', 'remote_data_store'))
7
+ Dir["#{File.dirname(__FILE__)}/magickly/*.rb"].each {|file| require file }
7
8
 
8
9
 
9
- class MagicklyApp < Sinatra::Base
10
- RESERVED_PARAMS = ['src']
10
+ module Magickly
11
+ # fallback for Dragonfly v0.8.2 and below
12
+ dragonfly_processor = Dragonfly::ImageMagick::Processor rescue Dragonfly::Processing::ImageMagickProcessor
13
+ @dragonfly_processor_methods = dragonfly_processor.instance_methods(false)
11
14
 
12
- enable :logging
13
- set :root, File.dirname(__FILE__)
14
- set :homepage, "http://github.com/afeld/magickly"
15
-
16
- dragonfly = Dragonfly[:images].configure_with(:imagemagick)
17
- dragonfly.configure do |c|
15
+ @dragonfly = Dragonfly[:images].configure_with(:imagemagick)
16
+ @dragonfly.configure do |c|
18
17
  c.datastore = Dragonfly::DataStorage::RemoteDataStore.new
19
18
  c.log = Logger.new($stdout)
20
19
  end
21
- set :dragonfly, dragonfly
22
-
23
- def magickify(src, options={})
24
- raise ArgumentError.new("src needed") if src.blank?
25
- escaped_src = URI.escape(src)
26
- image = settings.dragonfly.fetch(escaped_src)
27
-
28
- options.each do |method, val|
29
- if val == 'true'
30
- image = image.process method
31
- else
32
- image = image.process method, val
33
- end
34
- end
35
-
36
- image
37
- end
38
20
 
39
- before do
40
- dragonfly.datastore.configure do |d|
41
- # pass cookies to subsequent request
42
- d.cookie_str = request.env["rack.request.cookie_string"]
21
+ class << self
22
+ def dragonfly
23
+ @dragonfly
43
24
  end
44
25
 
45
- @options = ActiveSupport::OrderedHash.new
46
- request.query_string.split('&').each do |e|
47
- k,v = e.split('=')
48
- @options[k] = v unless RESERVED_PARAMS.include?(k)
26
+ def process_src(src, options={})
27
+ raise ArgumentError.new("src needed") if src.blank?
28
+ escaped_src = URI.escape(src)
29
+ image = Magickly.dragonfly.fetch(escaped_src)
30
+
31
+ process_image(image, options)
49
32
  end
50
- end
51
-
52
- get '/' do
53
- src = params['src']
54
33
 
55
- if src
56
- image = magickify(src, @options)
57
- image.to_response(env)
58
- else
59
- # fallback for Dragonfly v0.8.2 and below
60
- klass = Dragonfly::ImageMagick::Processor rescue Dragonfly::Processing::ImageMagickProcessor
61
- @methods = klass.instance_methods(false)
62
- haml :index
34
+ def process_image(image, options={})
35
+ options.each do |method, val|
36
+ if !@dragonfly_processor_methods.include?(method)
37
+ # might be an app-defined dragonfly shortcut
38
+ image = image.send(method, val)
39
+ elsif val == 'true'
40
+ image = image.process method
41
+ else
42
+ image = image.process method, val
43
+ end
44
+ end
45
+
46
+ image
63
47
  end
64
48
  end
65
-
66
- # start the server if ruby file executed directly
67
- run! if __FILE__ == $0
68
49
  end
69
50
 
51
+ require File.expand_path(File.join(File.dirname(__FILE__), 'shortcuts'))
52
+
53
+ # start the server if ruby file executed directly
54
+ Magickly::App.run! if __FILE__ == $0
@@ -0,0 +1,52 @@
1
+ module Magickly
2
+ class App < Sinatra::Base
3
+ RESERVED_PARAMS = ['src']
4
+
5
+ enable :logging
6
+ set :root, File.join(File.dirname(__FILE__), '..')
7
+ set :homepage, "http://github.com/afeld/magickly"
8
+
9
+ before do
10
+ Magickly.dragonfly.datastore.configure do |d|
11
+ # pass cookies to subsequent request
12
+ d.cookie_str = request.env["rack.request.cookie_string"]
13
+ end
14
+
15
+ @options = ActiveSupport::OrderedHash.new
16
+ request.query_string.split('&').each do |e|
17
+ k,v = e.split('=')
18
+ @options[k] = URI.unescape(v) unless RESERVED_PARAMS.include?(k)
19
+ end
20
+ end
21
+
22
+ get '/' do
23
+ src = params['src']
24
+
25
+ if src
26
+ uri = Addressable::URI.parse(src)
27
+ uri.site ||= Addressable::URI.parse(request.url).site
28
+
29
+ image = Magickly.process_src(uri.to_s, @options)
30
+ image.to_response(env)
31
+ else
32
+ # display demo page
33
+
34
+ # fallback for Dragonfly v0.8.2 and below
35
+ klass = Dragonfly::ImageMagick::Processor rescue Dragonfly::Processing::ImageMagickProcessor
36
+ @methods = klass.instance_methods(false)
37
+ haml :index
38
+ end
39
+ end
40
+
41
+ # start the server if ruby file executed directly
42
+ run! if __FILE__ == $0
43
+ end
44
+ end
45
+
46
+ class MagicklyApp < Magickly::App
47
+ # <b>DEPRECATED:</b> Please use <tt>Magickly::App</tt> instead.
48
+ def self.run
49
+ warn "This has been deprecated - please use Magickly::App.run"
50
+ super
51
+ end
52
+ end
@@ -0,0 +1,14 @@
1
+ Magickly.dragonfly.configure do |c|
2
+ c.job :resize_with_blur do |size|
3
+ process :convert, "-filter Gaussian -resize #{size}"
4
+ end
5
+
6
+ # c.job :tilt_shift do |coefficients|
7
+ # if coefficients == 'true'
8
+ # coefficients = "2,-2,0.5"
9
+ # end
10
+ #
11
+ # action = "\\( +clone -sparse-color Barycentric '0,0 black 0,%[fx:h-1] white' -function polynomial #{coefficients} \\) -compose Blur -set option:compose:args 15 -composite"
12
+ # process :convert, action
13
+ # end
14
+ end
@@ -22,6 +22,16 @@
22
22
  $('#src-img').change(updateResult);
23
23
  $('#params').change(updateResult);
24
24
  });
25
+
26
+ var _gaq = _gaq || [];
27
+ _gaq.push(['_setAccount', 'UA-22837777-1']);
28
+ _gaq.push(['_trackPageview']);
29
+
30
+ (function() {
31
+ var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
32
+ ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
33
+ var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
34
+ })();
25
35
 
26
36
  %body
27
37
  %h1 Welcome to Magickly
@@ -5,12 +5,12 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{magickly}
8
- s.version = "1.0.0"
8
+ s.version = "1.1.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Aidan Feldman"]
12
- s.date = %q{2011-04-19}
13
- s.description = %q{A simple wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.}
12
+ s.date = %q{2011-04-26}
13
+ s.description = %q{A service for image manipulation - built as an extensible wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.}
14
14
  s.email = %q{aidan.feldman@gmail.com}
15
15
  s.executables = ["magickly"]
16
16
  s.extra_rdoc_files = [
@@ -23,6 +23,7 @@ Gem::Specification.new do |s|
23
23
  ".rspec",
24
24
  "Gemfile",
25
25
  "Gemfile.lock",
26
+ "HISTORY.md",
26
27
  "LICENSE.txt",
27
28
  "README.md",
28
29
  "Rakefile",
@@ -31,20 +32,27 @@ Gem::Specification.new do |s|
31
32
  "config.ru",
32
33
  "lib/dragonfly/data_storage/remote_data_store.rb",
33
34
  "lib/magickly.rb",
35
+ "lib/magickly/app.rb",
36
+ "lib/public/imagemagick.png",
37
+ "lib/shortcuts.rb",
34
38
  "lib/views/index.haml",
35
39
  "magickly.gemspec",
36
- "spec/requests/magickly_spec.rb",
40
+ "spec/requests/magickly_app_spec.rb",
37
41
  "spec/spec_helper.rb",
38
- "spec/support/imagemagick.png"
42
+ "spec/support/imagemagick.png",
43
+ "spec/unit/magickly_spec.rb",
44
+ "spec/unit/remote_data_store_spec.rb"
39
45
  ]
40
46
  s.homepage = %q{http://github.com/afeld/magickly}
41
47
  s.licenses = ["MIT"]
42
48
  s.require_paths = ["lib"]
43
49
  s.rubygems_version = %q{1.7.2}
44
- s.summary = %q{Imagemagick as a service}
50
+ s.summary = %q{image manipulation as a (plugin-able) service}
45
51
  s.test_files = [
46
- "spec/requests/magickly_spec.rb",
47
- "spec/spec_helper.rb"
52
+ "spec/requests/magickly_app_spec.rb",
53
+ "spec/spec_helper.rb",
54
+ "spec/unit/magickly_spec.rb",
55
+ "spec/unit/remote_data_store_spec.rb"
48
56
  ]
49
57
 
50
58
  if s.respond_to? :specification_version then
@@ -54,6 +62,7 @@ Gem::Specification.new do |s|
54
62
  s.add_runtime_dependency(%q<sinatra>, ["~> 1.2.1"])
55
63
  s.add_runtime_dependency(%q<rack-cache>, [">= 0"])
56
64
  s.add_runtime_dependency(%q<dragonfly>, ["~> 0.8.2"])
65
+ s.add_runtime_dependency(%q<addressable>, ["~> 2.2"])
57
66
  s.add_runtime_dependency(%q<haml>, ["~> 3.0.25"])
58
67
  s.add_runtime_dependency(%q<httparty>, ["~> 0.7.3"])
59
68
  s.add_runtime_dependency(%q<activesupport>, [">= 2.0.0"])
@@ -63,10 +72,13 @@ Gem::Specification.new do |s|
63
72
  s.add_development_dependency(%q<rspec>, ["~> 2.4"])
64
73
  s.add_development_dependency(%q<webmock>, ["~> 1.6"])
65
74
  s.add_development_dependency(%q<imagesize>, ["~> 0.1"])
75
+ s.add_development_dependency(%q<ruby-debug19>, [">= 0"])
76
+ s.add_development_dependency(%q<ruby-debug>, [">= 0"])
66
77
  else
67
78
  s.add_dependency(%q<sinatra>, ["~> 1.2.1"])
68
79
  s.add_dependency(%q<rack-cache>, [">= 0"])
69
80
  s.add_dependency(%q<dragonfly>, ["~> 0.8.2"])
81
+ s.add_dependency(%q<addressable>, ["~> 2.2"])
70
82
  s.add_dependency(%q<haml>, ["~> 3.0.25"])
71
83
  s.add_dependency(%q<httparty>, ["~> 0.7.3"])
72
84
  s.add_dependency(%q<activesupport>, [">= 2.0.0"])
@@ -76,11 +88,14 @@ Gem::Specification.new do |s|
76
88
  s.add_dependency(%q<rspec>, ["~> 2.4"])
77
89
  s.add_dependency(%q<webmock>, ["~> 1.6"])
78
90
  s.add_dependency(%q<imagesize>, ["~> 0.1"])
91
+ s.add_dependency(%q<ruby-debug19>, [">= 0"])
92
+ s.add_dependency(%q<ruby-debug>, [">= 0"])
79
93
  end
80
94
  else
81
95
  s.add_dependency(%q<sinatra>, ["~> 1.2.1"])
82
96
  s.add_dependency(%q<rack-cache>, [">= 0"])
83
97
  s.add_dependency(%q<dragonfly>, ["~> 0.8.2"])
98
+ s.add_dependency(%q<addressable>, ["~> 2.2"])
84
99
  s.add_dependency(%q<haml>, ["~> 3.0.25"])
85
100
  s.add_dependency(%q<httparty>, ["~> 0.7.3"])
86
101
  s.add_dependency(%q<activesupport>, [">= 2.0.0"])
@@ -90,6 +105,8 @@ Gem::Specification.new do |s|
90
105
  s.add_dependency(%q<rspec>, ["~> 2.4"])
91
106
  s.add_dependency(%q<webmock>, ["~> 1.6"])
92
107
  s.add_dependency(%q<imagesize>, ["~> 0.1"])
108
+ s.add_dependency(%q<ruby-debug19>, [">= 0"])
109
+ s.add_dependency(%q<ruby-debug>, [">= 0"])
93
110
  end
94
111
  end
95
112
 
@@ -0,0 +1,109 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+
3
+ describe Magickly::App do
4
+ include Rack::Test::Methods
5
+
6
+ def app
7
+ Magickly::App
8
+ end
9
+
10
+ describe "GET /" do
11
+ def setup_image(host='http://www.foo.com')
12
+ @image_filename = 'imagemagick.png'
13
+ @image_url = "#{host}/#{@image_filename}"
14
+ @image_path = File.join(File.dirname(__FILE__), '..', 'support', @image_filename)
15
+ stub_request(:get, @image_url).to_return(:body => File.new(@image_path))
16
+ end
17
+
18
+ it "should display the demo page for no params" do
19
+ get '/'
20
+ last_response.should be_ok
21
+ # TODO test that it renders the view
22
+ end
23
+
24
+ it "retrieves an image with no options" do
25
+ setup_image
26
+
27
+ get "/?src=#{@image_url}"
28
+
29
+ a_request(:get, @image_url).should have_been_made.once
30
+ last_response.should be_ok
31
+
32
+ # check that the returned file is identical to the original
33
+ last_response.body.should eq IO.read(@image_path)
34
+ end
35
+
36
+ it "retrieves an image at a relative URI" do
37
+ setup_image "http://#{Rack::Test::DEFAULT_HOST}"
38
+
39
+ get "/?src=/#{@image_filename}"
40
+
41
+ a_request(:get, @image_url).should have_been_made.once
42
+ last_response.should be_ok
43
+
44
+ # check that the returned file is identical to the original
45
+ last_response.body.should eq IO.read(@image_path)
46
+ end
47
+
48
+ it "resizes an image" do
49
+ setup_image
50
+ width = 100
51
+
52
+ get "/?src=#{@image_url}&resize=#{width}x"
53
+
54
+ a_request(:get, @image_url).should have_been_made.once
55
+ last_response.should be_ok
56
+ ImageSize.new(last_response.body).get_width.should eq width
57
+ end
58
+
59
+ it "should use my Dragonfly shortcut with no arguments" do
60
+ setup_image
61
+ width = 100
62
+ shortcut = :filter_with_no_arguments
63
+ Magickly.dragonfly.configure do |c|
64
+ c.job shortcut do
65
+ process :convert, "-filter Gaussian -resize #{width}x"
66
+ end
67
+ end
68
+
69
+ get "/?src=#{@image_url}&#{shortcut}=true"
70
+
71
+ last_response.should be_ok
72
+ ImageSize.new(last_response.body).get_width.should eq width
73
+ end
74
+
75
+ it "should use my Dragonfly shortcut with one argument" do
76
+ setup_image
77
+ width = 100
78
+ shortcut = :filter_with_one_argument
79
+ Magickly.dragonfly.configure do |c|
80
+ c.job shortcut do |size|
81
+ process :thumb, size
82
+ end
83
+ end
84
+
85
+ get "/?src=#{@image_url}&#{shortcut}=#{width}x"
86
+
87
+ last_response.should be_ok
88
+ ImageSize.new(last_response.body).get_width.should eq width
89
+ end
90
+ end
91
+ end
92
+
93
+ describe MagicklyApp do
94
+ include Rack::Test::Methods
95
+
96
+ def app
97
+ MagicklyApp
98
+ end
99
+
100
+ describe "backward compatibility test" do
101
+
102
+ it "should display the demo page for no params" do
103
+ get '/'
104
+ last_response.should be_ok
105
+ # TODO test that it renders the view
106
+ end
107
+
108
+ end
109
+ end
@@ -5,7 +5,7 @@ require 'rack/test'
5
5
  require 'sinatra'
6
6
  require 'webmock/rspec'
7
7
  require 'image_size'
8
- #require 'ruby-debug'
8
+ require 'ruby-debug'
9
9
 
10
10
  # Requires supporting files with custom matchers and macros, etc,
11
11
  # in ./support/ and its subdirectories.
@@ -16,3 +16,4 @@ set :environment, :test
16
16
  RSpec.configure do |config|
17
17
 
18
18
  end
19
+
Binary file
@@ -0,0 +1,22 @@
1
+ require 'spec_helper'
2
+
3
+ describe Magickly do
4
+ describe ".process_src" do
5
+ it "retrieves an image with no options" do
6
+ image_url = "http://www.foo.com/imagemagick.png"
7
+ image_path = File.join(File.dirname(__FILE__), '..', 'support', 'imagemagick.png')
8
+ stub_request(:get, image_url).to_return(:body => File.new(image_path))
9
+
10
+ returned_image = Magickly.process_src(image_url)
11
+
12
+ returned_image.should_not be_nil
13
+
14
+ # check that the returned file is identical to the original
15
+ IO.read(returned_image.file.path).should eq IO.read(image_path)
16
+ end
17
+ end
18
+
19
+ describe ".process_image" do
20
+ it "doesn't modify the image if given no options"
21
+ end
22
+ end
@@ -0,0 +1,25 @@
1
+ require 'spec_helper'
2
+
3
+ describe Dragonfly::DataStorage::RemoteDataStore do
4
+ describe '#retrieve' do
5
+ it "should successfully make requests" do
6
+ url = "http://www.foo.com/iamgemagick.png"
7
+ stub_request(:get, url)
8
+ datastore = Dragonfly::DataStorage::RemoteDataStore.new
9
+
10
+ datastore.retrieve url
11
+ a_request(:get, url).should have_been_made.once
12
+ end
13
+
14
+ it "should return the image" do
15
+ url = "http://www.foo.com/imagemagick.png"
16
+ image_path = File.join(File.dirname(__FILE__), '..', 'support', 'imagemagick.png')
17
+ stub_request(:get, url).to_return(:body => File.new(image_path))
18
+ datastore = Dragonfly::DataStorage::RemoteDataStore.new
19
+
20
+ image,extra = datastore.retrieve(url)
21
+ image.should eq IO.read(image_path)
22
+ end
23
+ end
24
+ end
25
+
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: magickly
3
3
  version: !ruby/object:Gem::Version
4
- hash: 23
4
+ hash: 19
5
5
  prerelease:
6
6
  segments:
7
7
  - 1
8
+ - 1
8
9
  - 0
9
- - 0
10
- version: 1.0.0
10
+ version: 1.1.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - Aidan Feldman
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-04-19 00:00:00 Z
18
+ date: 2011-04-26 00:00:00 Z
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
21
21
  requirement: &id001 !ruby/object:Gem::Requirement
@@ -65,6 +65,21 @@ dependencies:
65
65
  type: :runtime
66
66
  - !ruby/object:Gem::Dependency
67
67
  requirement: &id004 !ruby/object:Gem::Requirement
68
+ none: false
69
+ requirements:
70
+ - - ~>
71
+ - !ruby/object:Gem::Version
72
+ hash: 7
73
+ segments:
74
+ - 2
75
+ - 2
76
+ version: "2.2"
77
+ version_requirements: *id004
78
+ name: addressable
79
+ prerelease: false
80
+ type: :runtime
81
+ - !ruby/object:Gem::Dependency
82
+ requirement: &id005 !ruby/object:Gem::Requirement
68
83
  none: false
69
84
  requirements:
70
85
  - - ~>
@@ -75,12 +90,12 @@ dependencies:
75
90
  - 0
76
91
  - 25
77
92
  version: 3.0.25
78
- version_requirements: *id004
93
+ version_requirements: *id005
79
94
  name: haml
80
95
  prerelease: false
81
96
  type: :runtime
82
97
  - !ruby/object:Gem::Dependency
83
- requirement: &id005 !ruby/object:Gem::Requirement
98
+ requirement: &id006 !ruby/object:Gem::Requirement
84
99
  none: false
85
100
  requirements:
86
101
  - - ~>
@@ -91,12 +106,12 @@ dependencies:
91
106
  - 7
92
107
  - 3
93
108
  version: 0.7.3
94
- version_requirements: *id005
109
+ version_requirements: *id006
95
110
  name: httparty
96
111
  prerelease: false
97
112
  type: :runtime
98
113
  - !ruby/object:Gem::Dependency
99
- requirement: &id006 !ruby/object:Gem::Requirement
114
+ requirement: &id007 !ruby/object:Gem::Requirement
100
115
  none: false
101
116
  requirements:
102
117
  - - ">="
@@ -107,12 +122,12 @@ dependencies:
107
122
  - 0
108
123
  - 0
109
124
  version: 2.0.0
110
- version_requirements: *id006
125
+ version_requirements: *id007
111
126
  name: activesupport
112
127
  prerelease: false
113
128
  type: :runtime
114
129
  - !ruby/object:Gem::Dependency
115
- requirement: &id007 !ruby/object:Gem::Requirement
130
+ requirement: &id008 !ruby/object:Gem::Requirement
116
131
  none: false
117
132
  requirements:
118
133
  - - ~>
@@ -122,12 +137,12 @@ dependencies:
122
137
  - 1
123
138
  - 5
124
139
  version: "1.5"
125
- version_requirements: *id007
140
+ version_requirements: *id008
126
141
  name: jeweler
127
142
  prerelease: false
128
143
  type: :development
129
144
  - !ruby/object:Gem::Dependency
130
- requirement: &id008 !ruby/object:Gem::Requirement
145
+ requirement: &id009 !ruby/object:Gem::Requirement
131
146
  none: false
132
147
  requirements:
133
148
  - - ">="
@@ -136,12 +151,12 @@ dependencies:
136
151
  segments:
137
152
  - 0
138
153
  version: "0"
139
- version_requirements: *id008
154
+ version_requirements: *id009
140
155
  name: rcov
141
156
  prerelease: false
142
157
  type: :development
143
158
  - !ruby/object:Gem::Dependency
144
- requirement: &id009 !ruby/object:Gem::Requirement
159
+ requirement: &id010 !ruby/object:Gem::Requirement
145
160
  none: false
146
161
  requirements:
147
162
  - - ">="
@@ -150,12 +165,12 @@ dependencies:
150
165
  segments:
151
166
  - 0
152
167
  version: "0"
153
- version_requirements: *id009
168
+ version_requirements: *id010
154
169
  name: rack-test
155
170
  prerelease: false
156
171
  type: :development
157
172
  - !ruby/object:Gem::Dependency
158
- requirement: &id010 !ruby/object:Gem::Requirement
173
+ requirement: &id011 !ruby/object:Gem::Requirement
159
174
  none: false
160
175
  requirements:
161
176
  - - ~>
@@ -165,12 +180,12 @@ dependencies:
165
180
  - 2
166
181
  - 4
167
182
  version: "2.4"
168
- version_requirements: *id010
183
+ version_requirements: *id011
169
184
  name: rspec
170
185
  prerelease: false
171
186
  type: :development
172
187
  - !ruby/object:Gem::Dependency
173
- requirement: &id011 !ruby/object:Gem::Requirement
188
+ requirement: &id012 !ruby/object:Gem::Requirement
174
189
  none: false
175
190
  requirements:
176
191
  - - ~>
@@ -180,12 +195,12 @@ dependencies:
180
195
  - 1
181
196
  - 6
182
197
  version: "1.6"
183
- version_requirements: *id011
198
+ version_requirements: *id012
184
199
  name: webmock
185
200
  prerelease: false
186
201
  type: :development
187
202
  - !ruby/object:Gem::Dependency
188
- requirement: &id012 !ruby/object:Gem::Requirement
203
+ requirement: &id013 !ruby/object:Gem::Requirement
189
204
  none: false
190
205
  requirements:
191
206
  - - ~>
@@ -195,11 +210,39 @@ dependencies:
195
210
  - 0
196
211
  - 1
197
212
  version: "0.1"
198
- version_requirements: *id012
213
+ version_requirements: *id013
199
214
  name: imagesize
200
215
  prerelease: false
201
216
  type: :development
202
- description: A simple wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.
217
+ - !ruby/object:Gem::Dependency
218
+ requirement: &id014 !ruby/object:Gem::Requirement
219
+ none: false
220
+ requirements:
221
+ - - ">="
222
+ - !ruby/object:Gem::Version
223
+ hash: 3
224
+ segments:
225
+ - 0
226
+ version: "0"
227
+ version_requirements: *id014
228
+ name: ruby-debug19
229
+ prerelease: false
230
+ type: :development
231
+ - !ruby/object:Gem::Dependency
232
+ requirement: &id015 !ruby/object:Gem::Requirement
233
+ none: false
234
+ requirements:
235
+ - - ">="
236
+ - !ruby/object:Gem::Version
237
+ hash: 3
238
+ segments:
239
+ - 0
240
+ version: "0"
241
+ version_requirements: *id015
242
+ name: ruby-debug
243
+ prerelease: false
244
+ type: :development
245
+ description: A service for image manipulation - built as an extensible wrapper of Imagemagick which handles caching, c/o the Dragonfly gem.
203
246
  email: aidan.feldman@gmail.com
204
247
  executables:
205
248
  - magickly
@@ -214,6 +257,7 @@ files:
214
257
  - .rspec
215
258
  - Gemfile
216
259
  - Gemfile.lock
260
+ - HISTORY.md
217
261
  - LICENSE.txt
218
262
  - README.md
219
263
  - Rakefile
@@ -222,11 +266,16 @@ files:
222
266
  - config.ru
223
267
  - lib/dragonfly/data_storage/remote_data_store.rb
224
268
  - lib/magickly.rb
269
+ - lib/magickly/app.rb
270
+ - lib/public/imagemagick.png
271
+ - lib/shortcuts.rb
225
272
  - lib/views/index.haml
226
273
  - magickly.gemspec
227
- - spec/requests/magickly_spec.rb
274
+ - spec/requests/magickly_app_spec.rb
228
275
  - spec/spec_helper.rb
229
276
  - spec/support/imagemagick.png
277
+ - spec/unit/magickly_spec.rb
278
+ - spec/unit/remote_data_store_spec.rb
230
279
  homepage: http://github.com/afeld/magickly
231
280
  licenses:
232
281
  - MIT
@@ -259,7 +308,9 @@ rubyforge_project:
259
308
  rubygems_version: 1.7.2
260
309
  signing_key:
261
310
  specification_version: 3
262
- summary: Imagemagick as a service
311
+ summary: image manipulation as a (plugin-able) service
263
312
  test_files:
264
- - spec/requests/magickly_spec.rb
313
+ - spec/requests/magickly_app_spec.rb
265
314
  - spec/spec_helper.rb
315
+ - spec/unit/magickly_spec.rb
316
+ - spec/unit/remote_data_store_spec.rb
@@ -1,42 +0,0 @@
1
- require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
-
3
- describe MagicklyApp do
4
- include Rack::Test::Methods
5
-
6
- def app
7
- MagicklyApp
8
- end
9
-
10
- it "says hello" do
11
- get '/'
12
- last_response.should be_ok
13
- end
14
-
15
- it "retrieves an image with no options" do
16
- image_url = "http://www.foo.com/imagemagick.png"
17
- image_path = File.join(File.dirname(__FILE__), '..', 'support', 'imagemagick.png')
18
- stub_request(:get, image_url).to_return(:body => File.new(image_path))
19
-
20
- get "/?src=#{image_url}"
21
-
22
- a_request(:get, image_url).should have_been_made.once
23
- last_response.should be_ok
24
-
25
- # check that the returned file is identical to the original
26
- last_response.body.should eq IO.read(image_path)
27
- end
28
-
29
- it "resizes an image" do
30
- image_url = "http://www.foo.com/imagemagick.png"
31
- image_path = File.join(File.dirname(__FILE__), '..', 'support', 'imagemagick.png')
32
- stub_request(:get, image_url).to_return(:body => File.new(image_path))
33
- width = 100
34
-
35
- get "/?src=#{image_url}&resize=#{width}x"
36
-
37
- a_request(:get, image_url).should have_been_made.once
38
- last_response.should be_ok
39
-
40
- ImageSize.new(last_response.body).get_width.should eq width
41
- end
42
- end