Commit a78e208d by kevalbhatt Committed by nixonrodrigues

ATLAS-3669 : UI: Import Glossary Terms CSV into a Glossary

parent cfee9cef
......@@ -109,7 +109,8 @@ module.exports = function(grunt) {
'jquery.sparkline.min.js': { 'jquery-sparkline': 'sparkline' },
'table-dragger.js': { 'table-dragger/dist': 'table-dragger' },
'jstree.min.js': { 'jstree/dist': 'jstree' },
'jquery.steps.min.js': { 'jquery-steps/build': 'jquery-steps' }
'jquery.steps.min.js': { 'jquery-steps/build': 'jquery-steps' },
'dropzone-amd-module.js': { 'dropzone/dist': "dropzone/js" }
}
},
......@@ -147,7 +148,8 @@ module.exports = function(grunt) {
'query-builder.default.min.css': { 'jQuery-QueryBuilder/dist/css': 'jQueryQueryBuilder/css' },
'daterangepicker.css': { 'bootstrap-daterangepicker': 'bootstrap-daterangepicker/css' },
'nv.d3.min.css': { 'nvd3/build': 'nvd3/css' },
'pretty-checkbox.min.css': { 'pretty-checkbox/dist': 'pretty-checkbox/css' }
'pretty-checkbox.min.css': { 'pretty-checkbox/dist': 'pretty-checkbox/css' },
'dropzone.css': { 'dropzone/dist': "dropzone/css" }
}
},
......
......@@ -33,6 +33,7 @@
"d3": "3.5.17",
"d3-tip": "0.6.8",
"dagre-d3": "0.4.17",
"dropzone": "5.5.1",
"font-awesome": "4.7.0",
"jQuery-QueryBuilder": "2.4.3",
"jquery": "3.3.1",
......
......@@ -608,4 +608,26 @@ td.searchTableName:hover {
z-index: 1;
left: calc(50% - 8px);
}
}
.dropzone {
border-radius: 10px;
border: 2px dashed $color_havelock_blue_approx;
.dz-default.dz-message {
font-weight: 500;
font-size: 20px;
}
&.single-file-center {
.dz-file-preview {
margin-left: calc(50% - 68px);
}
}
}
.dropzone-modal {
.modal-body {
background: $color_white_lilac_approx;
}
}
\ No newline at end of file
......@@ -56,6 +56,7 @@
<link rel="stylesheet" href="js/libs/nvd3/css/nv.d3.min.css?bust=<%- bust %>">
<link href="js/libs/jstree/css/default-dark/default-dark-theme.min.css?bust=<%- bust %>" rel="stylesheet">
<link href="js/libs/pretty-checkbox/css/pretty-checkbox.min.css?bust=<%- bust %>" rel="stylesheet">
<link href="js/libs/dropzone/css/dropzone.css?bust=<%- bust %>" rel="stylesheet">
<link href="js/libs/jstree/css/default/default-theme.min.css?bust=<%- bust %>" rel="stylesheet">
<link href="css/style.css?bust=<%- bust %>" rel="stylesheet">
</head>
......
......@@ -175,7 +175,8 @@ require.config({
'sparkline': 'libs/sparkline/jquery.sparkline.min',
'table-dragger': 'libs/table-dragger/table-dragger',
'jstree': 'libs/jstree/jstree.min',
'jquery-steps': 'libs/jquery-steps/jquery.steps.min'
'jquery-steps': 'libs/jquery-steps/jquery.steps.min',
'dropzone': 'libs/dropzone/js/dropzone-amd-module'
},
/**
......
......@@ -17,7 +17,7 @@
<div class="col-sm-12 {{#unless isAssignView}}add-seperator{{/unless}}">
<div class="row">
{{#unless isAssignView}}
<div class="col-sm-8 no-padding" style="margin-top: 5px;">
<div class="col-sm-7 no-padding" style="margin-top: 5px;">
<span class="pull-left">Terms</span>
<label class="switch pull-left">
<input type="checkbox" class="switch-input" name="glossaryView" value="text" />
......@@ -25,9 +25,17 @@
</label>
<span class="pull-left">Category</span>
</div>
<div class="{{#if isAssignView}}col-sm-2{{else}}col-sm-4{{/if}} no-padding-right">
<div class="{{#if isAssignView}}col-sm-2{{else}}col-sm-5{{/if}} no-padding-right">
<button type="button" class="btn btn-action btn-md pull-right" title="Refresh" data-id="refreshGlossary" onclick="this.blur();" type="button"><i class="fa fa-refresh"></i></button>
<button type="button" class="btn btn-action btn-md pull-right" data-id="createGlossary" type="button"><i class="fa fa-plus"></i></button>
<div class="dropdown pull-right">
<button type="button" data-toggle="dropdown" class="btn btn-action btn-md dropdown-toggle" type="button"><i class="fa fa-paperclip"></i></button>
<ul class="dropdown-menu">
<li><a href="{{importTmplUrl}}">Download Import template</a></li>
<li><a href="javascript:void(0)" data-id="importGlossary">Import Glossary</a></li>
</ul>
</div>
<!-- -->
{{/unless}}
</div>
</div>
......
<!--
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
-->
<form action={{importUrl}} id="importGlossary" class="dropzone single-file-center"></form>
\ No newline at end of file
......@@ -185,6 +185,12 @@ define(['require', 'utils/Enums', 'utils/Utils', 'underscore'], function(require
return glossaryUrl;
}
},
glossaryImportTempUrl: function() {
return this.glossaryApiUrl() + '/import/template';
},
glossaryImportUrl: function() {
return this.glossaryApiUrl() + '/import';
},
categoryApiUrl: function(options) {
var guid = options && options.guid,
list = options && options.list,
......
......@@ -22,9 +22,10 @@ define(['require',
'utils/Utils',
'utils/Messages',
'utils/Globals',
'utils/UrlLinks',
'utils/CommonViewFunction',
'jstree'
], function(require, Backbone, GlossaryLayoutViewTmpl, Utils, Messages, Globals, CommonViewFunction) {
], function(require, Backbone, GlossaryLayoutViewTmpl, Utils, Messages, Globals, UrlLinks, CommonViewFunction) {
'use strict';
var GlossaryLayoutView = Backbone.Marionette.LayoutView.extend(
......@@ -39,6 +40,7 @@ define(['require',
templateHelpers: function() {
return {
isAssignView: this.isAssignView,
importTmplUrl: UrlLinks.glossaryImportTempUrl(),
isAssignAttributeRelationView: this.isAssignAttributeRelationView
};
},
......@@ -51,7 +53,8 @@ define(['require',
searchCategory: "[data-id='searchCategory']",
glossaryView: 'input[name="glossaryView"]',
termTree: "[data-id='termTree']",
categoryTree: "[data-id='categoryTree']"
categoryTree: "[data-id='categoryTree']",
importGlossary: "[data-id='importGlossary']"
},
/** ui events hash */
events: function() {
......@@ -75,6 +78,7 @@ define(['require',
})
};
events["click " + this.ui.refreshGlossary] = 'getGlossary';
events["click " + this.ui.importGlossary] = 'onClickImportGlossary';
events["keyup " + this.ui.searchTerm] = function() {
this.ui.termTree.jstree("search", this.ui.searchTerm.val());
};
......@@ -740,6 +744,18 @@ define(['require',
updateTabState: true
});
}
},
onClickImportGlossary: function() {
var that = this;
require([
'views/glossary/ImportGlossaryLayoutView'
], function(ImportGlossaryLayoutView) {
var view = new ImportGlossaryLayoutView({
callback: function() {
that.getGlossary();
}
});
});
}
});
return GlossaryLayoutView;
......
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
define([
"require",
"backbone",
"hbs!tmpl/glossary/ImportGlossaryLayoutView_tmpl",
"modules/Modal",
'utils/CommonViewFunction',
"utils/Utils",
"utils/UrlLinks",
"dropzone"
], function(require, Backbone, ImportGlossaryLayoutViewTmpl, Modal, CommonViewFunction, Utils, UrlLinks, dropzone) {
var ImportGlossaryLayoutView = Backbone.Marionette.LayoutView.extend(
/** @lends ImportGlossaryLayoutView */
{
_viewName: "ImportGlossaryLayoutView",
template: ImportGlossaryLayoutViewTmpl,
templateHelpers: function() {
return {
importUrl: UrlLinks.glossaryImportUrl()
};
},
/** Layout sub regions */
regions: {},
/** ui selector cache */
ui: {},
/** ui events hash */
events: function() {
var events = {};
return events;
},
/**
* intialize a new ImportGlossaryLayoutView Layout
* @constructs
*/
initialize: function(options) {
_.extend(this, _.pick(options, "callback"));
var that = this;
this.modal = new Modal({
title: "Import Glossary",
content: this,
cancelText: "Cancel",
okText: "upload",
allowCancel: true,
okCloses: false,
mainClass: "dropzone-modal"
}).open();
this.modal.$el.find("button.ok").attr("disabled", true);
this.modal.on("ok", function(e) {
that.dropzone.processQueue();
});
this.modal.on("closeModal", function() {
that.modal.trigger("cancel");
});
},
bindEvents: function() {},
onRender: function() {
var that = this;
this.dropzone = null;
var updateButton = function(files) {
var buttonEl = that.modal.$el.find("button.ok");
if (files.length === 0) {
buttonEl.attr("disabled", true);
} else {
buttonEl.attr("disabled", false);
}
}
var headers = {};
headers[CommonViewFunction.restCsrfCustomHeader] = '""';
this.$("#importGlossary").dropzone({
url: UrlLinks.glossaryImportUrl(),
clickable: true,
acceptedFiles: ".csv,.xls,.xlsx",
autoProcessQueue: false,
maxFiles: 1,
addRemoveLinks: true,
init: function() {
that.dropzone = this;
this.on('addedfile', function(file) {
updateButton(this.files);
})
this.on('removedfile', function(file) {
updateButton(this.files);
})
},
maxfilesexceeded: function(file) {
this.removeAllFiles();
this.addFile(file);
},
success: function(file, response) {
that.modal.trigger("cancel");
Utils.notifySuccess({
content: "File: " + file.name + " added successfully"
});
that.callback();
},
error: function(file, response, responseObj) {
Utils.defaultErrorHandler(null, responseObj, { defaultErrorMessage: (response.errorMessage) || response });
that.modal.$el.find("button.ok").attr("disabled", false);
},
dictDefaultMessage: "Drop files here or click to upload.",
headers: headers
});
}
}
);
return ImportGlossaryLayoutView;
});
\ No newline at end of file
......@@ -109,7 +109,8 @@ module.exports = function(grunt) {
'jquery.sparkline.min.js': { 'jquery-sparkline': 'sparkline' },
'table-dragger.js': { 'table-dragger/dist': 'table-dragger' },
'jstree.min.js': { 'jstree/dist': 'jstree' },
'jquery.steps.min.js': { 'jquery-steps/build': 'jquery-steps' }
'jquery.steps.min.js': { 'jquery-steps/build': 'jquery-steps' },
'dropzone-amd-module.js': { 'dropzone/dist': "dropzone/js" }
}
},
......@@ -153,7 +154,8 @@ module.exports = function(grunt) {
'query-builder.default.min.css': { 'jQuery-QueryBuilder/dist/css': 'jQueryQueryBuilder/css' },
'daterangepicker.css': { 'bootstrap-daterangepicker': 'bootstrap-daterangepicker/css' },
'nv.d3.min.css': { 'nvd3/build': 'nvd3/css' },
'pretty-checkbox.min.css': { 'pretty-checkbox/dist': 'pretty-checkbox/css' }
'pretty-checkbox.min.css': { 'pretty-checkbox/dist': 'pretty-checkbox/css' },
'dropzone.css': { 'dropzone/dist': "dropzone/css" }
}
},
......
......@@ -33,6 +33,7 @@
"d3": "3.5.17",
"d3-tip": "0.6.8",
"dagre-d3": "0.4.17",
"dropzone": "5.7.0",
"font-awesome": "4.7.0",
"jQuery-QueryBuilder": "2.4.3",
"jquery": "3.3.1",
......
......@@ -425,4 +425,16 @@ span.tree-tooltip {
&.show {
display: block;
}
}
.glossary-dropdown {
left: -190px !important;
span a {
padding: 0px !important;
span {
margin-left: 0px !important;
}
}
}
\ No newline at end of file
......@@ -844,4 +844,26 @@ td.searchTableName:hover {
}
}
.dropzone {
border-radius: 10px;
border: 2px dashed $color_havelock_blue_approx;
.dz-default.dz-message {
font-weight: 500;
font-size: 20px;
}
&.single-file-center {
.dz-file-preview {
margin-left: calc(50% - 68px);
}
}
}
.dropzone-modal {
.modal-body {
background: $color_white_lilac_approx;
}
}
\ No newline at end of file
......@@ -54,6 +54,7 @@
<link href="js/libs/jQueryQueryBuilder/css/query-builder.default.min.css?bust=<%- bust %>" rel="stylesheet" />
<link href="js/libs/bootstrap-daterangepicker/css/daterangepicker.css?bust=<%- bust %>" rel="stylesheet" />
<link rel="stylesheet" href="js/libs/nvd3/css/nv.d3.min.css?bust=<%- bust %>" />
<link href="js/libs/dropzone/css/dropzone.css?bust=<%- bust %>" rel="stylesheet">
<link href="js/libs/jstree/css/default/default-theme.min.css?bust=<%- bust %>" rel="stylesheet" />
<link href="js/libs/pretty-checkbox/css/pretty-checkbox.min.css?bust=<%- bust %>" rel="stylesheet" />
<link href="css/style.css?bust=<%- bust %>" rel="stylesheet" />
......
......@@ -175,7 +175,8 @@ require.config({
'sparkline': 'libs/sparkline/jquery.sparkline.min',
'table-dragger': 'libs/table-dragger/table-dragger',
'jstree': 'libs/jstree/jstree.min',
'jquery-steps': 'libs/jquery-steps/jquery.steps.min'
'jquery-steps': 'libs/jquery-steps/jquery.steps.min',
'dropzone': 'libs/dropzone/js/dropzone-amd-module'
},
/**
......@@ -348,4 +349,4 @@ require(['App',
startApp();
}
});
});
});
\ No newline at end of file
<!--
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
-->
<form action={{importUrl}} id="importGlossary" class="dropzone single-file-center"></form>
\ No newline at end of file
......@@ -23,18 +23,22 @@
<button type="button" class="typeRefresh" data-id="showGlossaryType" title="Show Category">
<i class="fa fa-toggle-on switch-button"></i>
</button>
<button title="Create Glossary" type="button" data-id="createGlossary">
<!-- <button title="Create Glossary" type="button" data-id="createGlossary">
<i class="fa fa-plus"></i>
</button>
<!-- <button type="button" class="typeRefresh dropdown">
</button> -->
<button type="button" class="typeRefresh dropdown">
<div class=" btn-secondary dropdown-toggle" type="button" id="dropdownMenuButton" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<i class="fa fa-ellipsis-v"></i>
</div>
<ul class="dropdown-menu" aria-labelledby="dropdownMenuButton">
<ul class="dropdown-menu glossary-dropdown" aria-labelledby="dropdownMenuButton">
<li data-id="createGlossary" data-type="term"> <i class="fa fa-plus"></i><span>Create Glossary</span>
</li>
<li data-id="downloadTemplate" data-type="term"><i class="fa fa-download"></i> <span><a href="{{importTmplUrl}}"><span>Download Import template</span></a></span>
</li>
<li data-id="importGlossary" data-type="term"> <i class="fa fa-upload"></i><a href="javascript:void(0)"><span>Import Glossary</span></a>
</li>
</ul>
</button> -->
</button>
</div>
</div>
<div id="c_term" class="panel-collapse collapse jstree-with-action in">
......
......@@ -185,6 +185,12 @@ define(['require', 'utils/Enums', 'utils/Utils', 'underscore'], function(require
return glossaryUrl;
}
},
glossaryImportTempUrl: function() {
return this.glossaryApiUrl() + '/import/template';
},
glossaryImportUrl: function() {
return this.glossaryApiUrl() + '/import';
},
categoryApiUrl: function(options) {
var guid = options && options.guid,
list = options && options.list,
......
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
define([
"require",
"backbone",
"hbs!tmpl/glossary/ImportGlossaryLayoutView_tmpl",
"modules/Modal",
'utils/CommonViewFunction',
"utils/Utils",
"utils/UrlLinks",
"dropzone"
], function(require, Backbone, ImportGlossaryLayoutViewTmpl, Modal, CommonViewFunction, Utils, UrlLinks, dropzone) {
var ImportGlossaryLayoutView = Backbone.Marionette.LayoutView.extend(
/** @lends ImportGlossaryLayoutView */
{
_viewName: "ImportGlossaryLayoutView",
template: ImportGlossaryLayoutViewTmpl,
templateHelpers: function() {
return {
importUrl: UrlLinks.glossaryImportUrl()
};
},
/** Layout sub regions */
regions: {},
/** ui selector cache */
ui: {},
/** ui events hash */
events: function() {
var events = {};
return events;
},
/**
* intialize a new ImportGlossaryLayoutView Layout
* @constructs
*/
initialize: function(options) {
_.extend(this, _.pick(options, "callback"));
var that = this;
this.modal = new Modal({
title: "Import Glossary",
content: this,
cancelText: "Cancel",
okText: "upload",
allowCancel: true,
okCloses: false,
mainClass: "dropzone-modal"
}).open();
this.modal.$el.find("button.ok").attr("disabled", true);
this.modal.on("ok", function(e) {
that.dropzone.processQueue();
});
this.modal.on("closeModal", function() {
that.modal.trigger("cancel");
});
},
bindEvents: function() {},
onRender: function() {
var that = this;
this.dropzone = null;
var updateButton = function(files) {
var buttonEl = that.modal.$el.find("button.ok");
if (files.length === 0) {
buttonEl.attr("disabled", true);
} else {
buttonEl.attr("disabled", false);
}
}
var headers = {};
headers[CommonViewFunction.restCsrfCustomHeader] = '""';
this.$("#importGlossary").dropzone({
url: UrlLinks.glossaryImportUrl(),
clickable: true,
acceptedFiles: ".csv,.xls,.xlsx",
autoProcessQueue: false,
maxFiles: 1,
addRemoveLinks: true,
init: function() {
that.dropzone = this;
this.on('addedfile', function(file) {
updateButton(this.files);
})
this.on('removedfile', function(file) {
updateButton(this.files);
})
},
maxfilesexceeded: function(file) {
this.removeAllFiles();
this.addFile(file);
},
success: function(file, response) {
that.modal.trigger("cancel");
Utils.notifySuccess({
content: "File: " + file.name + " added successfully"
});
that.callback();
},
error: function(file, response, responseObj) {
Utils.defaultErrorHandler(null, responseObj, { defaultErrorMessage: (response.errorMessage) || response });
that.modal.$el.find("button.ok").attr("disabled", false);
},
dictDefaultMessage: "Drop files here or click to upload.",
headers: headers
});
}
}
);
return ImportGlossaryLayoutView;
});
\ No newline at end of file
......@@ -37,11 +37,15 @@ define([
refreshTree: '[data-id="refreshTree"]',
termSearchTree: '[data-id="termSearchTree"]',
createGlossary: '[data-id="createGlossary"]',
showGlossaryType: '[data-id="showGlossaryType"]'
showGlossaryType: '[data-id="showGlossaryType"]',
importGlossary: "[data-id='importGlossary']",
downloadTemplate: "[data-id='downloadTemplate']"
},
templateHelpers: function() {
return {
apiBaseUrl: UrlLinks.apiBaseUrl
apiBaseUrl: UrlLinks.apiBaseUrl,
importTmplUrl: UrlLinks.glossaryImportTempUrl()
};
},
events: function() {
......@@ -73,6 +77,13 @@ define([
this.isTermView = !this.isTermView;
this.glossarySwitchBtnUpdate();
};
events["click " + this.ui.importGlossary] = function(e) {
e.stopPropagation();
that.onClickImportGlossary();
};
events['click ' + this.ui.downloadTemplate] = function(e) {
e.stopPropagation();
};
return events;
},
bindEvents: function() {
......@@ -581,7 +592,8 @@ define([
gId: glossaryId,
guid: getSelectedParent,
gType: that.isTermView ? 'term' : 'category',
viewType: that.isTermView ? 'term' : 'category'
viewType: that.isTermView ? 'term' : 'category',
searchType: "basic"
}
var serachUrl = '#!/glossary/' + guid;
this.triggerSearch(params, serachUrl);
......@@ -683,6 +695,18 @@ define([
refresh: function(options) {
this.glossaryTermId = null;
this.fetchGlossary();
},
onClickImportGlossary: function() {
var that = this;
require([
'views/glossary/ImportGlossaryLayoutView'
], function(ImportGlossaryLayoutView) {
var view = new ImportGlossaryLayoutView({
callback: function() {
that.refresh();
}
});
});
}
});
return GlossaryTreeLayoutView;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment