diff --git a/CHANGELOG.md b/CHANGELOG.md index 26b026257..397c51f1b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -26,6 +26,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - Improve budget investment form https://github.com/consul/consul/pull/2280 - Prevent edition of investments if budget is in the final phase https://github.com/consul/consul/pull/2223 - Split 'routes.rb' file into multiple small files https://github.com/consul/consul/pull/1908 +- Design Improvements https://github.com/consul/consul/pull/2327 ### Deprecated - Budget's `description_*` columns will be erased from database in next release. Please run rake task `budgets:phases:generate_missing` to migrate them. Details at Warning section of https://github.com/consul/consul/pull/2323 diff --git a/Gemfile b/Gemfile index ed9d6fe56..a0dacb7bf 100644 --- a/Gemfile +++ b/Gemfile @@ -20,7 +20,7 @@ gem 'devise_security_extension', '~> 0.10.0' gem 'foundation-rails', '~> 6.2.4.0' gem 'foundation_rails_helper', '~> 2.0.0' gem 'graphiql-rails', '~> 1.4.1' -gem 'graphql', '~> 1.7.7' +gem 'graphql', '~> 1.7.8' gem 'groupdate', '~> 3.2.0' gem 'initialjs-rails', '~> 0.2.0.5' gem 'invisible_captcha', '~> 0.10.0' @@ -44,7 +44,7 @@ gem 'rollbar', '~> 2.15.5' gem 'rubyzip', '~> 1.2.0' gem 'sass-rails', '~> 5.0', '>= 5.0.4' gem 'savon', '~> 2.11.1' -gem 'sitemap_generator', '~> 6.0.0' +gem 'sitemap_generator', '~> 6.0.1' gem 'social-share-button', '~> 1.1' gem 'sprockets', '~> 3.7.1' gem 'turbolinks', '~> 2.5.3' @@ -66,7 +66,7 @@ group :development, :test do gem 'i18n-tasks', '~> 0.9.15' gem 'knapsack_pro', '~> 0.53.0' gem 'launchy', '~> 2.4.3' - gem 'letter_opener_web', '~> 1.3.1' + gem 'letter_opener_web', '~> 1.3.2' gem 'quiet_assets', '~> 1.1.0' gem 'spring', '~> 2.0.1' gem 'spring-commands-rspec', '~> 1.0.4' diff --git a/Gemfile.lock b/Gemfile.lock index 16770f1bc..0be37f902 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -522,7 +522,7 @@ DEPENDENCIES foundation-rails (~> 6.2.4.0) foundation_rails_helper (~> 2.0.0) graphiql-rails (~> 1.4.1) - graphql (~> 1.7.7) + graphql (~> 1.7.8) groupdate (~> 3.2.0) i18n-tasks (~> 0.9.15) initialjs-rails (~> 0.2.0.5) @@ -533,7 +533,7 @@ DEPENDENCIES kaminari (~> 1.1.1) knapsack_pro (~> 0.53.0) launchy (~> 2.4.3) - letter_opener_web (~> 1.3.1) + letter_opener_web (~> 1.3.2) mdl (~> 0.4.0) newrelic_rpm (~> 4.1.0.333) omniauth (~> 1.8.1) @@ -561,7 +561,7 @@ DEPENDENCIES sass-rails (~> 5.0, >= 5.0.4) savon (~> 2.11.1) scss_lint (~> 0.54.0) - sitemap_generator (~> 6.0.0) + sitemap_generator (~> 6.0.1) social-share-button (~> 1.1) spring (~> 2.0.1) spring-commands-rspec (~> 1.0.4) diff --git a/app/assets/javascripts/map.js.coffee b/app/assets/javascripts/map.js.coffee index 797232c4f..28ac34f29 100644 --- a/app/assets/javascripts/map.js.coffee +++ b/app/assets/javascripts/map.js.coffee @@ -83,4 +83,4 @@ App.Map = toogleMap: -> $('.map').toggle() - $('.location-map-remove-marker-button').toggle() \ No newline at end of file + $('.js-location-map-remove-marker').toggle() \ No newline at end of file diff --git a/app/assets/stylesheets/layout.scss b/app/assets/stylesheets/layout.scss index e47ba0343..854d6b1e6 100644 --- a/app/assets/stylesheets/layout.scss +++ b/app/assets/stylesheets/layout.scss @@ -22,6 +22,7 @@ // 20. Documents // 21. Related content // 22. Images +// 23. Maps // // 01. Global styles @@ -2427,10 +2428,6 @@ table { margin-bottom: 0 !important; padding: $line-height / 2; - &:first-child { - border-top: 1px solid $border; - } - @include breakpoint(medium) { .score-actions { @@ -2439,6 +2436,10 @@ table { } } + &:first-child { + border-top: 1px solid $border; + } + &:hover { background: #f9f9f9; @@ -2478,8 +2479,8 @@ table { position: relative; text-decoration: none; - &.score-positive:before, - &.score-negative:before { + &.score-positive::before, + &.score-negative::before { font-family: 'icons'; left: 0; position: absolute; @@ -2488,7 +2489,7 @@ table { &.score-positive { color: $color-success; - &:before { + &::before { color: $color-success; content: '\6c'; } @@ -2497,7 +2498,7 @@ table { &.score-negative { color: $color-alert; - &:before { + &::before { color: $color-alert; content: '\76'; } @@ -2511,3 +2512,28 @@ table { .images .button { margin-top: $line-height / 2; } + +// 23. Maps +// ----------------- + +.location-map-remove-marker { + border-bottom: 1px dotted #cf2a0e; + color: $delete; + display: inline-block; + margin-top: $line-height / 2; + + &:hover, + &:active, + &:focus { + border-bottom: 1px solid #cf2a0e; + color: #cf2a0e; + text-decoration: none; + } +} + +.leaflet-bar a { + + &.leaflet-disabled { + color: #525252 !important; + } +} diff --git a/app/assets/stylesheets/participation.scss b/app/assets/stylesheets/participation.scss index bc8633ec9..606de72f3 100644 --- a/app/assets/stylesheets/participation.scss +++ b/app/assets/stylesheets/participation.scss @@ -339,6 +339,7 @@ .topic-show, .milestone-content { + h1, p { word-wrap: break-word; } diff --git a/app/controllers/admin/budgets_controller.rb b/app/controllers/admin/budgets_controller.rb index 161610f58..04b8ea0b2 100644 --- a/app/controllers/admin/budgets_controller.rb +++ b/app/controllers/admin/budgets_controller.rb @@ -2,7 +2,7 @@ class Admin::BudgetsController < Admin::BaseController include FeatureFlags feature_flag :budgets - has_filters %w{current finished}, only: :index + has_filters %w{open finished}, only: :index load_and_authorize_resource diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index 495a25314..f03a05239 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -25,6 +25,7 @@ class ApplicationController < ActionController::Base layout :set_layout respond_to :html + helper_method :current_budget private @@ -120,4 +121,8 @@ class ApplicationController < ActionController::Base params[:filter] ||= "selected" end end + + def current_budget + Budget.current + end end diff --git a/app/controllers/management/budgets_controller.rb b/app/controllers/management/budgets_controller.rb index dd7259c99..470d1f9fd 100644 --- a/app/controllers/management/budgets_controller.rb +++ b/app/controllers/management/budgets_controller.rb @@ -19,7 +19,7 @@ class Management::BudgetsController < Management::BaseController end def print_investments - @budgets = Budget.current.order(created_at: :desc).page(params[:page]) + @budget = Budget.current end private diff --git a/app/controllers/valuation/budgets_controller.rb b/app/controllers/valuation/budgets_controller.rb index 744b0d4bf..cf99f95e3 100644 --- a/app/controllers/valuation/budgets_controller.rb +++ b/app/controllers/valuation/budgets_controller.rb @@ -5,10 +5,10 @@ class Valuation::BudgetsController < Valuation::BaseController load_and_authorize_resource def index - @budgets = @budgets.current.order(created_at: :desc).page(params[:page]) - @investments_with_valuation_open = {} - @budgets.each do |b| - @investments_with_valuation_open[b.id] = b.investments + @budget = Budget.current + if @budget.present? + @investments_with_valuation_open = {} + @investments_with_valuation_open = @budget.investments .by_valuator(current_user.valuator.try(:id)) .valuation_open .count diff --git a/app/helpers/map_locations_helper.rb b/app/helpers/map_locations_helper.rb index ae45e7c1d..85b02e28c 100644 --- a/app/helpers/map_locations_helper.rb +++ b/app/helpers/map_locations_helper.rb @@ -34,11 +34,11 @@ module MapLocationsHelper end def map_location_remove_marker(map_location, text) - content_tag :div, class: "text-right" do + content_tag :div, class: "margin-bottom" do content_tag :a, id: map_location_remove_marker_link_id(map_location), href: "#", - class: "location-map-remove-marker-button delete" do + class: "js-location-map-remove-marker location-map-remove-marker" do text end end diff --git a/app/models/budget.rb b/app/models/budget.rb index aba7b04ae..ceaffb19a 100644 --- a/app/models/budget.rb +++ b/app/models/budget.rb @@ -29,7 +29,12 @@ class Budget < ActiveRecord::Base scope :balloting, -> { where(phase: "balloting") } scope :reviewing_ballots, -> { where(phase: "reviewing_ballots") } scope :finished, -> { where(phase: "finished") } - scope :current, -> { where.not(phase: "finished") } + + scope :open, -> { where.not(phase: "finished") } + + def self.current + where.not(phase: "drafting").last + end def current_phase phases.send(phase) @@ -99,10 +104,6 @@ class Budget < ActiveRecord::Base balloting_process? || finished? end - def current? - !finished? - end - def heading_price(heading) heading_ids.include?(heading.id) ? heading.price : -1 end diff --git a/app/views/admin/budget_investments/_investments.html.erb b/app/views/admin/budget_investments/_investments.html.erb index 55ccf7f30..a60e2ac11 100644 --- a/app/views/admin/budget_investments/_investments.html.erb +++ b/app/views/admin/budget_investments/_investments.html.erb @@ -4,7 +4,7 @@ <% if @investments.any? %>

<%= page_entries_info @investments %>

- +
diff --git a/app/views/management/budgets/print_investments.html.erb b/app/views/management/budgets/print_investments.html.erb index bc115ea3d..d5be7c1ff 100644 --- a/app/views/management/budgets/print_investments.html.erb +++ b/app/views/management/budgets/print_investments.html.erb @@ -1,12 +1,10 @@
<%= t("admin.budget_investments.index.table_id") %>
-<% @budgets.each do |budget| %> - - - + + + -<% end %>
<%= budget.name %><%= budget.translated_phase %>
<%= @budget.name %><%= @budget.translated_phase %> <%= link_to t("management.budgets.print_investments"), - print_management_budget_investments_path(budget) %> + print_management_budget_investments_path(@budget) %>
diff --git a/app/views/valuation/budgets/index.html.erb b/app/views/valuation/budgets/index.html.erb index 6d65f9ee6..f1fd302b6 100644 --- a/app/views/valuation/budgets/index.html.erb +++ b/app/views/valuation/budgets/index.html.erb @@ -1,7 +1,5 @@

<%= t("valuation.budgets.index.title") %>

-

<%= page_entries_info @budgets %>

- @@ -12,25 +10,21 @@ - <% @budgets.each do |budget| %> - - - - - - - <% end %> + + + + + +
- <%= budget.name %> - - <%= t("budgets.phase.#{budget.phase}") %> - - <%= @investments_with_valuation_open[budget.id] %> - - <%= link_to t("valuation.budgets.index.evaluate"), - valuation_budget_budget_investments_path(budget_id: budget.id), - class: "button hollow expanded" %> -
+ <%= @budget.name %> + + <%= t("budgets.phase.#{@budget.phase}") %> + + <%= @investments_with_valuation_open %> + + <%= link_to t("valuation.budgets.index.evaluate"), + valuation_budget_budget_investments_path(budget_id: @budget.id), + class: "button hollow expanded" %> +
- -<%= paginate @budgets %> diff --git a/config/locales/en/activerecord.yml b/config/locales/en/activerecord.yml index 39d0e022a..931d7c62b 100644 --- a/config/locales/en/activerecord.yml +++ b/config/locales/en/activerecord.yml @@ -117,8 +117,8 @@ en: external_url: "Link to additional documentation" heading_id: "Heading" title: "Title" - location: "Location" - organization_name: "If you are proposing in the name of a collective/organization, write its name" + location: "Location (optional)" + organization_name: "If you are proposing in the name of a collective/organization, or on behalf of more people, write its name" image: "Proposal descriptive image" image_title: "Image title" budget/investment/milestone: diff --git a/config/locales/en/budgets.yml b/config/locales/en/budgets.yml index a7dd62016..7f25d243f 100644 --- a/config/locales/en/budgets.yml +++ b/config/locales/en/budgets.yml @@ -104,7 +104,7 @@ en: unfeasibility_explanation: Unfeasibility explanation code_html: 'Investment project code: %{code}' location_html: 'Location: %{location}' - organization_name_html: 'Organization: %{name}' + organization_name_html: 'Proposed on behalf of: %{name}' share: Share title: Investment project supports: Supports diff --git a/config/locales/es/activerecord.yml b/config/locales/es/activerecord.yml index 18296b7bf..522ecefa9 100644 --- a/config/locales/es/activerecord.yml +++ b/config/locales/es/activerecord.yml @@ -113,7 +113,7 @@ es: external_url: "Enlace a documentación adicional" location: "Ubicación" administrator_id: "Administrador" - organization_name: "Si estás proponiendo en nombre de una organización o colectivo, escribe su nombre" + organization_name: "Si estás proponiendo en nombre de una organización o colectivo, o en nombre de más gente, escribe su nombre" image: "Imagen descriptiva de la propuesta de inversión" image_title: "Título de la imagen" budget/heading: diff --git a/config/locales/es/budgets.yml b/config/locales/es/budgets.yml index 0027b1241..c7f84a3a9 100644 --- a/config/locales/es/budgets.yml +++ b/config/locales/es/budgets.yml @@ -59,7 +59,7 @@ es: tags_placeholder: "Escribe las etiquetas que desees separadas por una coma (',')" map_location: "Ubicación en el mapa" map_location_instructions: "Navega por el mapa hasta la ubicación y coloca el marcador." - map_remove_marker: "Eliminar el marcador" + map_remove_marker: "Eliminar marcador en el mapa" location: "Información adicional de la ubicación" index: title: Presupuestos participativos @@ -104,7 +104,7 @@ es: unfeasibility_explanation: Informe de inviabilidad code_html: 'Código propuesta de gasto: %{code}' location_html: 'Ubicación: %{location}' - organization_name_html: 'Organización: %{name}' + organization_name_html: 'Propuesto en nombre de: %{name}' share: Compartir title: Proyecto de inversión supports: Apoyos diff --git a/config/locales/es/general.yml b/config/locales/es/general.yml index c54875369..722b70fc3 100644 --- a/config/locales/es/general.yml +++ b/config/locales/es/general.yml @@ -338,7 +338,7 @@ es: tags_placeholder: "Escribe las etiquetas que desees separadas por una coma (',')" map_location: "Ubicación en el mapa" map_location_instructions: "Navega por el mapa hasta la ubicación y coloca el marcador." - map_remove_marker: "Eliminar el marcador" + map_remove_marker: "Eliminar marcador en el mapa" map_skip_checkbox: "Esta propuesta no tiene una ubicación concreta o no la conozco." index: featured_proposals: Destacadas diff --git a/config/secrets.yml.example b/config/secrets.yml.example index 3939d7b80..5157e350c 100644 --- a/config/secrets.yml.example +++ b/config/secrets.yml.example @@ -17,11 +17,11 @@ apis: &apis http_basic_auth: &http_basic_auth http_basic_auth: true - development: http_basic_username: "dev" http_basic_password: "pass" <<: *default + <<: *maps test: <<: *default diff --git a/spec/controllers/application_controller_spec.rb b/spec/controllers/application_controller_spec.rb new file mode 100644 index 000000000..f11068b65 --- /dev/null +++ b/spec/controllers/application_controller_spec.rb @@ -0,0 +1,19 @@ +require 'rails_helper' + +describe ApplicationController do + + describe "#current_budget" do + + it "returns the last budget that is not in draft phase" do + old_budget = create(:budget, phase: "finished", created_at: 2.years.ago) + previous_budget = create(:budget, phase: "accepting", created_at: 1.year.ago) + current_budget = create(:budget, phase: "accepting", created_at: 1.month.ago) + next_budget = create(:budget, phase: "drafting", created_at: 1.week.ago) + + budget = subject.instance_eval{ current_budget } + expect(budget).to eq(current_budget) + end + + end + +end \ No newline at end of file diff --git a/spec/features/management/budget_investments_spec.rb b/spec/features/management/budget_investments_spec.rb index f1ced7334..6132c40cd 100644 --- a/spec/features/management/budget_investments_spec.rb +++ b/spec/features/management/budget_investments_spec.rb @@ -259,9 +259,10 @@ feature 'Budget Investments' do context "Printing" do scenario 'Printing budget investments' do - 16.times { create(:budget_investment, budget: @budget) } + 16.times { create(:budget_investment, budget: @budget, heading: @heading) } click_link "Print Budget Investments" + expect(page).to have_content(@budget.name) within "#budget_#{@budget.id}" do click_link "Print Budget Investments" @@ -273,15 +274,17 @@ feature 'Budget Investments' do scenario "Filtering budget investments by heading to be printed", :js do district_9 = create(:budget_heading, group: @group, name: "District Nine") + another_heading = create(:budget_heading, group: @group) low_investment = create(:budget_investment, budget: @budget, title: 'Nuke district 9', heading: district_9, cached_votes_up: 1) mid_investment = create(:budget_investment, budget: @budget, title: 'Change district 9', heading: district_9, cached_votes_up: 10) top_investment = create(:budget_investment, budget: @budget, title: 'Destroy district 9', heading: district_9, cached_votes_up: 100) - unvoted_investment = create(:budget_investment, budget: @budget, title: 'Add new districts to the city') + unvoted_investment = create(:budget_investment, budget: @budget, heading: another_heading, title: 'Add new districts to the city') user = create(:user, :level_two) login_managed_user(user) click_link "Print Budget Investments" + expect(page).to have_content(@budget.name) within "#budget_#{@budget.id}" do click_link "Print Budget Investments" diff --git a/spec/features/valuation/budgets_spec.rb b/spec/features/valuation/budgets_spec.rb index ec3b780ab..4fd821c7e 100644 --- a/spec/features/valuation/budgets_spec.rb +++ b/spec/features/valuation/budgets_spec.rb @@ -24,18 +24,15 @@ feature 'Valuation budgets' do end scenario 'Filters by phase' do - budget1 = create(:budget) - budget2 = create(:budget, :accepting) - budget3 = create(:budget, :selecting) - budget4 = create(:budget, :balloting) - budget5 = create(:budget, :finished) + budget1 = create(:budget, :finished) + budget2 = create(:budget, :finished) + budget3 = create(:budget, :accepting) visit valuation_budgets_path - expect(page).to have_content(budget1.name) - expect(page).to have_content(budget2.name) + + expect(page).to_not have_content(budget1.name) + expect(page).to_not have_content(budget2.name) expect(page).to have_content(budget3.name) - expect(page).to have_content(budget4.name) - expect(page).not_to have_content(budget5.name) end end diff --git a/spec/features/valuation_spec.rb b/spec/features/valuation_spec.rb index c004f0773..1cb95d23d 100644 --- a/spec/features/valuation_spec.rb +++ b/spec/features/valuation_spec.rb @@ -66,6 +66,8 @@ feature 'Valuation' do scenario 'Access as a valuator is authorized' do create(:valuator, user: user) + create(:budget) + login_as(user) visit root_path @@ -78,6 +80,8 @@ feature 'Valuation' do scenario 'Access as an administrator is authorized' do create(:administrator, user: user) + create(:budget) + login_as(user) visit root_path @@ -90,6 +94,8 @@ feature 'Valuation' do scenario "Valuation access links" do create(:valuator, user: user) + create(:budget) + login_as(user) visit root_path @@ -100,6 +106,8 @@ feature 'Valuation' do scenario 'Valuation dashboard' do create(:valuator, user: user) + create(:budget) + login_as(user) visit root_path diff --git a/spec/models/budget_spec.rb b/spec/models/budget_spec.rb index 7369d15ac..fa0c6ed57 100644 --- a/spec/models/budget_spec.rb +++ b/spec/models/budget_spec.rb @@ -118,6 +118,43 @@ describe Budget do end end + describe "#current" do + + it "returns nil if there is only one budget and it is still in drafting phase" do + budget = create(:budget, phase: "drafting") + + expect(Budget.current).to eq(nil) + end + + it "returns the budget if there is only one and not in drafting phase" do + budget = create(:budget, phase: "accepting") + + expect(Budget.current).to eq(budget) + end + + it "returns the last budget created that is not in drafting phase" do + old_budget = create(:budget, phase: "finished", created_at: 2.years.ago) + previous_budget = create(:budget, phase: "accepting", created_at: 1.year.ago) + current_budget = create(:budget, phase: "accepting", created_at: 1.month.ago) + next_budget = create(:budget, phase: "drafting", created_at: 1.week.ago) + + expect(Budget.current).to eq(current_budget) + end + + end + + describe "#open" do + + it "returns all budgets that are not in the finished phase" do + phases = Budget::PHASES - ["finished"] + phases.each do |phase| + budget = create(:budget, phase: phase) + expect(Budget.open).to include(budget) + end + end + + end + describe "heading_price" do let(:group) { create(:budget_group, budget: budget) }