├── log
└── .gitkeep
├── .rspec
├── lib
├── tasks
│ └── .gitkeep
└── assets
│ └── .gitkeep
├── public
├── favicon.ico
├── robots.txt
├── 500.html
├── 422.html
└── 404.html
├── test
├── unit
│ ├── .gitkeep
│ ├── user_test.rb
│ └── email_test.rb
├── fixtures
│ ├── .gitkeep
│ ├── emails.yml
│ └── users.yml
├── functional
│ └── .gitkeep
├── integration
│ └── .gitkeep
├── performance
│ └── browsing_test.rb
└── test_helper.rb
├── app
├── mailers
│ └── .gitkeep
├── models
│ ├── .gitkeep
│ ├── user.rb
│ └── email.rb
├── views
│ ├── home
│ │ └── index.html.erb
│ ├── sessions
│ │ ├── create.html.erb
│ │ └── new.html.erb
│ ├── registrations
│ │ ├── create.html.erb
│ │ └── new.html.erb
│ ├── emails
│ │ ├── index.html.erb
│ │ └── edit.html.erb
│ └── layouts
│ │ └── application.html.erb
├── assets
│ ├── stylesheets
│ │ ├── main.css.scss
│ │ └── application.css
│ ├── images
│ │ └── rails.png
│ └── javascripts
│ │ └── application.js
├── helpers
│ ├── application_helper.rb
│ └── registrations_helper.rb
└── controllers
│ ├── home_controller.rb
│ ├── application_controller.rb
│ ├── sessions_controller.rb
│ ├── registrations_controller.rb
│ └── emails_controller.rb
├── vendor
├── plugins
│ └── .gitkeep
└── assets
│ ├── javascripts
│ └── .gitkeep
│ └── stylesheets
│ └── .gitkeep
├── README.md
├── config
├── initializers
│ ├── strong_parameters.rb
│ ├── mime_types.rb
│ ├── backtrace_silencers.rb
│ ├── session_store.rb
│ ├── warden.rb
│ ├── secret_token.rb
│ ├── wrap_parameters.rb
│ └── inflections.rb
├── environment.rb
├── boot.rb
├── locales
│ └── en.yml
├── database.yml
├── environments
│ ├── development.rb
│ ├── test.rb
│ └── production.rb
├── routes.rb
└── application.rb
├── db
├── migrate
│ ├── 20130808095750_add_state_to_emails.rb
│ ├── 20130730213054_create_users.rb
│ ├── 20130808025132_change_password_related_columns_on_users.rb
│ └── 20130730213936_create_emails.rb
├── seeds.rb
└── schema.rb
├── config.ru
├── spec
├── factories
│ ├── users.rb
│ └── emails.rb
├── features
│ └── users
│ │ ├── sign_out_spec.rb
│ │ ├── sign_up_spec.rb
│ │ └── sign_in_spec.rb
├── models
│ ├── user_spec.rb
│ └── email_spec.rb
├── spec_helper.rb
└── controllers
│ └── emails_controller_spec.rb
├── doc
└── README_FOR_APP
├── Rakefile
├── script
└── rails
├── bin
├── ri
├── rake
├── rdoc
├── sass
├── scss
├── thor
├── tilt
├── tt
├── erubis
├── rackup
├── rails
├── sprockets
└── sass-convert
├── .gitignore
├── Gemfile
└── Gemfile.lock
/log/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/.rspec:
--------------------------------------------------------------------------------
1 | --color
2 |
--------------------------------------------------------------------------------
/lib/tasks/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/public/favicon.ico:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/test/unit/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/app/mailers/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/app/models/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/lib/assets/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/test/fixtures/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/vendor/plugins/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/test/functional/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/test/integration/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/vendor/assets/javascripts/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/vendor/assets/stylesheets/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/app/views/home/index.html.erb:
--------------------------------------------------------------------------------
1 |
Home
--------------------------------------------------------------------------------
/app/assets/stylesheets/main.css.scss:
--------------------------------------------------------------------------------
1 | @import 'bootstrap';
2 |
--------------------------------------------------------------------------------
/app/helpers/application_helper.rb:
--------------------------------------------------------------------------------
1 | module ApplicationHelper
2 | end
3 |
--------------------------------------------------------------------------------
/app/helpers/registrations_helper.rb:
--------------------------------------------------------------------------------
1 | module RegistrationsHelper
2 | end
3 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | ## Drip
2 |
3 | This is a sample project to apply for a job posting with Drip.
4 |
--------------------------------------------------------------------------------
/app/controllers/home_controller.rb:
--------------------------------------------------------------------------------
1 | class HomeController < ApplicationController
2 | def index
3 | end
4 | end
--------------------------------------------------------------------------------
/app/assets/images/rails.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/antillas21/sample_project/master/app/assets/images/rails.png
--------------------------------------------------------------------------------
/app/views/sessions/create.html.erb:
--------------------------------------------------------------------------------
1 | Sessions#create
2 | Find me in app/views/sessions/create.html.erb
3 |
--------------------------------------------------------------------------------
/config/initializers/strong_parameters.rb:
--------------------------------------------------------------------------------
1 | ActiveRecord::Base.send(:include, ActiveModel::ForbiddenAttributesProtection)
2 |
--------------------------------------------------------------------------------
/app/views/registrations/create.html.erb:
--------------------------------------------------------------------------------
1 | Registrations#create
2 | Find me in app/views/registrations/create.html.erb
3 |
--------------------------------------------------------------------------------
/test/unit/user_test.rb:
--------------------------------------------------------------------------------
1 | require 'test_helper'
2 |
3 | class UserTest < ActiveSupport::TestCase
4 | # test "the truth" do
5 | # assert true
6 | # end
7 | end
8 |
--------------------------------------------------------------------------------
/test/unit/email_test.rb:
--------------------------------------------------------------------------------
1 | require 'test_helper'
2 |
3 | class EmailTest < ActiveSupport::TestCase
4 | # test "the truth" do
5 | # assert true
6 | # end
7 | end
8 |
--------------------------------------------------------------------------------
/db/migrate/20130808095750_add_state_to_emails.rb:
--------------------------------------------------------------------------------
1 | class AddStateToEmails < ActiveRecord::Migration
2 | def change
3 | add_column :emails, :state, :string
4 | end
5 | end
6 |
--------------------------------------------------------------------------------
/config.ru:
--------------------------------------------------------------------------------
1 | # This file is used by Rack-based servers to start the application.
2 |
3 | require ::File.expand_path('../config/environment', __FILE__)
4 | run SampleProject::Application
5 |
--------------------------------------------------------------------------------
/config/environment.rb:
--------------------------------------------------------------------------------
1 | # Load the rails application
2 | require File.expand_path('../application', __FILE__)
3 |
4 | # Initialize the rails application
5 | SampleProject::Application.initialize!
6 |
--------------------------------------------------------------------------------
/spec/factories/users.rb:
--------------------------------------------------------------------------------
1 | FactoryGirl.define do
2 | factory :user do
3 | sequence( :name ) { |n| "john #{n} doe" }
4 | sequence( :email ) { |n| "user-#{n}@example.com" }
5 | password 'password'
6 | end
7 | end
8 |
--------------------------------------------------------------------------------
/config/boot.rb:
--------------------------------------------------------------------------------
1 | require 'rubygems'
2 |
3 | # Set up gems listed in the Gemfile.
4 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path('../../Gemfile', __FILE__)
5 |
6 | require 'bundler/setup' if File.exists?(ENV['BUNDLE_GEMFILE'])
7 |
--------------------------------------------------------------------------------
/doc/README_FOR_APP:
--------------------------------------------------------------------------------
1 | Use this README file to introduce your application and point to useful places in the API for learning more.
2 | Run "rake doc:app" to generate API documentation for your models, controllers, helpers, and libraries.
3 |
--------------------------------------------------------------------------------
/public/robots.txt:
--------------------------------------------------------------------------------
1 | # See http://www.robotstxt.org/wc/norobots.html for documentation on how to use the robots.txt file
2 | #
3 | # To ban all spiders from the entire site uncomment the next two lines:
4 | # User-Agent: *
5 | # Disallow: /
6 |
--------------------------------------------------------------------------------
/config/initializers/mime_types.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 |
3 | # Add new mime types for use in respond_to blocks:
4 | # Mime::Type.register "text/richtext", :rtf
5 | # Mime::Type.register_alias "text/html", :iphone
6 |
--------------------------------------------------------------------------------
/config/locales/en.yml:
--------------------------------------------------------------------------------
1 | # Sample localization file for English. Add more files in this directory for other locales.
2 | # See https://github.com/svenfuchs/rails-i18n/tree/master/rails%2Flocale for starting points.
3 |
4 | en:
5 | hello: "Hello world"
6 |
--------------------------------------------------------------------------------
/spec/factories/emails.rb:
--------------------------------------------------------------------------------
1 | FactoryGirl.define do
2 | factory :email do
3 | from_email 'sender@example.com'
4 | to_email 'recipient@example.com'
5 | subject 'FactoryGirl spawned this email'
6 | user { FactoryGirl.create :user }
7 | end
8 | end
9 |
--------------------------------------------------------------------------------
/app/models/user.rb:
--------------------------------------------------------------------------------
1 | class User < ActiveRecord::Base
2 |
3 | has_secure_password
4 |
5 | validates :name, presence: true
6 | validates :email, presence: true
7 | validates :email, uniqueness: true
8 | validates :email, email: true
9 |
10 | has_many :emails
11 | end
12 |
--------------------------------------------------------------------------------
/Rakefile:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env rake
2 | # Add your own tasks in files placed in lib/tasks ending in .rake,
3 | # for example lib/tasks/capistrano.rake, and they will automatically be available to Rake.
4 |
5 | require File.expand_path('../config/application', __FILE__)
6 |
7 | SampleProject::Application.load_tasks
8 |
--------------------------------------------------------------------------------
/script/rails:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | # This command will automatically be run when you run "rails" with Rails 3 gems installed from the root of your application.
3 |
4 | APP_PATH = File.expand_path('../../config/application', __FILE__)
5 | require File.expand_path('../../config/boot', __FILE__)
6 | require 'rails/commands'
7 |
--------------------------------------------------------------------------------
/db/migrate/20130730213054_create_users.rb:
--------------------------------------------------------------------------------
1 | class CreateUsers < ActiveRecord::Migration
2 | def change
3 | create_table :users do |t|
4 | t.string :name
5 | t.string :email
6 | t.string :password_hash
7 | t.string :password_salt
8 | t.integer :login_count
9 | t.datetime :last_logged_in_at
10 |
11 | t.timestamps
12 | end
13 | end
14 | end
15 |
--------------------------------------------------------------------------------
/db/migrate/20130808025132_change_password_related_columns_on_users.rb:
--------------------------------------------------------------------------------
1 | class ChangePasswordRelatedColumnsOnUsers < ActiveRecord::Migration
2 | def up
3 | rename_column :users, :password_hash, :password_digest
4 | remove_column :users, :password_salt
5 | end
6 |
7 | def down
8 | rename_column :users, :password_digest, :password_hash
9 | add_column :users, :password_salt, :string
10 | end
11 | end
12 |
--------------------------------------------------------------------------------
/app/controllers/application_controller.rb:
--------------------------------------------------------------------------------
1 | class ApplicationController < ActionController::Base
2 | protect_from_forgery
3 |
4 | def authenticate_user!
5 | redirect_to login_path, notice: 'Please login to your account.' \
6 | unless current_user
7 | end
8 |
9 | helper_method :authenticate_user!
10 |
11 | def current_user
12 | env['warden'].user
13 | end
14 |
15 | helper_method :current_user
16 | end
17 |
--------------------------------------------------------------------------------
/bin/ri:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'ri' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('rdoc', 'ri')
17 |
--------------------------------------------------------------------------------
/bin/rake:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'rake' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('rake', 'rake')
17 |
--------------------------------------------------------------------------------
/bin/rdoc:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'rdoc' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('rdoc', 'rdoc')
17 |
--------------------------------------------------------------------------------
/bin/sass:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'sass' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('sass', 'sass')
17 |
--------------------------------------------------------------------------------
/bin/scss:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'scss' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('sass', 'scss')
17 |
--------------------------------------------------------------------------------
/bin/thor:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'thor' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('thor', 'thor')
17 |
--------------------------------------------------------------------------------
/bin/tilt:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'tilt' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('tilt', 'tilt')
17 |
--------------------------------------------------------------------------------
/bin/tt:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'tt' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('treetop', 'tt')
17 |
--------------------------------------------------------------------------------
/db/migrate/20130730213936_create_emails.rb:
--------------------------------------------------------------------------------
1 | class CreateEmails < ActiveRecord::Migration
2 | def change
3 | create_table :emails do |t|
4 | t.references :user
5 | t.string :from_name
6 | t.string :from_email
7 | t.string :to_email
8 | t.string :subject
9 | t.text :html_body
10 | t.text :text_body
11 |
12 | t.timestamps
13 | end
14 | add_index :emails, :user_id
15 | end
16 | end
17 |
--------------------------------------------------------------------------------
/bin/erubis:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'erubis' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('erubis', 'erubis')
17 |
--------------------------------------------------------------------------------
/bin/rackup:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'rackup' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('rack', 'rackup')
17 |
--------------------------------------------------------------------------------
/bin/rails:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'rails' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('railties', 'rails')
17 |
--------------------------------------------------------------------------------
/test/performance/browsing_test.rb:
--------------------------------------------------------------------------------
1 | require 'test_helper'
2 | require 'rails/performance_test_help'
3 |
4 | class BrowsingTest < ActionDispatch::PerformanceTest
5 | # Refer to the documentation for all available options
6 | # self.profile_options = { :runs => 5, :metrics => [:wall_time, :memory]
7 | # :output => 'tmp/performance', :formats => [:flat] }
8 |
9 | def test_homepage
10 | get '/'
11 | end
12 | end
13 |
--------------------------------------------------------------------------------
/bin/sprockets:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'sprockets' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('sprockets', 'sprockets')
17 |
--------------------------------------------------------------------------------
/bin/sass-convert:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env ruby
2 | #
3 | # This file was generated by Bundler.
4 | #
5 | # The application 'sass-convert' is installed as part of a gem, and
6 | # this file is here to facilitate running it.
7 | #
8 |
9 | require 'pathname'
10 | ENV['BUNDLE_GEMFILE'] ||= File.expand_path("../../Gemfile",
11 | Pathname.new(__FILE__).realpath)
12 |
13 | require 'rubygems'
14 | require 'bundler/setup'
15 |
16 | load Gem.bin_path('sass', 'sass-convert')
17 |
--------------------------------------------------------------------------------
/config/initializers/backtrace_silencers.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 |
3 | # You can add backtrace silencers for libraries that you're using but don't wish to see in your backtraces.
4 | # Rails.backtrace_cleaner.add_silencer { |line| line =~ /my_noisy_library/ }
5 |
6 | # You can also remove all the silencers if you're trying to debug a problem that might stem from framework code.
7 | # Rails.backtrace_cleaner.remove_silencers!
8 |
--------------------------------------------------------------------------------
/test/fixtures/emails.yml:
--------------------------------------------------------------------------------
1 | # Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/Fixtures.html
2 |
3 | one:
4 | user:
5 | from_name: MyString
6 | from_email: MyString
7 | to_email: MyString
8 | subject: MyString
9 | html_body: MyText
10 | text_body: MyText
11 |
12 | two:
13 | user:
14 | from_name: MyString
15 | from_email: MyString
16 | to_email: MyString
17 | subject: MyString
18 | html_body: MyText
19 | text_body: MyText
20 |
--------------------------------------------------------------------------------
/test/fixtures/users.yml:
--------------------------------------------------------------------------------
1 | # Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/Fixtures.html
2 |
3 | one:
4 | name: MyString
5 | email: MyString
6 | password_hash: MyString
7 | password_salt: MyString
8 | login_count: 1
9 | last_logged_in_at: 2013-07-30 14:30:54
10 |
11 | two:
12 | name: MyString
13 | email: MyString
14 | password_hash: MyString
15 | password_salt: MyString
16 | login_count: 1
17 | last_logged_in_at: 2013-07-30 14:30:54
18 |
--------------------------------------------------------------------------------
/config/initializers/session_store.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 |
3 | SampleProject::Application.config.session_store :cookie_store, key: '_SampleProject_session'
4 |
5 | # Use the database for sessions instead of the cookie-based default,
6 | # which shouldn't be used to store highly confidential information
7 | # (create the session table with "rails generate session_migration")
8 | # SampleProject::Application.config.session_store :active_record_store
9 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # See http://help.github.com/ignore-files/ for more about ignoring files.
2 | #
3 | # If you find yourself ignoring temporary files generated by your text editor
4 | # or operating system, you probably want to add a global ignore instead:
5 | # git config --global core.excludesfile ~/.gitignore_global
6 |
7 | # Ignore bundler config
8 | /.bundle
9 |
10 | # Ignore the default SQLite database.
11 | /db/*.sqlite3
12 |
13 | # Ignore all logfiles and tempfiles.
14 | /log/*.log
15 | /tmp
16 |
--------------------------------------------------------------------------------
/test/test_helper.rb:
--------------------------------------------------------------------------------
1 | ENV["RAILS_ENV"] = "test"
2 | require File.expand_path('../../config/environment', __FILE__)
3 | require 'rails/test_help'
4 |
5 | class ActiveSupport::TestCase
6 | # Setup all fixtures in test/fixtures/*.(yml|csv) for all tests in alphabetical order.
7 | #
8 | # Note: You'll currently still have to declare fixtures explicitly in integration tests
9 | # -- they do not yet inherit this setting
10 | fixtures :all
11 |
12 | # Add more helper methods to be used by all tests here...
13 | end
14 |
--------------------------------------------------------------------------------
/db/seeds.rb:
--------------------------------------------------------------------------------
1 | # This file should contain all the record creation needed to seed the database with its default values.
2 | # The data can then be loaded with the rake db:seed (or created alongside the db with db:setup).
3 | #
4 | # Examples:
5 | #
6 | # cities = City.create([{ name: 'Chicago' }, { name: 'Copenhagen' }])
7 | # Mayor.create(name: 'Emanuel', city: cities.first)
8 |
9 | user = User.create( name: 'John Doe', email: 'user@example.com', password: 'password' )
10 |
11 | 10.times { FactoryGirl.create( :email, user: user ) }
12 |
--------------------------------------------------------------------------------
/config/initializers/warden.rb:
--------------------------------------------------------------------------------
1 | Warden::Manager.serialize_into_session do |user|
2 | user.id
3 | end
4 |
5 | Warden::Manager.serialize_from_session do |id|
6 | User.find( id )
7 | end
8 |
9 | Warden::Strategies.add :password do
10 | def valid?
11 | params['user'].present?
12 | end
13 |
14 | def authenticate!
15 | user = User.find_by_email(params['user']['email'] )
16 | if user && user.authenticate( params['user']['password'] )
17 | success!( user )
18 | else
19 | fail!
20 | end
21 | end
22 | end
23 |
--------------------------------------------------------------------------------
/config/initializers/secret_token.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 |
3 | # Your secret key for verifying the integrity of signed cookies.
4 | # If you change this key, all old signed cookies will become invalid!
5 | # Make sure the secret is at least 30 characters and all random,
6 | # no regular words or you'll be exposed to dictionary attacks.
7 | SampleProject::Application.config.secret_token = 'daeb4832b8444434610f5f7944aabc9ae415fc3f3c3620ca7638711a18a28f05f79cf62d41ab77956b2863bbd45289a27a07cbbc90d5ccdbc893fdf014b3726d'
8 |
--------------------------------------------------------------------------------
/config/initializers/wrap_parameters.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 | #
3 | # This file contains settings for ActionController::ParamsWrapper which
4 | # is enabled by default.
5 |
6 | # Enable parameter wrapping for JSON. You can disable this by setting :format to an empty array.
7 | ActiveSupport.on_load(:action_controller) do
8 | wrap_parameters format: [:json]
9 | end
10 |
11 | # Disable root element in JSON by default.
12 | ActiveSupport.on_load(:active_record) do
13 | self.include_root_in_json = false
14 | end
15 |
--------------------------------------------------------------------------------
/app/controllers/sessions_controller.rb:
--------------------------------------------------------------------------------
1 | class SessionsController < ApplicationController
2 | def new
3 | @user = User.new
4 | end
5 |
6 | def create
7 | if env['warden'].authenticate
8 | flash[:notice] = 'You are now logged in.'
9 | redirect_to emails_path
10 | else
11 | @user = User.new
12 | flash[:error] = 'Invalid email or password.'
13 | render :new
14 | end
15 | end
16 |
17 | def destroy
18 | env['warden'].logout
19 | flash[:notice] = 'You logged out successfully.'
20 | redirect_to root_path
21 | end
22 | end
23 |
--------------------------------------------------------------------------------
/app/controllers/registrations_controller.rb:
--------------------------------------------------------------------------------
1 | class RegistrationsController < ApplicationController
2 | def new
3 | @user = User.new
4 | end
5 |
6 | def create
7 | @user = User.new(user_params)
8 | if @user.save
9 | env['warden'].set_user @user
10 | flash[:notice] = 'You have signed up successfully and are now logged in.'
11 | redirect_to emails_path
12 | else
13 | render :new
14 | end
15 | end
16 |
17 | private
18 | def user_params
19 | params.require(:user).permit(:name, :email, :password, :password_confirmation)
20 | end
21 | end
22 |
--------------------------------------------------------------------------------
/app/views/sessions/new.html.erb:
--------------------------------------------------------------------------------
1 | Login
2 |
3 | <%= form_for @user, url: sessions_url do |f| %>
4 |
5 | <%= f.label :email, class: 'control-label' %>
6 |
7 | <%= f.email_field :email %>
8 |
9 |
10 |
11 | <%= f.label :password, class: 'control-label' %>
12 |
13 | <%= f.password_field :password %>
14 |
15 |
16 |
17 | <%= f.submit 'Login', class: 'btn btn-primary' %>
18 |
19 | <% end %>
20 |
--------------------------------------------------------------------------------
/config/initializers/inflections.rb:
--------------------------------------------------------------------------------
1 | # Be sure to restart your server when you modify this file.
2 |
3 | # Add new inflection rules using the following format
4 | # (all these examples are active by default):
5 | # ActiveSupport::Inflector.inflections do |inflect|
6 | # inflect.plural /^(ox)$/i, '\1en'
7 | # inflect.singular /^(ox)en/i, '\1'
8 | # inflect.irregular 'person', 'people'
9 | # inflect.uncountable %w( fish sheep )
10 | # end
11 | #
12 | # These inflection rules are supported but not enabled by default:
13 | # ActiveSupport::Inflector.inflections do |inflect|
14 | # inflect.acronym 'RESTful'
15 | # end
16 |
--------------------------------------------------------------------------------
/app/assets/stylesheets/application.css:
--------------------------------------------------------------------------------
1 | /*
2 | * This is a manifest file that'll be compiled into application.css, which will include all the files
3 | * listed below.
4 | *
5 | * Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
6 | * or vendor/assets/stylesheets of plugins, if any, can be referenced here using a relative path.
7 | *
8 | * You're free to add application-wide styles to this file and they'll appear at the top of the
9 | * compiled file, but it's generally better to create a new file per style scope.
10 | *
11 | *= require_self
12 | *= require_tree .
13 | */
14 |
--------------------------------------------------------------------------------
/spec/features/users/sign_out_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | feature 'User sign out' do
4 | let!(:user) { FactoryGirl.create :user }
5 | let(:login_url) { 'http://www.example.com/login' }
6 |
7 | before do
8 | visit root_path
9 | click_link 'Login'
10 | fill_in 'Email', with: user.email
11 | fill_in 'Password', with: 'password'
12 | click_button 'Login'
13 | end
14 |
15 | scenario 'signs out successfully' do
16 | click_link 'Logout'
17 | page.current_url.should eq root_url
18 | page.should have_content 'You logged out successfully.'
19 | page.should_not have_content 'Logout'
20 | end
21 | end
22 |
--------------------------------------------------------------------------------
/app/models/email.rb:
--------------------------------------------------------------------------------
1 | class Email < ActiveRecord::Base
2 | belongs_to :user
3 |
4 | # validations
5 | validates :to_email, presence: true
6 | validates :to_email, email: true
7 | validates :from_email, presence: true
8 | validates :from_email, email: true
9 | validates :subject, presence: true
10 |
11 | state_machine initial: :draft do
12 | event :publish do
13 | transition :draft => :published
14 | end
15 |
16 | event :unpublish do
17 | transition :published => :draft
18 | end
19 | end
20 |
21 | before_validation on: :create do |email|
22 | email.send( :initialize_state_machines, dynamic: :force )
23 | end
24 | end
25 |
--------------------------------------------------------------------------------
/config/database.yml:
--------------------------------------------------------------------------------
1 | # SQLite version 3.x
2 | # gem install sqlite3
3 | #
4 | # Ensure the SQLite 3 gem is defined in your Gemfile
5 | # gem 'sqlite3'
6 | development:
7 | adapter: sqlite3
8 | database: db/development.sqlite3
9 | pool: 5
10 | timeout: 5000
11 |
12 | # Warning: The database defined as "test" will be erased and
13 | # re-generated from your development database when you run "rake".
14 | # Do not set this db to the same as development or production.
15 | test:
16 | adapter: sqlite3
17 | database: db/test.sqlite3
18 | pool: 5
19 | timeout: 5000
20 |
21 | production:
22 | adapter: sqlite3
23 | database: db/production.sqlite3
24 | pool: 5
25 | timeout: 5000
26 |
--------------------------------------------------------------------------------
/app/assets/javascripts/application.js:
--------------------------------------------------------------------------------
1 | // This is a manifest file that'll be compiled into application.js, which will include all the files
2 | // listed below.
3 | //
4 | // Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
5 | // or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
6 | //
7 | // It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
8 | // the compiled file.
9 | //
10 | // WARNING: THE FIRST BLANK LINE MARKS THE END OF WHAT'S TO BE PROCESSED, ANY BLANK LINE SHOULD
11 | // GO AFTER THE REQUIRES BELOW.
12 | //
13 | //= require jquery
14 | //= require jquery_ujs
15 | //= require bootstrap
16 | //= require_tree .
17 |
--------------------------------------------------------------------------------
/public/500.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | We're sorry, but something went wrong (500)
5 |
17 |
18 |
19 |
20 |
21 |
22 |
We're sorry, but something went wrong.
23 |
24 |
25 |
26 |
--------------------------------------------------------------------------------
/app/views/emails/index.html.erb:
--------------------------------------------------------------------------------
1 | Emails
2 |
3 |
4 |
5 |
6 | Subject
7 | Sender
8 | Recipient
9 | Published
10 | Actions
11 |
12 |
13 |
14 | <% @emails.find_each do |email| %>
15 |
16 | <%= email.subject %>
17 | <%= email.from_email %>
18 | <%= email.to_email %>
19 | <%= email.published? %>
20 |
21 | <%= link_to 'Edit', edit_email_path(email), class: 'btn btn-link' %>
22 | <%= link_to 'Publish', publish_email_path(email), method: :post, class: 'btn btn-link' %>
23 |
24 |
25 | <% end %>
26 |
27 |
28 |
--------------------------------------------------------------------------------
/public/422.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | The change you wanted was rejected (422)
5 |
17 |
18 |
19 |
20 |
21 |
22 |
The change you wanted was rejected.
23 |
Maybe you tried to change something you didn't have access to.
24 |
25 |
26 |
27 |
--------------------------------------------------------------------------------
/public/404.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | The page you were looking for doesn't exist (404)
5 |
17 |
18 |
19 |
20 |
21 |
22 |
The page you were looking for doesn't exist.
23 |
You may have mistyped the address or the page may have moved.
24 |
25 |
26 |
27 |
--------------------------------------------------------------------------------
/spec/models/user_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | describe User do
4 | describe 'validations' do
5 | it { should validate_presence_of :name }
6 | it { should validate_presence_of :email }
7 | it { should validate_uniqueness_of :email }
8 | end
9 |
10 | describe 'relationships' do
11 | it { should have_many :emails }
12 | end
13 |
14 | describe 'has_secure_password' do
15 | let(:user) { User.new( name: 'John Doe', email: 'john@example.com' ) }
16 |
17 | it 'validates presence of password on create' do
18 | user.should_not be_valid
19 | user.errors.messages.should include( {password_digest: ["can't be blank"]} )
20 | end
21 |
22 | it 'validates password and password confirmation match' do
23 | user.password = 'password'
24 | user.password_confirmation = 'donotmatch'
25 | user.should_not be_valid
26 | user.errors.messages.should include({ password: ["doesn't match confirmation"] })
27 | end
28 | end
29 | end
30 |
--------------------------------------------------------------------------------
/app/views/registrations/new.html.erb:
--------------------------------------------------------------------------------
1 | Sign up
2 |
3 | <%= form_for @user, url: signup_path, method: :post do |f| %>
4 | <%= f.error_messages %>
5 |
6 | <%= f.label :name, class: 'control-label' %>
7 |
8 | <%= f.text_field :name %>
9 |
10 |
11 |
12 | <%= f.label :email, class: 'control-label' %>
13 |
14 | <%= f.email_field :email %>
15 |
16 |
17 |
18 | <%= f.label :password, class: 'control-label' %>
19 |
20 | <%= f.password_field :password %>
21 |
22 |
23 |
24 | <%= f.label :password_confirmation, class: 'control-label' %>
25 |
26 | <%= f.password_field :password_confirmation %>
27 |
28 |
29 |
30 | <%= f.submit 'Sign up', class: 'btn btn-primary' %>
31 |
32 | <% end %>
33 |
--------------------------------------------------------------------------------
/app/controllers/emails_controller.rb:
--------------------------------------------------------------------------------
1 | class EmailsController < ApplicationController
2 | before_filter :authenticate_user!
3 | before_filter :retrieve_email, only: [:edit, :update, :publish, :unpublish]
4 |
5 | def index
6 | @emails = current_user.emails
7 | end
8 |
9 | def edit; end
10 |
11 | def update
12 | if @email.update_attributes email_params
13 | redirect_to emails_path, notice: 'Your changes have been saved.'
14 | else
15 | render :edit
16 | end
17 | end
18 |
19 | def publish
20 | @email.publish
21 | redirect_to edit_email_path(@email), notice: 'This email has been published.'
22 | end
23 |
24 | def unpublish
25 | @email.unpublish
26 | redirect_to edit_email_path(@email), notice: 'This email has been unpublished.'
27 | end
28 |
29 | private
30 | def email_params
31 | params.require(:email).permit(
32 | :from_name, :from_email, :to_email, :subject, :text_body, :html_body
33 | )
34 | end
35 |
36 | def retrieve_email
37 | @email = current_user.emails.find params[:id]
38 | end
39 | end
40 |
--------------------------------------------------------------------------------
/spec/models/email_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | describe Email do
4 | describe 'validations' do
5 | it { should validate_presence_of :from_email }
6 | it { should validate_presence_of :to_email }
7 | it { should validate_presence_of :subject }
8 | end
9 |
10 | describe 'relationships' do
11 | it { should belong_to :user }
12 | end
13 |
14 | describe 'new Email' do
15 | it 'starts as draft' do
16 | email = FactoryGirl.create(:email)
17 | email.state.should eq 'draft'
18 | end
19 | end
20 |
21 | context 'transition states' do
22 | describe '#publish' do
23 | it 'changes Email.state to published' do
24 | email = FactoryGirl.create(:email)
25 |
26 | expect{ email.publish }.to change{ email.state }.from('draft').to('published')
27 | end
28 | end
29 |
30 | describe '#unpublish' do
31 | it 'changes Email.state to draft' do
32 | email = FactoryGirl.create(:email)
33 | email.publish
34 |
35 | expect{ email.unpublish }.to change{ email.state }.from('published').to('draft')
36 | end
37 | end
38 | end
39 | end
40 |
--------------------------------------------------------------------------------
/Gemfile:
--------------------------------------------------------------------------------
1 | source 'https://rubygems.org'
2 |
3 | gem 'rails', '3.2.13'
4 | gem 'strong_parameters'
5 | gem 'bcrypt-ruby', '3.0.1'
6 | gem 'warden'
7 | gem 'dynamic_form'
8 | gem 'email_validator'
9 | gem 'state_machine'
10 |
11 | # Bundle edge Rails instead:
12 | # gem 'rails', :git => 'git://github.com/rails/rails.git'
13 |
14 | gem 'sqlite3'
15 |
16 |
17 | # Gems used only for assets and not required
18 | # in production environments by default.
19 | group :assets do
20 | gem 'sass-rails', '~> 3.2.3'
21 | gem 'coffee-rails', '~> 3.2.1'
22 | gem 'bootstrap-sass'
23 |
24 | # See https://github.com/sstephenson/execjs#readme for more supported runtimes
25 | # gem 'therubyracer', :platforms => :ruby
26 |
27 | gem 'uglifier', '>= 1.0.3'
28 | end
29 |
30 | gem 'jquery-rails'
31 |
32 | group :development, :test do
33 | gem 'rspec-rails'
34 | gem 'pry-rails'
35 | gem 'factory_girl_rails'
36 | gem 'capybara', '2.0.2'
37 | gem 'quiet_assets'
38 | end
39 |
40 | group :test do
41 | gem 'shoulda-matchers'
42 | end
43 |
44 | # To use ActiveModel has_secure_password
45 | # gem 'bcrypt-ruby', '~> 3.0.0'
46 |
47 | # To use Jbuilder templates for JSON
48 | # gem 'jbuilder'
49 |
50 | # Use unicorn as the app server
51 | # gem 'unicorn'
52 |
53 | # Deploy with Capistrano
54 | # gem 'capistrano'
55 |
56 | # To use debugger
57 | # gem 'debugger'
58 |
--------------------------------------------------------------------------------
/spec/features/users/sign_up_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | feature 'User Signup' do
4 | scenario 'new record' do
5 | visit root_path
6 | click_link 'Sign up'
7 |
8 | fill_in 'Name', with: 'Test User'
9 | fill_in 'Email', with: 'user@example.com'
10 | password_field_id = 'user_password'
11 | fill_in password_field_id, with: 'password'
12 | password_confirmation_field_id = 'user_password_confirmation'
13 | fill_in password_confirmation_field_id, with: 'password'
14 | click_button 'Sign up'
15 |
16 | page.should have_content 'You have signed up successfully and are now logged in.'
17 | page.current_url.should eq emails_url
18 | page.should_not have_content 'Sign up'
19 | end
20 |
21 | scenario 'exisiting record' do
22 | User.create( name: 'Existing User', email: 'user@example.com', password: 'password' )
23 |
24 | visit root_path
25 | click_link 'Sign up'
26 |
27 | fill_in 'Name', with: 'Test User'
28 | fill_in 'Email', with: 'user@example.com'
29 | password_field_id = 'user_password'
30 | fill_in password_field_id, with: 'password'
31 | password_confirmation_field_id = 'user_password_confirmation'
32 | fill_in password_confirmation_field_id, with: 'password'
33 | click_button 'Sign up'
34 |
35 | page.should have_content 'Email has already been taken'
36 | page.current_url.should eq signup_url
37 | end
38 | end
39 |
--------------------------------------------------------------------------------
/spec/features/users/sign_in_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | feature 'User sign in' do
4 | let!(:user) { FactoryGirl.create :user }
5 | let(:login_url) { 'http://www.example.com/login' }
6 |
7 | scenario 'signs in with valid credentials' do
8 | visit root_path
9 | click_link 'Login'
10 | page.current_url.should eq login_url
11 |
12 | fill_in 'Email', with: user.email
13 | fill_in 'Password', with: 'password'
14 | click_button 'Login'
15 |
16 | page.should have_content 'You are now logged in.'
17 | page.current_url.should eq emails_url
18 | page.should_not have_content 'Login'
19 | end
20 |
21 | scenario 'attempts to sign in with invalid email address => fail' do
22 | visit root_path
23 | click_link 'Login'
24 | page.current_url.should eq login_url
25 |
26 | fill_in 'Email', with: 'foo@example.com'
27 | fill_in 'Password', with: 'password'
28 | click_button 'Login'
29 |
30 | page.current_url.should eq login_url
31 | page.should have_content 'Invalid email or password.'
32 | end
33 |
34 | scenario 'attempts to sign in with invalid password => fail' do
35 | visit root_path
36 | click_link 'Login'
37 | page.current_url.should eq login_url
38 |
39 | fill_in 'Email', with: user.email
40 | fill_in 'Password', with: 'notmypassword'
41 | click_button 'Login'
42 |
43 | page.current_url.should eq login_url
44 | page.should have_content 'Invalid email or password.'
45 | end
46 | end
47 |
--------------------------------------------------------------------------------
/config/environments/development.rb:
--------------------------------------------------------------------------------
1 | SampleProject::Application.configure do
2 | # Settings specified here will take precedence over those in config/application.rb
3 |
4 | # In the development environment your application's code is reloaded on
5 | # every request. This slows down response time but is perfect for development
6 | # since you don't have to restart the web server when you make code changes.
7 | config.cache_classes = false
8 |
9 | # Log error messages when you accidentally call methods on nil.
10 | config.whiny_nils = true
11 |
12 | # Show full error reports and disable caching
13 | config.consider_all_requests_local = true
14 | config.action_controller.perform_caching = false
15 |
16 | # Don't care if the mailer can't send
17 | config.action_mailer.raise_delivery_errors = false
18 |
19 | # Print deprecation notices to the Rails logger
20 | config.active_support.deprecation = :log
21 |
22 | # Only use best-standards-support built into browsers
23 | config.action_dispatch.best_standards_support = :builtin
24 |
25 | # Raise exception on mass assignment protection for Active Record models
26 | config.active_record.mass_assignment_sanitizer = :strict
27 |
28 | # Log the query plan for queries taking more than this (works
29 | # with SQLite, MySQL, and PostgreSQL)
30 | config.active_record.auto_explain_threshold_in_seconds = 0.5
31 |
32 | # Do not compress assets
33 | config.assets.compress = false
34 |
35 | # Expands the lines which load the assets
36 | config.assets.debug = true
37 | end
38 |
--------------------------------------------------------------------------------
/db/schema.rb:
--------------------------------------------------------------------------------
1 | # encoding: UTF-8
2 | # This file is auto-generated from the current state of the database. Instead
3 | # of editing this file, please use the migrations feature of Active Record to
4 | # incrementally modify your database, and then regenerate this schema definition.
5 | #
6 | # Note that this schema.rb definition is the authoritative source for your
7 | # database schema. If you need to create the application database on another
8 | # system, you should be using db:schema:load, not running all the migrations
9 | # from scratch. The latter is a flawed and unsustainable approach (the more migrations
10 | # you'll amass, the slower it'll run and the greater likelihood for issues).
11 | #
12 | # It's strongly recommended to check this file into your version control system.
13 |
14 | ActiveRecord::Schema.define(:version => 20130808095750) do
15 |
16 | create_table "emails", :force => true do |t|
17 | t.integer "user_id"
18 | t.string "from_name"
19 | t.string "from_email"
20 | t.string "to_email"
21 | t.string "subject"
22 | t.text "html_body"
23 | t.text "text_body"
24 | t.datetime "created_at", :null => false
25 | t.datetime "updated_at", :null => false
26 | t.string "state"
27 | end
28 |
29 | add_index "emails", ["user_id"], :name => "index_emails_on_user_id"
30 |
31 | create_table "users", :force => true do |t|
32 | t.string "name"
33 | t.string "email"
34 | t.string "password_digest"
35 | t.integer "login_count"
36 | t.datetime "last_logged_in_at"
37 | t.datetime "created_at", :null => false
38 | t.datetime "updated_at", :null => false
39 | end
40 |
41 | end
42 |
--------------------------------------------------------------------------------
/config/environments/test.rb:
--------------------------------------------------------------------------------
1 | SampleProject::Application.configure do
2 | # Settings specified here will take precedence over those in config/application.rb
3 |
4 | # The test environment is used exclusively to run your application's
5 | # test suite. You never need to work with it otherwise. Remember that
6 | # your test database is "scratch space" for the test suite and is wiped
7 | # and recreated between test runs. Don't rely on the data there!
8 | config.cache_classes = true
9 |
10 | # Configure static asset server for tests with Cache-Control for performance
11 | config.serve_static_assets = true
12 | config.static_cache_control = "public, max-age=3600"
13 |
14 | # Log error messages when you accidentally call methods on nil
15 | config.whiny_nils = true
16 |
17 | # Show full error reports and disable caching
18 | config.consider_all_requests_local = true
19 | config.action_controller.perform_caching = false
20 |
21 | # Raise exceptions instead of rendering exception templates
22 | config.action_dispatch.show_exceptions = false
23 |
24 | # Disable request forgery protection in test environment
25 | config.action_controller.allow_forgery_protection = false
26 |
27 | # Tell Action Mailer not to deliver emails to the real world.
28 | # The :test delivery method accumulates sent emails in the
29 | # ActionMailer::Base.deliveries array.
30 | config.action_mailer.delivery_method = :test
31 |
32 | # Raise exception on mass assignment protection for Active Record models
33 | config.active_record.mass_assignment_sanitizer = :strict
34 |
35 | # Print deprecation notices to the stderr
36 | config.active_support.deprecation = :stderr
37 | end
38 |
--------------------------------------------------------------------------------
/spec/spec_helper.rb:
--------------------------------------------------------------------------------
1 | # This file is copied to spec/ when you run 'rails generate rspec:install'
2 | ENV["RAILS_ENV"] ||= 'test'
3 | require File.expand_path("../../config/environment", __FILE__)
4 | require 'rspec/rails'
5 | require 'rspec/autorun'
6 | require 'capybara/rspec'
7 |
8 | # Requires supporting ruby files with custom matchers and macros, etc,
9 | # in spec/support/ and its subdirectories.
10 | Dir[Rails.root.join("spec/support/**/*.rb")].each {|f| require f}
11 |
12 | RSpec.configure do |config|
13 | # ## Mock Framework
14 | #
15 | # If you prefer to use mocha, flexmock or RR, uncomment the appropriate line:
16 | #
17 | # config.mock_with :mocha
18 | # config.mock_with :flexmock
19 | # config.mock_with :rr
20 |
21 | # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
22 | # config.fixture_path = "#{::Rails.root}/spec/fixtures"
23 |
24 | # If you're not using ActiveRecord, or you'd prefer not to run each of your
25 | # examples within a transaction, remove the following line or assign false
26 | # instead of true.
27 | config.use_transactional_fixtures = true
28 |
29 | # If true, the base class of anonymous controllers will be inferred
30 | # automatically. This will be the default behavior in future versions of
31 | # rspec-rails.
32 | config.infer_base_class_for_anonymous_controllers = false
33 |
34 | # Run specs in random order to surface order dependencies. If you find an
35 | # order dependency and want to debug it, you can fix the order by providing
36 | # the seed, which is printed after each run.
37 | # --seed 1234
38 | config.order = "random"
39 |
40 | config.include Warden::Test::Helpers, type: :controller
41 | Warden.test_mode!
42 |
43 | config.after :each do
44 | Warden.test_reset!
45 | end
46 | end
47 |
--------------------------------------------------------------------------------
/app/views/emails/edit.html.erb:
--------------------------------------------------------------------------------
1 | Edit Email
2 |
3 | <%= form_for @email, html: { class: 'form-horizontal' } do |f| %>
4 | <%= f.error_messages %>
5 |
6 | <%= f.label :from_name, class: 'control-label' %>
7 |
8 | <%= f.text_field :from_name, class: 'span8' %>
9 |
10 |
11 |
12 | <%= f.label :from_email, class: 'control-label' %>
13 |
14 | <%= f.email_field :from_email, class: 'span8' %>
15 |
16 |
17 |
18 | <%= f.label :to_email, class: 'control-label' %>
19 |
20 | <%= f.email_field :to_email, class: 'span8' %>
21 |
22 |
23 |
24 | <%= f.label :subject, class: 'control-label' %>
25 |
26 | <%= f.text_field :subject, class: 'span8' %>
27 |
28 |
29 |
30 | <%= f.label :text_body, class: 'control-label' %>
31 |
32 | <%= f.text_area :text_body, class: 'span8', rows: 8 %>
33 |
34 |
35 |
36 | <%= f.label :html_body, class: 'control-label' %>
37 |
38 | <%= f.text_area :html_body, class: 'span8', rows: 8 %>
39 |
40 |
41 |
42 | <%= f.submit 'Save changes', class: 'btn btn-primary' %>
43 | <% if @email.draft? %>
44 | <%= link_to 'Publish', publish_email_path(@email), method: :post, class: 'btn btn-success' %>
45 | <% else %>
46 | <%= link_to 'Unpublish', unpublish_email_path(@email), method: :post, class: 'btn btn-success' %>
47 | <% end %>
48 |
49 | <% end %>
50 |
--------------------------------------------------------------------------------
/app/views/layouts/application.html.erb:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | SampleProject
5 | <%= stylesheet_link_tag "application", :media => "all" %>
6 | <%= javascript_include_tag "application" %>
7 | <%= csrf_meta_tags %>
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 | <%= link_to 'Drip', root_path, class: 'brand' %>
24 |
25 |
26 |
27 |
28 |
29 | <% if current_user %>
30 | <%= link_to 'Emails', emails_path %>
31 | <%= link_to 'Logout', logout_path, method: :delete %>
32 | <% else %>
33 | <%= link_to 'Login', login_path %>
34 | <%= link_to 'Sign up', signup_path %>
35 | <% end %>
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 | <% if flash.any? %>
46 | <% flash.each do |k, v| %>
47 |
48 | ×
49 | <%= v %>
50 |
51 | <% end %>
52 | <% end %>
53 |
54 |
55 |
56 | <%= yield %>
57 |
58 |
59 |
60 |
61 |
62 |
--------------------------------------------------------------------------------
/spec/controllers/emails_controller_spec.rb:
--------------------------------------------------------------------------------
1 | require 'spec_helper'
2 |
3 | describe EmailsController, type: :controller do
4 |
5 | def stub_sign_in user
6 | request.env['warden'].stub :authenticate! => user
7 | controller.stub current_user: user
8 | end
9 |
10 | before :each do
11 | @user = FactoryGirl.create :user
12 | @email = FactoryGirl.create(:email, user: @user)
13 | stub_sign_in @user
14 | end
15 |
16 |
17 | describe 'GET #index' do
18 | before :each do
19 | get :index
20 | end
21 |
22 | it 'should be success' do
23 | response.should be_success
24 | end
25 |
26 | it 'renders the index view' do
27 | response.should render_template :index
28 | end
29 | end
30 |
31 | describe 'GET #edit' do
32 | before :each do
33 | get :edit, id: @email.id
34 | end
35 |
36 | it 'should be success' do
37 | response.should be_success
38 | end
39 |
40 | it 'renders the edit view' do
41 | response.should render_template :edit
42 | end
43 |
44 | it 'assigns an Email record to the :email variable' do
45 | assigns(:email).should eq @email
46 | end
47 | end
48 |
49 | describe 'PUT #update' do
50 | context 'valid attributes' do
51 | before :each do
52 | put :update, id: @email.id, email: { subject: 'Modified Subject Text' }
53 | end
54 |
55 | it 'should be success' do
56 | response.status.should eq 302
57 | end
58 |
59 | it 'redirect_to emails_path' do
60 | response.should redirect_to emails_path
61 | end
62 |
63 | it 'assigns an Email record to the :email variable' do
64 | assigns(:email).should eq @email
65 | end
66 |
67 | it 'updates Email attributes' do
68 | @email.reload
69 | @email.subject.should eq 'Modified Subject Text'
70 | end
71 | end
72 |
73 | context 'invalid/missing attributes' do
74 | before :each do
75 | put :update, id: @email.id, email: { subject: nil }
76 | end
77 |
78 | it 're-renders edit template' do
79 | response.should render_template :edit
80 | end
81 |
82 | it 'assigns an Email record to the :email variable' do
83 | assigns(:email).should eq @email
84 | end
85 |
86 | it 'does not update Email attributes' do
87 | @email.reload
88 | @email.subject.should eq 'FactoryGirl spawned this email'
89 | end
90 | end
91 |
92 | end
93 | end
94 |
--------------------------------------------------------------------------------
/config/routes.rb:
--------------------------------------------------------------------------------
1 | SampleProject::Application.routes.draw do
2 |
3 | # The priority is based upon order of creation:
4 | # first created -> highest priority.
5 |
6 | get '/login', to: 'sessions#new', as: 'login'
7 | post '/login', to: 'sessions#create', as: 'sessions'
8 | delete '/logout', to: 'sessions#destroy', as: 'logout'
9 |
10 | get '/signup', to: 'registrations#new', as: 'signup'
11 | post '/signup', to: 'registrations#create', as: 'signup'
12 |
13 | resources :emails do
14 | member do
15 | post :publish
16 | post :unpublish
17 | end
18 | end
19 |
20 | # Sample of regular route:
21 | # match 'products/:id' => 'catalog#view'
22 | # Keep in mind you can assign values other than :controller and :action
23 |
24 | # Sample of named route:
25 | # match 'products/:id/purchase' => 'catalog#purchase', :as => :purchase
26 | # This route can be invoked with purchase_url(:id => product.id)
27 |
28 | # Sample resource route (maps HTTP verbs to controller actions automatically):
29 | # resources :products
30 |
31 | # Sample resource route with options:
32 | # resources :products do
33 | # member do
34 | # get 'short'
35 | # post 'toggle'
36 | # end
37 | #
38 | # collection do
39 | # get 'sold'
40 | # end
41 | # end
42 |
43 | # Sample resource route with sub-resources:
44 | # resources :products do
45 | # resources :comments, :sales
46 | # resource :seller
47 | # end
48 |
49 | # Sample resource route with more complex sub-resources
50 | # resources :products do
51 | # resources :comments
52 | # resources :sales do
53 | # get 'recent', :on => :collection
54 | # end
55 | # end
56 |
57 | # Sample resource route within a namespace:
58 | # namespace :admin do
59 | # # Directs /admin/products/* to Admin::ProductsController
60 | # # (app/controllers/admin/products_controller.rb)
61 | # resources :products
62 | # end
63 |
64 | # You can have the root of your site routed with "root"
65 | # just remember to delete public/index.html.
66 | # root :to => 'welcome#index'
67 |
68 | # See how all your routes lay out with "rake routes"
69 |
70 | # This is a legacy wild controller route that's not recommended for RESTful applications.
71 | # Note: This route will make all actions in every controller accessible via GET requests.
72 | # match ':controller(/:action(/:id))(.:format)'
73 | root :to => "home#index"
74 | end
75 |
--------------------------------------------------------------------------------
/config/environments/production.rb:
--------------------------------------------------------------------------------
1 | SampleProject::Application.configure do
2 | # Settings specified here will take precedence over those in config/application.rb
3 |
4 | # Code is not reloaded between requests
5 | config.cache_classes = true
6 |
7 | # Full error reports are disabled and caching is turned on
8 | config.consider_all_requests_local = false
9 | config.action_controller.perform_caching = true
10 |
11 | # Disable Rails's static asset server (Apache or nginx will already do this)
12 | config.serve_static_assets = false
13 |
14 | # Compress JavaScripts and CSS
15 | config.assets.compress = true
16 |
17 | # Don't fallback to assets pipeline if a precompiled asset is missed
18 | config.assets.compile = false
19 |
20 | # Generate digests for assets URLs
21 | config.assets.digest = true
22 |
23 | # Defaults to nil and saved in location specified by config.assets.prefix
24 | # config.assets.manifest = YOUR_PATH
25 |
26 | # Specifies the header that your server uses for sending files
27 | # config.action_dispatch.x_sendfile_header = "X-Sendfile" # for apache
28 | # config.action_dispatch.x_sendfile_header = 'X-Accel-Redirect' # for nginx
29 |
30 | # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies.
31 | # config.force_ssl = true
32 |
33 | # See everything in the log (default is :info)
34 | # config.log_level = :debug
35 |
36 | # Prepend all log lines with the following tags
37 | # config.log_tags = [ :subdomain, :uuid ]
38 |
39 | # Use a different logger for distributed setups
40 | # config.logger = ActiveSupport::TaggedLogging.new(SyslogLogger.new)
41 |
42 | # Use a different cache store in production
43 | # config.cache_store = :mem_cache_store
44 |
45 | # Enable serving of images, stylesheets, and JavaScripts from an asset server
46 | # config.action_controller.asset_host = "http://assets.example.com"
47 |
48 | # Precompile additional assets (application.js, application.css, and all non-JS/CSS are already added)
49 | # config.assets.precompile += %w( search.js )
50 |
51 | # Disable delivery errors, bad email addresses will be ignored
52 | # config.action_mailer.raise_delivery_errors = false
53 |
54 | # Enable threaded mode
55 | # config.threadsafe!
56 |
57 | # Enable locale fallbacks for I18n (makes lookups for any locale fall back to
58 | # the I18n.default_locale when a translation can not be found)
59 | config.i18n.fallbacks = true
60 |
61 | # Send deprecation notices to registered listeners
62 | config.active_support.deprecation = :notify
63 |
64 | # Log the query plan for queries taking more than this (works
65 | # with SQLite, MySQL, and PostgreSQL)
66 | # config.active_record.auto_explain_threshold_in_seconds = 0.5
67 | end
68 |
--------------------------------------------------------------------------------
/config/application.rb:
--------------------------------------------------------------------------------
1 | require File.expand_path('../boot', __FILE__)
2 |
3 | require 'rails/all'
4 | require 'warden'
5 |
6 | if defined?(Bundler)
7 | # If you precompile assets before deploying to production, use this line
8 | Bundler.require(*Rails.groups(:assets => %w(development test)))
9 | # If you want your assets lazily compiled in production, use this line
10 | # Bundler.require(:default, :assets, Rails.env)
11 | end
12 |
13 | module SampleProject
14 | class Application < Rails::Application
15 | # Settings in config/environments/* take precedence over those specified here.
16 | # Application configuration should go into files in config/initializers
17 | # -- all .rb files in that directory are automatically loaded.
18 |
19 | # Custom directories with classes and modules you want to be autoloadable.
20 | # config.autoload_paths += %W(#{config.root}/extras)
21 |
22 | # Only load the plugins named here, in the order given (default is alphabetical).
23 | # :all can be used as a placeholder for all plugins not explicitly named.
24 | # config.plugins = [ :exception_notification, :ssl_requirement, :all ]
25 |
26 | # Activate observers that should always be running.
27 | # config.active_record.observers = :cacher, :garbage_collector, :forum_observer
28 |
29 | # Set Time.zone default to the specified zone and make Active Record auto-convert to this zone.
30 | # Run "rake -D time" for a list of tasks for finding time zone names. Default is UTC.
31 | # config.time_zone = 'Central Time (US & Canada)'
32 |
33 | # The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded.
34 | # config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s]
35 | # config.i18n.default_locale = :de
36 |
37 | # Configure the default encoding used in templates for Ruby 1.9.
38 | config.encoding = "utf-8"
39 |
40 | # Configure sensitive parameters which will be filtered from the log file.
41 | config.filter_parameters += [:password]
42 |
43 | # Enable escaping HTML in JSON.
44 | config.active_support.escape_html_entities_in_json = true
45 |
46 | # Use SQL instead of Active Record's schema dumper when creating the database.
47 | # This is necessary if your schema can't be completely dumped by the schema dumper,
48 | # like if you have constraints or database-specific column types
49 | # config.active_record.schema_format = :sql
50 |
51 | # Enforce whitelist mode for mass assignment.
52 | # This will create an empty whitelist of attributes available for mass-assignment for all models
53 | # in your app. As such, your models will need to explicitly whitelist or blacklist accessible
54 | # parameters by using an attr_accessible or attr_protected declaration.
55 | config.active_record.whitelist_attributes = false
56 |
57 | # Enable the asset pipeline
58 | config.assets.enabled = true
59 |
60 | # Version of your assets, change this if you want to expire all your assets
61 | config.assets.version = '1.0'
62 |
63 | # config Warden
64 | config.middleware.use Warden::Manager do |manager|
65 | manager.default_strategies :password
66 | end
67 | end
68 | end
69 |
--------------------------------------------------------------------------------
/Gemfile.lock:
--------------------------------------------------------------------------------
1 | GEM
2 | remote: https://rubygems.org/
3 | specs:
4 | actionmailer (3.2.13)
5 | actionpack (= 3.2.13)
6 | mail (~> 2.5.3)
7 | actionpack (3.2.13)
8 | activemodel (= 3.2.13)
9 | activesupport (= 3.2.13)
10 | builder (~> 3.0.0)
11 | erubis (~> 2.7.0)
12 | journey (~> 1.0.4)
13 | rack (~> 1.4.5)
14 | rack-cache (~> 1.2)
15 | rack-test (~> 0.6.1)
16 | sprockets (~> 2.2.1)
17 | activemodel (3.2.13)
18 | activesupport (= 3.2.13)
19 | builder (~> 3.0.0)
20 | activerecord (3.2.13)
21 | activemodel (= 3.2.13)
22 | activesupport (= 3.2.13)
23 | arel (~> 3.0.2)
24 | tzinfo (~> 0.3.29)
25 | activeresource (3.2.13)
26 | activemodel (= 3.2.13)
27 | activesupport (= 3.2.13)
28 | activesupport (3.2.13)
29 | i18n (= 0.6.1)
30 | multi_json (~> 1.0)
31 | arel (3.0.2)
32 | bcrypt-ruby (3.0.1)
33 | bootstrap-sass (2.3.2.1)
34 | sass (~> 3.2)
35 | bourne (1.1.2)
36 | mocha (= 0.10.5)
37 | builder (3.0.4)
38 | capybara (2.0.2)
39 | mime-types (>= 1.16)
40 | nokogiri (>= 1.3.3)
41 | rack (>= 1.0.0)
42 | rack-test (>= 0.5.4)
43 | selenium-webdriver (~> 2.0)
44 | xpath (~> 1.0.0)
45 | childprocess (0.3.9)
46 | ffi (~> 1.0, >= 1.0.11)
47 | coderay (1.0.9)
48 | coffee-rails (3.2.2)
49 | coffee-script (>= 2.2.0)
50 | railties (~> 3.2.0)
51 | coffee-script (2.2.0)
52 | coffee-script-source
53 | execjs
54 | coffee-script-source (1.6.3)
55 | diff-lcs (1.1.3)
56 | dynamic_form (1.1.4)
57 | email_validator (1.4.0)
58 | activemodel
59 | erubis (2.7.0)
60 | execjs (1.4.0)
61 | multi_json (~> 1.0)
62 | factory_girl (4.1.0)
63 | activesupport (>= 3.0.0)
64 | factory_girl_rails (4.1.0)
65 | factory_girl (~> 4.1.0)
66 | railties (>= 3.0.0)
67 | ffi (1.9.0)
68 | hike (1.2.3)
69 | i18n (0.6.1)
70 | journey (1.0.4)
71 | jquery-rails (3.0.4)
72 | railties (>= 3.0, < 5.0)
73 | thor (>= 0.14, < 2.0)
74 | json (1.8.0)
75 | mail (2.5.4)
76 | mime-types (~> 1.16)
77 | treetop (~> 1.4.8)
78 | metaclass (0.0.1)
79 | method_source (0.8.1)
80 | mime-types (1.23)
81 | mini_portile (0.5.1)
82 | mocha (0.10.5)
83 | metaclass (~> 0.0.1)
84 | multi_json (1.7.7)
85 | nokogiri (1.6.0)
86 | mini_portile (~> 0.5.0)
87 | polyglot (0.3.3)
88 | pry (0.9.12.2)
89 | coderay (~> 1.0.5)
90 | method_source (~> 0.8)
91 | slop (~> 3.4)
92 | pry-rails (0.3.1)
93 | pry (>= 0.9.10)
94 | quiet_assets (1.0.2)
95 | railties (>= 3.1, < 5.0)
96 | rack (1.4.5)
97 | rack-cache (1.2)
98 | rack (>= 0.4)
99 | rack-ssl (1.3.3)
100 | rack
101 | rack-test (0.6.2)
102 | rack (>= 1.0)
103 | rails (3.2.13)
104 | actionmailer (= 3.2.13)
105 | actionpack (= 3.2.13)
106 | activerecord (= 3.2.13)
107 | activeresource (= 3.2.13)
108 | activesupport (= 3.2.13)
109 | bundler (~> 1.0)
110 | railties (= 3.2.13)
111 | railties (3.2.13)
112 | actionpack (= 3.2.13)
113 | activesupport (= 3.2.13)
114 | rack-ssl (~> 1.3.2)
115 | rake (>= 0.8.7)
116 | rdoc (~> 3.4)
117 | thor (>= 0.14.6, < 2.0)
118 | rake (10.1.0)
119 | rdoc (3.12.2)
120 | json (~> 1.4)
121 | rspec-core (2.12.2)
122 | rspec-expectations (2.12.1)
123 | diff-lcs (~> 1.1.3)
124 | rspec-mocks (2.12.2)
125 | rspec-rails (2.12.2)
126 | actionpack (>= 3.0)
127 | activesupport (>= 3.0)
128 | railties (>= 3.0)
129 | rspec-core (~> 2.12.0)
130 | rspec-expectations (~> 2.12.0)
131 | rspec-mocks (~> 2.12.0)
132 | rubyzip (0.9.9)
133 | sass (3.2.10)
134 | sass-rails (3.2.6)
135 | railties (~> 3.2.0)
136 | sass (>= 3.1.10)
137 | tilt (~> 1.3)
138 | selenium-webdriver (2.33.0)
139 | childprocess (>= 0.2.5)
140 | multi_json (~> 1.0)
141 | rubyzip
142 | websocket (~> 1.0.4)
143 | shoulda-matchers (1.4.2)
144 | activesupport (>= 3.0.0)
145 | bourne (~> 1.1.2)
146 | slop (3.4.5)
147 | sprockets (2.2.2)
148 | hike (~> 1.2)
149 | multi_json (~> 1.0)
150 | rack (~> 1.0)
151 | tilt (~> 1.1, != 1.3.0)
152 | sqlite3 (1.3.7)
153 | state_machine (1.2.0)
154 | strong_parameters (0.2.1)
155 | actionpack (~> 3.0)
156 | activemodel (~> 3.0)
157 | railties (~> 3.0)
158 | thor (0.18.1)
159 | tilt (1.4.1)
160 | treetop (1.4.14)
161 | polyglot
162 | polyglot (>= 0.3.1)
163 | tzinfo (0.3.37)
164 | uglifier (2.1.2)
165 | execjs (>= 0.3.0)
166 | multi_json (~> 1.0, >= 1.0.2)
167 | warden (1.2.3)
168 | rack (>= 1.0)
169 | websocket (1.0.7)
170 | xpath (1.0.0)
171 | nokogiri (~> 1.3)
172 |
173 | PLATFORMS
174 | ruby
175 |
176 | DEPENDENCIES
177 | bcrypt-ruby (= 3.0.1)
178 | bootstrap-sass
179 | capybara (= 2.0.2)
180 | coffee-rails (~> 3.2.1)
181 | dynamic_form
182 | email_validator
183 | factory_girl_rails
184 | jquery-rails
185 | pry-rails
186 | quiet_assets
187 | rails (= 3.2.13)
188 | rspec-rails
189 | sass-rails (~> 3.2.3)
190 | shoulda-matchers
191 | sqlite3
192 | state_machine
193 | strong_parameters
194 | uglifier (>= 1.0.3)
195 | warden
196 |
--------------------------------------------------------------------------------