pgadmin4/web/pgadmin/misc/dependencies/static/js/dependencies.js
Libor M 94864104e4 Added and fixed gettext usage for better translation coverage. Fixes #5284
1) Fixed usage gettext('') instead of _('') in javascript files.
  2) Fixed usage gettext('') instead of `${gettext('')}` in javascript files,
     because "pybabel extract" not support extracting from this syntax.
2020-03-24 11:14:05 +05:30

255 lines
8.9 KiB
JavaScript

/////////////////////////////////////////////////////////////
//
// pgAdmin 4 - PostgreSQL Tools
//
// Copyright (C) 2013 - 2020, The pgAdmin Development Team
// This software is released under the PostgreSQL Licence
//
//////////////////////////////////////////////////////////////
define('misc.dependencies', [
'sources/gettext', 'underscore', 'jquery', 'backbone',
'pgadmin', 'pgadmin.browser', 'pgadmin.alertifyjs', 'pgadmin.backgrid',
'sources/utils',
], function(gettext, _, $, Backbone, pgAdmin, pgBrowser, Alertify, Backgrid, pgadminUtils) {
if (pgBrowser.NodeDependencies)
return pgBrowser.NodeDependencies;
var wcDocker = window.wcDocker;
pgBrowser.NodeDependencies = pgBrowser.NodeDependencies || {};
_.extend(pgBrowser.NodeDependencies, {
init: function() {
if (this.initialized) {
return;
}
this.initialized = true;
this.dependenciesPanel = pgBrowser.docker.findPanels('dependencies')[0];
/* Parameter is used to set the proper label of the
* backgrid header cell.
*/
_.bindAll(this, 'showDependencies', '__loadMoreRows', '__appendGridToPanel');
// Defining Backbone Model for Dependencies.
var Model = Backbone.Model.extend({
defaults: {
icon: 'icon-unknown',
type: undefined,
name: undefined,
/* field contains 'Database Name' for 'Tablespace and Role node',
* for other node it contains 'Restriction'.
*/
field: undefined,
},
// This function is used to fetch/set the icon for the type(Function, Role, Database, ....)
parse: function(res) {
var node = pgBrowser.Nodes[res.type];
if(res.icon == null || res.icon == '') {
res.icon = node ? (_.isFunction(node['node_image']) ?
(node['node_image']).apply(node, [null, null]) :
(node['node_image'] || ('icon-' + res.type))) :
('icon-' + res.type);
}
res.type = pgadminUtils.titleize(res.type.replace(/_/g, ' '), true);
return res;
},
});
// Defining Backbone Collection for Dependencies.
this.dependenciesCollection = new(Backbone.Collection.extend({
model: Model,
}))(null);
pgBrowser.Events.on('pgadmin-browser:tree:selected', this.showDependencies);
this.__appendGridToPanel();
},
/* Function is used to create and render backgrid with
* empty collection. We just want to add backgrid into the
* panel only once.
*/
__appendGridToPanel: function() {
var $container = this.dependenciesPanel.layout().scene().find('.pg-panel-content'),
$gridContainer = $container.find('.pg-panel-dependencies-container'),
grid = new Backgrid.Grid({
emptyText: gettext('No data found'),
columns: [{
name: 'type',
label: gettext('Type'),
// Extend it to render the icon as per the type.
cell: Backgrid.Cell.extend({
render: function() {
Backgrid.Cell.prototype.render.apply(this, arguments);
this.$el.prepend($('<i>', {
class: 'wcTabIcon ' + this.model.get('icon'),
}));
return this;
},
}),
editable: false,
},
{
name: 'name',
label: gettext('Name'),
cell: 'string',
editable: false,
},
{
name: 'field',
label: '', // label kept blank, it will change dynamically
cell: 'string',
editable: false,
},
],
collection: this.dependenciesCollection,
className: 'backgrid table presentation table-bordered table-noouter-border table-hover',
});
// Condition is used to save grid object to change the label of the header.
this.dependenciesGrid = grid;
$gridContainer.append(grid.render().el);
return true;
},
// Fetch the actual data and update the collection
showDependencies: function(item, data, node) {
let self = this,
msg = gettext('Please select an object in the tree view.'),
panel = this.dependenciesPanel,
$container = panel.layout().scene().find('.pg-panel-content'),
$msgContainer = $container.find('.pg-panel-depends-message'),
$gridContainer = $container.find('.pg-panel-dependencies-container'),
treeHierarchy = node.getTreeNodeHierarchy(item),
n_type = data._type,
url = node.generate_url(item, 'dependency', data, true);
if (node) {
/* We fetch the Dependencies and Dependencies tab only for
* those node who set the parameter hasDepends to true.
*/
msg = gettext('No dependency information is available for the selected object.');
if (node.hasDepends) {
/* Updating the label for the 'field' type of the backbone model.
* Label should be "Database" if the node type is tablespace or role
* and dependencies tab is selected. For other nodes and dependencies tab
* it should be 'Restriction'.
*/
this.dependenciesGrid.columns.models[2].set({
'label': gettext('Restriction'),
});
// Hide message container and show grid container.
$msgContainer.addClass('d-none');
$gridContainer.removeClass('d-none');
var timer = '';
$.ajax({
url: url,
type: 'GET',
beforeSend: function(xhr) {
xhr.setRequestHeader(pgAdmin.csrf_token_header, pgAdmin.csrf_token);
// Generate a timer for the request
timer = setTimeout(function() {
// notify user if request is taking longer than 1 second
$msgContainer.text(gettext('Fetching dependency information from the server...'));
$msgContainer.removeClass('d-none');
msg = '';
}, 1000);
},
})
.done(function(res) {
clearTimeout(timer);
if (res.length > 0) {
if (!$msgContainer.hasClass('d-none')) {
$msgContainer.addClass('d-none');
}
$gridContainer.removeClass('d-none');
self.dependenciesData = res;
// Load only 100 rows
self.dependenciesCollection.reset(self.dependenciesData.splice(0, 100), {parse: true});
// Load more rows on scroll down
pgBrowser.Events.on(
'pgadmin-browser:panel-dependencies:' +
wcDocker.EVENT.SCROLLED,
self.__loadMoreRows
);
} else {
// Do not listen the scroll event
pgBrowser.Events.off(
'pgadmin-browser:panel-dependencies:' +
wcDocker.EVENT.SCROLLED
);
self.dependenciesCollection.reset({silent: true});
$msgContainer.text(msg);
$msgContainer.removeClass('d-none');
if (!$gridContainer.hasClass('d-none')) {
$gridContainer.addClass('d-none');
}
}
})
.fail(function(xhr, error, message) {
var _label = treeHierarchy[n_type].label;
pgBrowser.Events.trigger(
'pgadmin:node:retrieval:error', 'depends', xhr, error, message
);
if (!Alertify.pgHandleItemError(xhr, error, message, {
item: item,
info: treeHierarchy,
})) {
Alertify.pgNotifier(
error, xhr,
gettext('Error retrieving data from the server: %s', message || _label),
function(msg) {
if(msg === 'CRYPTKEY_SET') {
self.showDependencies(item, data, node);
} else {
console.warn(arguments);
}
});
}
// show failed message.
$msgContainer.text(gettext('Failed to retrieve data from the server.'));
});
}
} if (msg != '') {
$msgContainer.text(msg);
$msgContainer.removeClass('d-none');
if (!$gridContainer.hasClass('d-none')) {
$gridContainer.addClass('d-none');
}
}
},
__loadMoreRows: function() {
if (this.dependenciesPanel.length < 1) return ;
let elem = this.dependenciesPanel.$container.find('.pg-panel-dependencies-container').closest('.wcFrameCenter')[0];
if ((elem.scrollHeight - 10) < elem.scrollTop + elem.offsetHeight) {
if (this.dependenciesData.length > 0) {
this.dependenciesCollection.add(this.dependenciesData.splice(0, 100), {parse: true});
}
}
},
});
return pgBrowser.NodeDependencies;
});