adds edit/create modal and related actions

This commit is contained in:
zmagod 2018-03-23 16:00:33 +01:00
parent 3be3c00574
commit baf69461f5
8 changed files with 378 additions and 67 deletions

View file

@ -1,47 +0,0 @@
(function() {
'use strict';
function initEditCoumnModal() {}
function initDeleteColumnModal() {
$('[data-action="destroy"]').on('click', function() {
var element = $(this);
var modal_html = $("#deleteRepositoryColumn");
$.get(element.closest('li').attr('data-destroy-url'), function(data) {
modal_html.find('.modal-body').html(data.html)
.promise()
.done(function() {
modal_html.modal('show');
initSubmitAction(modal_html, $(modal_html.find('form')));
});
})
});
}
function initSubmitAction(modal, form) {
modal.find('[data-action="delete"]').on('click', function() {
form.submit();
modal.modal('hide')
animateSpinner();
processResponse(form);
});
}
function processResponse(form) {
form.on('ajax:success', function(e, data) {
$('.list-group-item[data-id="' + data.id + '"]').remove();
HelperModule.flashAlertMsg(data.message, 'success');
animateSpinner(null, false);
}).on('ajax:error', function(e, xhr, status, error) {
HelperModule.flashAlertMsg(error.message, 'danger');
animateSpinner(null, false);
})
}
$(document).ready(function() {
initEditCoumnModal();
initDeleteColumnModal();
})
})()

View file

@ -0,0 +1,202 @@
(function() {
'use strict';
// @TODO refactor that eventually
function initEditCoumnModal() {
var modalID = '#manageRepositoryColumn';
var colRadID = '#repository_column_data_type_repositorylistvalue';
var tagsInputID = '[data-role="tagsinput"]';
var formID = '[data-role="manage-repository-column-form"]';
$('[data-action="edit"]').off('click').on('click', function() {
var editUrl = $(this).closest('li').attr('data-edit-url');
$.get(editUrl, function(data) {
$(data.html).appendTo('body').promise().done(function() {
$(modalID).modal('show').promise().done(function() {
$(modalID).on('hidden.bs.modal', function () {
// remove edit modal window
$(modalID).remove();
$('.modal-backdrop').remove();
});
_initTagInput();
setTimeout(function() {
$('#repository_column_name').focus();
}, 500)
if($(modalID).attr('data-edit-type') === 'RepositoryListValue') {
var values = JSON.parse($(tagsInputID).attr('data-value'));
$(colRadID).click().promise().done(function() {
$.each(values, function(index, element) {
$(tagsInputID).tagsinput('add', element);
});
});
}
$('[data-action="save"]').on('click', function() {
if($(colRadID).is(':checked')) {
$('#list_items').val($(tagsInputID).val());
}
_processResponse($(formID), 'update');
$(formID).submit();
$('#manageRepositoryColumn').modal('hide');
});
});
});
});
});
}
function initDeleteColumnModal() {
$('[data-action="destroy"]').off('click').on('click', function() {
var element = $(this);
var modal_html = $("#deleteRepositoryColumn");
$.get(element.closest('li').attr('data-destroy-url'), function(data) {
modal_html.find('.modal-body').html(data.html)
.promise()
.done(function() {
modal_html.modal('show');
_initSubmitAction(modal_html, $(modal_html.find('form')));
});
});
});
}
// @TODO refactor that eventually
function initNewColumnModal() {
var modalID = '#manageRepositoryColumn';
$('[data-action="new-column-modal"]').off('click').on('click', function() {
var modalUrl = $(this).attr('data-modal-url');
$.get(modalUrl, function(data) {
$(data.html).appendTo('body').promise().done(function() {
$(modalID).modal('show').promise().done(function() {
$(modalID).on('hidden.bs.modal', function () {
// remove create new modal window
$(modalID).remove();
$('.modal-backdrop').remove();
});
_initTagInput();
setTimeout(function() {
$('#repository_column_name').focus();
}, 500);
$('[data-action="save"]').on('click', function() {
var colRad = '#repository_column_data_type_repositorylistvalue';
if($(colRad).is(':checked')) {
$('#list_items')
.val($('[data-role="tagsinput"]').val());
}
var form = $('[data-role="manage-repository-column-form"]');
_processResponse(form, 'create');
form.submit();
$(modalID).modal('hide');
});
});
});
});
});
}
/* *********************************
Helper methods
********************************* */
function _insertNewListItem(column) {
var html = '<li class="list-group-item" data-id="' + column.id + '" ';
html += 'data-destroy-url="' + column.destroy_html_url + '"';
html += 'data-edit-url="' + column.edit_url + '">';
html += '<span class="pull-left">' + column.name + '</span>';
html += '<span class="controlls pull-right">';
html += '<span class="glyphicon glyphicon-trash" aria-hidden="true" ';
html += 'data-action="destroy"></span>&nbsp;';
html += '<button class="btn btn-primary" data-action="edit">';
html += '<%= I18n.t "libraries.repository_columns.index.edit_column" %>';
html += '</button></span></li>';
$(html).insertBefore('.repository-columns-body ul li:first')
.promise()
.done(function() {
initDeleteColumnModal();
initEditCoumnModal();
// remove create new modal window
$('#manageRepositoryColumn').remove();
$('.modal-backdrop').remove();
});
// remove 'no column' list item
$('[data-attr="no-columns"]').remove();
}
function _replaceListItem(column) {
$('.list-group-item[data-id="' + column.id + '"]')
.find('span.pull-left').text(column.name);
}
function _initTagInput() {
$('[name="repository_column[data_type]"]')
.on('click', function() {
var listValueId = 'repository_column_data_type_repositorylistvalue';
if($(this).attr('id') === listValueId) {
$('[data-role="tagsinput"]').tagsinput({
maxChars: <%= Constants::NAME_MAX_LENGTH %>,
trimValue: true
});
$('.bootstrap-tagsinput').show();
} else {
$('.bootstrap-tagsinput').hide();
}
});
}
function _removeElementFromDom(column) {
$('.list-group-item[data-id="' + column.id + '"]').remove();
if($('.list-group-item').length === 0) {
location.reload();
}
}
function _initSubmitAction(modal, form) {
modal.find('[data-action="delete"]').on('click', function() {
form.submit();
modal.modal('hide')
animateSpinner();
_processResponse(form, 'destroy');
});
}
function _processResponse(form, action) {
form.on('ajax:success', function(e, data) {
switch(action) {
case 'destroy':
_removeElementFromDom(data);
break;
case 'create':
_insertNewListItem(data);
break;
case 'update':
_replaceListItem(data);
break;
default:
location.reload();
}
HelperModule.flashAlertMsg(data.message, 'success');
animateSpinner(null, false);
}).on('ajax:error', function(e, xhr) {
HelperModule.flashAlertMsg(xhr.responseJSON.message, 'danger');
animateSpinner(null, false);
})
}
/* *********************************
Initializers
********************************* */
$(document).ready(function() {
initEditCoumnModal();
initDeleteColumnModal();
initNewColumnModal();
});
})();

View file

@ -1,28 +1,41 @@
class RepositoryColumnsController < ApplicationController
include InputSanitizeHelper
before_action :load_vars, except: %i(create index)
before_action :load_vars_nested, only: %i(create index)
before_action :load_vars, except: %i(create index create_html)
before_action :load_vars_nested, only: %i(create index create_html)
before_action :check_create_permissions, only: :create
before_action :check_manage_permissions, except: %i(create index)
before_action :check_manage_permissions, except: %i(create index create_html)
before_action :load_repository_columns, only: :index
def index
def index; end
def create_html
@repository_column = RepositoryColumn.new
respond_to do |format|
format.json do
render json: {
html: render_to_string(
partial: 'repository_columns/manage_column_modal.html.erb'
)
}
end
end
end
def create
@repository_column = RepositoryColumn.new(repository_column_params)
@repository_column.repository = @repository
@repository_column.created_by = current_user
@repository_column.data_type = :RepositoryTextValue
respond_to do |format|
if @repository_column.save
generate_repository_list_items(params[:list_items])
format.json do
render json: {
id: @repository_column.id,
name: escape_input(@repository_column.name),
message: t('libraries.repository_columns.create.success_flash',
name: @repository_column.name),
edit_url:
edit_repository_repository_column_path(@repository,
@repository_column),
@ -30,15 +43,14 @@ class RepositoryColumnsController < ApplicationController
repository_repository_column_path(@repository,
@repository_column),
destroy_html_url:
repository_columns_destroy_html_path(
@repository, @repository_column
)
repository_columns_destroy_html_path(@repository,
@repository_column)
},
status: :ok
end
else
format.json do
render json: @repository_column.errors.to_json,
render json: { message: @repository_column.errors.full_messages },
status: :unprocessable_entity
end
end
@ -48,7 +60,11 @@ class RepositoryColumnsController < ApplicationController
def edit
respond_to do |format|
format.json do
render json: { status: :ok }
render json: {
html: render_to_string(
partial: 'repository_columns/manage_column_modal.html.erb'
)
}
end
end
end
@ -58,9 +74,15 @@ class RepositoryColumnsController < ApplicationController
format.json do
@repository_column.update_attributes(repository_column_params)
if @repository_column.save
render json: { status: :ok }
update_repository_list_items(params[:list_items])
render json: {
id: @repository_column.id,
name: escape_input(@repository_column.name),
message: t('libraries.repository_columns.update.success_flash',
name: @repository_column.name)
}, status: :ok
else
render json: @repository_column.errors.to_json,
render json: { message: @repository_column.errors.full_messages },
status: :unprocessable_entity
end
end
@ -82,7 +104,6 @@ class RepositoryColumnsController < ApplicationController
def destroy
@del_repository_column = @repository_column.dup
column_id = @repository_column.id
respond_to do |format|
format.json do
if @repository_column.destroy
@ -122,7 +143,8 @@ class RepositoryColumnsController < ApplicationController
end
def load_repository_columns
@repository_columns = @repository.repository_columns.order(:created_at)
@repository_columns = @repository.repository_columns
.order(created_at: :desc)
end
def check_create_permissions
@ -134,6 +156,47 @@ class RepositoryColumnsController < ApplicationController
end
def repository_column_params
params.require(:repository_column).permit(:name)
params.require(:repository_column).permit(:name, :data_type)
end
def generate_repository_list_items(item_names)
return unless @repository_column.data_type == 'RepositoryListValue'
item_names.split(',').uniq.each do |name|
RepositoryListItem.create(
repository: @repository,
repository_column: @repository_column,
data: name,
created_by: current_user,
last_modified_by: current_user
)
end
end
def update_repository_list_items(item_names)
return unless @repository_column.data_type == 'RepositoryListValue'
items_list = item_names.split(',').uniq
existing = @repository_column.repository_list_items.pluck(:data)
existing.each do |name|
next if items_list.include? name
list_item_id = @repository_column.repository_list_items
.find_by_data(name)
.destroy
.id
RepositoryCell.where(
'value_type = ? AND value_id = ?',
'RepositoryListValue',
list_item_id
).destroy_all
end
items_list.each do |name|
next if @repository_column.repository_list_items.find_by_data(name)
RepositoryListItem.create(
repository: @repository,
repository_column: @repository_column,
data: name,
created_by: current_user,
last_modified_by: current_user
)
end
end
end

View file

@ -0,0 +1,16 @@
module RepositoryColumnsHelper
def form_url(repository, column)
return repository_repository_columns_path(repository) if column.new_record?
repository_repository_column_path(repository, column)
end
def disabled?(column, type)
return false if column.new_record?
column.data_type == type ? false : true
end
def checked?(column, type)
return true if column.new_record? && type == 'RepositoryTextValue'
return true if column.data_type == type
end
end

View file

@ -0,0 +1,60 @@
<div class="modal fade"
id="manageRepositoryColumn"
tabindex="-1"
role="dialog"
aria-labelledby="manangeRepositoryColumnLabel"
data-edit-type="<%= @repository_column.data_type unless @repository_column.new_record? %>">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">
<% if @repository_column.new_record? %>
<%= t("libraries.manange_modal_column.new.title") %>
<% else %>
<%= t("libraries.manange_modal_column.edit.title", name: @repository_column.name) %>
<% end %>
</h4>
</div>
<div class="modal-body">
<%= bootstrap_form_for @repository_column,
url: form_url(@repository, @repository_column),
remote: true,
data: { role: "manage-repository-column-form" } do |f| %>
<%= hidden_field_tag :list_items %>
<%= f.text_field :name %>
<%= f.form_group :data_type, label: { text: 'Column type' } do %>
<br />
<%= f.radio_button :data_type,
'RepositoryTextValue',
label: 'Text',
inline: true,
checked: checked?(@repository_column, 'RepositoryTextValue'),
disabled: disabled?(@repository_column, 'RepositoryTextValue') %>
<%= f.radio_button :data_type,
'RepositoryFileValue',
label: 'File',
inline: true,
checked: checked?(@repository_column, 'RepositoryFileValue'),
disabled: disabled?(@repository_column, 'RepositoryFileValue') %>
<%= f.radio_button :data_type,
'RepositoryListValue',
label: 'Dropdown',
inline: true,
checked: checked?(@repository_column, 'RepositoryListValue'),
disabled: disabled?(@repository_column, 'RepositoryListValue') %>
<% end %>
<input class="form-control"
data-role="tagsinput"
style="display: none"
data-value="<%= @repository_column.repository_list_items.pluck(:data) %>"
/>
<% end %>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-primary" data-action="save"><%= t("general.save") %></button>
<button type="button" class="btn btn-default" data-dismiss="modal"><%= t("general.cancel")%></button>
</div>
</div>
</div>
</div>repository_repository_column

View file

@ -10,7 +10,9 @@
<h2><strong><%=t 'libraries.repository_columns.index.manage_column' %></strong></h2>
</div>
<div class="col-md-6 text-right">
<button class="btn btn-primary btn-lg">
<button class="btn btn-primary btn-lg"
data-modal-url="<%= repository_columns_create_html_path(@repository) %>"
data-action="new-column-modal">
<span class="glyphicon glyphicon-plus"></span>&nbsp;<%=t 'libraries.repository_columns.index.new_column' %>
</button>
</div>
@ -20,7 +22,7 @@
<ul class="list-group"
data-repository-id="<%= @repository.id %>">
<% if @repository_columns.length.zero? %>
<li class="list-group-item text-center">
<li class="list-group-item text-center" data-attr="no-columns">
<strong><%=t 'libraries.repository_columns.index.no_column' %></strong>
</li>
<% else %>
@ -28,7 +30,8 @@
<% cache column do %>
<li class="list-group-item"
data-id="<%= column.id %>"
data-destroy-url="<%= repository_columns_destroy_html_path(@repository, column) %>">
data-destroy-url="<%= repository_columns_destroy_html_path(@repository, column) %>"
data-edit-url="<%= edit_repository_repository_column_path(@repository, column) %>">
<span class="pull-left"><%= column.name %></span>
<span class="controlls pull-right">
<span class="glyphicon glyphicon-trash"

View file

@ -986,8 +986,18 @@ en:
default_column: 'Name'
libraries:
manange_modal_column:
new:
title: "Add New Column"
edit:
title: "Edit %{name} Column"
repository_columns:
head_title: '%{repository} | Manage Columns'
update:
success_flash: "Column %{name} was successfully updated."
create:
success_flash: "Column %{name} was successfully created."
destroy:
success_flash: "Column %{name} was successfully deleted."
error_flash: "Something went wrong! Please try again later."

View file

@ -469,8 +469,12 @@ Rails.application.routes.draw do
as: 'delete_records',
defaults: { format: 'json' }
get 'repository_columns/:id/destroy_html',
to: 'repository_columns#destroy_html',
as: 'columns_destroy_html'
to: 'repository_columns#destroy_html',
as: 'columns_destroy_html'
get 'create_html',
to: 'repository_columns#create_html',
as: 'columns_create_html',
defaults: { format: 'json' }
resources :repository_columns, only: %i(index create edit update destroy)
resources :repository_rows, only: %i(create edit update)