dandify 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (46) hide show
  1. checksums.yaml +7 -0
  2. data/MIT-LICENSE +22 -0
  3. data/README.md +52 -0
  4. data/Rakefile +15 -0
  5. data/app/assets/javascripts/spree/backend/dandify.js +0 -0
  6. data/app/assets/javascripts/spree/frontend/dandify.js +0 -0
  7. data/app/assets/stylesheets/spree/backend/dandify.css +42 -0
  8. data/app/assets/stylesheets/spree/frontend/dandify.css +0 -0
  9. data/app/controllers/spree/admin/stylesheets_controller.rb +58 -0
  10. data/app/controllers/spree/stylesheets_controller.rb +15 -0
  11. data/app/helpers/spree/admin/navigation_helper_decorator.rb +9 -0
  12. data/app/helpers/spree/admin/stylesheet_helper.rb +9 -0
  13. data/app/models/spree/blank_stylesheet.rb +7 -0
  14. data/app/models/spree/stylesheet.rb +30 -0
  15. data/app/models/spree/stylesheet_version.rb +5 -0
  16. data/app/models/spree/user_decorator.rb +5 -0
  17. data/app/overrides/spree/admin/shared/_configuration_menu/add_dandify_to_admin_configuration_sidebar.html.erb.deface +2 -0
  18. data/app/overrides/spree/shared/_head/add_dandystyles_link.html.erb.deface +2 -0
  19. data/app/views/spree/admin/stylesheets/_form.html.erb +11 -0
  20. data/app/views/spree/admin/stylesheets/_versions.html.erb +32 -0
  21. data/app/views/spree/admin/stylesheets/edit.html.erb +19 -0
  22. data/app/views/spree/admin/stylesheets/new.html.erb +19 -0
  23. data/app/views/spree/admin/stylesheets/show.html.erb +23 -0
  24. data/app/views/spree/stylesheets/show.css.erb +1 -0
  25. data/config/locales/en.yml +37 -0
  26. data/config/routes.rb +9 -0
  27. data/config/spring.rb +1 -0
  28. data/db/migrate/20140616202617_create_spree_stylesheets.rb +10 -0
  29. data/db/migrate/20140617221725_add_paper_trail_versions.rb +13 -0
  30. data/lib/dandify.rb +7 -0
  31. data/lib/dandify/engine.rb +18 -0
  32. data/lib/dandify/version.rb +3 -0
  33. data/lib/generators/dandify/install/install_generator.rb +24 -0
  34. data/lib/tasks/dandify_tasks.rake +4 -0
  35. data/spec/controllers/spree/admin/stylesheets_controller_spec.rb +71 -0
  36. data/spec/controllers/spree/stylesheets_controller_spec.rb +36 -0
  37. data/spec/factories/stylesheet_factory.rb +5 -0
  38. data/spec/features/dandy_style_spec.rb +10 -0
  39. data/spec/features/managing_stylsheet_spec.rb +80 -0
  40. data/spec/features/sidebar_spec.rb +41 -0
  41. data/spec/features/viewing_admin_spec.rb +49 -0
  42. data/spec/helpers/admin/navigation_helper_spec.rb +14 -0
  43. data/spec/models/spree/blank_stylesheet_spec.rb +7 -0
  44. data/spec/models/spree/stylesheet_spec.rb +102 -0
  45. data/spec/spec_helper.rb +59 -0
  46. metadata +296 -0
data/config/routes.rb ADDED
@@ -0,0 +1,9 @@
1
+ Spree::Core::Engine.add_routes do
2
+ namespace :admin do
3
+ resource :stylesheets do
4
+ post 'restore', to: 'stylesheets#restore'
5
+ end
6
+ end
7
+
8
+ match 'dandystyles', to: 'stylesheets#show', via: :all
9
+ end
data/config/spring.rb ADDED
@@ -0,0 +1 @@
1
+ Spring.application_root = './spec/dummy'
@@ -0,0 +1,10 @@
1
+ class CreateSpreeStylesheets < ActiveRecord::Migration
2
+ def change
3
+ create_table :spree_stylesheets do |t|
4
+ t.text :style_raw
5
+ t.text :style_compressed
6
+
7
+ t.timestamps
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,13 @@
1
+ class AddPaperTrailVersions < ActiveRecord::Migration
2
+ def change
3
+ create_table :versions do |t|
4
+ t.string :item_type, :null => false
5
+ t.integer :item_id, :null => false
6
+ t.string :event, :null => false
7
+ t.string :whodunnit
8
+ t.text :object
9
+ t.datetime :created_at
10
+ end
11
+ add_index :versions, [:item_type, :item_id]
12
+ end
13
+ end
data/lib/dandify.rb ADDED
@@ -0,0 +1,7 @@
1
+ require 'spree_core'
2
+ require 'sass'
3
+ require 'paper_trail'
4
+ require 'dandify/engine'
5
+
6
+ module Dandify
7
+ end
@@ -0,0 +1,18 @@
1
+ module Dandify
2
+ class Engine < ::Rails::Engine
3
+ require 'spree/core'
4
+ isolate_namespace Spree
5
+ engine_name 'dandify'
6
+
7
+ config.autoload_paths += Dir["#{config.root}/lib"]
8
+ config.generators { |gen| gen.test_framework :rspec }
9
+
10
+ def self.activate
11
+ Dir[File.join(__dir__, '../../app/**/*_decorator*.rb')].each do |klass|
12
+ Rails.application.config.cache_classes ? require(klass) : load(klass)
13
+ end
14
+ end
15
+
16
+ config.to_prepare(&method(:activate).to_proc)
17
+ end
18
+ end
@@ -0,0 +1,3 @@
1
+ module Dandify
2
+ VERSION = '0.0.1'
3
+ end
@@ -0,0 +1,24 @@
1
+ module Dandify
2
+ module Generators
3
+ class InstallGenerator < Rails::Generators::Base
4
+ class_option :auto_run_migrations, type: :boolean, default: true
5
+
6
+ def add_migrations
7
+ run 'bundle exec rake railties:install:migrations FROM=dandify'
8
+ end
9
+
10
+ def add_stylesheets
11
+ inject_into_file 'vendor/assets/stylesheets/spree/backend/all.css', "*= require spree/backend/dandify\n", before: /\*\//, verbose: true
12
+ end
13
+
14
+ def run_migrations
15
+ res = ask('Would you like to run the migrations now? [Y/n]').downcase
16
+ if ['', 'y'].include?(res)
17
+ run 'bundle exec rake db:migrate'
18
+ else
19
+ logger 'Skipping rake db:migrate, don\'t forget to run it!'
20
+ end
21
+ end
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,4 @@
1
+ # desc "Explaining what the task does"
2
+ # task :dandify do
3
+ # # Task goes here
4
+ # end
@@ -0,0 +1,71 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::Admin::StylesheetsController do
4
+ stub_authorization!
5
+
6
+ let(:show_path) { spree.admin_stylesheets_path }
7
+ let(:good_style) { 'body {color:#ffff00;}' }
8
+ let(:bad_style) { 'body {color:#ffff00;' }
9
+
10
+ before do
11
+ user = create :admin_user
12
+ controller.stub(try_spree_current_user: user)
13
+ end
14
+
15
+ context '#show' do
16
+ it 'assigns new instance when none is found' do
17
+ spree_get :show
18
+ expect(assigns[:style]).to be_new_record
19
+ end
20
+
21
+ it 'assigns existing' do
22
+ style = create :stylesheet
23
+ spree_get :show
24
+ expect(assigns[:style]).to eq style
25
+ end
26
+ end
27
+
28
+ context '#new' do
29
+ it 'can create first a revision' do
30
+ style = create :stylesheet
31
+ spree_get :show
32
+ expect(assigns[:style]).to eq style
33
+ expect(response).to render_template(:show)
34
+ end
35
+
36
+ it 'can not create first revision because error' do
37
+ spree_post :create, stylesheet: { style_raw: bad_style }
38
+ expect(response).to render_template(:new)
39
+ end
40
+ end
41
+
42
+ context '#edit' do
43
+ it 'can create a revision' do
44
+ create :stylesheet
45
+ spree_get :show
46
+ expect(response).to render_template(:show)
47
+ end
48
+
49
+ it 'can not create a revision because error' do
50
+ spree_post :update, stylesheet: { style_raw: bad_style }
51
+ expect(response).to render_template(:edit)
52
+ end
53
+ end
54
+
55
+ context '#restore', versioning: true do
56
+ before { create :stylesheet }
57
+
58
+ it 'fails to reify when there is only one revision' do
59
+ spree_post :restore
60
+ expect(flash[:error]).to eq Spree.t('dandify.restore.error')
61
+ expect(response).to redirect_to show_path
62
+ end
63
+
64
+ it 'able to reify when there is more than one revision' do
65
+ spree_post :update, stylesheet: { style_raw: good_style }
66
+ spree_post :restore
67
+ expect(flash[:success]).to eq Spree.t('dandify.restore.success')
68
+ expect(response).to redirect_to show_path
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,36 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::StylesheetsController, '#show' do
4
+ context 'with a bad format' do
5
+ it 'responds with blank sheet' do
6
+ spree_get :show, format: :xml
7
+
8
+ expect(response.header['Content-Type']).to include 'text/css'
9
+ end
10
+
11
+ it 'responds with found sheet' do
12
+ css = create(:stylesheet).style_compressed
13
+ spree_get :show, format: :atom
14
+
15
+ expect(response.header['Content-Type']).to include 'text/css'
16
+ expect(assigns[:style].style_compressed).to eq css
17
+ end
18
+ end
19
+
20
+ context 'when there is no stylesheet' do
21
+ it 'displays a blank stylesheet' do
22
+ spree_get :show, format: :css
23
+
24
+ expect(assigns[:style]).to be_a Spree::BlankStylesheet
25
+ end
26
+ end
27
+
28
+ context 'when there is a stylesheet' do
29
+ it 'assigns the stored sheet' do
30
+ create :stylesheet
31
+ spree_get :show, format: :css
32
+
33
+ expect(assigns[:style]).to be_a Spree::Stylesheet
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,5 @@
1
+ FactoryGirl.define do
2
+ factory :stylesheet, class: Spree::Stylesheet do
3
+ style_raw '#main { display: none; }'
4
+ end
5
+ end
@@ -0,0 +1,10 @@
1
+ require 'spec_helper'
2
+
3
+ feature 'Dandy stylesheet' do
4
+ scenario 'store contains dandystylesheet' do
5
+ visit spree.root_path
6
+ expect(page).to(
7
+ have_xpath('//link[contains(@href, "/dandystyles.css")]', visible: false)
8
+ )
9
+ end
10
+ end
@@ -0,0 +1,80 @@
1
+ require 'spec_helper'
2
+
3
+ feature 'Managing stylesheets' do
4
+ stub_authorization!
5
+
6
+ let(:show_path) { spree.admin_stylesheets_path }
7
+ let(:new_path) { spree.new_admin_stylesheets_path }
8
+ let(:edit_path) { spree.edit_admin_stylesheets_path }
9
+ let(:restore_path) { spree.restore_admin_stylesheets_path }
10
+ let(:style) { 'body {display: none;}' }
11
+
12
+ context 'without existing style' do
13
+ scenario 'user can create styles' do
14
+ visit new_path
15
+ fill_in Spree.t('dandify.form.label'), with: style
16
+ click_button Spree.t(:create)
17
+
18
+ expect(page.status_code).to be(200)
19
+ expect(page).to have_text Spree.t('dandify.show.title')
20
+ end
21
+ end
22
+
23
+ context 'with existing style' do
24
+ before { create :stylesheet }
25
+
26
+ scenario 'user sees first audit trail', versioning: true do
27
+ visit show_path
28
+
29
+ within_row(1) { expect(page).to have_content('Create') }
30
+ end
31
+
32
+ scenario 'user can edit exiting styles' do
33
+ visit edit_path
34
+
35
+ fill_in Spree.t('dandify.form.label'), with: style
36
+ click_button Spree.t(:update)
37
+
38
+ expect(page.status_code).to be(200)
39
+ expect(page).to have_text(Spree.t('dandify.show.title'))
40
+ end
41
+
42
+ scenario 'user creates new audit trail on edit', versioning: true do
43
+ visit edit_path
44
+
45
+ fill_in Spree.t('dandify.form.label'), with: style
46
+ click_button Spree.t(:update)
47
+
48
+ visit show_path
49
+
50
+ within_row(1) { page.should have_content('Update') }
51
+ within_row(2) { page.should have_content('Create') }
52
+ end
53
+ end
54
+
55
+ context 'restoring stylesheet' do
56
+ before { create :stylesheet }
57
+
58
+ let(:css_path) { 'table#listing_versions tbody tr' }
59
+
60
+ scenario 'not possible when there is only one version', versioning: true do
61
+ visit show_path
62
+
63
+ page.should have_css(css_path, count: 1)
64
+ within_row(1) { expect(page).to have_link('', href: edit_path) }
65
+ end
66
+
67
+ scenario 'user can restore to previous version', versioning: true do
68
+ visit edit_path
69
+
70
+ fill_in Spree.t('dandify.form.label'), with: style
71
+ click_button Spree.t(:update)
72
+
73
+ visit show_path
74
+
75
+ page.should have_css(css_path, count: 2)
76
+ within_row(1) { expect(page).to have_link('', href: edit_path) }
77
+ within_row(2) { expect(page).to have_link('', href: restore_path) }
78
+ end
79
+ end
80
+ end
@@ -0,0 +1,41 @@
1
+ require 'spec_helper'
2
+
3
+ describe 'In the admin' do
4
+ stub_authorization!
5
+
6
+ let(:configuration_path) { spree.edit_admin_general_settings_path }
7
+ let(:show_path) { spree.admin_stylesheets_path }
8
+ let(:new_path) { spree.new_admin_stylesheets_path }
9
+ let(:edit_path) { spree.edit_admin_stylesheets_path }
10
+
11
+ context 'on the configuration page' do
12
+ it 'the user views Dandify link in sidebar' do
13
+ visit configuration_path
14
+ expect(page).to have_link(Spree.t('dandify.sidebar'), href: show_path)
15
+ end
16
+
17
+ it 'the user views non-highlighted Dandify link in sidebar' do
18
+ visit configuration_path
19
+ expect(page).to_not(
20
+ have_selector(:css, "li.active a[href='#{show_path}']")
21
+ )
22
+ end
23
+ end
24
+
25
+ context 'the user views highlighted sidebar link' do
26
+ it 'on Dandify show page' do
27
+ visit show_path
28
+ expect(page).to have_selector(:css, "li.active a[href='#{show_path}']")
29
+ end
30
+
31
+ it 'on Dandify edit page' do
32
+ visit edit_path
33
+ expect(page).to have_selector(:css, "li.active a[href='#{show_path}']")
34
+ end
35
+
36
+ it 'on Dandify new page' do
37
+ visit new_path
38
+ expect(page).to have_selector(:css, "li.active a[href='#{show_path}']")
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,49 @@
1
+ require 'spec_helper'
2
+
3
+ feature 'Viewing stylesheet administration page' do
4
+ stub_authorization!
5
+
6
+ let(:show_path) { spree.admin_stylesheets_path }
7
+
8
+ context 'without existing style' do
9
+ scenario 'user views page with no stylesheet' do
10
+ visit show_path
11
+
12
+ expect(page).to have_text Spree.t('dandify.show.none')
13
+ end
14
+
15
+ scenario 'user has access to create link' do
16
+ visit show_path
17
+
18
+ expect(page).to have_text Spree.t('dandify.show.buttons.new')
19
+ end
20
+
21
+ scenario 'user does not have access to edit link' do
22
+ visit show_path
23
+
24
+ expect(page).to_not have_text Spree.t('dandify.show.buttons.edit')
25
+ end
26
+ end
27
+
28
+ context 'with existing style' do
29
+ before { create :stylesheet }
30
+
31
+ scenario 'user views page with an active stylesheet' do
32
+ visit show_path
33
+
34
+ expect(page).to_not have_text Spree.t('dandify.show.none')
35
+ end
36
+
37
+ scenario 'user does not have access to create link' do
38
+ visit show_path
39
+
40
+ expect(page).to_not have_text Spree.t('dandify.show.buttons.new')
41
+ end
42
+
43
+ scenario 'user has access to edit link' do
44
+ visit show_path
45
+
46
+ expect(page).to have_text Spree.t('dandify.show.buttons.edit')
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,14 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::Admin::NavigationHelper do
4
+ describe '#link_to_restore_url' do
5
+ let(:restore_path) { spree.edit_admin_stylesheets_path }
6
+
7
+ context 'link to restore URL' do
8
+ it 'should build circular restore button' do
9
+ restore_button = helper.link_to_restore_url(restore_path)
10
+ restore_button.should include(Spree.t('dandify.confirm.restore'))
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,7 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::BlankStylesheet, '#style_compressed' do
4
+ it 'returns a blank string' do
5
+ expect(Spree::BlankStylesheet.new.style_compressed).to eq ''
6
+ end
7
+ end
@@ -0,0 +1,102 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::Stylesheet do
4
+ context 'versions', versioning: true do
5
+ it { should be_versioned }
6
+
7
+ it 'restores previous versions' do
8
+ style = create :stylesheet
9
+ style.update style_raw: 'h1{display:none; color: blue;}'
10
+
11
+ expect(style.versions.size).to eq(2)
12
+ end
13
+ end
14
+
15
+ context 'validations' do
16
+ let(:valid_css) { '#main {background-color: #0000ff}' }
17
+ let(:invalid_css) { 'main {background-color #0000ff}' }
18
+
19
+ it { should validate_presence_of(:style_raw) }
20
+
21
+ it 'pass with proper vanilla syntax' do
22
+ expect(style_with valid_css).to be_valid
23
+ end
24
+
25
+ it 'fail with bad vanilla syntax' do
26
+ expect(style_with invalid_css).to_not be_valid
27
+ end
28
+ end
29
+
30
+ context 'processing raw' do
31
+ it 'allows both css and scss' do
32
+ expect(style_with(<<-CSS)).to be_valid
33
+
34
+ $font-stack: Helvetica, sans-serif;
35
+
36
+ body {
37
+ font: 100% $font-stack
38
+ }
39
+
40
+ h1 { display: inline ;}
41
+
42
+ CSS
43
+ end
44
+
45
+ context 'compresses' do
46
+ it 'vanilla css' do
47
+ compressed = "#main{display:block}.foo{width:300px;height:200px}\n"
48
+ expect(create_style_with(<<-CSS).style_compressed).to eq compressed
49
+
50
+ #main {
51
+ display: block;
52
+ }
53
+
54
+ .foo {
55
+ width: 300px;
56
+ height: 200px;
57
+ }
58
+
59
+ CSS
60
+ end
61
+
62
+ it 'compresses scss' do
63
+ compressed = "nav ul{margin:0;padding:0}a{display:block}\n"
64
+ expect(create_style_with(<<-CSS).style_compressed).to eq compressed
65
+
66
+ nav {
67
+ ul {
68
+ margin: 0;
69
+ padding: 0;
70
+ }
71
+ }
72
+
73
+ a {
74
+ display: block;
75
+ }
76
+
77
+ CSS
78
+ end
79
+ end
80
+ end
81
+
82
+ def create_style_with(css)
83
+ style = style_with(css)
84
+ style.save
85
+ style
86
+ end
87
+
88
+ def style_with(css)
89
+ Spree::Stylesheet.new(style_raw: css)
90
+ end
91
+ end
92
+
93
+ describe Spree::Stylesheet, '#load_style' do
94
+ it 'returns Blanksheet when no sheet is found' do
95
+ expect(Spree::Stylesheet.load_style).to be_a Spree::BlankStylesheet
96
+ end
97
+
98
+ it 'returns a found instance of itself' do
99
+ styles = create :stylesheet
100
+ expect(Spree::Stylesheet.load_style).to eq styles
101
+ end
102
+ end