Merge pull request #4041 from consul/table_actions

Refactor code to render admin table actions
This commit is contained in:
Javi Martín
2020-10-21 13:35:36 +02:00
committed by GitHub
95 changed files with 771 additions and 628 deletions

View File

@@ -59,6 +59,7 @@ gem "translator-text", "~> 0.1.0"
gem "turbolinks", "~> 5.2.1"
gem "turnout", "~> 2.5.0"
gem "uglifier", "~> 4.2.0"
gem "view_component", "~> 2.19.1", require: "view_component/engine"
gem "whenever", "~> 1.0.0", require: false
gem "wicked_pdf", "~> 2.1.0"
gem "wkhtmltopdf-binary", "~> 0.12.4"

View File

@@ -608,6 +608,8 @@ GEM
uniform_notifier (1.13.0)
user_agent_parser (2.6.0)
uuidtools (2.1.5)
view_component (2.19.1)
activesupport (>= 5.0.0, < 7.0)
warden (1.2.9)
rack (>= 2.0.9)
wasabi (3.5.0)
@@ -728,6 +730,7 @@ DEPENDENCIES
turbolinks (~> 5.2.1)
turnout (~> 2.5.0)
uglifier (~> 4.2.0)
view_component (~> 2.19.1)
web-console (~> 3.7.0)
webdrivers (~> 4.4.1)
whenever (~> 1.0.0)

View File

@@ -236,16 +236,8 @@ $sidebar-active: #f4fcd0;
table-layout: fixed;
}
[type="submit"] ~ a,
a ~ a {
margin-left: 0;
margin-right: 0;
margin-top: $line-height / 2;
@include breakpoint(medium) {
margin-left: $line-height / 2;
margin-top: 0;
}
[type="submit"] ~ a {
margin-left: $line-height / 2;
}
}

View File

@@ -0,0 +1,12 @@
.admin .table-actions {
align-items: baseline;
display: flex;
> :not(:first-child) {
margin-left: $line-height / 2;
}
> p {
align-self: flex-start;
}
}

View File

@@ -27,3 +27,4 @@
@import "jquery-ui/sortable";
@import "leaflet";
@import "sticky_overrides";
@import "admin/*";

View File

@@ -0,0 +1,11 @@
<%= render Admin::TableActionsComponent.new(budget, actions: [:edit], edit_text: t("admin.budgets.index.edit_budget")) do %>
<%= link_to t("admin.budgets.index.budget_investments"),
admin_budget_budget_investments_path(budget_id: budget.id),
class: "button hollow medium" %>
<%= link_to t("admin.budgets.index.edit_groups"), admin_budget_groups_path(budget) %>
<% if budget.poll.present? %>
<%= link_to t("admin.budgets.index.admin_ballots"), admin_poll_booth_assignments_path(budget.poll) %>
<% else %>
<%= link_to_create_budget_poll %>
<% end %>
<% end %>

View File

@@ -0,0 +1,21 @@
class Admin::Budgets::TableActionsComponent < ApplicationComponent
attr_reader :budget
def initialize(budget)
@budget = budget
end
private
def link_to_create_budget_poll
balloting_phase = budget.phases.find_by(kind: "balloting")
link_to t("admin.budgets.index.admin_ballots"),
admin_polls_path(poll: {
name: budget.name,
budget_id: budget.id,
starts_at: balloting_phase.starts_at,
ends_at: balloting_phase.ends_at }),
method: :post
end
end

View File

@@ -0,0 +1,12 @@
<%= render Admin::TableActionsComponent.new(actions: []) do %>
<%= link_to restore_text, restore_path,
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless record.confirmed_hide? %>
<%= link_to confirm_hide_text, confirm_hide_path,
method: :put,
class: "button" %>
<% end %>
<% end %>

View File

@@ -0,0 +1,34 @@
class Admin::HiddenTableActionsComponent < ApplicationComponent
attr_reader :record
def initialize(record)
@record = record
end
private
def restore_text
t("admin.actions.restore")
end
def restore_path
action_path(:restore)
end
def confirm_hide_text
t("admin.actions.confirm_hide")
end
def confirm_hide_path
action_path(:confirm_hide)
end
def action_path(action)
url_for({
controller: "admin/hidden_#{record.model_name.plural}",
action: action,
id: record,
only_path: true
}.merge(request.query_parameters))
end
end

View File

@@ -0,0 +1,13 @@
<%= render Admin::TableActionsComponent.new(actions: []) do %>
<% if can_verify? %>
<%= link_to t("admin.organizations.index.verify"),
verify_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button success small-5" %>
<% end %>
<% if can_reject? %>
<%= link_to t("admin.organizations.index.reject"),
reject_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button hollow alert small-5" %>
<% end %>
<% end %>

View File

@@ -0,0 +1,18 @@
class Admin::Organizations::TableActionsComponent < ApplicationComponent
delegate :can?, to: :controller
attr_reader :organization
def initialize(organization)
@organization = organization
end
private
def can_verify?
can? :verify, organization
end
def can_reject?
can? :reject, organization
end
end

View File

@@ -0,0 +1,36 @@
<%= tag.table options do %>
<thead>
<tr>
<th><%= t("admin.poll_officers.officer.name") %></th>
<th><%= t("admin.poll_officers.officer.email") %></th>
<th class="small-3"><%= t("admin.actions.actions") %></th>
</tr>
</thead>
<tbody>
<% officers.each do |officer| %>
<tr>
<td>
<%= officer.name %>
</td>
<td>
<%= officer.email %>
</td>
<td>
<% if officer.persisted? %>
<%= render Admin::TableActionsComponent.new(officer,
actions: [:destroy],
destroy_text: t("admin.poll_officers.officer.delete")
) %>
<% else %>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.poll_officers.officer.add"),
add_user_path(officer),
method: :post,
class: "button success expanded" %>
<% end %>
<% end %>
</td>
</tr>
<% end %>
</tbody>
<% end %>

View File

@@ -0,0 +1,18 @@
class Admin::Poll::Officers::OfficersComponent < ApplicationComponent
attr_reader :officers, :options
def initialize(officers, **options)
@officers = officers
@options = options
end
private
def add_user_path(officer)
{
controller: "admin/poll/officers",
action: :create,
user_id: officer.user_id
}
end
end

View File

@@ -0,0 +1,7 @@
<% if already_has_role? %>
<%= render Admin::TableActionsComponent.new(record, actions: actions) %>
<% else %>
<%= render Admin::TableActionsComponent.new(actions: []) do %>
<%= link_to add_user_text, add_user_path, method: :post, class: "button success expanded" %>
<% end %>
<% end %>

View File

@@ -0,0 +1,30 @@
class Admin::Roles::TableActionsComponent < ApplicationComponent
attr_reader :record, :actions
def initialize(record, actions: [:destroy])
@record = record
@actions = actions
end
private
def role
record.class.name.tableize
end
def already_has_role?
record.persisted?
end
def add_user_text
t("admin.#{role}.#{role.singularize}.add")
end
def add_user_path
{
controller: "admin/#{role}",
action: :create,
user_id: record.user
}
end
end

View File

@@ -0,0 +1,11 @@
<div class="table-actions">
<%= content %>
<% if actions.include?(:edit) %>
<%= link_to edit_text, edit_path, edit_options %>
<% end %>
<% if actions.include?(:destroy) %>
<%= link_to destroy_text, destroy_path, destroy_options %>
<% end %>
</div>

View File

@@ -0,0 +1,46 @@
class Admin::TableActionsComponent < ApplicationComponent
attr_reader :record, :options
def initialize(record = nil, **options)
@record = record
@options = options
end
private
def actions
options[:actions] || [:edit, :destroy]
end
def edit_text
options[:edit_text] || t("admin.actions.edit")
end
def edit_path
options[:edit_path] || admin_polymorphic_path(record, action: :edit)
end
def edit_options
{ class: "button hollow" }.merge(options[:edit_options] || {})
end
def destroy_text
options[:destroy_text] || t("admin.actions.delete")
end
def destroy_path
options[:destroy_path] || admin_polymorphic_path(record)
end
def destroy_options
{
method: :delete,
class: "button hollow alert",
data: { confirm: destroy_confirmation }
}.merge(options[:destroy_options] || {})
end
def destroy_confirmation
options[:destroy_confirmation] || t("admin.actions.confirm")
end
end

View File

@@ -0,0 +1,2 @@
class ApplicationComponent < ViewComponent::Base
end

View File

@@ -1,5 +1,5 @@
class Admin::Poll::BoothAssignmentsController < Admin::Poll::BaseController
before_action :load_poll, except: [:create, :destroy]
before_action :load_poll, except: [:create]
def index
@booth_assignments = @poll.booth_assignments.includes(:booth).order("poll_booths.name")
@@ -36,9 +36,8 @@ class Admin::Poll::BoothAssignmentsController < Admin::Poll::BaseController
end
def destroy
@poll = Poll.find(booth_assignment_params[:poll_id])
@booth = Poll::Booth.find(booth_assignment_params[:booth_id])
@booth_assignment = ::Poll::BoothAssignment.find(params[:id])
@booth_assignment = @poll.booth_assignments.find(params[:id])
@booth = @booth_assignment.booth
@booth_assignment.destroy!

View File

@@ -97,18 +97,6 @@ module BudgetsHelper
investment.group.headings.count > 1
end
def link_to_create_budget_poll(budget)
balloting_phase = budget.phases.find_by(kind: "balloting")
link_to t("admin.budgets.index.admin_ballots"),
admin_polls_path(poll: {
name: budget.name,
budget_id: budget.id,
starts_at: balloting_phase.starts_at,
ends_at: balloting_phase.ends_at }),
method: :post
end
def budget_subnav_items_for(budget)
{
results: t("budgets.results.link"),

View File

@@ -30,27 +30,17 @@
</td>
<td>
<% if admin_notification.draft? %>
<div class="small-4 column">
<%= link_to t("admin.admin_notifications.index.edit"),
edit_admin_admin_notification_path(admin_notification),
class: "button expanded hollow" %>
</div>
<div class="small-4 column">
<%= link_to t("admin.admin_notifications.index.delete"),
admin_admin_notification_path(admin_notification),
method: :delete, class: "button expanded hollow alert" %>
</div>
<div class="small-4 column">
<%= link_to t("admin.admin_notifications.index.preview"),
admin_admin_notification_path(admin_notification),
class: "button expanded" %>
</div>
<%= render Admin::TableActionsComponent.new(admin_notification) do |actions| %>
<%= actions.link_to t("admin.admin_notifications.index.preview"),
admin_admin_notification_path(admin_notification),
class: "button" %>
<% end %>
<% else %>
<div class="small-4 column">
<%= link_to t("admin.admin_notifications.index.view"),
admin_admin_notification_path(admin_notification),
class: "button expanded" %>
</div>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.admin_notifications.index.view"),
admin_admin_notification_path(admin_notification),
class: "button" %>
<% end %>
<% end %>
</td>
</tr>

View File

@@ -29,13 +29,10 @@
<%= administrator.description %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_administrator_path(administrator),
class: "button hollow" %>
<%= link_to t("admin.administrators.administrator.delete"),
admin_administrator_path(administrator),
method: :delete,
class: "button hollow alert" %>
<%= render Admin::Roles::TableActionsComponent.new(
administrator,
actions: [:edit, :destroy]
) %>
</td>
</tr>
<% end %>

View File

@@ -17,20 +17,8 @@
<tr>
<td><%= user.name %></td>
<td><%= user.email %></td>
<td class="text-right">
<% if user.administrator? && user.administrator.persisted? %>
<%= link_to t("admin.administrators.administrator.delete"),
admin_administrator_path(user.administrator),
method: :delete,
class: "button hollow alert expanded" %>
<% else %>
<%= link_to t("admin.administrators.administrator.add"),
{ controller: "admin/administrators",
action: :create,
user_id: user },
method: :post,
class: "button success expanded" %>
<% end %>
<td>
<%= render Admin::Roles::TableActionsComponent.new(user.administrator || user.build_administrator) %>
</td>
</tr>
<% end %>

View File

@@ -34,9 +34,11 @@
<%= audit.user&.name %>
</td>
<td>
<%= link_to t("shared.show"),
admin_polymorphic_path(audit),
class: "button hollow primary" %>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("shared.show"),
admin_polymorphic_path(audit),
class: "button hollow primary" %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -21,15 +21,10 @@
<td><%= banner.post_started_at %></td>
<td><%= banner.post_ended_at %></td>
<td>
<div class="small-12 medium-6 column">
<%= link_to t("admin.banners.index.edit"), edit_admin_banner_path(banner),
class: "button hollow expanded" %>
</div>
<div class="small-12 medium-6 column">
<%= link_to t("admin.banners.index.delete"), admin_banner_path(banner),
method: :delete,
class: "button hollow alert expanded" %>
</div>
<%= render Admin::TableActionsComponent.new(banner,
edit_text: t("admin.banners.index.edit"),
destroy_text: t("admin.banners.index.delete")
) %>
</td>
</tr>
<tr>

View File

@@ -16,26 +16,20 @@
<th><%= t("admin.budget_groups.name") %></th>
<th><%= Budget::Group.human_attribute_name(:max_votable_headings) %></th>
<th><%= t("admin.budget_groups.headings_name") %></th>
<th><%= t("admin.budget_groups.headings_edit") %></th>
<th><%= t("admin.actions.actions") %></th>
</tr>
</thead>
<tbody>
<% @groups.each do |group| %>
<tr id="<%= dom_id(group) %>">
<td><%= link_to group.name, edit_admin_budget_group_path(@budget, group) %></td>
<td><%= group.name %></td>
<td><%= group.max_votable_headings %></td>
<td><%= group.headings.count %></td>
<td><%= link_to t("admin.budget_groups.headings_manage"),
admin_budget_group_headings_path(@budget, group) %></td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_budget_group_path(@budget, group),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_budget_group_path(@budget, group),
method: :delete,
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(group) do |actions| %>
<%= actions.link_to t("admin.budget_groups.headings_manage"),
admin_budget_group_headings_path(@budget, group) %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -24,7 +24,7 @@
<tbody>
<% @headings.each do |heading| %>
<tr id="<%= dom_id(heading) %>" class="heading">
<td><%= link_to heading.name, edit_admin_budget_group_heading_path(@budget, @group, heading) %></td>
<td><%= heading.name %></td>
<td><%= @budget.formatted_heading_price(heading) %></td>
<% if @budget.approval_voting? %>
<td><%= heading.max_ballot_lines %></td>
@@ -34,13 +34,7 @@
<%= heading.allow_custom_content ? t("admin.shared.true_value") : t("admin.shared.false_value") %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_budget_group_heading_path(@budget, @group, heading),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_budget_group_heading_path(@budget, @group, heading),
method: :delete,
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(heading) %>
</td>
</tr>
<% end %>

View File

@@ -14,10 +14,7 @@
<tr>
<th><%= t("admin.budgets.index.table_name") %></th>
<th><%= t("admin.budgets.index.table_phase") %></th>
<th><%= t("admin.budgets.index.table_investments") %></th>
<th><%= t("admin.budgets.index.table_edit_groups") %></th>
<th><%= t("admin.budgets.index.table_edit_budget") %></th>
<th><%= t("admin.budgets.index.table_admin_ballots") %></th>
<th><%= t("admin.actions.actions") %></th>
</tr>
</thead>
<tbody>
@@ -30,22 +27,7 @@
<%= t("budgets.phase.#{budget.phase}") %>
</td>
<td>
<%= link_to t("admin.budgets.index.budget_investments"),
admin_budget_budget_investments_path(budget_id: budget.id),
class: "button hollow medium" %>
</td>
<td class="small">
<%= link_to t("admin.budgets.index.edit_groups"), admin_budget_groups_path(budget) %>
</td>
<td class="small">
<%= link_to t("admin.budgets.index.edit_budget"), edit_admin_budget_path(budget) %>
</td>
<td class="small">
<% if budget.poll.present? %>
<%= link_to t("admin.budgets.index.admin_ballots"), admin_poll_booth_assignments_path(budget.poll) %>
<% else %>
<%= link_to_create_budget_poll(budget) %>
<% end %>
<%= render Admin::Budgets::TableActionsComponent.new(budget) %>
</td>
</tr>
<% end %>

View File

@@ -4,10 +4,11 @@
<td><%= Dashboard::Action.human_attribute_name("action_type_resource") %></td>
<td class="text-center"><%= t("admin.dashboard.actions.index.active") %></td>
<td colspan="4">&nbsp;</td>
<td class="text-right">
<%= link_to t("admin.dashboard.actions.index.edit"),
admin_settings_path(anchor: "tab-proposals"),
class: "button hollow" %>
<td>
<%= render Admin::TableActionsComponent.new(
actions: [:edit],
edit_path: admin_settings_path(anchor: "tab-proposals"),
) %>
</td>
</tr>
<% end %>

View File

@@ -17,7 +17,7 @@
<th class="text-center"><%= t("admin.dashboard.actions.index.day_offset") %></th>
<th class="text-center"><%= t("admin.dashboard.actions.index.required_supports") %></th>
<th class="text-center"><%= t("admin.dashboard.actions.index.order") %></th>
<th class="text-right small-3"><%= t("admin.actions.actions") %></th>
<th class="small-3"><%= t("admin.actions.actions") %></th>
</tr>
</thead>
@@ -31,15 +31,8 @@
<td class="text-center"><%= number_with_delimiter(action.day_offset, delimiter: ".") %></td>
<td class="text-center"><%= number_with_delimiter(action.required_supports, delimiter: ".") %></td>
<td class="text-center"><%= action.order %></td>
<td class="text-right">
<%= link_to t("admin.dashboard.actions.index.edit"),
edit_admin_dashboard_action_path(action),
class: "button hollow" %>
<%= link_to t("admin.dashboard.actions.index.delete"),
admin_dashboard_action_path(action),
method: :delete,
class: "button hollow alert",
data: { confirm: t("admin.actions.confirm") } %>
<td>
<%= render Admin::TableActionsComponent.new(action) %>
</td>
</tr>
<% end %>

View File

@@ -10,7 +10,7 @@
<tr>
<th><%= t("admin.dashboard.administrator_tasks.index.source") %></th>
<th><%= t("admin.dashboard.administrator_tasks.index.resource") %></th>
<th class="text-right"><%= t("admin.actions.actions") %></th>
<th><%= t("admin.actions.actions") %></th>
</tr>
</thead>
@@ -23,11 +23,12 @@
<td>
<%= task.source.action.title %>
</td>
<td class="text-right">
<td>
<% unless task.executed_at? %>
<%= link_to t("admin.dashboard.administrator_tasks.index.solve"),
edit_admin_dashboard_administrator_task_path(task),
class: "button hollow" %>
<%= render Admin::TableActionsComponent.new(task,
actions: [:edit],
edit_text: t("admin.dashboard.administrator_tasks.index.solve")
) %>
<% end %>
</td>
</tr>

View File

@@ -22,17 +22,7 @@
<td><%= geozone.census_code %></td>
<td class="break"><%= geozone.html_map_coordinates %></td>
<td>
<div class="small-6 column">
<%= link_to t("admin.geozones.index.edit"),
edit_admin_geozone_path(geozone),
class: "button hollow expanded" %>
</div>
<div class="small-6 column">
<%= link_to t("admin.geozones.index.delete"),
admin_geozone_path(geozone),
method: :delete,
class: "button hollow alert expanded" %>
</div>
<%= render Admin::TableActionsComponent.new(geozone) %>
</td>
</tr>
<% end %>

View File

@@ -24,17 +24,7 @@
</div>
</td>
<td class="align-top">
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_budget_investment_path(investment, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless investment.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_budget_investment_path(investment, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(investment) %>
</td>
</tr>
<% end %>

View File

@@ -23,17 +23,7 @@
<% end %>
</td>
<td>
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_comment_path(comment, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless comment.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_comment_path(comment, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(comment) %>
</td>
</tr>
<% end %>

View File

@@ -24,17 +24,7 @@
</div>
</td>
<td class="align-top">
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_debate_path(debate, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless debate.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_debate_path(debate, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(debate) %>
</td>
</tr>
<% end %>

View File

@@ -24,17 +24,7 @@
</div>
</td>
<td class="align-top">
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_proposal_notification_path(proposal_notification, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless proposal_notification.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_proposal_notification_path(proposal_notification, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(proposal_notification) %>
</td>
</tr>
<% end %>

View File

@@ -28,17 +28,7 @@
</div>
</td>
<td class="align-top">
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_proposal_path(proposal, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless proposal.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_proposal_path(proposal, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(proposal) %>
</td>
</tr>
<% end %>

View File

@@ -19,17 +19,7 @@
</td>
<td>
<%= link_to t("admin.actions.restore"),
restore_admin_hidden_user_path(user, request.query_parameters),
method: :put,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow warning" %>
<% unless user.confirmed_hide? %>
<%= link_to t("admin.actions.confirm_hide"),
confirm_hide_admin_hidden_user_path(user, request.query_parameters),
method: :put,
class: "button" %>
<% end %>
<%= render Admin::HiddenTableActionsComponent.new(user) %>
</td>
</tr>
<% end %>

View File

@@ -17,14 +17,6 @@
<% end %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_widget_card_path(card),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_widget_card_path(card),
method: :delete,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(card) %>
</td>
</tr>

View File

@@ -35,9 +35,7 @@
<td class="text-center"><%= I18n.l process.end_date %></td>
<td class="text-center"><%= process.total_comments %></td>
<td>
<%= link_to t("admin.legislation.processes.index.delete"), admin_legislation_process_path(process),
method: :delete,
class: "button hollow alert expanded" %>
<%= render Admin::TableActionsComponent.new(process, actions: [:destroy]) %>
</td>
</tr>
<% end %>

View File

@@ -12,14 +12,6 @@
<%= local_census_record.postal_code %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_local_census_record_path(local_census_record),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_local_census_record_path(local_census_record),
method: :delete,
class: "button hollow alert",
data: { confirm: t("admin.actions.confirm") } %>
<%= render Admin::TableActionsComponent.new(local_census_record) %>
</td>
</tr>

View File

@@ -22,10 +22,7 @@
<%= manager.email %>
</td>
<td>
<%= link_to t("admin.managers.manager.delete"),
admin_manager_path(manager),
method: :delete,
class: "button hollow alert expanded" %>
<%= render Admin::Roles::TableActionsComponent.new(manager) %>
</td>
</tr>
<% end %>

View File

@@ -18,19 +18,7 @@
<td><%= user.name %></td>
<td><%= user.email %></td>
<td>
<% if user.manager? && user.manager.persisted? %>
<%= link_to t("admin.managers.manager.delete"),
admin_manager_path(user.manager),
method: :delete,
class: "button hollow alert expanded" %>
<% else %>
<%= link_to t("admin.managers.manager.add"),
{ controller: "admin/managers",
action: :create,
user_id: user },
method: :post,
class: "button success expanded" %>
<% end %>
<%= render Admin::Roles::TableActionsComponent.new(user.manager || user.build_manager) %>
</td>
</tr>
<% end %>

View File

@@ -23,12 +23,7 @@
<%= status.description %>
</td>
<td>
<%= link_to t("admin.statuses.index.edit"),
edit_admin_milestone_status_path(status),
class: "button hollow" %>
<%= link_to t("admin.statuses.index.delete"),
admin_milestone_status_path(status),
method: :delete, class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(status) %>
</td>
</tr>
<% end %>

View File

@@ -56,10 +56,10 @@
<% end %>
</td>
<td class="small-2">
<%= link_to t("admin.milestones.index.delete"),
admin_polymorphic_path(milestone),
method: :delete,
class: "button hollow alert expanded" %>
<%= render Admin::TableActionsComponent.new(milestone,
actions: [:destroy],
destroy_text: t("admin.milestones.index.delete")
) %>
</td>
</tr>
<% end %>

View File

@@ -24,10 +24,7 @@
<%= moderator.email %>
</td>
<td>
<%= link_to t("admin.moderators.moderator.delete"),
admin_moderator_path(moderator),
method: :delete,
class: "button hollow alert expanded" %>
<%= render Admin::Roles::TableActionsComponent.new(moderator) %>
</td>
</tr>
<% end %>

View File

@@ -18,19 +18,7 @@
<td><%= user.name %></td>
<td><%= user.email %></td>
<td>
<% if user.moderator? && user.moderator.persisted? %>
<%= link_to t("admin.moderators.moderator.delete"),
admin_moderator_path(user.moderator),
method: :delete,
class: "button hollow alert expanded" %>
<% else %>
<%= link_to t("admin.moderators.moderator.add"),
{ controller: "admin/moderators",
action: :create,
user_id: user },
method: :post,
class: "button success expanded" %>
<% end %>
<%= render Admin::Roles::TableActionsComponent.new(user.moderator || user.build_moderator) %>
</td>
</tr>
<% end %>

View File

@@ -29,18 +29,11 @@
<% end %>
</td>
<td>
<div class="small-4 column">
<%= link_to t("admin.newsletters.index.edit"), edit_admin_newsletter_path(newsletter),
class: "button hollow expanded" %>
</div>
<div class="small-4 column">
<%= link_to t("admin.newsletters.index.delete"), admin_newsletter_path(newsletter),
method: :delete, class: "button hollow alert expanded" %>
</div>
<div class="small-4 column">
<%= link_to t("admin.newsletters.index.preview"), admin_newsletter_path(newsletter),
class: "button expanded" %>
</div>
<%= render Admin::TableActionsComponent.new(newsletter) do |actions| %>
<%= actions.link_to t("admin.newsletters.index.preview"),
admin_newsletter_path(newsletter),
class: "button" %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -16,9 +16,7 @@
<tbody>
<% @officials.each do |official| %>
<tr>
<td>
<%= link_to official.name, edit_admin_official_path(official) %>
</td>
<td><%= official.name %></td>
<td>
<span class="label level-<%= official.official_level %>">
<%= official.official_position %>
@@ -28,8 +26,11 @@
<%= t("admin.officials.level_#{official.official_level}") %>
</td>
<td>
<%= link_to t("admin.officials.search.edit_official"),
edit_admin_official_path(official), class: "button hollow expanded" %>
<%= render Admin::TableActionsComponent.new(
actions: [:edit],
edit_path: edit_admin_official_path(official),
edit_text: t("admin.officials.search.edit_official")
) %>
</td>
</tr>
<% end %>

View File

@@ -32,15 +32,11 @@
<%= t("admin.officials.level_#{user.official_level}") %>
</td>
<td>
<% if user.official? %>
<%= link_to t("admin.officials.search.edit_official"),
edit_admin_official_path(user),
class: "button hollow expanded" %>
<% else %>
<%= link_to t("admin.officials.search.make_official"),
edit_admin_official_path(user),
class: "button expanded" %>
<% end %>
<%= render Admin::TableActionsComponent.new(
actions: [:edit],
edit_path: edit_admin_official_path(user),
edit_text: user.official? ? t("admin.officials.search.edit_official") : t("admin.officials.search.make_official")
) %>
</td>
</tr>
<% end %>

View File

@@ -48,17 +48,7 @@
<% end %>
</td>
<td>
<% if can? :verify, organization %>
<%= link_to t("admin.organizations.index.verify"),
verify_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button success small-5" %>
<% end %>
<% if can? :reject, organization %>
<%= link_to t("admin.organizations.index.reject"),
reject_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button hollow alert small-5" %>
<% end %>
<%= render Admin::Organizations::TableActionsComponent.new(organization) %>
</td>
</tr>
<% end %>

View File

@@ -44,17 +44,7 @@
<% end %>
</td>
<td>
<% if can? :verify, organization %>
<%= link_to t("admin.organizations.index.verify"),
verify_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button success small-5" %>
<% end %>
<% if can? :reject, organization %>
<%= link_to t("admin.organizations.index.reject"),
reject_admin_organization_path(organization, request.query_parameters),
method: :put, class: "button hollow alert small-5" %>
<% end %>
<%= render Admin::Organizations::TableActionsComponent.new(organization) %>
</td>
</tr>
<% end %>

View File

@@ -11,24 +11,29 @@
</span>
</td>
<td>
<%= link_to t("admin.booth_assignments.manage.actions.unassign"),
admin_poll_booth_assignment_path(@poll, booth_assignment, booth_id: booth.id),
method: :delete,
remote: true,
title: t("admin.booth_assignments.manage.actions.unassign"),
class: "button hollow alert expanded",
data: (booth_assignment.shifts? ? { confirm: "#{t("admin.poll_booth_assignments.alert.shifts")}" } : nil) if !@poll.expired? %>
<% unless @poll.expired? %>
<%= render Admin::TableActionsComponent.new(booth_assignment,
actions: [:destroy],
destroy_text: t("admin.booth_assignments.manage.actions.unassign"),
destroy_confirmation: (booth_assignment.shifts? ? "#{t("admin.poll_booth_assignments.alert.shifts")}" : ""),
destroy_options: { remote: true }
) %>
<% end %>
</td>
<% else %>
<td>
<span class="disabled"><%= t("admin.booth_assignments.manage.status.unassigned") %></span>
</td>
<td>
<%= link_to t("admin.booth_assignments.manage.actions.assign"),
admin_poll_booth_assignments_path(@poll, booth_id: booth.id),
method: :post,
remote: true,
title: t("admin.booth_assignments.manage.actions.assign"),
class: "button hollow expanded" if !@poll.expired? %>
<% unless @poll.expired? %>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.booth_assignments.manage.actions.assign"),
admin_poll_booth_assignments_path(@poll, booth_id: booth.id),
method: :post,
remote: true,
title: t("admin.booth_assignments.manage.actions.assign"),
class: "button hollow expanded" %>
<% end %>
<% end %>
</td>
<% end %>

View File

@@ -5,15 +5,18 @@
<td>
<%= booth.location %>
</td>
<td class="text-right">
<td>
<% if controller_name == "shifts" || controller_name == "booths" && action_name == "available" %>
<%= link_to t("admin.booths.booth.shifts"),
new_admin_booth_shift_path(booth),
class: "button hollow" %>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.booths.booth.shifts"),
new_admin_booth_shift_path(booth),
class: "button hollow" %>
<% end %>
<% else %>
<%= link_to t("admin.booths.booth.edit"),
edit_admin_booth_path(booth),
class: "button hollow" %>
<%= render Admin::TableActionsComponent.new(booth,
actions: [:edit],
edit_text: t("admin.booths.booth.edit")
) %>
<% end %>
</td>
</tr>

View File

@@ -18,7 +18,7 @@
<thead>
<th><%= t("admin.booths.index.name") %></th>
<th><%= t("admin.booths.index.location") %></th>
<th class="text-right"><%= t("admin.actions.actions") %></th>
<th><%= t("admin.actions.actions") %></th>
</thead>
<tbody>
<% @booths.each do |booth| %>

View File

@@ -1,31 +1 @@
<table>
<thead>
<tr>
<th><%= t("admin.poll_officers.officer.name") %></th>
<th><%= t("admin.poll_officers.officer.email") %></th>
<th class="small-3"><%= t("admin.actions.actions") %></th>
</tr>
</thead>
<tbody>
<tr>
<td>
<%= officer.name %>
</td>
<td>
<%= officer.email %>
</td>
<td>
<% if officer.persisted? %>
<%= link_to t("admin.poll_officers.officer.delete"),
admin_officer_path(officer),
method: :delete,
class: "button hollow alert expanded" %>
<% else %>
<%= link_to t("admin.poll_officers.officer.add"), { controller: "admin/poll/officers", action: :create, user_id: officer.user_id },
method: :post,
class: "button success expanded" %>
<% end %>
</td>
</tr>
</tbody>
</table>
<%= render Admin::Poll::Officers::OfficersComponent.new([officer]) %>

View File

@@ -11,42 +11,7 @@
</h3>
<% if @officers.any? %>
<table id="officers">
<thead>
<tr>
<th><%= t("admin.poll_officers.officer.name") %></th>
<th><%= t("admin.poll_officers.officer.email") %></th>
<th class="small-3"><%= t("admin.actions.actions") %></th>
</tr>
</thead>
<tbody>
<% @officers.each do |officer| %>
<tr>
<td>
<%= officer.name %>
</td>
<td>
<%= officer.email %>
</td>
<td>
<% if officer.persisted? %>
<%= link_to t("admin.poll_officers.officer.delete"),
admin_officer_path(officer),
method: :delete,
class: "button hollow alert expanded"
%>
<% else %>
<%= link_to t("admin.poll_officers.officer.add"),
{ controller: "admin/poll/officers", action: :create,
user_id: officer.user_id },
method: :post,
class: "button success expanded" %>
<% end %>
</td>
</tr>
<% end %>
</tbody>
</table>
<%= render Admin::Poll::Officers::OfficersComponent.new(@officers, id: "officers") %>
<%= paginate @officers %>
<% end %>

View File

@@ -1,8 +1,6 @@
<tr id="<%= dom_id(poll) %>" class="poll">
<td>
<strong>
<%= link_to poll.name, admin_poll_path(poll) %>
</strong>
<strong><%= poll.name %></strong>
</td>
<td class="text-center">
<%= l poll.starts_at.to_date %>
@@ -11,18 +9,12 @@
<%= l poll.ends_at.to_date %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_poll_path(poll),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_poll_path(poll),
method: :delete,
"data-confirm": t("admin.polls.destroy.alert"),
class: "button hollow alert" %>
<%= link_to t("admin.actions.configure"),
admin_poll_path(poll),
class: "button hollow " %>
<%= render Admin::TableActionsComponent.new(poll,
destroy_confirmation: t("admin.polls.destroy.alert")
) do |actions| %>
<%= actions.link_to t("admin.actions.configure"),
admin_poll_path(poll),
class: "button hollow " %>
<% end %>
</td>
</tr>

View File

@@ -18,9 +18,7 @@
<% @poll.questions.each do |question| %>
<tr id="<%= dom_id(question) %>">
<td>
<strong>
<%= link_to question.title, admin_question_path(question) %>
</strong>
<strong><%= question.title %></strong>
<% if question.proposal.present? %>
<small>
<%= link_to t("admin.polls.show.see_proposal"),
@@ -30,19 +28,10 @@
<% end %>
</td>
<td>
<div class="small-4 column">
<%= link_to t("admin.polls.show.edit_answers"), admin_question_path(question),
class: "button hollow expanded" %>
</div>
<div class="small-4 column">
<%= link_to t("shared.edit"), edit_admin_question_path(question),
class: "button hollow expanded" %>
</div>
<div class="small-4 column">
<%= link_to t("shared.delete"), admin_question_path(question),
class: "button hollow alert expanded",
method: :delete %>
</div>
<%= render Admin::TableActionsComponent.new(question) do |actions| %>
<%= actions.link_to t("admin.polls.show.edit_answers"), admin_question_path(question),
class: "button hollow" %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -5,21 +5,21 @@
<thead>
<th class="medium-6"><%= t("admin.polls.index.name") %></th>
<th><%= t("admin.polls.index.dates") %></th>
<th class="text-right"><%= t("admin.actions.actions") %></th>
<th><%= t("admin.actions.actions") %></th>
</thead>
<tbody>
<% @polls.each do |poll| %>
<tr id="<%= dom_id(poll) %>" class="poll">
<td>
<%= link_to poll.name, manage_admin_poll_booth_assignments_path(poll) %>
</td>
<td><%= poll.name %></td>
<td>
<%= l poll.starts_at.to_date %> - <%= l poll.ends_at.to_date %>
</td>
<td class="text-right">
<%= link_to t("admin.booth_assignments.manage_assignments"),
manage_admin_poll_booth_assignments_path(poll),
class: "button hollow" %>
<td>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.booth_assignments.manage_assignments"),
manage_admin_poll_booth_assignments_path(poll),
class: "button hollow" %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -27,12 +27,7 @@
<% end %>
</td>
<td>
<div class="small-6 column">
<%= link_to t("shared.edit"), edit_admin_question_path(question), class: "button hollow expanded" %>
</div>
<div class="small-6 column">
<%= link_to t("shared.delete"), admin_question_path(question), class: "button hollow alert expanded", method: :delete %>
<div class="small-6 column">
<%= render Admin::TableActionsComponent.new(question) %>
</td>
</tr>
<% end %>

View File

@@ -15,9 +15,11 @@
</p>
</td>
<td>
<%= link_to t("admin.questions.index.create_question"),
new_admin_question_path(proposal_id: proposal.id),
class: "button hollow" %>
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<%= actions.link_to t("admin.questions.index.create_question"),
new_admin_question_path(proposal_id: proposal.id),
class: "button hollow" %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -27,7 +27,7 @@
<table>
<tr>
<th scope="col"><%= t("admin.questions.show.answers.document_title") %></th>
<th scope="col" class="text-right"><%= t("admin.questions.show.answers.document_actions") %></th>
<th scope="col"><%= t("admin.questions.show.answers.document_actions") %></th>
</tr>
<% @answer.documents.each do |document| %>
@@ -35,18 +35,18 @@
<td>
<%= link_to document.title, document.attachment.url %>
</td>
<td class="text-right">
<%= link_to t("documents.buttons.download_document"),
document.attachment.url,
target: "_blank",
rel: "nofollow",
class: "button hollow" %>
<td>
<%= render Admin::TableActionsComponent.new(document,
actions: [:destroy],
destroy_path: document_path(document)
) do |actions| %>
<%= actions.link_to t("documents.buttons.download_document"),
document.attachment.url,
target: "_blank",
rel: "nofollow",
class: "button hollow" %>
<%= link_to t("admin.shared.delete"),
document_path(document),
method: :delete,
class: "button hollow alert",
data: { confirm: t("admin.actions.confirm") } %>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -17,9 +17,7 @@
<tr>
<th><%= t("admin.answers.videos.index.video_title") %></th>
<th><%= t("admin.answers.videos.index.video_url") %></th>
<th class="text-right">
<%= t("admin.actions.actions") %>
</th>
<th><%= t("admin.actions.actions") %></th>
</tr>
</thead>
@@ -28,16 +26,8 @@
<tr id="<%= dom_id(video) %>" class="poll_question_answer_video">
<td><%= video.title %></td>
<td><%= link_to "#{video.url}", video.url %></td>
<td class="text-right">
<%= link_to t("shared.edit"),
edit_admin_video_path(video),
class: "button hollow" %>
<%= link_to t("shared.delete"),
admin_video_path(video),
class: "button hollow alert",
method: :delete %>
<td>
<%= render Admin::TableActionsComponent.new(video) %>
</td>
</tr>
<% end %>

View File

@@ -10,9 +10,7 @@
<tr>
<th><%= t("admin.poll_shifts.new.table_name") %></th>
<th><%= t("admin.poll_shifts.new.table_email") %></th>
<th class="text-right">
<%= t("admin.poll_shifts.new.table_shift") %>
</th>
<th><%= t("admin.poll_shifts.new.table_shift") %></th>
</tr>
</thead>
<tbody>
@@ -24,10 +22,12 @@
<td>
<%= user.email %>
</td>
<td class="text-right">
<%= link_to t("admin.poll_shifts.new.edit_shifts"),
new_admin_booth_shift_path(officer_id: user.poll_officer.id),
class: "button hollow" %>
<td>
<%= render Admin::TableActionsComponent.new(
actions: [:edit],
edit_text: t("admin.poll_shifts.new.edit_shifts"),
edit_path: new_admin_booth_shift_path(officer_id: user.poll_officer.id)
) %>
</td>
</tr>
<% end %>

View File

@@ -6,7 +6,7 @@
<th><%= t("admin.poll_shifts.new.officer") %></th>
<th><%= t("admin.poll_shifts.new.table_email") %></th>
<th><%= Poll::Shift.human_attribute_name(:task) %></th>
<th class="small-3"><%= t("admin.poll_shifts.new.shift") %></th>
<th><%= t("admin.poll_shifts.new.shift") %></th>
</tr>
</thead>
<tbody>
@@ -17,10 +17,10 @@
<td><%= shift.officer_email %></td>
<td><%= t("admin.poll_shifts.#{shift.task}") %></td>
<td>
<%= link_to t("admin.poll_shifts.new.remove_shift"),
admin_booth_shift_path(@booth, shift),
method: :delete,
class: "button hollow alert expanded" %>
<%= render Admin::TableActionsComponent.new(shift,
actions: [:destroy],
destroy_text: t("admin.poll_shifts.new.remove_shift")
) %>
</td>
</tr>
<% end %>

View File

@@ -36,14 +36,7 @@
<%= number_to_percentage(progress_bar.percentage, strip_insignificant_zeros: true) %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
admin_polymorphic_path(progress_bar, action: :edit),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_polymorphic_path(progress_bar),
method: :delete,
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(progress_bar) %>
</td>
</tr>
<% end %>

View File

@@ -17,14 +17,8 @@
<% end %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_widget_card_path(card, page_id: params[:page_id]),
class: "button hollow" %>
<%= link_to t("admin.actions.delete"),
admin_widget_card_path(card, page_id: params[:page_id]),
method: :delete,
data: { confirm: t("admin.actions.confirm") },
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(card,
edit_path: edit_admin_widget_card_path(card, page_id: params[:page_id])
) %>
</td>
</tr>

View File

@@ -34,9 +34,10 @@
<td><%= link_to "#{content_block.name} (#{content_block.locale})", edit_admin_site_customization_content_block_path(content_block) %></td>
<td><%= raw content_block.body %></td>
<td>
<%= link_to t("admin.site_customization.content_blocks.index.delete"),
admin_site_customization_content_block_path(content_block),
method: :delete, class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(content_block,
actions: [:destroy],
destroy_text: t("admin.site_customization.content_blocks.index.delete")
) %>
</td>
</tr>
<% end %>
@@ -45,9 +46,11 @@
<td><%= link_to "#{content_block.heading.name} (#{content_block.locale})", admin_site_customization_edit_heading_content_block_path(content_block) %></td>
<td><%= raw content_block.body %></td>
<td>
<%= link_to t("admin.site_customization.content_blocks.index.delete"),
admin_site_customization_delete_heading_content_block_path(content_block.id),
method: :delete, class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(
actions: [:destroy],
destroy_text: t("admin.site_customization.content_blocks.index.delete"),
destroy_path: admin_site_customization_delete_heading_content_block_path(content_block)
) %>
</td>
</tr>
<% end %>

View File

@@ -26,11 +26,10 @@
<td><%= link_to document.title, document.attachment.url, target: :blank %></td>
<td>
<div class="small-12 medium-6 column">
<%= link_to t("admin.shared.delete"),
admin_site_customization_document_path(document),
method: :delete,
class: "button hollow alert",
data: { confirm: t("admin.actions.confirm") } %>
<%= render Admin::TableActionsComponent.new(
actions: [:destroy],
destroy_path: admin_site_customization_document_path(document)
) %>
</div>
</td>
</tr>

View File

@@ -35,20 +35,17 @@
<td><%= I18n.l page.created_at, format: :short %></td>
<td><%= t("admin.site_customization.pages.page.status_#{page.status}") %></td>
<td>
<div class="small-6 column">
<%= render Admin::TableActionsComponent.new(page,
actions: [:destroy],
destroy_text: t("admin.site_customization.pages.index.delete")
) do |actions| %>
<% if page.status == "published" %>
<%= link_to t("admin.site_customization.pages.index.see_page"),
page.url,
target: "_blank",
class: "button hollow expanded" %>
<%= actions.link_to t("admin.site_customization.pages.index.see_page"),
page.url,
target: "_blank",
class: "button hollow" %>
<% end %>
</div>
<div class="small-6 column end">
<%= link_to t("admin.site_customization.pages.index.delete"),
admin_site_customization_page_path(page),
method: :delete,
class: "button hollow alert expanded" %>
</div>
<% end %>
</td>
</tr>
<% end %>

View File

@@ -18,32 +18,29 @@
<%= t("admin.system_emails.#{system_email_title}.description") %>
</td>
<td>
<% if system_email_actions.include?("view") %>
<div class="small-4 column">
<%= link_to t("admin.shared.view"), admin_system_email_view_path(system_email_title),
class: "button hollow expanded" %>
</div>
<% end %>
<% if system_email_actions.include?("preview_pending") %>
<div class="small-4 column">
<%= link_to t("admin.system_emails.preview_pending.action"),
admin_system_email_preview_pending_path(system_email_title),
class: "button expanded" %>
</div>
<div class="small-4 column">
<%= link_to t("admin.system_emails.preview_pending.send_pending"),
admin_system_email_send_pending_path(system_email_title),
class: "button success expanded",
method: :put %>
</div>
<% end %>
<% if system_email_actions.include?("edit_info") %>
<div class="small-8 column">
<%= render Admin::TableActionsComponent.new(actions: []) do |actions| %>
<% if system_email_actions.include?("view") %>
<%= actions.link_to t("admin.shared.view"),
admin_system_email_view_path(system_email_title),
class: "button hollow" %>
<% end %>
<% if system_email_actions.include?("preview_pending") %>
<%= actions.link_to t("admin.system_emails.preview_pending.action"),
admin_system_email_preview_pending_path(system_email_title),
class: "button" %>
<%= actions.link_to t("admin.system_emails.preview_pending.send_pending"),
admin_system_email_send_pending_path(system_email_title),
class: "button success",
method: :put %>
<% end %>
<% if system_email_actions.include?("edit_info") %>
<p class="help-text">
<%= t("admin.system_emails.edit_info") %><br>
<code><%= "app/views/mailer/#{system_email_title}.html.erb" %></code>
</p>
</div>
<% end %>
<% end %>
</td>
</tr>

View File

@@ -30,7 +30,7 @@
<% end %>
</td>
<td id="tag_<%= tag.id %>">
<%= link_to t("admin.tags.destroy"), admin_tag_path(tag), method: :delete, class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(tag, actions: [:destroy], destroy_text: t("admin.tags.destroy")) %>
</td>
</tr>
<% end %>

View File

@@ -6,12 +6,6 @@
<%= group.valuators.count %>
</td>
<td>
<%= link_to t("admin.actions.delete"),
admin_valuator_group_path(group),
method: :delete, class: "button hollow alert" %>
<%= link_to t("admin.actions.edit"),
edit_admin_valuator_group_path(group),
class: "button hollow" %>
<%= render Admin::TableActionsComponent.new(group) %>
</td>
</tr>

View File

@@ -19,12 +19,6 @@
<%= valuator_abilities(valuator) %>
</td>
<td>
<%= link_to t("admin.actions.edit"),
edit_admin_valuator_path(valuator),
class: "button hollow" %>
<%= link_to t("admin.valuators.valuator.delete"),
admin_valuator_path(valuator),
method: :delete,
class: "button hollow alert" %>
<%= render Admin::TableActionsComponent.new(valuator) %>
</td>
</tr>

View File

@@ -112,6 +112,7 @@ module Consul
# * English: https://github.com/consul/consul/blob/master/CUSTOMIZE_EN.md
# * Spanish: https://github.com/consul/consul/blob/master/CUSTOMIZE_ES.md
#
config.autoload_paths << "#{Rails.root}/app/components/custom"
config.autoload_paths << "#{Rails.root}/app/controllers/custom"
config.autoload_paths << "#{Rails.root}/app/models/custom"
config.paths["app/views"].unshift(Rails.root.join("app", "views", "custom"))

View File

@@ -16,8 +16,8 @@ module ActionDispatch::Routing::UrlFor
end
def admin_polymorphic_path(resource, options = {})
if %w[Budget::Group Budget::Heading Poll::Booth Poll::Officer
Poll::Question Poll::Question::Answer::Video].include?(resource.class.name)
if %w[Budget::Group Budget::Heading Poll::Booth Poll::BoothAssignment Poll::Officer
Poll::Question Poll::Question::Answer::Video Poll::Shift].include?(resource.class.name)
resolve = resolve_for(resource)
resolve_options = resolve.pop

View File

@@ -1,3 +1,27 @@
class WickedPdf
# Wicked Pdf magic breaks ViewComponent
# https://github.com/mileszs/wicked_pdf/pull/925
module PdfHelper
def render(*args)
options = args.first
if options.is_a?(Hash) && options.key?(:pdf)
render_with_wicked_pdf(options)
else
super
end
end
def render_to_string(*args)
options = args.first
if options.is_a?(Hash) && options.key?(:pdf)
render_to_string_with_wicked_pdf(options)
else
super
end
end
end
end
# WickedPDF Global Configuration
#
# Use this to set up shared configuration options for your entire application.

View File

@@ -72,10 +72,6 @@ en:
budget_investments: Manage projects
table_name: Name
table_phase: Phase
table_investments: Investments
table_edit_groups: Headings groups
table_edit_budget: Edit
table_admin_ballots: Ballots
edit_groups: Edit headings groups
edit_budget: Edit budget
admin_ballots: Admin ballots
@@ -117,7 +113,6 @@ en:
budget_groups:
name: "Name"
headings_name: "Headings"
headings_edit: "Edit Headings"
headings_manage: "Manage headings"
no_groups: "There are no groups."
amount:
@@ -297,8 +292,6 @@ en:
table_name: Name
table_description: Description
table_actions: Actions
delete: Delete
edit: Edit
edit:
title: Edit milestone status
update:
@@ -361,8 +354,6 @@ en:
index:
description: "When users create proposals they can access a dashboard of their proposal, where you can propose resources and recommendations to get support for their idea."
create: Create resource or action
edit: Edit
delete: Delete
active: 'Yes'
inactive: 'No'
title: Resources and actions
@@ -497,7 +488,6 @@ en:
banner_title: Header colors
index:
create: New process
delete: Delete
title: Collaborative legislation
filters:
active: Active
@@ -629,7 +619,6 @@ en:
no_managers: There are no managers.
manager:
add: Add
delete: Delete
search:
title: "Managers: User search"
menu:
@@ -709,7 +698,6 @@ en:
no_administrators: There are no administrators.
administrator:
add: Add
delete: Delete
restricted_removal: "Sorry, you can't remove yourself from the administrators"
search:
title: "Administrators: User search"
@@ -724,7 +712,6 @@ en:
no_moderators: There are no moderators.
moderator:
add: Add
delete: Delete
search:
title: "Moderators: User search"
segment_recipient:
@@ -751,8 +738,6 @@ en:
sent: Sent
actions: Actions
draft: Draft
edit: Edit
delete: Delete
preview: Preview
empty_newsletters: There are no newsletters to show
new:
@@ -788,8 +773,6 @@ en:
sent: Sent
actions: Actions
draft: Draft
edit: Edit
delete: Delete
preview: Preview
view: View
empty_notifications: There are no notifications to show
@@ -887,7 +870,6 @@ en:
can_edit_dossier: "Can edit dossier"
valuator:
add: Add to valuators
delete: Delete
search:
title: "Valuators: User search"
form:
@@ -1301,7 +1283,6 @@ en:
author: Author
content: Content
created_at: Created at
delete: Delete
color_help: Hexadecimal format
show_results_and_stats: "Show results and stats"
results_and_stats_reminder: "Marking these checkboxes the results and/or stats will be publicly available and every user will see them."
@@ -1309,8 +1290,6 @@ en:
index:
title: Geozone
create: Create geozone
edit: Edit
delete: Delete
geozone:
name: Name
external_code: External code

View File

@@ -72,10 +72,6 @@ es:
budget_investments: Gestionar proyectos de gasto
table_name: Nombre
table_phase: Fase
table_investments: Proyectos de gasto
table_edit_groups: Grupos de partidas
table_edit_budget: Editar
table_admin_ballots: Urnas
edit_groups: Editar grupos de partidas
edit_budget: Editar presupuesto
admin_ballots: Gestionar urnas
@@ -117,7 +113,6 @@ es:
budget_groups:
name: "Nombre"
headings_name: "Partidas"
headings_edit: "Editar Partidas"
headings_manage: "Gestionar partidas"
no_groups: "No hay grupos."
amount:
@@ -297,8 +292,6 @@ es:
table_name: Nombre
table_description: Descripción
table_actions: Acciones
delete: Borrar
edit: Editar
edit:
title: Editar estado de seguimiento
update:
@@ -361,8 +354,6 @@ es:
index:
description: "Cuando los usuarios crean propuestas pueden acceder a un panel de progreso de su propuesta, donde se le puede proponer recursos y recomendaciones para conseguir apoyos a su idea."
create: Crear recurso o acción
edit: Editar
delete: Borrar
active: 'Si'
inactive: 'No'
title: Recursos y acciones
@@ -497,7 +488,6 @@ es:
banner_title: Colores del encabezado
index:
create: Nuevo proceso
delete: Borrar
title: Procesos de legislación colaborativa
filters:
active: Activos
@@ -628,7 +618,6 @@ es:
no_managers: No hay gestores.
manager:
add: Añadir como gestor
delete: Borrar
search:
title: "Gestores: Búsqueda de usuarios"
menu:
@@ -708,7 +697,6 @@ es:
no_administrators: No hay administradores.
administrator:
add: Añadir como Administrador
delete: Borrar
restricted_removal: "Lo sentimos, no puedes eliminarte a ti mismo de la lista"
search:
title: "Administradores: Búsqueda de usuarios"
@@ -723,7 +711,6 @@ es:
no_moderators: No hay moderadores.
moderator:
add: Añadir como Moderador
delete: Borrar
search:
title: "Moderadores: Búsqueda de usuarios"
segment_recipient:
@@ -750,8 +737,6 @@ es:
sent: Enviado
actions: Acciones
draft: Borrador
edit: Editar
delete: Borrar
preview: Previsualizar
empty_newsletters: No hay newsletters para mostrar
new:
@@ -787,8 +772,6 @@ es:
sent: Enviado
actions: Acciones
draft: Borrador
edit: Editar
delete: Borrar
preview: Previsualizar
view: Visualizar
empty_notifications: No hay notificaciones para mostrar
@@ -886,7 +869,6 @@ es:
can_edit_dossier: "Puede editar informes"
valuator:
add: Añadir como evaluador
delete: Borrar
search:
title: "Evaluadores: Búsqueda de usuarios"
form:
@@ -1300,7 +1282,6 @@ es:
author: Autor
content: Contenido
created_at: Fecha de creación
delete: Eliminar
color_help: Formato hexadecimal
show_results_and_stats: "Mostrar resultados y estadísticas"
results_and_stats_reminder: "Si marcas estas casillas los resultados y/o estadísticas serán públicos y podrán verlos todos los usuarios."
@@ -1308,8 +1289,6 @@ es:
index:
title: Zonas
create: Crear una zona
edit: Editar
delete: Borrar
geozone:
name: Nombre
external_code: Código externo

View File

@@ -278,6 +278,14 @@ resolve "Poll::Booth" do |booth, options|
[:booth, options.merge(id: booth)]
end
resolve "Poll::BoothAssignment" do |assignment, options|
[assignment.poll, :booth_assignment, options.merge(id: assignment)]
end
resolve "Poll::Shift" do |shift, options|
[:booth, :shift, options.merge(booth_id: shift.booth, id: shift)]
end
resolve "Poll::Officer" do |officer, options|
[:officer, options.merge(id: officer)]
end

View File

@@ -0,0 +1,30 @@
require "rails_helper"
describe Admin::Budgets::TableActionsComponent, type: :component do
let(:budget) { create(:budget) }
let(:component) { Admin::Budgets::TableActionsComponent.new(budget) }
it "renders links to edit budget, manage investments and edit groups and manage ballots" do
render_inline component
expect(page).to have_css "a", count: 4
expect(page).to have_link "Manage projects", href: /investments/
expect(page).to have_link "Edit headings groups", href: /groups/
expect(page).to have_link "Edit budget", href: /edit/
expect(page).to have_link "Admin ballots"
end
it "renders link to create new poll for budgets without polls" do
render_inline component
expect(page).to have_css "a[href*='polls'][data-method='post']", text: "Admin ballots"
end
it "renders link to manage ballots for budgets with polls" do
budget.poll = create(:poll, budget: budget)
render_inline component
expect(page).to have_link "Admin ballots", href: /booth_assignments/
end
end

View File

@@ -0,0 +1,14 @@
require "rails_helper"
describe Admin::HiddenTableActionsComponent, type: :component do
let(:record) { create(:user) }
let(:component) { Admin::HiddenTableActionsComponent.new(record) }
it "renders links to restore and confirm hide" do
render_inline component
expect(page).to have_css "a", count: 2
expect(page).to have_css "a[href*='restore'][data-method='put']", text: "Restore"
expect(page).to have_css "a[href*='confirm_hide'][data-method='put']", text: "Confirm moderation"
end
end

View File

@@ -0,0 +1,46 @@
require "rails_helper"
describe Admin::Organizations::TableActionsComponent, type: :component do
let(:organization) { create(:organization) }
let(:component) { Admin::Organizations::TableActionsComponent.new(organization) }
it "renders links to verify and reject when it can" do
allow(component).to receive(:can_verify?).and_return(true)
allow(component).to receive(:can_reject?).and_return(true)
render_inline component
expect(page).to have_css "a", count: 2
expect(page).to have_css "a[href*='verify'][data-method='put']", text: "Verify"
expect(page).to have_css "a[href*='reject'][data-method='put']", text: "Reject"
end
it "renders link to verify when it cannot reject" do
allow(component).to receive(:can_verify?).and_return(true)
allow(component).to receive(:can_reject?).and_return(false)
render_inline component
expect(page).to have_css "a", count: 1
expect(page).to have_link "Verify"
end
it "renders link to reject when it cannot verify" do
allow(component).to receive(:can_verify?).and_return(false)
allow(component).to receive(:can_reject?).and_return(true)
render_inline component
expect(page).to have_css "a", count: 1
expect(page).to have_link "Reject"
end
it "does not render any actions when it cannot verify nor reject" do
allow(component).to receive(:can_verify?).and_return(false)
allow(component).to receive(:can_reject?).and_return(false)
render_inline component
expect(page).not_to have_css "a"
end
end

View File

@@ -0,0 +1,35 @@
require "rails_helper"
describe Admin::Poll::Officers::OfficersComponent, type: :component do
let(:existing_officer) { create(:poll_officer, name: "Old officer") }
let(:new_officer) { build(:poll_officer, name: "New officer") }
let(:officers) { [existing_officer, new_officer] }
let(:component) { Admin::Poll::Officers::OfficersComponent.new(officers) }
it "renders as many rows as officers" do
within "tbody" do
expect(page).to have_css "tr", count: 2
expect(page).to have_css "a", count: 2
end
end
it "renders link to destroy for existing officers" do
render_inline component
row = page.find("tr", text: "Old officer")
expect(row).to have_css "a[data-method='delete']", text: "Delete"
end
it "renders link to add for new officers" do
render_inline component
row = page.find("tr", text: "New officer")
expect(row).to have_css "a[data-method='post']", text: "Add"
end
it "accepts table options" do
render_inline Admin::Poll::Officers::OfficersComponent.new(officers, class: "my-officers-table")
expect(page).to have_css "table.my-officers-table"
end
end

View File

@@ -0,0 +1,17 @@
require "rails_helper"
describe Admin::Roles::TableActionsComponent, type: :component do
let(:user) { create(:user) }
it "renders link to add the role for new records" do
render_inline Admin::Roles::TableActionsComponent.new(user.build_manager)
expect(page).to have_css "a[data-method='post']", text: "Add"
end
it "renders link to remove the role for existing records" do
render_inline Admin::Roles::TableActionsComponent.new(create(:manager, user: user))
expect(page).to have_css "a[data-method='delete']", text: "Delete"
end
end

View File

@@ -0,0 +1,68 @@
require "rails_helper"
describe Admin::TableActionsComponent, type: :component do
let(:record) { create(:banner) }
it "renders links to edit and destroy a record by default" do
render_inline Admin::TableActionsComponent.new(record)
expect(page).to have_css "a", count: 2
expect(page).to have_css "a[href*='edit']", text: "Edit"
expect(page).to have_css "a[data-method='delete']", text: "Delete"
end
context "actions parameter is passed" do
it "renders a link to edit a record if passed" do
render_inline Admin::TableActionsComponent.new(record, actions: [:edit])
expect(page).to have_link "Edit"
expect(page).not_to have_link "Delete"
end
it "renders a link to destroy a record if passed" do
render_inline Admin::TableActionsComponent.new(record, actions: [:destroy])
expect(page).to have_link "Delete"
expect(page).not_to have_link "Edit"
end
end
it "allows custom texts for actions" do
render_inline Admin::TableActionsComponent.new(record, edit_text: "change", destroy_text: "annihilate")
expect(page).to have_link "annihilate"
expect(page).to have_link "change"
expect(page).not_to have_link "Delete"
expect(page).not_to have_link "Edit"
end
it "allows custom URLs" do
render_inline Admin::TableActionsComponent.new(edit_path: "/myedit", destroy_path: "/mydestroy")
expect(page).to have_link "Edit", href: "/myedit"
expect(page).to have_link "Delete", href: "/mydestroy"
end
it "allows custom confirmation text" do
render_inline Admin::TableActionsComponent.new(record, destroy_confirmation: "Are you mad? Be careful!")
expect(page).to have_css "a[data-confirm='Are you mad? Be careful!']"
end
it "allows custom options" do
render_inline Admin::TableActionsComponent.new(record, edit_options: { id: "edit_me" })
expect(page).to have_css "a#edit_me"
end
it "allows custom content" do
render_inline Admin::TableActionsComponent.new(record) do
"<a href='/'>Main</a>".html_safe
end
expect(page).to have_css "a", count: 3
expect(page).to have_link "Main", href: "/"
expect(page).to have_link "Edit"
expect(page).to have_link "Delete"
end
end

View File

@@ -11,6 +11,11 @@ require "spec_helper"
require "capybara/rails"
require "capybara/rspec"
require "selenium/webdriver"
require "view_component/test_helpers"
RSpec.configure do |config|
config.include ViewComponent::TestHelpers, type: :component
end
Rails.application.load_tasks if Rake::Task.tasks.empty?

View File

@@ -148,6 +148,22 @@ describe "Polymorphic routes" do
)
end
it "routes booth assignments" do
poll = create(:poll)
assignment = create(:poll_booth_assignment, poll: poll)
expect(admin_polymorphic_path(assignment)).to eq(
admin_poll_booth_assignment_path(poll, assignment)
)
end
it "routes poll shifts" do
booth = create(:poll_booth)
shift = create(:poll_shift, booth: booth)
expect(admin_polymorphic_path(shift)).to eq(admin_booth_shift_path(booth, shift))
end
it "supports routes for actions like edit" do
proposal = create(:proposal)
milestone = create(:milestone, milestoneable: proposal)

View File

@@ -128,7 +128,7 @@ describe "Admin budget groups" do
click_button "Create new group"
expect(page).to have_content "Group created successfully!"
expect(page).to have_link "All City"
expect(page).to have_content "All City"
end
scenario "Maximum number of headings in which a user can vote is set to 1 by default" do

View File

@@ -148,7 +148,7 @@ describe "Admin budget headings" do
click_button "Create new heading"
expect(page).to have_content "Heading created successfully!"
expect(page).to have_link "All City"
expect(page).to have_content "All City"
expect(page).to have_content "€1,000"
expect(page).to have_content "10000"
expect(page).to have_content "Yes"

View File

@@ -19,7 +19,7 @@ describe "Admin officials" do
scenario "Edit an official" do
visit admin_officials_path
click_link official.name
click_link "Edit official"
expect(page).to have_current_path(edit_admin_official_path(official))

View File

@@ -16,7 +16,7 @@ describe "Admin booths assignments" do
visit booth_assignments_admin_polls_path
expect(page).to have_link(poll.name, href: manage_admin_poll_booth_assignments_path(poll))
expect(page).to have_link("Manage assignments", href: manage_admin_poll_booth_assignments_path(poll))
expect(page).to have_content(second_poll.name)
within("#poll_#{second_poll.id}") do

View File

@@ -58,7 +58,7 @@ describe "Admin polls" do
poll = create(:poll)
visit admin_polls_path
click_link poll.name
click_link "Configure"
expect(page).to have_content poll.name
end

View File

@@ -52,7 +52,7 @@ describe "Admin poll questions" do
question = create(:poll_question, poll: poll)
visit admin_poll_path(poll)
click_link question.title
click_link "Edit answers"
expect(page).to have_content(question.title)
expect(page).to have_content(question.author.name)