Commit bca28ed5406430518439b18e7b55fa7ec408c430

Authored by Fabio Teixeira
1 parent 8f633a81

Add ratings communities plugin

Signed-off-by: Alexandre Torres <alexandrekry@gmail.com>
Signed-off-by: Andre Bernardes <andrebsguedes@gmail.com>
Signed-off-by: Brenddon Gontijo <brenddongontijo@msn.com>
Signed-off-by: DylanGuedes <djmgguedes@gmail.com>
Signed-off-by: Fabio Teixeira <fabio1079@gmail.com>
Signed-off-by: Filipe Ribeiro <firibeiro77@live.com>
Signed-off-by: Gabriela Navarro <navarro1703@gmail.com
Signed-off-by: Hebert Douglas <hebertdougl@gmail.com>
Signed-off-by: Omar Junior <omarroinuj@gmail.com>
Signed-off-by: Pedro de Lyra  <pedrodelyra@gmail.com>
Signed-off-by: Simião Carvalho <simiaosimis@gmail.com>
Signed-off-by: Tallys Martins <tallysmartins@gmail.com>
Showing 33 changed files with 1043 additions and 0 deletions   Show diff stats
plugins/communities_ratings/controllers/communities_ratings_plugin_admin_controller.rb 0 → 100644
... ... @@ -0,0 +1,17 @@
  1 +class CommunitiesRatingsPluginAdminController < PluginAdminController
  2 +
  3 + append_view_path File.join(File.dirname(__FILE__) + '/../views')
  4 +
  5 + def index
  6 + end
  7 +
  8 + def update
  9 + if @environment.update_attributes(params[:environment])
  10 + session[:notice] = _('Configuration updated successfully.')
  11 + else
  12 + session[:notice] = _('Configuration could not be saved.')
  13 + end
  14 + render :action => 'index'
  15 + end
  16 +
  17 +end
0 18 \ No newline at end of file
... ...
plugins/communities_ratings/controllers/communities_ratings_plugin_profile_controller.rb 0 → 100644
... ... @@ -0,0 +1,65 @@
  1 +class CommunitiesRatingsPluginProfileController < ProfileController
  2 + include RatingsHelper
  3 +
  4 + def new_rating
  5 + @rating_available = can_rate_now?
  6 + @users_ratings = get_ratings(profile.id)
  7 + @users_ratings = @users_ratings.paginate(
  8 + :per_page => environment.communities_ratings_per_page,
  9 + :page => params[:npage]
  10 + )
  11 + @default_rate = environment.communities_ratings_default_rating
  12 + @min_rate = Environment.communities_ratings_min_rating
  13 +
  14 + if request.post?
  15 + if @rating_available
  16 + create_new_rate
  17 + else
  18 + session[:notice] = _("You cant vote on this community")
  19 + end
  20 + end
  21 + end
  22 +
  23 + private
  24 +
  25 + def can_rate_now?
  26 + return false unless user
  27 +
  28 + ratings = CommunityRating.where(
  29 + :community_id=>profile.id,
  30 + :person_id=>user.id
  31 + )
  32 +
  33 + return false if !ratings.empty? && environment.communities_ratings_vote_once
  34 +
  35 + if ratings.empty?
  36 + true
  37 + else
  38 + elapsed_time_since_last_rating = Time.zone.now - ratings.last.created_at
  39 + elapsed_time_since_last_rating > environment.communities_ratings_cooldown.hours
  40 + end
  41 + end
  42 +
  43 + def create_new_rate
  44 + community_rating = CommunityRating.new(params[:community_rating])
  45 + community_rating.person = current_user.person
  46 + community_rating.community = profile
  47 + community_rating.value = params[:community_rating_value] if params[:community_rating_value]
  48 +
  49 + if params[:comments] and (not params[:comments][:body].empty?)
  50 + comment = Comment.new(params[:comments])
  51 + comment.author = community_rating.person
  52 + comment.community = community_rating.community
  53 + comment.save
  54 +
  55 + community_rating.comment = comment
  56 + end
  57 +
  58 + if community_rating.save
  59 + session[:notice] = _("#{profile.name} successfully rated!")
  60 + redirect_to :controller => 'profile', :action => 'index'
  61 + else
  62 + session[:notice] = _("Sorry, there were problems rating this profile.")
  63 + end
  64 + end
  65 +end
... ...
plugins/communities_ratings/db/migrate/20150701122801_create_community_ratings.rb 0 → 100644
... ... @@ -0,0 +1,11 @@
  1 +class CreateCommunityRatings < ActiveRecord::Migration
  2 + def change
  3 + create_table :community_ratings do |t|
  4 + t.belongs_to :community
  5 + t.belongs_to :person
  6 + t.integer :value
  7 +
  8 + t.timestamps
  9 + end
  10 + end
  11 +end
... ...
plugins/communities_ratings/db/migrate/20150706161041_add_comments_count_to_community.rb 0 → 100644
... ... @@ -0,0 +1,11 @@
  1 +class AddCommentsCountToCommunity < ActiveRecord::Migration
  2 + def self.up
  3 + change_table :profiles do |t|
  4 + t.integer :comments_count
  5 + end
  6 + end
  7 +
  8 + def self.down
  9 + remove_column :profiles, :comments_count
  10 + end
  11 +end
... ...
plugins/communities_ratings/db/migrate/20150707133834_add_community_rating_to_comments.rb 0 → 100644
... ... @@ -0,0 +1,11 @@
  1 +class AddCommunityRatingToComments < ActiveRecord::Migration
  2 + def self.up
  3 + change_table :comments do |t|
  4 + t.belongs_to :community_rating
  5 + end
  6 + end
  7 +
  8 + def self.down
  9 + remove_column :comments, :community_rating_id
  10 + end
  11 +end
... ...
plugins/communities_ratings/db/migrate/20150710171028_add_communities_rating_config_to_environment.rb 0 → 100644
... ... @@ -0,0 +1,9 @@
  1 +class AddCommunitiesRatingConfigToEnvironment < ActiveRecord::Migration
  2 + def change
  3 + add_column :environments, :communities_ratings_cooldown, :integer, :default => 24
  4 + add_column :environments, :communities_ratings_default_rating, :integer, :default => 1
  5 + add_column :environments, :communities_ratings_order, :string, :default => "most recent"
  6 + add_column :environments, :communities_ratings_per_page, :integer, :default => 10
  7 + add_column :environments, :communities_ratings_vote_once, :boolean, :default => false
  8 + end
  9 +end
... ...
plugins/communities_ratings/lib/communities_ratings_block.rb 0 → 100644
... ... @@ -0,0 +1,31 @@
  1 +class CommunitiesRatingsBlock < Block
  2 + include RatingsHelper
  3 +
  4 + def self.description
  5 + _('Community Ratings')
  6 + end
  7 +
  8 + def help
  9 + _('This block displays the community ratings.')
  10 + end
  11 +
  12 + def content(args = {})
  13 + block = self
  14 +
  15 + proc do
  16 + render(
  17 + :file => 'blocks/communities_ratings_block',
  18 + :locals => {:block => block}
  19 + )
  20 + end
  21 + end
  22 +
  23 + def limit_number_of_ratings
  24 + count = self.owner.community_ratings.count
  25 + count > 3 ? 3 : count
  26 + end
  27 +
  28 + def cacheable?
  29 + false
  30 + end
  31 +end
... ...
plugins/communities_ratings/lib/communities_ratings_plugin.rb 0 → 100644
... ... @@ -0,0 +1,47 @@
  1 +class CommunitiesRatingsPlugin < Noosfero::Plugin
  2 + include Noosfero::Plugin::HotSpot
  3 +
  4 + def self.plugin_name
  5 + "Communities Ratings"
  6 + end
  7 +
  8 + def self.plugin_description
  9 + _("A plugin that allows you to rate a community and comment about it.")
  10 + end
  11 +
  12 + module Hotspots
  13 + def communities_ratings_plugin_comments_extra_fields
  14 + nil
  15 + end
  16 +
  17 + def communities_ratings_title
  18 + nil
  19 + end
  20 +
  21 + def communities_ratings_plugin_star_message
  22 + nil
  23 + end
  24 +
  25 + def communities_ratings_plugin_extra_fields_show_data user_rating
  26 + nil
  27 + end
  28 + end
  29 +
  30 + def self.extra_blocks
  31 + {
  32 + CommunitiesRatingsBlock => { :type => [Community], :position => ['1']}
  33 + }
  34 + end
  35 +
  36 + def stylesheet?
  37 + true
  38 + end
  39 +
  40 + def js_files
  41 + %w(
  42 + public/rate.js
  43 + public/comunities_rating_management.js
  44 + )
  45 + end
  46 +
  47 +end
... ...
plugins/communities_ratings/lib/community_rating.rb 0 → 100644
... ... @@ -0,0 +1,17 @@
  1 +class CommunityRating < ActiveRecord::Base
  2 + belongs_to :person
  3 + belongs_to :community
  4 +
  5 + attr_accessible :value, :person, :community
  6 +
  7 + validates :value,
  8 + :presence => true, :inclusion => {
  9 + in: 1..5, message: _("must be between 1 and 5")
  10 + }
  11 +
  12 + validates :community_id, :person_id,
  13 + :presence => true
  14 +
  15 + has_one :comment
  16 +
  17 +end
... ...
plugins/communities_ratings/lib/ext/comments.rb 0 → 100644
... ... @@ -0,0 +1,8 @@
  1 +require_dependency "comment"
  2 +
  3 +Comment.class_eval do
  4 + alias :community :source
  5 + alias :community= :source=
  6 +
  7 + belongs_to :community_rating
  8 +end
... ...
plugins/communities_ratings/lib/ext/community.rb 0 → 100644
... ... @@ -0,0 +1,7 @@
  1 +require_dependency 'community'
  2 +
  3 +Community.class_eval do
  4 + has_many :community_ratings
  5 +
  6 + has_many :comments, :class_name => 'Comment', :foreign_key => 'source_id', :dependent => :destroy, :order => 'created_at asc'
  7 +end
... ...
plugins/communities_ratings/lib/ext/environment.rb 0 → 100644
... ... @@ -0,0 +1,35 @@
  1 +require_dependency 'environment'
  2 +
  3 +Environment.class_eval do
  4 + attr_accessible :communities_ratings_cooldown, :communities_ratings_default_rating, :communities_ratings_order, :communities_ratings_per_page, :communities_ratings_vote_once
  5 +
  6 + COMMUNITIES_RATINGS_ORDER_OPTIONS = ["Most Recent", "Best Ratings"]
  7 + COMMUNITIES_RATINGS_MINIMUM_RATING = 1
  8 + COMMUNITIES_RATINGS_MAX_COOLDOWN = 1000
  9 +
  10 + validates :communities_ratings_default_rating,
  11 + :presence => true, :numericality => {
  12 + greater_than_or_equal_to: COMMUNITIES_RATINGS_MINIMUM_RATING,
  13 + less_than_or_equal_to: 5
  14 + }
  15 +
  16 + validates :communities_ratings_cooldown,
  17 + :presence => true, :numericality => {
  18 + greater_than_or_equal_to: 0,
  19 + less_than_or_equal_to: COMMUNITIES_RATINGS_MAX_COOLDOWN
  20 + }
  21 +
  22 + validates :communities_ratings_per_page,
  23 + :presence => true, :numericality => {
  24 + :greater_than_or_equal_to => 5,
  25 + :less_than_or_equal_to => 20
  26 + }
  27 +
  28 + def self.communities_ratings_min_rating
  29 + COMMUNITIES_RATINGS_MINIMUM_RATING
  30 + end
  31 +
  32 + def self.communities_ratings_order_options
  33 + COMMUNITIES_RATINGS_ORDER_OPTIONS
  34 + end
  35 +end
... ...
plugins/communities_ratings/lib/ext/person.rb 0 → 100644
... ... @@ -0,0 +1,5 @@
  1 +require_dependency 'person'
  2 +
  3 +Person.class_eval do
  4 + has_many :community_ratings
  5 +end
... ...
plugins/communities_ratings/lib/ratings_helper.rb 0 → 100644
... ... @@ -0,0 +1,10 @@
  1 +module RatingsHelper
  2 +
  3 + def get_ratings (profile_id)
  4 + if Environment.default.communities_ratings_order.downcase == ("best ratings")
  5 + ratings = CommunityRating.where(community_id: profile_id).order("value DESC")
  6 + else
  7 + ratings = CommunityRating.where(community_id: profile_id).order("created_at DESC")
  8 + end
  9 + end
  10 +end
0 11 \ No newline at end of file
... ...
plugins/communities_ratings/public/comunities_rating_management.js 0 → 100644
... ... @@ -0,0 +1,35 @@
  1 +(function($) {
  2 + "use strict";
  3 +
  4 + var VoteOnce = {
  5 + init: function() {
  6 + this.cacheDom();
  7 + this.setEvents();
  8 + },
  9 +
  10 +
  11 + cacheDom: function() {
  12 + this.$vote_once_checkbox = $("#environment_communities_ratings_vote_once");
  13 + this.$hours_timer_input = $("#environment_communities_ratings_cooldown");
  14 + },
  15 +
  16 +
  17 + setEvents: function() {
  18 + this.$vote_once_checkbox.on("click", this.verifyHoursTimerDisable.bind(this));
  19 + },
  20 +
  21 +
  22 + verifyHoursTimerDisable: function() {
  23 + if (this.$vote_once_checkbox.is(":checked")) {
  24 + this.$hours_timer_input.attr("disabled", "disabled");
  25 + } else {
  26 + this.$hours_timer_input.removeAttr("disabled");
  27 + }
  28 + }
  29 + }
  30 +
  31 +
  32 + $(document).ready(function() {
  33 + VoteOnce.init();
  34 + });
  35 +}) (jQuery);
... ...
plugins/communities_ratings/public/images/small-star-negative.png 0 → 100644

529 Bytes

plugins/communities_ratings/public/images/small-star-positive.png 0 → 100644

509 Bytes

plugins/communities_ratings/public/images/star-negative.png 0 → 100644

642 Bytes

plugins/communities_ratings/public/images/star-positive.png 0 → 100644

637 Bytes

plugins/communities_ratings/public/images/user-not-logged.png 0 → 100644

2.48 KB

plugins/communities_ratings/public/rate.js 0 → 100644
... ... @@ -0,0 +1,122 @@
  1 +;(function($, undefined) {
  2 + "use strict";
  3 +
  4 + /*
  5 + * All global data that are used in the stars feature.
  6 + */
  7 + var DATA = {
  8 + selected_rate: 0, // The actual selected star when the user click on a star
  9 + MAXIMUM_STARS: 5, // (const) The maximum number of allowed stars
  10 + MINIMUM_STARS: 1, // (const) The minimum number of allowed stars
  11 + DATA_RATE_ATTRIBUTE: "data-star-rate", // (const) The data attribute with the star rate
  12 + NOT_SELECTED_VALUE: 0 // (const) The value when there is no selected rate
  13 + }
  14 +
  15 +
  16 + /*
  17 + * Prepare the global data that are variable.
  18 + * If the user already rated the community, set the selected_rate as the rated value
  19 + */
  20 + function set_global_data() {
  21 + var selected_rate = parseInt($("#selected-star-rate").val());
  22 + var MINIMUM_STARS = parseInt($("#MINIMUM_STARS").val());
  23 + DATA.selected_rate = selected_rate;
  24 + DATA.MINIMUM_STARS = MINIMUM_STARS;
  25 + }
  26 +
  27 +
  28 + /*
  29 + * Given a start rate, an end rate and the elements, it makes a regex that filter
  30 + * the elements by the given range and returns it.
  31 + */
  32 + function star_filter(start, end, elements) {
  33 + var test_regex = undefined;
  34 +
  35 + // Verify if it is a valid range and makes its range regex: /[start-end]/
  36 + if (end >= start) {
  37 + test_regex = new RegExp("["+(start)+"-"+(end)+"]");
  38 + } else {
  39 + // If the range is invalid, make a regex that will return no element
  40 + test_regex = new RegExp("[]");
  41 + }
  42 +
  43 + // Filter the elements that are in the given range
  44 + var result = elements.filter(function(i, element) {
  45 + var rate = parseInt(element.getAttribute(DATA.DATA_RATE_ATTRIBUTE));
  46 +
  47 + return test_regex.test(rate);
  48 + });
  49 +
  50 + return result;
  51 + }
  52 +
  53 +
  54 + /*
  55 + * Show or hide the stars depending on the mouse position and the limit rate.
  56 + * Given the mouseover rate, the limit rate and the css classes to be swapped,
  57 + *
  58 + * It verify if the user already selected a star rate:
  59 + * If true:
  60 + * It swap the css classes from the selected star up to the given limit rate
  61 + * If false:
  62 + * It swap the css classes from the minimum rate up to the mouseover rate
  63 + */
  64 + function change_stars_class(rate_mouseover, limit_rate, remove_class, add_class) {
  65 + var previous_stars = undefined;
  66 +
  67 + // The default not selected rate value is 0 and minimum is 1.
  68 + if (DATA.selected_rate >= DATA.MINIMUM_STARS) {
  69 + previous_stars = star_filter(DATA.selected_rate+1, limit_rate, $("."+remove_class));
  70 + } else {
  71 + previous_stars = star_filter(DATA.MINIMUM_STARS, rate_mouseover, $("."+remove_class));
  72 + }
  73 +
  74 + previous_stars.switchClass(remove_class, add_class);
  75 + }
  76 +
  77 +
  78 + /*
  79 + * Sets the stars mouse events.
  80 + */
  81 + function set_star_hover_actions() {
  82 + $(".star-negative, .star-positive")
  83 + .on("mouseover", function() { // On mouse over, show the current rate star
  84 + var rate_mouseover = parseInt(this.getAttribute(DATA.DATA_RATE_ATTRIBUTE));
  85 +
  86 + change_stars_class(rate_mouseover, rate_mouseover, "star-negative", "star-positive");
  87 + })
  88 +
  89 + .on("mouseout", function() { // On mouse out, hide the stars
  90 + var rate_mouseover = parseInt(this.getAttribute(DATA.DATA_RATE_ATTRIBUTE));
  91 +
  92 + change_stars_class(rate_mouseover, DATA.MAXIMUM_STARS, "star-positive", "star-negative");
  93 + })
  94 +
  95 + .on("click", function() { // On mouse click, set the selected star rate
  96 + var rate_mouseover = parseInt(this.getAttribute(DATA.DATA_RATE_ATTRIBUTE));
  97 +
  98 + // If the new rate is different from actual, update it
  99 + if (rate_mouseover !== DATA.selected_rate && rate_mouseover > DATA.MINIMUM_STARS) {
  100 + DATA.selected_rate = rate_mouseover;
  101 + } else { // or else, uncheck it
  102 + DATA.selected_rate = DATA.MINIMUM_STARS;
  103 + }
  104 +
  105 + // Mark the selected_rate
  106 + $("#selected-star-rate").val(DATA.selected_rate);
  107 +
  108 + var star_notice = $(".star-notice");
  109 + star_notice.find("span").html(DATA.selected_rate);
  110 + star_notice.removeClass("star-hide");
  111 + });
  112 + }
  113 +
  114 +
  115 + /*
  116 + * When the page DOM is ready, set all the stars events
  117 + */
  118 + $(document).ready(function() {
  119 + set_global_data();
  120 + set_star_hover_actions();
  121 + });
  122 +}) (jQuery);
... ...
plugins/communities_ratings/style.css 0 → 100644
... ... @@ -0,0 +1,145 @@
  1 +.star-container {
  2 + width: 100%;
  3 + height: 20px;
  4 +}
  5 +
  6 +.star-negative, .star-positive {
  7 + width: 20px;
  8 + height: 20px;
  9 + background-repeat: no-repeat;
  10 + margin-right: 2px;
  11 + position: relative;
  12 + float: left;
  13 + cursor: pointer;
  14 +}
  15 +
  16 +.star-negative {
  17 + background-image: url('public/images/star-negative.png');
  18 +}
  19 +
  20 +.star-positive {
  21 + background-image: url('public/images/star-positive.png');
  22 +}
  23 +
  24 +.small-star-negative, .small-star-positive {
  25 + background-repeat: no-repeat;
  26 + float: left;
  27 + height: 15px;
  28 + margin-right: 2px;
  29 + position: relative;
  30 + width: 15px;
  31 +}
  32 +
  33 +.small-star-negative {
  34 + background-image: url('public/images/small-star-negative.png');
  35 +}
  36 +
  37 +.small-star-positive {
  38 + background-image: url('public/images/small-star-positive.png');
  39 +}
  40 +
  41 +.star-hide {
  42 + display: none;
  43 +}
  44 +
  45 +.star-rate-data {
  46 + width: 100%;
  47 + padding-top: 20px;
  48 + position: relative;
  49 + overflow: auto;
  50 +}
  51 +
  52 +.star-profile-information, .star-rate-form {
  53 + display: table-cell;
  54 + vertical-align: top;
  55 + width: 362px;
  56 +}
  57 +
  58 +.star-profile-information {
  59 + width: 134px;
  60 +}
  61 +
  62 +.star-rate-form {
  63 + display: table-cell;
  64 + vertical-align: top;
  65 +}
  66 +
  67 +.star-profile-image, .star-profile-name {
  68 + text-align: center;
  69 +}
  70 +
  71 +.star-profile-name {
  72 + word-break: break-word;
  73 + margin: auto;
  74 + margin-top: 5px;
  75 + width: 66px;
  76 +}
  77 +
  78 +.star-rate-data .star-rate-form .star-comment-container .formfield textarea {
  79 + width: 361px;
  80 +}
  81 +
  82 +/************* Users ratings list ****************/
  83 +
  84 +.ratings-list .user-rating-block,
  85 +.ratings-list .make-report-block {
  86 + border-top: 1px solid #D3D6DE;
  87 + margin-top: 25px;
  88 + padding-top: 20px;
  89 +}
  90 +
  91 +.ratings-list .make-report-block {
  92 + padding-bottom: 25px;
  93 +}
  94 +
  95 +.ratings-list .see-more{
  96 + border-top: 1px solid #D3D6DE;
  97 +}
  98 +.ratings-list .user-rating-block .user-testimony-container {
  99 + display: table-cell;
  100 + padding-left: 20px;
  101 +}
  102 +
  103 +.ratings-list .make-report-block .make-report-container {
  104 + display: table-cell;
  105 +}
  106 +
  107 +.ratings-list .user-rating-block .user-testimony-container .star-container {
  108 + display: table-cell;
  109 +}
  110 +
  111 +.ratings-list .user-rating-block .user-testimony-container .testimony-rate-date {
  112 + display: table-cell;
  113 + max-width: 95px;
  114 + min-width: 95px;
  115 + padding-right: 160px;
  116 + white-space: nowrap;
  117 +}
  118 +
  119 +.ratings-list .user-rating-block .user-testimony-container .user-testimony {
  120 + margin-top: 10px;
  121 + word-break: break-word;
  122 +}
  123 +
  124 +.ratings-list .make-report-block .make-report-container .make-report-message {
  125 + font-size: 14px;
  126 + font-style: italic;
  127 + word-break: break-word;
  128 +}
  129 +
  130 +.ratings-list .make-report-block .make-report-container .button-bar {
  131 + overflow: auto;
  132 + padding-top: 15px;
  133 +}
  134 +
  135 +.ratings-list .user-rating-block .star-profile-information {
  136 + border-right: 1px dotted #D3D6DE;
  137 +}
  138 +
  139 +.ratings-list .icon-arrow-right-p {
  140 + background: url(/designs/themes/base/imgs/arrow-right-p.png) 100% 50% no-repeat;
  141 + display: block;
  142 + float: right;
  143 + margin-top: 20px;
  144 + padding-right: 15px;
  145 +}
0 146 \ No newline at end of file
... ...
plugins/communities_ratings/test/functional/communities_ratings_plugin_admin_controller_test.rb 0 → 100644
... ... @@ -0,0 +1,49 @@
  1 +require File.expand_path(File.dirname(__FILE__)) + '/../../../../test/test_helper'
  2 +require File.expand_path(File.dirname(__FILE__)) + '/../../controllers/communities_ratings_plugin_admin_controller'
  3 +
  4 +# Re-raise errors caught by the controller.
  5 +class CommunitiesRatingsPluginAdminController; def rescue_action(e) raise e end; end
  6 +
  7 +class CommunitiesRatingsPluginAdminControllerTest < ActionController::TestCase
  8 +
  9 + def setup
  10 + @controller = CommunitiesRatingsPluginAdminController.new
  11 + @request = ActionController::TestRequest.new
  12 + @response = ActionController::TestResponse.new
  13 +
  14 + @environment = Environment.default
  15 + @environment.enabled_plugins = ['CommunitiesRatingsPlugin']
  16 + @environment.save
  17 +
  18 + @community = Community.create(:name => "TestCommunity")
  19 +
  20 + login_as(create_admin_user(@environment))
  21 + end
  22 +
  23 + test "should update communities rating plugin configuration" do
  24 + post :update, :environment => { :communities_ratings_default_rating => 5,
  25 + :communities_ratings_cooldown => 12,
  26 + :communities_ratings_order => "Most Recent",
  27 + :communities_ratings_per_page => 10,
  28 + :communities_ratings_vote_once => true }
  29 +
  30 + assert :success
  31 + @environment.reload
  32 + assert_equal 5, @environment.communities_ratings_default_rating
  33 + assert_equal "Configuration updated successfully.", session[:notice]
  34 + end
  35 +
  36 + test "should not update communities rating plugin configuration with wrong cooldown time" do
  37 + post :update, :environment => { :communities_ratings_default_rating => 5,
  38 + :communities_ratings_cooldown => -50,
  39 + :communities_ratings_order => "Most Recent",
  40 + :communities_ratings_per_page => 10,
  41 + :communities_ratings_vote_once => true }
  42 +
  43 + assert :success
  44 + @environment.reload
  45 + assert_equal 24, @environment.communities_ratings_cooldown
  46 + assert_equal "Configuration could not be saved.", session[:notice]
  47 + end
  48 +end
  49 +
... ...
plugins/communities_ratings/test/functional/communities_ratings_plugin_profile_controller_test.rb 0 → 100644
... ... @@ -0,0 +1,65 @@
  1 +require File.expand_path(File.dirname(__FILE__)) + '/../../../../test/test_helper'
  2 +require File.expand_path(File.dirname(__FILE__)) + '/../../controllers/communities_ratings_plugin_profile_controller'
  3 +
  4 +# Re-raise errors caught by the controller.
  5 +class CommunitiesRatingsPluginProfileController; def rescue_action(e) raise e end; end
  6 +
  7 +class CommunitiesRatingsPluginProfileControllerTest < ActionController::TestCase
  8 +
  9 + def setup
  10 + @controller = CommunitiesRatingsPluginProfileController.new
  11 + @request = ActionController::TestRequest.new
  12 + @response = ActionController::TestResponse.new
  13 +
  14 + @environment = Environment.default
  15 + @environment.enabled_plugins = ['CommunitiesRatingsPlugin']
  16 + @environment.save
  17 +
  18 + @person = create_user('testuser').person
  19 + @community = Community.create(:name => "TestCommunity")
  20 +
  21 + login_as(@person.identifier)
  22 + @controller.stubs(:logged_in?).returns(true)
  23 + @controller.stubs(:current_user).returns(@person.user)
  24 + end
  25 +
  26 + test "should add new comment to community" do
  27 + post :new_rating, profile: @community.identifier, :comments => {:body => "This is a test"}, :community_rating_value => 4
  28 + assert_equal "#{@community.name} successfully rated!", session[:notice]
  29 + end
  30 +
  31 + test "Create community_rating without comment body" do
  32 + post :new_rating, profile: @community.identifier, :comments => {:body => ""}, :community_rating_value => 2
  33 +
  34 + assert_equal "#{@community.name} successfully rated!", session[:notice]
  35 + end
  36 +
  37 + test "Do not create community_rating without a rate value" do
  38 + post :new_rating, profile: @community.identifier, :comments => {:body => ""}, :community_rating_value => nil
  39 +
  40 + assert_equal "Sorry, there were problems rating this profile.", session[:notice]
  41 + end
  42 +
  43 + test "do not create two ratings when environment vote once is true" do
  44 + @environment.communities_ratings_vote_once = true
  45 + @environment.save
  46 + post :new_rating, profile: @community.identifier, :comments => {:body => "This is a test"}, :community_rating_value => 3
  47 +
  48 + assert_equal "#{@community.name} successfully rated!", session[:notice]
  49 +
  50 + post :new_rating, profile: @community.identifier, :comments => {:body => "This is a test 2"}, :community_rating_value => 3
  51 + assert_equal "You cant vote on this community", session[:notice]
  52 + end
  53 +
  54 + test "Display unavailable rating message for users that must wait the rating cooldown time" do
  55 + post :new_rating, profile: @community.identifier, :comments => {:body => ""}, :community_rating_value => 3
  56 + assert_not_match(/The administrators set the minimum time of/, @response.body)
  57 + valid_rating = CommunityRating.last
  58 +
  59 + post :new_rating, profile: @community.identifier, :comments => {:body => ""}, :community_rating_value => 3
  60 + assert_match(/The administrators set the minimum time of/, @response.body)
  61 + new_rating = CommunityRating.last
  62 +
  63 + assert_equal valid_rating.id, new_rating.id
  64 + end
  65 +end
... ...
plugins/communities_ratings/test/unit/community_rating_test.rb 0 → 100644
... ... @@ -0,0 +1,23 @@
  1 +require 'test_helper'
  2 +
  3 +class CommunityRatingTest < ActiveSupport::TestCase
  4 + test "The value must be between 1 and 5" do
  5 + cr1 = CommunityRating.new :value => -1
  6 + cr2 = CommunityRating.new :value => 6
  7 +
  8 + assert_equal false, cr1.valid?
  9 + assert_equal false, cr2.valid?
  10 +
  11 + assert_equal true, cr1.errors[:value].include?("must be between 1 and 5")
  12 + assert_equal true, cr2.errors[:value].include?("must be between 1 and 5")
  13 +
  14 + cr1.value = 1
  15 + cr1.valid?
  16 +
  17 + cr2.value = 5
  18 + cr2.valid?
  19 +
  20 + assert_equal false, cr1.errors[:value].include?("must be between 1 and 5")
  21 + assert_equal false, cr2.errors[:value].include?("must be between 1 and 5")
  22 + end
  23 +end
... ...
plugins/communities_ratings/test/unit/environment_test.rb 0 → 100644
... ... @@ -0,0 +1,34 @@
  1 +require 'test_helper'
  2 +
  3 +class EnvironmentTest < ActiveSupport::TestCase
  4 + test "Communities ratings default rating validation" do
  5 + environment = Environment.new :communities_ratings_default_rating => 0
  6 + environment.valid?
  7 +
  8 + assert_equal "must be greater than or equal to 1", environment.errors[:communities_ratings_default_rating].first
  9 +
  10 + environment.communities_ratings_default_rating = 6
  11 + environment.valid?
  12 +
  13 + assert_equal "must be less than or equal to 5", environment.errors[:communities_ratings_default_rating].first
  14 + end
  15 +
  16 + test "Communities ratings cooldown validation" do
  17 + environment = Environment.new :communities_ratings_cooldown => -1
  18 + environment.valid?
  19 +
  20 + assert_equal "must be greater than or equal to 0", environment.errors[:communities_ratings_cooldown].first
  21 + end
  22 +
  23 + test "communities ratings per page validation" do
  24 + environment = Environment.new :communities_ratings_per_page => 4
  25 + environment.valid?
  26 +
  27 + assert_equal "must be greater than or equal to 5", environment.errors[:communities_ratings_per_page].first
  28 +
  29 + environment.communities_ratings_per_page = 21
  30 + environment.valid?
  31 +
  32 + assert_equal "must be less than or equal to 20", environment.errors[:communities_ratings_per_page].first
  33 + end
  34 +end
... ...
plugins/communities_ratings/test/unit/ratings_helper_test.rb 0 → 100644
... ... @@ -0,0 +1,62 @@
  1 +require File.expand_path(File.dirname(__FILE__)) + '/../../../../test/test_helper'
  2 +require 'ratings_helper'
  3 +
  4 +class RatingsHelperTest < ActiveSupport::TestCase
  5 + include RatingsHelper
  6 +
  7 + def setup
  8 +
  9 + @environment = Environment.default
  10 + @environment.enabled_plugins = ['CommunitiesRatingsPlugin']
  11 + @environment.save
  12 + @person = create_user('testuser').person
  13 + @community = Community.create(:name => "TestCommunity")
  14 + end
  15 +
  16 + should "get the ratings of a community ordered by most recent ratings" do
  17 + ratings_array = []
  18 +
  19 + first_rating = CommunityRating.new
  20 + first_rating.community = @community
  21 + first_rating.person = @person
  22 + first_rating.value = 3
  23 + first_rating.save
  24 +
  25 + most_recent_rating = CommunityRating.new
  26 + most_recent_rating.community = @community
  27 + most_recent_rating.person = @person
  28 + most_recent_rating.value = 5
  29 + sleep 2
  30 + most_recent_rating.save
  31 +
  32 + ratings_array << most_recent_rating
  33 + ratings_array << first_rating
  34 +
  35 + assert_equal @environment.communities_ratings_order, "most recent"
  36 + assert_equal ratings_array, get_ratings(@community.id)
  37 + end
  38 +
  39 + should "get the ratings of a community ordered by best ratings" do
  40 + ratings_array = []
  41 + @environment.communities_ratings_order = "best ratings"
  42 + @environment.save
  43 +
  44 + first_rating = CommunityRating.new
  45 + first_rating.community = @community
  46 + first_rating.person = @person
  47 + first_rating.value = 3
  48 + first_rating.save
  49 +
  50 + second_rating = CommunityRating.new
  51 + second_rating.community = @community
  52 + second_rating.person = @person
  53 + second_rating.value = 5
  54 + sleep 2
  55 + second_rating.save
  56 +
  57 + ratings_array << second_rating
  58 + ratings_array << first_rating
  59 +
  60 + assert_equal ratings_array, get_ratings(@community.id)
  61 + end
  62 +end
... ...
plugins/communities_ratings/views/blocks/communities_ratings_block.html.erb 0 → 100644
... ... @@ -0,0 +1,21 @@
  1 +<div class="ratings-title">
  2 + <%= block_title(block.title) %>
  3 + <% if block.get_ratings(block.owner.id).empty? %>
  4 + <div class="ratings-list">
  5 + <%= _("This community does not have any ratings") %>
  6 + <%= render :partial => 'shared/make_report_block' %>
  7 + </div>
  8 + <% else %>
  9 + <div class="ratings-list">
  10 + <% block.get_ratings(block.owner.id).each_with_index do |r, index| %>
  11 + <% break if index >= block.limit_number_of_ratings %>
  12 + <%= render :partial => "shared/user_rating_container", :locals => {:user_rate => r} %>
  13 + <% end %>
  14 +
  15 + <%= render :partial => 'shared/make_report_block' %>
  16 +
  17 + <div class="see-more">
  18 + <%= link_to _('See more'), url_for(:controller => 'communities_ratings_plugin_profile', :action => 'new_rating'), :class => 'icon-arrow-right-p' %>
  19 + </div>
  20 +<% end %>
  21 +</div>
... ...
plugins/communities_ratings/views/communities_ratings_plugin_admin/index.html.erb 0 → 100644
... ... @@ -0,0 +1,49 @@
  1 +<h1><%= _("Communities Rating Management") %> </h1>
  2 +
  3 +<%= labelled_form_for(:environment, :url => {:action => 'update'}) do |f| %>
  4 + <table>
  5 + <tr>
  6 + <th><%= c_('Configuration') %></th>
  7 + <th><%= _('Value') %></th>
  8 + </tr>
  9 +
  10 + <tr>
  11 + <td><%= _('Default amount of stars marked on evaluations') %></td>
  12 + <td><%= select :environment, :communities_ratings_default_rating, (Environment.communities_ratings_min_rating)..5 %></td>
  13 + </tr>
  14 +
  15 + <tr>
  16 + <td><%= _('Can only vote for one community once') %></td>
  17 + <td><%= check_box :environment, :communities_ratings_vote_once %></td>
  18 + </tr>
  19 + <tr>
  20 + <td><%= _('Time cooldown between evaluations from the same user') %></td>
  21 +
  22 + <% hours_options = {size: 1} %>
  23 + <% hours_options[:disabled] = "disabled" if environment.communities_ratings_vote_once %>
  24 + <td><%= text_field :environment, :communities_ratings_cooldown, hours_options %>
  25 + <%= _('hours') %>
  26 + </td>
  27 + </tr>
  28 +
  29 + <tr>
  30 + <td><%= _('Order ratings by') %></td>
  31 + <td><%= select :environment, :communities_ratings_order, (Environment.communities_ratings_order_options) %></td>
  32 + </tr>
  33 +
  34 + <tr>
  35 + <td><%= _('Ratings per page') %></td>
  36 + <td>
  37 + <%= select :environment, :communities_ratings_per_page, 5..20 %>
  38 + </td>
  39 + </tr>
  40 + </table>
  41 +
  42 + <div>
  43 + <% button_bar do %>
  44 + <%= submit_button('save', c_('Save changes')) %>
  45 + <%= button :back, _('Back'), :controller => 'plugins' %>
  46 + <% end %>
  47 + </div>
  48 +
  49 +<% end %>
... ...
plugins/communities_ratings/views/communities_ratings_plugin_profile/_new_rating_fields.html.erb 0 → 100644
... ... @@ -0,0 +1,70 @@
  1 +<div class="star-page-title">
  2 + <%= @plugins.dispatch(:communities_ratings_title).collect { |content| instance_exec(&content) }.join("") %>
  3 +</div>
  4 +
  5 +<div class="star-rate-data">
  6 +
  7 + <div class="star-profile-information">
  8 + <div class="star-profile-image">
  9 + <%= profile_image(current_user.person, :portrait) %>
  10 + </div>
  11 +
  12 + <div class="star-profile-name">
  13 + <%= current_user.name %>
  14 + </div>
  15 + </div>
  16 +
  17 + <% if @rating_available %>
  18 + <div class="star-rate-form">
  19 + <div data-rate-url=<%= url_for controller: "communities_ratings_plugin_profile", :action => "rate" %>>
  20 + <div class="star-rate-text">
  21 + <%= @plugins.dispatch(:communities_ratings_plugin_star_message).collect { |content| instance_exec(&content) }.join("") %>
  22 + </div>
  23 +
  24 + <div class="star-container" data-min-rate="<%= @default_rate %>">
  25 +
  26 + <% (1..5).each do |rate_number| %>
  27 + <% if rate_number <= @default_rate %>
  28 + <div class="star-positive" data-star-rate="<%= rate_number %>"></div>
  29 + <% else %>
  30 + <div class="star-negative" data-star-rate="<%= rate_number %>"></div>
  31 + <% end %>
  32 + <% end %>
  33 + </div>
  34 +
  35 + <div class="star-notice star-hide">
  36 + <%= _("Rated as") %> <span></span> <%= _("stars") %>
  37 + </div>
  38 + </div>
  39 +
  40 + <div class="star-comment-container">
  41 + <%= form_for :comments do |c| %>
  42 + <div class="formfieldline formfield type-text">
  43 + <%= c.label :body, _('Comment (Optional):'), :class => "formlabel" %>
  44 + <%= c.text_area :body %>
  45 + </div>
  46 +
  47 + <%= @plugins.dispatch(:communities_ratings_plugin_comments_extra_fields).collect { |content| instance_exec(&content) }.join("") %>
  48 +
  49 + <div class="button-bar">
  50 + <%= submit_button(:save, _('Save'), :cancel => {controller: 'profile', action: 'index'}) %>
  51 + </div>
  52 +
  53 + <input type="hidden" id="selected-star-rate" name="community_rating_value" value="<%= @default_rate %>">
  54 + <input type="hidden" id="MINIMUM_STARS" name="community_rating_min_value" value="<%= @min_rate %>">
  55 + <% end %>
  56 + </div>
  57 +
  58 + <% elsif environment.communities_ratings_vote_once %>
  59 + <div class="star-rate-form rating-vote-once">
  60 + <%= _("Hi, #{current_user.name}! The administrators set that you can only vote once for this community.") %>
  61 + </div>
  62 + <% else %>
  63 + <div class="star-rate-form rating-cooldown">
  64 + <%= _("Hi, #{current_user.name}! The administrators set the minimum time of #{environment.communities_ratings_cooldown} hour(s) between each evaluation. You can take a ride into our web site while you wait for the next record.") %>
  65 + </div>
  66 + <% end %>
  67 +
  68 +
  69 + </div>
  70 +</div>
0 71 \ No newline at end of file
... ...
plugins/communities_ratings/views/communities_ratings_plugin_profile/new_rating.html.erb 0 → 100644
... ... @@ -0,0 +1,17 @@
  1 +<% if logged_in? %>
  2 + <%= render :partial => "new_rating_fields" %>
  3 +<% else %>
  4 + <div class="ratings-list">
  5 + <%= render :partial => "shared/make_report_block" %>
  6 + </div>
  7 +<% end %>
  8 +
  9 +<div class="ratings-list">
  10 + <% @users_ratings.each do |user_rate| %>
  11 + <%= render :partial => "shared/user_rating_container", :locals => {:user_rate => user_rate} %>
  12 + <% end %>
  13 +</div>
  14 +
  15 +<div id='pagination-profiles'>
  16 + <%= pagination_links @users_ratings, :param_name => 'npage' %>
  17 +</div>
0 18 \ No newline at end of file
... ...
plugins/communities_ratings/views/shared/_make_report_block.html.erb 0 → 100644
... ... @@ -0,0 +1,34 @@
  1 +<% logged_in_image = profile_image(current_user.person, :portrait) if current_user %>
  2 +<% logged_out_image = image_tag('plugins/communities_ratings/public/images/user-not-logged.png') %>
  3 +
  4 +<div class="make-report-block">
  5 + <div class="star-profile-information">
  6 + <div class="star-profile-image">
  7 + <%= logged_in? ? logged_in_image : logged_out_image %>
  8 + </div>
  9 +
  10 + <div class="star-profile-name">
  11 + <%= logged_in? ? current_user.person.name : _('User not logged *') %>
  12 + </div>
  13 + </div>
  14 +
  15 + <div class="make-report-container">
  16 + <div class="make-report-message">
  17 + <%= _('Report your experiences.') %>
  18 + </div>
  19 +
  20 + <div class="button-bar">
  21 + <% if logged_in? %>
  22 + <%= button('rate',_('Rate Community'), {:controller => 'communities_ratings_plugin_profile', :action => 'new_rating'}) %>
  23 + <% else %>
  24 + <%= button('rate',_('Rate Community'), {:controller => 'account', :action => 'login'}) %>
  25 + <% end %>
  26 + </div>
  27 +
  28 + <% unless logged_in? %>
  29 + <div class="alert">
  30 + <%= _('* You must be logged in to submit a report.') %>
  31 + </div>
  32 + <% end %>
  33 + </div>
  34 +</div>
0 35 \ No newline at end of file
... ...
plugins/communities_ratings/views/shared/_user_rating_container.html.erb 0 → 100644
... ... @@ -0,0 +1,33 @@
  1 +<div class="user-rating-block">
  2 + <div class="star-profile-information">
  3 + <div class="star-profile-image">
  4 + <%= profile_image(user_rate.person, :portrait) %>
  5 + </div>
  6 +
  7 + <div class="star-profile-name">
  8 + <%= user_rate.person.name %>
  9 + </div>
  10 + </div>
  11 +
  12 + <div class="user-testimony-container">
  13 + <div class="testimony-rate-date">
  14 + <%= time_ago_in_words(user_rate.created_at) %>
  15 + </div>
  16 +
  17 + <div class="star-container">
  18 + <% (1..5).each do |rate_number| %>
  19 + <% if rate_number <= user_rate.value %>
  20 + <div class="small-star-positive"></div>
  21 + <% else %>
  22 + <div class="small-star-negative"></div>
  23 + <% end %>
  24 + <% end %>
  25 + </div>
  26 +
  27 + <div class="user-testimony">
  28 + <%= user_rate.comment.body unless user_rate.comment.nil? %>
  29 + </div>
  30 +
  31 + <%= @plugins.dispatch(:communities_ratings_plugin_extra_fields_show_data, user_rate).collect { |content| instance_exec(&content) }.join("") %>
  32 + </div>
  33 +</div>
... ...