diff --git a/.gitignore b/.gitignore index 6087bad..3bad0ea 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,4 @@ public/system .*.swp .DS* **/.DS* +.sass-cache/ diff --git a/.rvmrc b/.rvmrc index a4b9dff..9498791 100644 --- a/.rvmrc +++ b/.rvmrc @@ -4,44 +4,52 @@ # development environment upon cd'ing into the directory # First we specify our desired [@], the @gemset name is optional. -environment_id="ruby-1.9.2-p136@danbarberphoto" +environment_id="ruby-1.9.2-p290@danbarberphoto" + +# +# Uncomment following line if you want options to be set only for given project. +# +# PROJECT_JRUBY_OPTS=( --1.9 ) # # First we attempt to load the desired environment directly from the environment -# file, this is very fast and efficicent compared to running through the entire +# file. This is very fast and efficient compared to running through the entire # CLI and selector. If you want feedback on which environment was used then # insert the word 'use' after --create as this triggers verbose mode. # if [[ -d "${rvm_path:-$HOME/.rvm}/environments" \ - && -s "${rvm_path:-$HOME/.rvm}/environments/$environment_id" ]] ; then + && -s "${rvm_path:-$HOME/.rvm}/environments/$environment_id" ]] +then \. "${rvm_path:-$HOME/.rvm}/environments/$environment_id" + + if [[ -s "${rvm_path:-$HOME/.rvm}/hooks/after_use" ]] + then + . "${rvm_path:-$HOME/.rvm}/hooks/after_use" + fi else # If the environment file has not yet been created, use the RVM CLI to select. - rvm --create use "$environment_id" + if ! rvm --create use "$environment_id" + then + echo "Failed to create RVM environment '${environment_id}'." + exit 1 + fi fi # # If you use an RVM gemset file to install a list of gems (*.gems), you can have -# it be automatically loaded, uncomment the following and adjust the filename if +# it be automatically loaded. Uncomment the following and adjust the filename if # necessary. # # filename=".gems" -# if [[ -s "$filename" ]] ; then +# if [[ -s "$filename" ]] +# then # rvm gemset import "$filename" | grep -v already | grep -v listed | grep -v complete | sed '/^$/d' # fi -# -# If you use bundler and would like to run bundle each time you enter the -# directory you can uncomment the following code. -# -# # Ensure that Bundler is installed, install it if it is not. -# if ! command -v bundle ; then -# printf "The rubygem 'bundler' is not installed, installing it now.\n" -# gem install bundler -# fi -# -# # Bundle while redcing excess noise. -# printf "Bundling your gems this may take a few minutes on a fresh clone.\n" -# bundle | grep -v 'Using' | grep -v 'complete' | sed '/^$/d' -# +# If you use bundler, this might be useful to you: +# if command -v bundle && [[ -s Gemfile ]] +# then +# bundle install +# fi + diff --git a/Gemfile b/Gemfile index 801a0d5..c4330a7 100644 --- a/Gemfile +++ b/Gemfile @@ -35,9 +35,11 @@ gem 'aws-s3', :require => 'aws/s3' # Bundle gems for the local environment. Make sure to # put test-only gems in this group so their generators # and rake tasks are available in development mode: -# group :development, :test do -# gem 'webrat' -# end +group :development do + gem 'ruby_parser' + gem 'hpricot' + gem 'powder' +end gem 'sass-rails', "~> 3.1.0" gem "exception_notification", :git => "git://github.com/rails/exception_notification", :require => 'exception_notifier' diff --git a/Gemfile.lock b/Gemfile.lock index 2093375..991fbe6 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -65,6 +65,7 @@ GEM execjs (1.2.9) multi_json (~> 1.0) hike (1.2.1) + hpricot (0.8.4) i18n (0.6.0) jquery-rails (1.0.16) railties (~> 3.0) @@ -87,6 +88,8 @@ GEM polyamorous (0.5.0) activerecord (~> 3.0) polyglot (0.3.2) + powder (0.1.6) + thor (>= 0.11.5) rack (1.3.5) rack-cache (1.1) rack (>= 0.4) @@ -115,6 +118,8 @@ GEM rdiscount (1.6.8) rdoc (3.11) json (~> 1.4) + ruby_parser (2.3.1) + sexp_processor (~> 3.0) sass (3.1.10) sass-rails (3.1.4) actionpack (~> 3.1.0) @@ -122,6 +127,7 @@ GEM sass (>= 3.1.4) sprockets (~> 2.0.0) tilt (~> 1.3.2) + sexp_processor (3.0.7) sprockets (2.0.3) hike (~> 1.2) rack (~> 1.0) @@ -158,12 +164,15 @@ DEPENDENCIES coffee-rails (~> 3.1.0) devise exception_notification! + hpricot jquery-rails mini_exiftool paperclip pg + powder rails (= 3.1.1) rdiscount + ruby_parser sass-rails (~> 3.1.0) sqlite3-ruby squeel diff --git a/README b/README index 6966fe9..edc5de1 100644 --- a/README +++ b/README @@ -91,7 +91,11 @@ mode. With gems, use sudo gem install ruby-debug. Example: class WeblogController < ActionController::Base def index +<<<<<<< HEAD @posts = Post.find(:all) +======= + @posts = Post.all +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc debugger end end @@ -139,7 +143,11 @@ To reload your controllers and models after launching the console run reload! More information about irb can be found at: +<<<<<<< HEAD link:http://www.rubycentral.com/pickaxe/irb.html +======= +link:http://www.rubycentral.org/pickaxe/irb.html +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc == dbconsole @@ -156,8 +164,18 @@ PostgreSQL and SQLite 3. The default directory structure of a generated Ruby on Rails application: |-- app +<<<<<<< HEAD | |-- controllers | |-- helpers +======= + | |-- assets + | |-- images + | |-- javascripts + | `-- stylesheets + | |-- controllers + | |-- helpers + | |-- mailers +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc | |-- models | `-- views | `-- layouts @@ -171,11 +189,15 @@ The default directory structure of a generated Ruby on Rails application: | `-- tasks |-- log |-- public +<<<<<<< HEAD | |-- images | |-- javascripts | `-- stylesheets |-- script | `-- performance +======= + |-- script +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc |-- test | |-- fixtures | |-- functional @@ -188,11 +210,22 @@ The default directory structure of a generated Ruby on Rails application: | |-- sessions | `-- sockets `-- vendor +<<<<<<< HEAD +======= + |-- assets + `-- stylesheets +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc `-- plugins app Holds all the code that's specific to this particular application. +<<<<<<< HEAD +======= +app/assets + Contains subdirectories for images, stylesheets, and JavaScript files. + +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc app/controllers Holds controllers that should be named like weblogs_controller.rb for automated URL mapping. All controllers should descend from @@ -237,8 +270,12 @@ lib the load path. public +<<<<<<< HEAD The directory available for the web server. Contains subdirectories for images, stylesheets, and javascripts. Also contains the dispatchers and the +======= + The directory available for the web server. Also contains the dispatchers and the +>>>>>>> cbb3800953736b1e2692d88c642ae066ac86adbc default HTML files. This should be set as the DOCUMENT_ROOT of your web server. diff --git a/app/assets/images/admin/logo.png b/app/assets/images/admin/logo.png new file mode 100644 index 0000000..fec2fca Binary files /dev/null and b/app/assets/images/admin/logo.png differ diff --git a/app/assets/javascripts/admin.js b/app/assets/javascripts/admin.js new file mode 100644 index 0000000..7bd1f59 --- /dev/null +++ b/app/assets/javascripts/admin.js @@ -0,0 +1,9 @@ +// This is a manifest file that'll be compiled into including all the files listed below. +// Add new JavaScript/Coffee code in separate files in this directory and they'll automatically +// be included in the compiled file accessible from http://example.com/assets/application.js +// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the +// the compiled file. +// +//= require jquery +//= require jquery_ujs +//= require_directory ./admin diff --git a/app/assets/javascripts/admin/admin.js.coffee b/app/assets/javascripts/admin/admin.js.coffee new file mode 100644 index 0000000..7615679 --- /dev/null +++ b/app/assets/javascripts/admin/admin.js.coffee @@ -0,0 +1,3 @@ +# Place all the behaviors and hooks related to the matching controller here. +# All this logic will automatically be available in application.js. +# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/ diff --git a/app/assets/javascripts/admin/dashboard.js.coffee b/app/assets/javascripts/admin/dashboard.js.coffee new file mode 100644 index 0000000..7615679 --- /dev/null +++ b/app/assets/javascripts/admin/dashboard.js.coffee @@ -0,0 +1,3 @@ +# Place all the behaviors and hooks related to the matching controller here. +# All this logic will automatically be available in application.js. +# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/ diff --git a/app/assets/javascripts/admin/downloads.js.coffee b/app/assets/javascripts/admin/downloads.js.coffee new file mode 100644 index 0000000..7615679 --- /dev/null +++ b/app/assets/javascripts/admin/downloads.js.coffee @@ -0,0 +1,3 @@ +# Place all the behaviors and hooks related to the matching controller here. +# All this logic will automatically be available in application.js. +# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/ diff --git a/app/assets/javascripts/admin/flash.js.coffee b/app/assets/javascripts/admin/flash.js.coffee new file mode 100644 index 0000000..18cfe29 --- /dev/null +++ b/app/assets/javascripts/admin/flash.js.coffee @@ -0,0 +1,4 @@ +$ -> + $(".flash a.close").click -> + $(this).parent().fadeOut(200) + false \ No newline at end of file diff --git a/app/assets/javascripts/admin/unlocks.js.coffee b/app/assets/javascripts/admin/unlocks.js.coffee new file mode 100644 index 0000000..7615679 --- /dev/null +++ b/app/assets/javascripts/admin/unlocks.js.coffee @@ -0,0 +1,3 @@ +# Place all the behaviors and hooks related to the matching controller here. +# All this logic will automatically be available in application.js. +# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/ diff --git a/app/assets/javascripts/home.js.coffee b/app/assets/javascripts/home.js.coffee new file mode 100644 index 0000000..7615679 --- /dev/null +++ b/app/assets/javascripts/home.js.coffee @@ -0,0 +1,3 @@ +# Place all the behaviors and hooks related to the matching controller here. +# All this logic will automatically be available in application.js. +# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/ diff --git a/app/assets/stylesheets/admin.css b/app/assets/stylesheets/admin.css new file mode 100644 index 0000000..ab7dfe9 --- /dev/null +++ b/app/assets/stylesheets/admin.css @@ -0,0 +1,8 @@ +/* + * This is a manifest file that'll automatically include all the stylesheets available in this directory + * and any sub-directories. You're free to add application-wide styles to this file and they'll appear at + * the top of the compiled file, but it's generally better to create a new file per style scope. + *= require_self + *= require formtastic + *= require_directory ./admin +*/ \ No newline at end of file diff --git a/app/assets/stylesheets/admin/admin.css.sass b/app/assets/stylesheets/admin/admin.css.sass new file mode 100644 index 0000000..9b3261a --- /dev/null +++ b/app/assets/stylesheets/admin/admin.css.sass @@ -0,0 +1,141 @@ +// Place all the styles related to the admin/admin controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ + +@import "../includes/v_linear_grad" +@import "../includes/round_corners" +@import "../includes/transition" +@import "../includes/box_shadow" + +body + background-color: #999 + color: #333 + font-family: "Helvetica Neue", "Arial", sans-serif + font-size: 14px + line-height: 18px + margin: 0 + padding: 0 + +#page, #login + background: #fafafa + padding: 1em 2em 3em + border-bottom: 1px solid #666 + @include box-shadow("0 1px 4px rgba(0, 0, 0, 0.3)") + +#login + width: 40em + margin: 5em auto 0 + +header + background: #333 + margin: -2.5em -2em 0 + #user + position: absolute + top: 1em + right: 2em + color: #ccc + a + color: #999 + h1 + background: #333 + font-size: 2em + margin-bottom: 0em + a + width: 263px + height: 24px + display: inline-block + padding: 1em 1em + text-indent: -1000em + background: url(/assets/admin/logo.png) 1em 0.75em no-repeat + &:hover + background-color: inherit + +#login + h1 + margin-bottom: 0.5em + position: relative + z-index: 1 + @include box-shadow("0 1px 2px rgba(0, 0, 0, 0.3)") + +h2 + margin-top: 1.2em + +p, ol, ul, td + font-family: "Helvetica Neue", "Arial", sans-serif + font-size: 1em + line-height: 1.5em + +pre + background-color: #eee + padding: 0.5em + font-size: 0.9em + +a + color: #000 + &:hover + color: #fff + background-color: #000 + +div + &.field, &.actions + margin-bottom: 0.5em + +#notice + color: green + +.field_with_errors + padding: 0.3em + background-color: red + display: table + +table + border: 1px solid #bbb + border-spacing: 0 + @include box-shadow("0 2px 2px rgba(0, 0, 0, 0.2)") + @include round-corners(5px) + td, th + border-bottom: 1px solid #bbb + tr:nth-child(even) td + background: #f0f0f0 + tr:nth-child(odd) td + background: #fff + thead + background: #ddd + color: #333 + td, th + text-align: left + padding: 0.5em 0.7em + tfoot td + background: #ddd !important + border-bottom: 0 + +#error_explanation + width: 450px + border: 2px solid red + padding: 7px + padding-bottom: 0 + margin-bottom: 20px + background-color: #f0f0f0 + h2 + text-align: left + font-weight: bold + padding: 5px 5px 5px 15px + font-size: 12px + margin: -7px + margin-bottom: 0px + background-color: #c00 + color: #fff + ul li + font-size: 12px + list-style: square + +form ul.taxonomies + border: 1px solid #ccc + @include round-corners(3px) + @include box-shadow("inset 2px 2px 4px rgba(0, 0, 0, 0.1)") + margin-top: 1em + padding: 1em + width: 25% + float: right + > li + font-weight: bold \ No newline at end of file diff --git a/app/assets/stylesheets/admin/dashboard.css.sass b/app/assets/stylesheets/admin/dashboard.css.sass new file mode 100644 index 0000000..e84d552 --- /dev/null +++ b/app/assets/stylesheets/admin/dashboard.css.sass @@ -0,0 +1,3 @@ +// Place all the styles related to the admin/dashboard controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ diff --git a/app/assets/stylesheets/admin/downloads.css.sass b/app/assets/stylesheets/admin/downloads.css.sass new file mode 100644 index 0000000..5b0ab4e --- /dev/null +++ b/app/assets/stylesheets/admin/downloads.css.sass @@ -0,0 +1,3 @@ +// Place all the styles related to the admin/downloads controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ diff --git a/app/assets/stylesheets/admin/flash.css.sass b/app/assets/stylesheets/admin/flash.css.sass new file mode 100644 index 0000000..db7d3e0 --- /dev/null +++ b/app/assets/stylesheets/admin/flash.css.sass @@ -0,0 +1,40 @@ +@import "../includes/round_corners" +@import "../includes/box_shadow" + +.alert, .notice + position: relative + font-size: 1em + border-style: solid + border-width: 0 0 1px + padding: 0.7em 2em + margin: -1em -2em 0 + a.close + font-size: 1em + position: absolute + font-weight: bold + right: 0em + top: 0em + text-decoration: none + padding: 0.7em 1em + color: #666 + +.alert + border-color: #cc6633 + background: #ffddcc + color: #662200 + a.close + color: #662200 + &:hover, &:focus + background-color: #cc6633 + color: #ffddcc + +.notice + border-color: #449911 + background: #ddffcc + color: #226600 + a.close + color: #226600 + &:hover, &:focus + background-color: #449911 + color: #ddffcc + \ No newline at end of file diff --git a/app/assets/stylesheets/admin/formtastic.css.sass b/app/assets/stylesheets/admin/formtastic.css.sass new file mode 100644 index 0000000..97bc6b8 --- /dev/null +++ b/app/assets/stylesheets/admin/formtastic.css.sass @@ -0,0 +1,103 @@ +@import "../includes/v_linear_grad" +@import "../includes/round_corners" +@import "../includes/transition" +@import "../includes/box_shadow" +@import "../includes/button" + +form.formtastic + background: white + border: 1px solid #ccc + margin: 0 0 1em + padding: 0 1em + @include box-shadow("0 2px 2px rgba(0, 0, 0, 0.05)") + label + text-align: right + margin-right: 1em + .required + label + font-weight: bold + @include round-corners(5px) + ol, ul + margin-bottom: 0.5em + .input + margin-bottom: 0em + margin-top: 0em + overflow: hidden + padding: 0.5em 0 + .label + width: 13em + textarea + height: 10em + input, textarea + font-family: "Helvetica Neue", "Arial", sans-serif + font-size: 1em + margin-right: 5px + border-width: 1px + border-style: solid + border-color: #999 #DDD #DDD #999 + padding: 0.3em + @include round-corners(2px) + @include box-shadow("inset 1px 1px 4px rgba(0, 0, 0, 0.1)") + &:focus + border-color: #67A #9AF #9AF #67A + @include box-shadow("0 0 4px rgba(0, 128, 255, 0.5), inset 1px 1px 4px rgba(0, 0, 0, 0.1)") + &[type=text], &[type=email] + width: 15em + &[type=number] + width: 3.5em + text-align: right + &:-webkit-inner-spin-button, &:-webkit-outer-spin-button + -webkit-appearance: none + margin: 0 + + input[type=submit], a.button + @include button + &[name=commit] + background-color: #9C7 + border-color: #370 + color: white + text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.5) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.25), inset -1px -1px 0 rgba(255, 255, 255, 0.2), inset 1px 1px 0 rgba(255, 255, 255, 0.3), inset 0 0 6px rgba(0, 0, 0, 0.1), 0 1px 2px rgba(0, 0, 0, 0.3)") + &:hover, &:focus + background-color: #8B6 + + .error input + border-width: 1px + border-style: solid + border-color: #933 #FBB #FBB #933 + background: #FFEFEF + padding: 0.3em + box-shadow: inset 1px 1px 4px rgba(0, 0, 0, 0.1) + + .inline-errors + display: inline + margin-left: 1em + color: #933 + + fieldset.inputs + padding: 1em 0 + border-bottom: 1px solid #ccc + fieldset.buttons + padding: 1.5em 0 1em + .stringish, .text + input, textarea + width: 40% + + .help + margin-left: 14em + margin-top: -0.5em + p + font-size: 0.8em + color: #999 + +a.button + @include button + +a.button.new + background-color: #7AC + border-color: #047 + color: white + text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.5) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.25), inset -1px -1px 0 rgba(255, 255, 255, 0.2), inset 1px 1px 0 rgba(255, 255, 255, 0.3), inset 0 0 6px rgba(0, 0, 0, 0.1), 0 1px 2px rgba(0, 0, 0, 0.3)") + &:hover, &:focus + background-color: #69B diff --git a/app/assets/stylesheets/admin/menu.css.sass b/app/assets/stylesheets/admin/menu.css.sass new file mode 100644 index 0000000..fbcae73 --- /dev/null +++ b/app/assets/stylesheets/admin/menu.css.sass @@ -0,0 +1,50 @@ +@import "../includes/v_linear_grad" +@import "../includes/round_corners" +@import "../includes/transition" +@import "../includes/box_shadow" + +header + nav + ul + font-size: 1em + @include v-linear-grad(rgba(0,0,0,0), rgba(0,0,0,0.2)) + @include box-shadow("0 1px 2px rgba(0, 0, 0, 0.3), inset 0 -1px 0 rgba(255, 255, 255, 0.5)") + background-color: #DDD + border-style: solid + border-width: 0 0 1px 0 + border-color: #999 + color: white + margin: 0 0 1em + padding: 0 1em + list-style: none + height: 35px + position: relative + z-index: 100 + li a + @include v-linear-grad(rgba(0,0,0,0), rgba(0,0,0,0.2)) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.1), inset 0 -1px 0 rgba(255, 255, 255, 0.5)") + background-color: #DDD + color: #444 + text-decoration: none + display: block + height: 21px + float: left + padding: 7px 1em 7px + text-shadow: 0 1px 0 rgba(255, 255, 255, 0.5) + @include transition(all 0.15s 0s ease) + &:hover, &:focus + @include v-linear-grad(rgba(0,0,0,0), rgba(0,0,0,0.2)) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.1), inset 0 -1px 0 rgba(255, 255, 255, 0.5)") + text-shadow: 0 1px 0 rgba(255, 255, 255, 0.5) + color: #444 + background-color: white + &:active + background-color: #ccc + &.selected + @include v-linear-grad(rgba(0,0,0,0.4), rgba(0,0,0,0)) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.1), inset 0 -1px 0 rgba(255, 255, 255, 0.2), inset 0 0 6px rgba(0, 0, 0, 0.4)") + text-shadow: 0 1px 0 rgba(0, 0, 0, 0.5) + background-color: #999 + color: white + &:hover + background-color: #aaa \ No newline at end of file diff --git a/app/assets/stylesheets/admin/unlocks.css.scss b/app/assets/stylesheets/admin/unlocks.css.scss new file mode 100644 index 0000000..a13ad4c --- /dev/null +++ b/app/assets/stylesheets/admin/unlocks.css.scss @@ -0,0 +1,3 @@ +// Place all the styles related to the admin/unlocks controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ diff --git a/app/assets/stylesheets/application/home.css.sass b/app/assets/stylesheets/application/home.css.sass new file mode 100644 index 0000000..f0ddc68 --- /dev/null +++ b/app/assets/stylesheets/application/home.css.sass @@ -0,0 +1,3 @@ +// Place all the styles related to the home controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ diff --git a/app/assets/stylesheets/home.css.scss b/app/assets/stylesheets/home.css.scss new file mode 100644 index 0000000..f0ddc68 --- /dev/null +++ b/app/assets/stylesheets/home.css.scss @@ -0,0 +1,3 @@ +// Place all the styles related to the home controller here. +// They will automatically be included in application.css. +// You can use Sass (SCSS) here: http://sass-lang.com/ diff --git a/app/assets/stylesheets/includes/_button.sass b/app/assets/stylesheets/includes/_button.sass new file mode 100644 index 0000000..38c92e8 --- /dev/null +++ b/app/assets/stylesheets/includes/_button.sass @@ -0,0 +1,24 @@ +@mixin button + display: inline-block + position: relative + font-family: "Helvetica Neue", "Arial", sans-serif + font-size: 1em + text-decoration: none + padding: 0.3em 1em + @include v-linear-grad(rgba(0,0,0,0), rgba(0,0,0,0.2)) + @include box-shadow("0 1px 0 rgba(0, 0, 0, 0.25), inset -1px -1px 0 rgba(255, 255, 255, 0.5), inset 1px 1px 0 rgba(255, 255, 255, 0.6), inset 0 0 6px rgba(0, 0, 0, 0.1), 0 1px 2px rgba(0, 0, 0, 0.3)") + border-width: 1px + border-style: solid + border-color: #888 + background-color: white + color: #555 + text-shadow: 0 1px 0 rgba(255, 255, 255, 0.5) + font-weight: bold + cursor: pointer + @include transition(all 0.15s 0s ease) + @include round-corners(3px) + &:hover, &:focus + background-color: #eee + color: #555 + &:active + top: 1px diff --git a/app/assets/stylesheets/includes/_round_corners.sass b/app/assets/stylesheets/includes/_round_corners.sass new file mode 100644 index 0000000..1ab96aa --- /dev/null +++ b/app/assets/stylesheets/includes/_round_corners.sass @@ -0,0 +1,5 @@ +@mixin round-corners($radius) + border-radius: $radius + -moz-border-radius: $radius + -webkit-border-radius: $radius + -o-border-radius: $radius diff --git a/app/assets/stylesheets/includes/_transition.sass b/app/assets/stylesheets/includes/_transition.sass new file mode 100644 index 0000000..94a2fb1 --- /dev/null +++ b/app/assets/stylesheets/includes/_transition.sass @@ -0,0 +1,5 @@ +@mixin transition($value) + -moz-transition: $value + -webkit-transition: $value + -o-transition: $value + transition: $value \ No newline at end of file diff --git a/app/assets/stylesheets/includes/_v_linear_grad.sass b/app/assets/stylesheets/includes/_v_linear_grad.sass new file mode 100644 index 0000000..0d401f6 --- /dev/null +++ b/app/assets/stylesheets/includes/_v_linear_grad.sass @@ -0,0 +1,7 @@ +@mixin v-linear-grad($from, $to) + background-image: -moz-linear-gradient(top, $from 0%, $to 100%) + background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, $from), color-stop(100%, $to)) + background-image: -webkit-linear-gradient(top, $from 0%, $to 100%) + background-image: -o-linear-gradient(top, $from 0%, $to 100%) + background-image: -ms-linear-gradient(top, $from 0%, $to 100%) + background-image: linear-gradient(top, $from 0%, $to 100%) diff --git a/app/controllers/admin/admin_controller.rb b/app/controllers/admin/admin_controller.rb new file mode 100644 index 0000000..57cf8cf --- /dev/null +++ b/app/controllers/admin/admin_controller.rb @@ -0,0 +1,10 @@ +class Admin::AdminController < ApplicationController + layout 'admin/layouts/admin' + before_filter :authenticate_admin_user! + before_filter :admin_menu + + def admin_menu + @admin_menu = { :dashboard => '', + :admin_users => '' } + end +end diff --git a/app/controllers/admin/admin_users_controller.rb b/app/controllers/admin/admin_users_controller.rb index 6428fe3..ec4e7ac 100644 --- a/app/controllers/admin/admin_users_controller.rb +++ b/app/controllers/admin/admin_users_controller.rb @@ -1,2 +1,69 @@ -class Admin::AdminUsersController < Admin::ResourcesController +class Admin::AdminUsersController < Admin::AdminController + + def index + @admin_users = AdminUser.all + end + + def new + @admin_user = AdminUser.new + end + + def edit + @admin_user = AdminUser.find(params[:id]) + end + + def update + @admin_user = AdminUser.find(params[:id]) + + respond_to do |format| + if @admin_user.update_attributes(params[:admin_user]) + format.html { redirect_to(admin_admin_users_path, :notice => 'Admin User was successfully updated.') } + format.xml { head :ok } + else + format.html { render :action => "edit" } + format.xml { render :xml => @admin_user.errors, :status => :unprocessable_entity } + end + end + end + + def create + @admin_user = AdminUser.new(params[:admin_user]) + + respond_to do |format| + if @admin_user.save + format.html { redirect_to(admin_admin_users_path, :notice => 'Admin User was successfully added.') } + format.xml { head :ok } + else + format.html { render :action => "edit" } + format.xml { render :xml => @admin_user.errors, :status => :unprocessable_entity } + end + end + end + + def destroy + @admin_user = AdminUser.find(params[:id]) + @admin_user.destroy + + respond_to do |format| + format.html { redirect_to(admin_admin_users_path, :notice => 'Admin User was deleted.') } + format.xml { head :ok } + end + end + + # Allow the current logged in user to change their password + def edit_password + @admin_user = current_admin_user + end + + def update_password + @admin_user = current_admin_user + + if @admin_user.update_with_password(params[:admin_user]) + sign_in(@admin_user, :bypass => true) + redirect_to admin_dashboard_path, :notice => "Password updated!" + else + render :edit_password + end + end + end diff --git a/app/controllers/admin/confirmations_controller.rb b/app/controllers/admin/confirmations_controller.rb new file mode 100644 index 0000000..1561fa2 --- /dev/null +++ b/app/controllers/admin/confirmations_controller.rb @@ -0,0 +1,60 @@ +class Admin::ConfirmationsController < ::Devise::PasswordsController + layout "admin/layouts/login" + + skip_before_filter(:authenticate_user!) + # PUT /resource/confirmation + def update + with_unconfirmed_confirmable do + if @confirmable.has_no_password? + @confirmable.attempt_set_password(params[:admin_user]) + if @confirmable.valid? + do_confirm + else + do_show + @confirmable.errors.clear #so that we wont render :new + end + else + self.class.add_error_on(self, :email, :password_allready_set) + end + end + + if !@confirmable.errors.empty? + render_with_scope :new + end + end + + # GET /resource/confirmation?confirmation_token=abcdef + def show + with_unconfirmed_confirmable do + if @confirmable.has_no_password? + do_show + else + do_confirm + end + end + if !@confirmable.errors.empty? + render_with_scope :new + end + end + + protected + def with_unconfirmed_confirmable + @confirmable = AdminUser.find_or_initialize_with_error_by(:confirmation_token, params[:confirmation_token]) + if !@confirmable.new_record? + @confirmable.only_if_unconfirmed {yield} + end + end + + def do_show + @confirmation_token = params[:confirmation_token] + @requires_password = true + self.resource = @confirmable + render_with_scope :show + end + + def do_confirm + @confirmable.confirm! + set_flash_message :notice, :confirmed + sign_in_and_redirect(resource_name, @confirmable) + end +end \ No newline at end of file diff --git a/app/controllers/admin/dashboard_controller.rb b/app/controllers/admin/dashboard_controller.rb new file mode 100644 index 0000000..a4ecb27 --- /dev/null +++ b/app/controllers/admin/dashboard_controller.rb @@ -0,0 +1,2 @@ +class Admin::DashboardController < Admin::AdminController +end diff --git a/app/controllers/admin/passwords_controller.rb b/app/controllers/admin/passwords_controller.rb new file mode 100644 index 0000000..1fdcc20 --- /dev/null +++ b/app/controllers/admin/passwords_controller.rb @@ -0,0 +1,3 @@ +class Admin::PasswordsController < ::Devise::PasswordsController + layout "admin/layouts/login" +end diff --git a/app/controllers/admin/registrations_controller.rb b/app/controllers/admin/registrations_controller.rb new file mode 100644 index 0000000..c8d47ad --- /dev/null +++ b/app/controllers/admin/registrations_controller.rb @@ -0,0 +1,3 @@ +class Admin::RegistrationsController < ::Devise::RegistrationsController + layout "admin/layouts/login" +end diff --git a/app/controllers/admin/sessions_controller.rb b/app/controllers/admin/sessions_controller.rb new file mode 100644 index 0000000..02c3808 --- /dev/null +++ b/app/controllers/admin/sessions_controller.rb @@ -0,0 +1,3 @@ +class Admin::SessionsController < ::Devise::SessionsController + layout "admin/layouts/login" +end \ No newline at end of file diff --git a/app/controllers/admin/unlocks_controller.rb b/app/controllers/admin/unlocks_controller.rb new file mode 100644 index 0000000..a399b7d --- /dev/null +++ b/app/controllers/admin/unlocks_controller.rb @@ -0,0 +1,3 @@ +class Admin::UnlocksController < ::Devise::UnlocksController + layout "admin/layouts/login" +end diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index e8065d9..b2544fc 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -1,3 +1,12 @@ class ApplicationController < ActionController::Base protect_from_forgery + + def after_sign_in_path_for(resource_or_scope) + admin_dashboard_path + end + + def after_sign_out_path_for(resource_or_scope) + new_admin_user_session_path + end + end diff --git a/app/controllers/home_controller.rb b/app/controllers/home_controller.rb new file mode 100644 index 0000000..95f2992 --- /dev/null +++ b/app/controllers/home_controller.rb @@ -0,0 +1,4 @@ +class HomeController < ApplicationController + def index + end +end diff --git a/app/helpers/admin/admin_helper.rb b/app/helpers/admin/admin_helper.rb new file mode 100644 index 0000000..53c4d49 --- /dev/null +++ b/app/helpers/admin/admin_helper.rb @@ -0,0 +1,2 @@ +module Admin::AdminHelper +end diff --git a/app/helpers/admin/dashboard_helper.rb b/app/helpers/admin/dashboard_helper.rb new file mode 100644 index 0000000..4052b7c --- /dev/null +++ b/app/helpers/admin/dashboard_helper.rb @@ -0,0 +1,2 @@ +module Admin::DashboardHelper +end diff --git a/app/helpers/admin/downloads_helper.rb b/app/helpers/admin/downloads_helper.rb new file mode 100644 index 0000000..5d6e8d9 --- /dev/null +++ b/app/helpers/admin/downloads_helper.rb @@ -0,0 +1,2 @@ +module Admin::DownloadsHelper +end diff --git a/app/helpers/admin/unlocks_helper.rb b/app/helpers/admin/unlocks_helper.rb new file mode 100644 index 0000000..3367487 --- /dev/null +++ b/app/helpers/admin/unlocks_helper.rb @@ -0,0 +1,2 @@ +module Admin::UnlocksHelper +end diff --git a/app/helpers/home_helper.rb b/app/helpers/home_helper.rb new file mode 100644 index 0000000..23de56a --- /dev/null +++ b/app/helpers/home_helper.rb @@ -0,0 +1,2 @@ +module HomeHelper +end diff --git a/app/models/admin_user.rb b/app/models/admin_user.rb index dff5393..d74ea3d 100644 --- a/app/models/admin_user.rb +++ b/app/models/admin_user.rb @@ -1,8 +1,36 @@ class AdminUser < ActiveRecord::Base + # Include default devise modules. Others available are: + # :token_authenticatable, :encryptable, :confirmable, :lockable, :timeoutable and :omniauthable + devise :database_authenticatable, :confirmable, + :recoverable, :rememberable, :trackable, :validatable, :lockable - ROLE = Typus::Configuration.roles.keys.sort - LANGUAGE = Typus.locales + # Setup accessible (or protected) attributes for your model + attr_accessible :email, :password, :password_confirmation, :remember_me + + # new function to set the password without knowing the current password used in our confirmation controller. + def attempt_set_password(params) + p = {} + p[:password] = params[:password] + p[:password_confirmation] = params[:password_confirmation] + update_attributes(p) + end + + # new function to return whether a password has been set + def has_no_password? + self.encrypted_password.blank? + end - enable_as_typus_user + # new function to provide access to protected method unless_confirmed + def only_if_unconfirmed + unless_confirmed {yield} + end + def password_required? + # Password is required if it is being set, but not for new records + if !persisted? + false + else + !password.nil? || !password_confirmation.nil? + end + end end diff --git a/app/views/admin/admin_users/_admin_user.html.haml b/app/views/admin/admin_users/_admin_user.html.haml new file mode 100644 index 0000000..c18c7b8 --- /dev/null +++ b/app/views/admin/admin_users/_admin_user.html.haml @@ -0,0 +1,7 @@ +%tr + %td= admin_user.email + %td= admin_user.last_sign_in_at + %td= admin_user.last_sign_in_ip + %td{ :class => :actions } + - unless admin_user == current_admin_user + = link_to "Delete", admin_admin_user_path(admin_user), :method => :delete, :confirm => "Are you sure you wish to delete this Admin User?" \ No newline at end of file diff --git a/app/views/admin/admin_users/_form.html.haml b/app/views/admin/admin_users/_form.html.haml new file mode 100644 index 0000000..0fed776 --- /dev/null +++ b/app/views/admin/admin_users/_form.html.haml @@ -0,0 +1,3 @@ += semantic_form_for [:admin, admin_user] do |f| + = f.inputs :email + = f.buttons \ No newline at end of file diff --git a/app/views/admin/admin_users/edit.html.haml b/app/views/admin/admin_users/edit.html.haml new file mode 100644 index 0000000..3ace240 --- /dev/null +++ b/app/views/admin/admin_users/edit.html.haml @@ -0,0 +1,2 @@ +%h2 Edit Admin User += render :partial => "form", :locals => { :admin_user => @admin_user } \ No newline at end of file diff --git a/app/views/admin/admin_users/edit_password.html.haml b/app/views/admin/admin_users/edit_password.html.haml new file mode 100644 index 0000000..546dd0c --- /dev/null +++ b/app/views/admin/admin_users/edit_password.html.haml @@ -0,0 +1,11 @@ +%h3 Change your password + += semantic_form_for(@admin_user, :url => update_password_admin_admin_user_path, :html => { :method => :put }) do |f| + = f.inputs do + = f.input :current_password + = f.inputs do + = f.input :password, :label => "New Password" + = f.input :password_confirmation, :label => "Confirm Password" + + = f.buttons do + = f.submit "Change my password" diff --git a/app/views/admin/admin_users/index.html.haml b/app/views/admin/admin_users/index.html.haml new file mode 100644 index 0000000..6c31788 --- /dev/null +++ b/app/views/admin/admin_users/index.html.haml @@ -0,0 +1,16 @@ +%h2 Admin Users + +%table + %thead + %tr + %th Email + %th Last Signed In? + %th IP Address + %th + %tbody + = render :partial => "admin_user", :collection => @admin_users + %tfoot + %tr + %td{:colspan => 4} +%br/ += link_to 'New Admin User', new_admin_admin_user_path, :class => [:button, :new] diff --git a/app/views/admin/admin_users/new.html.haml b/app/views/admin/admin_users/new.html.haml new file mode 100644 index 0000000..68e75bd --- /dev/null +++ b/app/views/admin/admin_users/new.html.haml @@ -0,0 +1,2 @@ +%h2 New Admin User += render :partial => "form", :locals => { :admin_user => @admin_user } \ No newline at end of file diff --git a/app/views/admin/confirmations/new.html.haml b/app/views/admin/confirmations/new.html.haml new file mode 100644 index 0000000..e3e870b --- /dev/null +++ b/app/views/admin/confirmations/new.html.haml @@ -0,0 +1,11 @@ +%h3 Resend confirmation instructions + += semantic_form_for(resource, :as => resource_name, :url => confirmation_path(resource_name), :html => { :method => :post }) do |f| + + = f.inputs do + = f.input :email + + = f.buttons do + = f.submit "Resend confirmation instructions" + += render :partial => "devise/shared/links" diff --git a/app/views/admin/confirmations/show.html.haml b/app/views/admin/confirmations/show.html.haml new file mode 100644 index 0000000..c0d5022 --- /dev/null +++ b/app/views/admin/confirmations/show.html.haml @@ -0,0 +1,12 @@ +%h3= "Account Activation for #{resource.email}" + += semantic_form_for resource, :as => resource_name, :url => update_user_confirmation_path, :html => {:method => 'put'}, :id => 'activation-form' do |f| + = devise_error_messages! + = field_set_tag "", :class => "inputs" do + %ol + - if @requires_password + = f.input :password, :label => 'Choose a Password' + = f.input :password_confirmation, :label => 'Confirm Password' + = hidden_field_tag :confirmation_token,@confirmation_token + = f.buttons do + = f.submit "Activate" diff --git a/app/views/admin/dashboard/index.html.haml b/app/views/admin/dashboard/index.html.haml new file mode 100644 index 0000000..22f9e2d --- /dev/null +++ b/app/views/admin/dashboard/index.html.haml @@ -0,0 +1 @@ +%p This is the admin dashboard. \ No newline at end of file diff --git a/app/views/admin/layouts/admin.html.haml b/app/views/admin/layouts/admin.html.haml new file mode 100644 index 0000000..2d738a4 --- /dev/null +++ b/app/views/admin/layouts/admin.html.haml @@ -0,0 +1,14 @@ +!!! +%html + %head + %title= "#{APP_CONFIG['name']} Admin" + = stylesheet_link_tag "admin" + = javascript_include_tag "admin" + = csrf_meta_tag + + %body + #page + %header{ :role => "banner" }= render :partial => "admin/shared/header" + = render :partial => "shared/flash_messages" + = yield + %footer{ :role => "footer" }= render :partial => "admin/shared/footer" \ No newline at end of file diff --git a/app/views/admin/layouts/login.html.haml b/app/views/admin/layouts/login.html.haml new file mode 100644 index 0000000..4206e89 --- /dev/null +++ b/app/views/admin/layouts/login.html.haml @@ -0,0 +1,13 @@ +!!! +%html + %head + %title= "#{APP_CONFIG['name']} Admin" + = stylesheet_link_tag "admin" + = javascript_include_tag "admin" + = csrf_meta_tag + + %body + #login + %header{ :role => "banner" }= render :partial => "admin/shared/login_header" + = render :partial => "shared/flash_messages" + = yield \ No newline at end of file diff --git a/app/views/admin/passwords/edit.html.haml b/app/views/admin/passwords/edit.html.haml new file mode 100644 index 0000000..2016bb0 --- /dev/null +++ b/app/views/admin/passwords/edit.html.haml @@ -0,0 +1,14 @@ +%h3 Change your password + += semantic_form_for(resource, :as => resource_name, :url => password_path(resource_name), :html => { :method => :put }) do |f| + = devise_error_messages! + = f.hidden_field :reset_password_token + + = f.inputs do + = f.input :password, :label => "New Password" + = f.input :password_confirmation, :label => "Confirm Password" + + = f.buttons do + = f.submit "Change my password" + += render :partial => "devise/shared/links" \ No newline at end of file diff --git a/app/views/admin/passwords/new.html.haml b/app/views/admin/passwords/new.html.haml new file mode 100644 index 0000000..1614978 --- /dev/null +++ b/app/views/admin/passwords/new.html.haml @@ -0,0 +1,11 @@ +%h3 Forgot your password? + += semantic_form_for(resource, :as => resource_name, :url => password_path(resource_name), :html => { :method => :post }) do |f| + + = f.inputs do + = f.input :email + + = f.buttons do + = f.submit "Reset Password" + += render :partial => "devise/shared/links" \ No newline at end of file diff --git a/app/views/admin/sessions/new.html.haml b/app/views/admin/sessions/new.html.haml new file mode 100644 index 0000000..b1166d9 --- /dev/null +++ b/app/views/admin/sessions/new.html.haml @@ -0,0 +1,14 @@ +%h3 Sign in + += semantic_form_for(resource, :as => resource_name, :url => session_path(resource_name)) do |f| + = f.inputs do + = f.input :email + = f.input :password + + - if devise_mapping.rememberable? + = f.input :remember_me, :as => :boolean + + = f.buttons do + = f.submit "Sign In" + += render :partial => "devise/shared/links" \ No newline at end of file diff --git a/app/views/admin/shared/_footer.html.haml b/app/views/admin/shared/_footer.html.haml new file mode 100644 index 0000000..e69de29 diff --git a/app/views/admin/shared/_header.html.haml b/app/views/admin/shared/_header.html.haml new file mode 100644 index 0000000..0d917fc --- /dev/null +++ b/app/views/admin/shared/_header.html.haml @@ -0,0 +1,3 @@ +%h1= link_to "Abiquo Downloads", admin_dashboard_path += render :partial => "admin/shared/user" += render :partial => "admin/shared/menu" \ No newline at end of file diff --git a/app/views/admin/shared/_login_header.html.haml b/app/views/admin/shared/_login_header.html.haml new file mode 100644 index 0000000..74be139 --- /dev/null +++ b/app/views/admin/shared/_login_header.html.haml @@ -0,0 +1 @@ +%h1= link_to "Abiquo Downloads", admin_dashboard_path diff --git a/app/views/admin/shared/_menu.html.haml b/app/views/admin/shared/_menu.html.haml new file mode 100644 index 0000000..afe9917 --- /dev/null +++ b/app/views/admin/shared/_menu.html.haml @@ -0,0 +1,4 @@ +%nav + %ul + - @admin_menu.each do |key, value| + = render :partial => "admin/shared/menu_item", :locals => { :menu_item => key } diff --git a/app/views/admin/shared/_menu_item.html.haml b/app/views/admin/shared/_menu_item.html.haml new file mode 100644 index 0000000..b8fb8ab --- /dev/null +++ b/app/views/admin/shared/_menu_item.html.haml @@ -0,0 +1 @@ +%li= link_to menu_item.to_s.gsub(/_/, ' ').titleize, { :controller => menu_item }, :class => (params[:controller] == "admin/" + menu_item.to_s ? "selected" : nil) \ No newline at end of file diff --git a/app/views/admin/shared/_user.html.haml b/app/views/admin/shared/_user.html.haml new file mode 100644 index 0000000..9071c7e --- /dev/null +++ b/app/views/admin/shared/_user.html.haml @@ -0,0 +1,6 @@ +#user + %strong= current_admin_user.email + | + = link_to "Change Password", edit_password_admin_admin_user_path + | + = link_to "Logout", destroy_admin_user_session_path, :method => :delete \ No newline at end of file diff --git a/app/views/admin/unlocks/new.html.haml b/app/views/admin/unlocks/new.html.haml new file mode 100644 index 0000000..43256b7 --- /dev/null +++ b/app/views/admin/unlocks/new.html.haml @@ -0,0 +1,11 @@ +%h3 Resend unlock instructions + += semantic_form_for(resource, :as => resource_name, :url => unlock_path(resource_name), :html => { :method => :post }) do |f| + + = f.inputs do + = f.input :email + + = f.buttons do + = f.submit "Resend unlock instructions" + += render :partial => "devise/shared/links" diff --git a/app/views/home/index.html.haml b/app/views/home/index.html.haml new file mode 100644 index 0000000..1491738 --- /dev/null +++ b/app/views/home/index.html.haml @@ -0,0 +1 @@ +%h1= APP_CONFIG['name'] \ No newline at end of file diff --git a/app/views/layouts/application.html.haml b/app/views/layouts/application.html.haml new file mode 100644 index 0000000..25669f0 --- /dev/null +++ b/app/views/layouts/application.html.haml @@ -0,0 +1,9 @@ +!!! +%html + %head + %title= APP_CONFIG['name'] + = stylesheet_link_tag "application" + = javascript_include_tag "application" + = csrf_meta_tags + %body + = yield diff --git a/app/views/shared/_banner.html.haml b/app/views/shared/_banner.html.haml new file mode 100644 index 0000000..2597466 --- /dev/null +++ b/app/views/shared/_banner.html.haml @@ -0,0 +1,2 @@ +%header{:role => :banner} + %h1 Abiquo Downloads \ No newline at end of file diff --git a/app/views/shared/_flash_messages.html.haml b/app/views/shared/_flash_messages.html.haml new file mode 100644 index 0000000..133b4bc --- /dev/null +++ b/app/views/shared/_flash_messages.html.haml @@ -0,0 +1,10 @@ +- if !flash[:notice].blank? + %p.flash.notice + = flash[:notice] + = link_to raw("×"), "#", :class => :close + +- if !flash[:alert].blank? + %p.flash.alert + = flash[:alert] + = link_to raw("×"), "#", :class => :close + \ No newline at end of file diff --git a/config/config.yml b/config/config.yml index 6a4b653..edfbda1 100644 --- a/config/config.yml +++ b/config/config.yml @@ -1,4 +1,4 @@ name: Dan Barber Photo page_title: Dan Barber Photography meta_description: "" -meta_keywords: "" \ No newline at end of file +meta_keywords: "" diff --git a/config/environments/development.rb b/config/environments/development.rb index c85b54c..3adc909 100644 --- a/config/environments/development.rb +++ b/config/environments/development.rb @@ -41,4 +41,4 @@ DanBarberPhoto::Application.configure do config.action_mailer.default_url_options = { :host => "danbarberphoto.dev" } -end \ No newline at end of file +end diff --git a/config/environments/production.rb b/config/environments/production.rb index 978091c..b0f5837 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -58,7 +58,7 @@ DanBarberPhoto::Application.configure do # Send deprecation notices to registered listeners config.active_support.deprecation = :notify - # Heroku Sendgrid settings. + # Settings for Sendgrid Free on Heroku ActionMailer::Base.smtp_settings = { :address => 'smtp.sendgrid.net', :port => '587', diff --git a/config/environments/test.rb b/config/environments/test.rb index b1a0a1d..59d2952 100644 --- a/config/environments/test.rb +++ b/config/environments/test.rb @@ -7,7 +7,11 @@ DanBarberPhoto::Application.configure do # and recreated between test runs. Don't rely on the data there! config.cache_classes = true - # Log error messages when you accidentally call methods on nil. + # Configure static asset server for tests with Cache-Control for performance + config.serve_static_assets = true + config.static_cache_control = "public, max-age=3600" + + # Log error messages when you accidentally call methods on nil config.whiny_nils = true # Show full error reports and disable caching @@ -32,4 +36,7 @@ DanBarberPhoto::Application.configure do # Print deprecation notices to the stderr config.active_support.deprecation = :stderr + + # Allow pass debug_assets=true as a query parameter to load pages with unpackaged assets + config.assets.allow_debugging = true end diff --git a/config/initializers/devise.rb b/config/initializers/devise.rb new file mode 100644 index 0000000..e6289c4 --- /dev/null +++ b/config/initializers/devise.rb @@ -0,0 +1,210 @@ +# Use this hook to configure devise mailer, warden hooks and so forth. The first +# four configuration values can also be set straight in your models. +Devise.setup do |config| + # ==> Mailer Configuration + # Configure the e-mail address which will be shown in Devise::Mailer, + # note that it will be overwritten if you use your own mailer class with default "from" parameter. + config.mailer_sender = "please-change-me-at-config-initializers-devise@example.com" + + # Configure the class responsible to send e-mails. + # config.mailer = "Devise::Mailer" + + # ==> ORM configuration + # Load and configure the ORM. Supports :active_record (default) and + # :mongoid (bson_ext recommended) by default. Other ORMs may be + # available as additional gems. + require 'devise/orm/active_record' + + # ==> Configuration for any authentication mechanism + # Configure which keys are used when authenticating a user. The default is + # just :email. You can configure it to use [:username, :subdomain], so for + # authenticating a user, both parameters are required. Remember that those + # parameters are used only when authenticating and not when retrieving from + # session. If you need permissions, you should implement that in a before filter. + # You can also supply a hash where the value is a boolean determining whether + # or not authentication should be aborted when the value is not present. + # config.authentication_keys = [ :email ] + + # Configure parameters from the request object used for authentication. Each entry + # given should be a request method and it will automatically be passed to the + # find_for_authentication method and considered in your model lookup. For instance, + # if you set :request_keys to [:subdomain], :subdomain will be used on authentication. + # The same considerations mentioned for authentication_keys also apply to request_keys. + # config.request_keys = [] + + # Configure which authentication keys should be case-insensitive. + # These keys will be downcased upon creating or modifying a user and when used + # to authenticate or find a user. Default is :email. + config.case_insensitive_keys = [ :email ] + + # Configure which authentication keys should have whitespace stripped. + # These keys will have whitespace before and after removed upon creating or + # modifying a user and when used to authenticate or find a user. Default is :email. + config.strip_whitespace_keys = [ :email ] + + # Tell if authentication through request.params is enabled. True by default. + # config.params_authenticatable = true + + # Tell if authentication through HTTP Basic Auth is enabled. False by default. + # config.http_authenticatable = false + + # If http headers should be returned for AJAX requests. True by default. + # config.http_authenticatable_on_xhr = true + + # The realm used in Http Basic Authentication. "Application" by default. + # config.http_authentication_realm = "Application" + + # It will change confirmation, password recovery and other workflows + # to behave the same regardless if the e-mail provided was right or wrong. + # Does not affect registerable. + # config.paranoid = true + + # ==> Configuration for :database_authenticatable + # For bcrypt, this is the cost for hashing the password and defaults to 10. If + # using other encryptors, it sets how many times you want the password re-encrypted. + # + # Limiting the stretches to just one in testing will increase the performance of + # your test suite dramatically. However, it is STRONGLY RECOMMENDED to not use + # a value less than 10 in other environments. + config.stretches = Rails.env.test? ? 1 : 10 + + # Setup a pepper to generate the encrypted password. + # config.pepper = "09f42a4393b21d179831660ef0102527e36691cfe7d0d72f2b23c0b712275223dbca9eced7e781dcb6cbb14f129aed2086c91ab8bb38c519321a61fb1a93c170" + + # ==> Configuration for :confirmable + # A period that the user is allowed to access the website even without + # confirming his account. For instance, if set to 2.days, the user will be + # able to access the website for two days without confirming his account, + # access will be blocked just in the third day. Default is 0.days, meaning + # the user cannot access the website without confirming his account. + # config.confirm_within = 2.days + + # Defines which key will be used when confirming an account + # config.confirmation_keys = [ :email ] + + # ==> Configuration for :rememberable + # The time the user will be remembered without asking for credentials again. + # config.remember_for = 2.weeks + + # If true, a valid remember token can be re-used between multiple browsers. + # config.remember_across_browsers = true + + # If true, extends the user's remember period when remembered via cookie. + # config.extend_remember_period = false + + # If true, uses the password salt as remember token. This should be turned + # to false if you are not using database authenticatable. + config.use_salt_as_remember_token = true + + # Options to be passed to the created cookie. For instance, you can set + # :secure => true in order to force SSL only cookies. + # config.cookie_options = {} + + # ==> Configuration for :validatable + # Range for password length. Default is 6..128. + # config.password_length = 6..128 + + # Email regex used to validate email formats. It simply asserts that + # an one (and only one) @ exists in the given string. This is mainly + # to give user feedback and not to assert the e-mail validity. + # config.email_regexp = /\A[^@]+@[^@]+\z/ + + # ==> Configuration for :timeoutable + # The time you want to timeout the user session without activity. After this + # time the user will be asked for credentials again. Default is 30 minutes. + # config.timeout_in = 30.minutes + + # ==> Configuration for :lockable + # Defines which strategy will be used to lock an account. + # :failed_attempts = Locks an account after a number of failed attempts to sign in. + # :none = No lock strategy. You should handle locking by yourself. + config.lock_strategy = :failed_attempts + + # Defines which key will be used when locking and unlocking an account + # config.unlock_keys = [ :email ] + + # Defines which strategy will be used to unlock an account. + # :email = Sends an unlock link to the user email + # :time = Re-enables login after a certain amount of time (see :unlock_in below) + # :both = Enables both strategies + # :none = No unlock strategy. You should handle unlocking by yourself. + # config.unlock_strategy = :both + + # Number of authentication tries before locking an account if lock_strategy + # is failed attempts. + config.maximum_attempts = 5 + + # Time interval to unlock the account if :time is enabled as unlock_strategy. + # config.unlock_in = 1.hour + + # ==> Configuration for :recoverable + # + # Defines which key will be used when recovering the password for an account + # config.reset_password_keys = [ :email ] + + # Time interval you can reset your password with a reset password key. + # Don't put a too small interval or your users won't have the time to + # change their passwords. + config.reset_password_within = 2.hours + + # ==> Configuration for :encryptable + # Allow you to use another encryption algorithm besides bcrypt (default). You can use + # :sha1, :sha512 or encryptors from others authentication tools as :clearance_sha1, + # :authlogic_sha512 (then you should set stretches above to 20 for default behavior) + # and :restful_authentication_sha1 (then you should set stretches to 10, and copy + # REST_AUTH_SITE_KEY to pepper) + # config.encryptor = :sha512 + + # ==> Configuration for :token_authenticatable + # Defines name of the authentication token params key + # config.token_authentication_key = :auth_token + + # If true, authentication through token does not store user in session and needs + # to be supplied on each request. Useful if you are using the token as API token. + # config.stateless_token = false + + # ==> Scopes configuration + # Turn scoped views on. Before rendering "sessions/new", it will first check for + # "users/sessions/new". It's turned off by default because it's slower if you + # are using only default views. + # config.scoped_views = false + + # Configure the default scope given to Warden. By default it's the first + # devise role declared in your routes (usually :user). + # config.default_scope = :user + + # Configure sign_out behavior. + # Sign_out action can be scoped (i.e. /users/sign_out affects only :user scope). + # The default is true, which means any logout action will sign out all active scopes. + # config.sign_out_all_scopes = true + + # ==> Navigation configuration + # Lists the formats that should be treated as navigational. Formats like + # :html, should redirect to the sign in page when the user does not have + # access, but formats like :xml or :json, should return 401. + # + # If you have any extra navigational formats, like :iphone or :mobile, you + # should add them to the navigational formats lists. + # + # The :"*/*" and "*/*" formats below is required to match Internet + # Explorer requests. + # config.navigational_formats = [:"*/*", "*/*", :html] + + # The default HTTP method used to sign out a resource. Default is :delete. + config.sign_out_via = :delete + + # ==> OmniAuth + # Add a new OmniAuth provider. Check the wiki for more information on setting + # up on your models and hooks. + # config.omniauth :github, 'APP_ID', 'APP_SECRET', :scope => 'user,public_repo' + + # ==> Warden configuration + # If you want to use other strategies, that are not supported by Devise, or + # change the failure app, you can configure them inside the config.warden block. + # + # config.warden do |manager| + # manager.failure_app = AnotherApp + # manager.intercept_401 = false + # manager.default_strategies(:scope => :user).unshift :some_external_strategy + # end +end diff --git a/config/locales/devise.en.yml b/config/locales/devise.en.yml new file mode 100644 index 0000000..b182635 --- /dev/null +++ b/config/locales/devise.en.yml @@ -0,0 +1,58 @@ +# Additional translations at http://github.com/plataformatec/devise/wiki/I18n + +en: + errors: + messages: + expired: "has expired, please request a new one" + not_found: "not found" + already_confirmed: "was already confirmed, please try signing in" + not_locked: "was not locked" + not_saved: + one: "1 error prohibited this %{resource} from being saved:" + other: "%{count} errors prohibited this %{resource} from being saved:" + + devise: + failure: + already_authenticated: 'You are already signed in.' + unauthenticated: 'You need to sign in or sign up before continuing.' + unconfirmed: 'You have to confirm your account before continuing.' + locked: 'Your account is locked.' + invalid: 'Invalid email or password.' + invalid_token: 'Invalid authentication token.' + timeout: 'Your session expired, please sign in again to continue.' + inactive: 'Your account was not activated yet.' + sessions: + signed_in: 'Signed in successfully.' + signed_out: 'Signed out successfully.' + passwords: + send_instructions: 'You will receive an email with instructions about how to reset your password in a few minutes.' + updated: 'Your password was changed successfully. You are now signed in.' + updated_not_active: 'Your password was changed successfully.' + send_paranoid_instructions: "If your e-mail exists on our database, you will receive a password recovery link on your e-mail" + confirmations: + send_instructions: 'You will receive an email with instructions about how to confirm your account in a few minutes.' + send_paranoid_instructions: 'If your e-mail exists on our database, you will receive an email with instructions about how to confirm your account in a few minutes.' + confirmed: 'Your account was successfully confirmed. You are now signed in.' + registrations: + signed_up: 'Welcome! You have signed up successfully.' + inactive_signed_up: 'You have signed up successfully. However, we could not sign you in because your account is %{reason}.' + updated: 'You updated your account successfully.' + destroyed: 'Bye! Your account was successfully cancelled. We hope to see you again soon.' + reasons: + inactive: 'inactive' + unconfirmed: 'unconfirmed' + locked: 'locked' + unlocks: + send_instructions: 'You will receive an email with instructions about how to unlock your account in a few minutes.' + unlocked: 'Your account was successfully unlocked. You are now signed in.' + send_paranoid_instructions: 'If your account exists, you will receive an email with instructions about how to unlock it in a few minutes.' + omniauth_callbacks: + success: 'Successfully authorized from %{kind} account.' + failure: 'Could not authorize you from %{kind} because "%{reason}".' + mailer: + confirmation_instructions: + subject: 'Confirmation instructions' + reset_password_instructions: + subject: 'Reset password instructions' + unlock_instructions: + subject: 'Unlock Instructions' diff --git a/config/routes.rb b/config/routes.rb index b058a68..8d64a95 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -1,6 +1,29 @@ DanBarberPhoto::Application.routes.draw do resources :contacts + as :admin_user do + match '/admin_users/confirmation' => 'admin/confirmations#update', :via => :put, :as => :update_user_confirmation + end + + devise_for :admin_users, :controllers => { + :sessions => "admin/sessions", + :passwords => "admin/passwords", + #:registrations => "admin/registrations", + :confirmations => "admin/confirmations", + :unlocks => "admin/unlocks" + } + + namespace :admin do + root :to => "dashboard#index", :as => :dashboard + resources :admin_users + resource :admin_user do + member do + get :edit_password + put :update_password + end + end + end + # The priority is based upon order of creation: # first created -> highest priority. @@ -67,8 +90,6 @@ DanBarberPhoto::Application.routes.draw do end end - root :to => 'pages#index' - match 'about' => 'pages#about', :as => :about #match 'contact' => 'pages#contact', :as => :contact resources :contacts, :only => [:new, :create] @@ -77,4 +98,12 @@ DanBarberPhoto::Application.routes.draw do # Note: This route will make all actions in every controller accessible via GET requests. # match ':controller(/:action(/:id(.:format)))' + # root :to => 'welcome#index' + root :to => 'pages#index' + + # See how all your routes lay out with "rake routes" + + # This is a legacy wild controller route that's not recommended for RESTful applications. + # Note: This route will make all actions in every controller accessible via GET requests. + # match ':controller(/:action(/:id(.:format)))' end diff --git a/db/migrate/20111007155450_devise_create_admin_users.rb b/db/migrate/20111007155450_devise_create_admin_users.rb new file mode 100644 index 0000000..516496d --- /dev/null +++ b/db/migrate/20111007155450_devise_create_admin_users.rb @@ -0,0 +1,28 @@ +class DeviseCreateAdminUsers < ActiveRecord::Migration + def self.up + create_table(:admin_users) do |t| + t.database_authenticatable :null => false + t.recoverable + t.rememberable + t.trackable + + # t.encryptable + t.confirmable + t.lockable :lock_strategy => :failed_attempts, :unlock_strategy => :both + # t.token_authenticatable + + + t.timestamps + end + + add_index :admin_users, :email, :unique => true + add_index :admin_users, :reset_password_token, :unique => true + add_index :admin_users, :confirmation_token, :unique => true + add_index :admin_users, :unlock_token, :unique => true + # add_index :admin_users, :authentication_token, :unique => true + end + + def self.down + drop_table :admin_users + end +end diff --git a/db/migrate/20111013085444_add_sessions_table.rb b/db/migrate/20111013085444_add_sessions_table.rb new file mode 100644 index 0000000..fd942cc --- /dev/null +++ b/db/migrate/20111013085444_add_sessions_table.rb @@ -0,0 +1,16 @@ +class AddSessionsTable < ActiveRecord::Migration + def up + create_table :sessions do |t| + t.string :session_id, :null => false + t.text :data + t.timestamps + end + + add_index :sessions, :session_id + add_index :sessions, :updated_at + end + + def down + drop_table :sessions + end +end diff --git a/db/schema.rb b/db/schema.rb index c67b931..4c30654 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -1,3 +1,4 @@ +# encoding: UTF-8 # This file is auto-generated from the current state of the database. Instead # of editing this file, please use the migrations feature of Active Record to # incrementally modify your database, and then regenerate this schema definition. @@ -10,18 +11,25 @@ # # It's strongly recommended to check this file into your version control system. -ActiveRecord::Schema.define(:version => 20101216180143) do +ActiveRecord::Schema.define(:version => 20111013085444) do create_table "admin_users", :force => true do |t| - t.string "first_name", :default => "", :null => false - t.string "last_name", :default => "", :null => false - t.string "role", :null => false - t.string "email", :null => false - t.boolean "status", :default => false - t.string "token", :null => false - t.string "salt", :null => false - t.string "crypted_password", :null => false - t.string "preferences" + t.string "email", :default => "", :null => false + t.string "encrypted_password", :limit => 128, :default => "", :null => false + t.string "reset_password_token" + t.datetime "reset_password_sent_at" + t.datetime "remember_created_at" + t.integer "sign_in_count", :default => 0 + t.datetime "current_sign_in_at" + t.datetime "last_sign_in_at" + t.string "current_sign_in_ip" + t.string "last_sign_in_ip" + t.string "confirmation_token" + t.datetime "confirmed_at" + t.datetime "confirmation_sent_at" + t.integer "failed_attempts", :default => 0 + t.string "unlock_token" + t.datetime "locked_at" t.datetime "created_at" t.datetime "updated_at" end diff --git a/logo.png b/logo.png new file mode 100644 index 0000000..fec2fca Binary files /dev/null and b/logo.png differ diff --git a/public/index.html_ b/public/index.html_ new file mode 100644 index 0000000..9d9811a --- /dev/null +++ b/public/index.html_ @@ -0,0 +1,241 @@ + + + + Ruby on Rails: Welcome aboard + + + + +
+ + +
+ + + + +
+

Getting started

+

Here’s how to get rolling:

+ +
    +
  1. +

    Use rails generate to create your models and controllers

    +

    To see all available options, run it without parameters.

    +
  2. + +
  3. +

    Set up a default route and remove public/index.html

    +

    Routes are set up in config/routes.rb.

    +
  4. + +
  5. +

    Create your database

    +

    Run rake db:create to create your database. If you're not using SQLite (the default), edit config/database.yml with your username and password.

    +
  6. +
+
+
+ + +
+ + diff --git a/test/fixtures/admin_users.yml b/test/fixtures/admin_users.yml new file mode 100644 index 0000000..5394fa3 --- /dev/null +++ b/test/fixtures/admin_users.yml @@ -0,0 +1,11 @@ +# Read about fixtures at http://api.rubyonrails.org/classes/Fixtures.html + +# This model initially had no columns defined. If you add columns to the +# model remove the '{}' from the fixture names and add the columns immediately +# below each fixture, per the syntax in the comments below +# +one: {} +# column: value +# +two: {} +# column: value diff --git a/test/functional/admin/admin_controller_test.rb b/test/functional/admin/admin_controller_test.rb new file mode 100644 index 0000000..d32ccbb --- /dev/null +++ b/test/functional/admin/admin_controller_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class Admin::AdminControllerTest < ActionController::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/functional/admin/dashboard_controller_test.rb b/test/functional/admin/dashboard_controller_test.rb new file mode 100644 index 0000000..2b0b8a1 --- /dev/null +++ b/test/functional/admin/dashboard_controller_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class Admin::DashboardControllerTest < ActionController::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/functional/admin/downloads_controller_test.rb b/test/functional/admin/downloads_controller_test.rb new file mode 100644 index 0000000..2cc27e1 --- /dev/null +++ b/test/functional/admin/downloads_controller_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class Admin::DownloadsControllerTest < ActionController::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/functional/admin/unlocks_controller_test.rb b/test/functional/admin/unlocks_controller_test.rb new file mode 100644 index 0000000..2cd3d95 --- /dev/null +++ b/test/functional/admin/unlocks_controller_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class Admin::UnlocksControllerTest < ActionController::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/functional/home_controller_test.rb b/test/functional/home_controller_test.rb new file mode 100644 index 0000000..730478d --- /dev/null +++ b/test/functional/home_controller_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class HomeControllerTest < ActionController::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/unit/admin_user_test.rb b/test/unit/admin_user_test.rb new file mode 100644 index 0000000..6215c04 --- /dev/null +++ b/test/unit/admin_user_test.rb @@ -0,0 +1,7 @@ +require 'test_helper' + +class AdminUserTest < ActiveSupport::TestCase + # test "the truth" do + # assert true + # end +end diff --git a/test/unit/helpers/admin/admin_helper_test.rb b/test/unit/helpers/admin/admin_helper_test.rb new file mode 100644 index 0000000..28ed129 --- /dev/null +++ b/test/unit/helpers/admin/admin_helper_test.rb @@ -0,0 +1,4 @@ +require 'test_helper' + +class Admin::AdminHelperTest < ActionView::TestCase +end diff --git a/test/unit/helpers/admin/dashboard_helper_test.rb b/test/unit/helpers/admin/dashboard_helper_test.rb new file mode 100644 index 0000000..70e2bb0 --- /dev/null +++ b/test/unit/helpers/admin/dashboard_helper_test.rb @@ -0,0 +1,4 @@ +require 'test_helper' + +class Admin::DashboardHelperTest < ActionView::TestCase +end diff --git a/test/unit/helpers/admin/downloads_helper_test.rb b/test/unit/helpers/admin/downloads_helper_test.rb new file mode 100644 index 0000000..2ad3995 --- /dev/null +++ b/test/unit/helpers/admin/downloads_helper_test.rb @@ -0,0 +1,4 @@ +require 'test_helper' + +class Admin::DownloadsHelperTest < ActionView::TestCase +end diff --git a/test/unit/helpers/admin/unlocks_helper_test.rb b/test/unit/helpers/admin/unlocks_helper_test.rb new file mode 100644 index 0000000..d4d5215 --- /dev/null +++ b/test/unit/helpers/admin/unlocks_helper_test.rb @@ -0,0 +1,4 @@ +require 'test_helper' + +class Admin::UnlocksHelperTest < ActionView::TestCase +end diff --git a/test/unit/helpers/home_helper_test.rb b/test/unit/helpers/home_helper_test.rb new file mode 100644 index 0000000..4740a18 --- /dev/null +++ b/test/unit/helpers/home_helper_test.rb @@ -0,0 +1,4 @@ +require 'test_helper' + +class HomeHelperTest < ActionView::TestCase +end