4974-datasources-and-improvements #4

Merged
guillermo merged 24 commits from 4974-datasources-and-improvements into master 2023-02-03 12:26:09 +00:00
3 changed files with 217 additions and 235 deletions
Showing only changes of commit fd3074d1ca - Show all commits

View File

@ -1,6 +1,5 @@
var Conf = { var Conf = {
appName: 'Verdnatura', appName: 'Verdnatura',
dsName: 'verdnatura',
odbcPath: 'HKCU\\Software\\ODBC\\ODBC.INI\\', odbcPath: 'HKCU\\Software\\ODBC\\ODBC.INI\\',
regPath: 'HKCU\\SOFTWARE\\Verdnatura\\vn-access', regPath: 'HKCU\\SOFTWARE\\Verdnatura\\vn-access',
defaultModule: 'vn', defaultModule: 'vn',
@ -8,38 +7,14 @@ var Conf = {
defaultBranch: 'master', defaultBranch: 'master',
defaultDatasource: 'production', defaultDatasource: 'production',
defaultRemoteURL: 'https://salix.verdnatura.es', defaultRemoteURL: 'https://salix.verdnatura.es',
defaultServer: 'db.verdnatura.es',
dbName: 'vn2008', dbName: 'vn2008',
maxCorruptSize: 600, maxCorruptSize: 600,
odbcDriver: 'MySQL ODBC 8.0 Unicode Driver', odbcDriver: 'MySQL ODBC 8.0 Unicode Driver',
driverPath: '\\MySQL\\Connector ODBC 8.0\\myodbc8w.dll', driverPath: '\\MySQL\\Connector ODBC 8.0\\myodbc8w.dll',
version: 4, version: 4,
cdnURL: 'https://cdn.verdnatura.es/vn-access', cdnURL: 'https://cdn.verdnatura.es/vn-access',
datasources: { identifier: '.vn'
production: {
DESCRIPTION: 'production',
SERVER: 'db.verdnatura.es',
PORT: '3306',
SSLMODE: 'VERIFY_IDENTITY'
},
test: {
DESCRIPTION: 'test',
SERVER: 'test-db.verdnatura.es',
PORT: '3306',
SSLMODE: 'VERIFY_IDENTITY'
},
dev: {
DESCRIPTION: 'dev',
SERVER: 'dev-db.verdnatura.es',
PORT: '3307',
SSLMODE: 'DISABLED'
},
localhost: {
DESCRIPTION: 'local',
SERVER: 'localhost',
PORT: '3306',
SSLMODE: 'DISABLED'
}
}
}; };
var Locale = { var Locale = {
@ -116,31 +91,54 @@ var App = {
// Creates the MySQL ODBC connection // Creates the MySQL ODBC connection
this.createODBC( this.createODBC(
Conf.odbcPath, Conf.odbcPath,
Conf.dsName, Conf.defaultDatasource + Conf.identifier,
Conf.odbcDriver Conf.odbcDriver
); );
this.createDatasources();
this.regWrite(Conf.regPath, 'remoteURL', Conf.defaultRemoteURL); this.regWrite(Conf.regPath, 'remoteURL', Conf.defaultRemoteURL);
this.regWrite(Conf.regPath, 'lastExecutedVersion', Conf.version); this.regWrite(Conf.regPath, 'lastExecutedVersion', Conf.version);
// Delete old strings values (REMOVE IN VERSION 5) // Delete old strings values (REMOVE IN VERSION 5)
this.regDelete(Conf.regPath + 'configured'); this.regDelete(Conf.regPath + 'configured');
this.regDelete(Conf.regPath + 'remember'); this.regDelete(Conf.regPath + 'remember');
// this.regDelete(Conf.odbcPath + 'verdnatura'); ToDo: Descomentar al subir
} }
var notSignOut = this.regRead(Conf.regPath, 'notSignOut'); var notSignOut = this.regRead(Conf.regPath, 'notSignOut');
var password = this.regRead(Conf.odbcPath + Conf.dsName, 'PWD');
this.$('user').value = this.regRead(Conf.odbcPath + Conf.dsName, 'UID');
this.$('password').value = password;
// Branch options // Branch options
this.request('GET', 'mdbBranches', null, function(err, res) {
if (err)
throw new Error ('Version could not be retrieved: '+ err.message +': ');
var selectBranch = document.querySelector('#branch');
var option = [];
for (var x in res) {
option[x] = document.createElement('option');
option[x].text = res[x].name
option[x].value = res[x].name
selectBranch.options.add(option[x])
}
});
this.$('branch').value = this.getBranch(); this.$('branch').value = this.getBranch();
this.onChangeBranch(); this.onChangeBranch();
// Datasource options // Datasource options
this.$('datasource').value = this.getDatasource(); var selectDatarouce = document.querySelector('#datasource');
var option = [];
var odbcName;
var allOdbc = this.EnumValues('HKCU\\SOFTWARE\\ODBC\\ODBC.INI\\ODBC Data Sources\\')
for (var y in allOdbc) {
if (allOdbc[y].slice(-3) == Conf.identifier) {
odbcName = allOdbc[y].replace(Conf.identifier, '')
option[y] = document.createElement('option');
option[y].text = odbcName
option[y].value = odbcName
selectDatarouce.options.add(option[y])
}
}
this.$('datasource').value = this.getDatasource();
if (notSignOut && password) { if (notSignOut && password) {
this.$('password').value = password; this.$('password').value = password;
this.$('notSignOut').checked = true; this.$('notSignOut').checked = true;
@ -160,14 +158,13 @@ var App = {
}, },
createODBC: function(path, dsName, driverName) { createODBC: function(path, dsName, driverName) {
var driverPath = this.getEnv('ProgramFiles') + Conf.driverPath; var driverPath = this.getEnv('ProgramFiles') + Conf.driverPath;
var datasource = Conf.defaultDatasource;
var params = { var params = {
Driver: driverPath, Driver: driverPath,
DESCRIPTION: Conf.appName, DESCRIPTION: Conf.appName,
SERVER: Conf.datasources[datasource].SERVER, SERVER: Conf.defaultServer,
DATABASE: Conf.dbName, DATABASE: Conf.dbName,
SSLCA: this.certFile, SSLCA: this.certFile,
SSLMODE: Conf.datasources[datasource].SSLMODE, SSLMODE: 'VERIFY_IDENTITY',
SSLCIPHER: 'AES256-SHA', SSLCIPHER: 'AES256-SHA',
AUTO_RECONNECT: 1, AUTO_RECONNECT: 1,
NO_PROMPT: 1, NO_PROMPT: 1,
@ -177,17 +174,20 @@ var App = {
this.regWrite(path + 'ODBC Data Sources', dsName, driverName); this.regWrite(path + 'ODBC Data Sources', dsName, driverName);
this.regWrites(path + dsName, params); this.regWrites(path + dsName, params);
}, },
updateODBC: function(path, dsName, datasource) { updateODBC: function() {
var params = Conf.datasources[datasource] var odbcPath = this.getOdbcPath();
var datasourcePath = this.getDatasourcePath(); var myUID = this.regRead(odbcPath, 'remoteUser');
var myUID = this.regRead(datasourcePath, 'UID'); var myPWD = this.regRead(odbcPath, 'remotePass');
var myPWD = this.regRead(datasourcePath, 'PWD');
var params = [];
if (myUID && myPWD) { if (myUID && myPWD) {
params['UID'] = myUID; params['UID'] = myUID;
params['PWD'] = myPWD; params['PWD'] = myPWD;
} else {
params['UID'] = this.regRead(odbcPath, 'UID');
params['PWD'] = null;
} }
this.regWrites(path + dsName, params); this.regWrites(odbcPath, params);
}, },
disableUi: function(disabled, loadMessage) { disableUi: function(disabled, loadMessage) {
if (disabled) if (disabled)
@ -253,21 +253,20 @@ var App = {
this.$("datasource").className = null; this.$("datasource").className = null;
}; };
if (!hasUpdate) { if (!hasUpdate) {
this.updateDatasource(myDatasource); this.regWrite(Conf.regPath, 'currentDatasource', myDatasource);
this.updateODBC( this.updateODBC();
Conf.odbcPath,
Conf.dsName,
myDatasource
);
}; };
if (hasChangeCredentials) { if (hasChangeCredentials) {
var datasourcePath = this.getDatasourcePath(); var odbcPath = this.getOdbcPath();
var myUID = this.regRead(datasourcePath, 'UID'); var myUID = this.regRead(odbcPath, 'remoteUser');
var myPWD = this.regRead(datasourcePath, 'PWD'); var myPWD = this.regRead(odbcPath, 'remotePass');
if (myUID && myPWD) { if (myUID && myPWD) {
this.$('user').value = myUID; this.$('user').value = myUID;
this.$('password').value = myPWD; this.$('password').value = myPWD;
}; } else {
this.$('user').value = this.regRead(odbcPath, 'UID')
this.$('password').value = this.regRead(odbcPath, 'PWD')
}
}; };
this.$('user').focus(); this.$('user').focus();
}, },
@ -320,43 +319,11 @@ var App = {
if (!password) if (!password)
throw new Error(_('Enter a password')); throw new Error(_('Enter a password'));
this.regWrite(Conf.odbcPath + Conf.dsName, 'UID', user); this.regWrite(this.getOdbcPath(), 'UID', user);
this.regWrite(Conf.odbcPath + Conf.dsName, 'PWD', password); this.regWrite(this.getOdbcPath(), 'PWD', password);
// Check the cretentials and return the last version number
var version = this.fetchVersion();
// Check if there is a new version, and if there is, download it
if (version) {
this.disableUi(true, _('Updating'));
var remoteFile = version
? '.archive/'+ this.module +'/'+ version +'.7z'
: this.module +'.7z?'+ new Date().getTime();
remoteFile = Conf.cdnURL +'/'+ remoteFile;
var request = new ActiveXObject("MSXML2.XMLHTTP.6.0");
request.open('GET', remoteFile, true);
request.onreadystatechange = function() {
App.onRequestReady(request);
};
request.send();
} else
this.openMdb();
} catch (err) {
this.catchError(err);
}
},
/**
* Gets information about the version to download.
* cmdle
* @return {Number|Boolean} Version number, %false if cannot
* fetch or %null if local is up-to-date
*/
fetchVersion: function() {
var mysqlConn = new ActiveXObject('ADODB.Connection'); var mysqlConn = new ActiveXObject('ADODB.Connection');
var datasource = this.getDatasource(); var datasource = this.getDatasource();
var user = this.$('user').value;
var password = this.$('password').value;
// FIXME: Can't login in dev-db // FIXME: Can't login in dev-db
if (datasource == 'dev') { if (datasource == 'dev') {
@ -365,14 +332,15 @@ var App = {
// Check credentials // Check credentials
try { try {
var odbcPath = this.getOdbcPath()
mysqlConn.open(this.getODBCString({ mysqlConn.open(this.getODBCString({
Driver: '{'+ Conf.odbcDriver +'}', Driver: '{'+ Conf.odbcDriver +'}',
SERVER: Conf.datasources[datasource].SERVER, SERVER: this.regRead(odbcPath, 'SERVER'),
DATABASE: Conf.dbName, DATABASE: Conf.dbName,
UID: user, UID: user,
PWD: password, PWD: password,
SSLCA: this.certFile, SSLCA: this.certFile,
SSLMODE: Conf.datasources[datasource].SSLMODE, SSLMODE: this.regRead(odbcPath, 'SSLMODE'),
SSLCIPHER: 'AES256-SHA', SSLCIPHER: 'AES256-SHA',
ENABLE_CLEARTEXT_PLUGIN : 1 ENABLE_CLEARTEXT_PLUGIN : 1
})); }));
@ -399,42 +367,68 @@ var App = {
} }
mysqlConn.close(); mysqlConn.close();
// Request to obtain the token and lastest version of this module // Check the cretentials and return the last version number
try { var version = this.fetchVersion();
var request = new ActiveXObject("MSXML2.XMLHTTP.6.0");
urlLoginMethod = this.getRemoteURL() + '/api/Accounts/login'
request.open('POST', urlLoginMethod, false);
request.setRequestHeader('Content-Type', 'application/json')
var params = JSON.stringify({
"user": user,
"password": password
});
request.onreadystatechange = function() {
App.onRequestTokenReady(request);
}
request.send(params);
} catch (err) {
throw err;
};
// Check if there is a new version, and if there is, download it
if (version) {
this.disableUi(true, _('Updating'));
var remoteFile = version
? '.archive/'+ this.module +'/'+ version +'.7z'
: this.module +'.7z?'+ new Date().getTime();
remoteFile = Conf.cdnURL +'/'+ remoteFile;
var request = new ActiveXObject('MSXML2.XMLHTTP.6.0');
request.open('GET', remoteFile, true);
request.onreadystatechange = function() {
App.onRequestReady(request);
};
request.send();
} else
this.openMdb();
} catch (err) {
this.catchError(err);
}
},
/**
* Gets information about the version to download.
* cmdle
* @return {Number|Boolean} Version number, %false if cannot
* fetch or %null if local is up-to-date
*/
fetchVersion: function() {
// To obtain the lastest version of this module
var params = {
filter: {
fields: ['version'],
where: {
app: this.module,
branchFk: this.$('branch').value
},
}
};
this.request('GET', 'MdbVersions/findOne', params, function(err, res) {
if (err)
throw new Error ('Version could not be retrieved: '+ err.message +': ');
alert(this.lockFile)
// Checks if it's already open // Checks if it's already open
if (this.fso.fileExists(this.lockFile)) if (App.fso.fileExists(this.lockFile))
try { try {
this.fso.deleteFile(this.lockFile); App.fso.deleteFile(this.lockFile);
return this.lastVersion; return res.version;
} catch (e) { } catch (e) {
throw new Error(_('Application it\'s already open')); throw new Error(_('Application it\'s already open'));
} }
// Checks if MDB exists // Checks if MDB exists
if (!this.fso.fileExists(this.mdbFile)) if (!App.fso.fileExists(this.mdbFile))
return this.lastVersion; return res.version;
// If it's abnormaly bigger, maybe is corrupted, so force download // If it's abnormaly bigger, maybe is corrupted, so force download
var file = this.fso.getFile(this.mdbFile); var file = App.fso.getFile(this.mdbFile);
if (file.size > Conf.maxCorruptSize * 1024 * 1024) if (file.size > Conf.maxCorruptSize * 1024 * 1024)
return this.lastVersion; return res.version;
// Obtains the local version number from the MDB file // Obtains the local version number from the MDB file
var localVersion = this.mdbGetValue( var localVersion = this.mdbGetValue(
@ -445,9 +439,10 @@ var App = {
localVersion = false; localVersion = false;
// Determines if should download // Determines if should download
return !localVersion || this.lastVersion === false || localVersion != this.lastVersion return !localVersion || res.version === false || localVersion != res.version
? this.lastVersion ? res.version
: null; : null;
});
}, },
mdbGetValue: function(query, field, parseFn) { mdbGetValue: function(query, field, parseFn) {
var value; var value;
@ -516,53 +511,6 @@ var App = {
this.catchError(e); this.catchError(e);
} }
}, },
onRequestTokenReady: function(request) {
if (request.readyState !== 4)
return;
try {
if (request.status == 401) // Unhauthorized
throw new Error('Bad login in the remoteURL "' + this.getRemoteURL() +
'":\nThe latest version could not be obtained');
else if (request.status !== 200 )
throw new Error('HTTP: '+ request.statusText + ' ' + request.status);
this.response = JSON.parse(request.responseText)
if (this.response) {
var request = new ActiveXObject("MSXML2.ServerXMLHTTP");
var filter = '&filter=' + JSON.stringify({
"fields":["version"],
"where":{
"app": this.module,
"branchFk": this.$('branch').value
},
});
var urlVersionMethod = this.getRemoteURL() + '/api/MdbVersions?access_token=' + this.response.token + filter
request.open('GET', urlVersionMethod, false);
request.onreadystatechange = function() {
App.onRequestVersionReady(request);
};
request.send();
}
} catch (err) {
throw err;
}
},
onRequestVersionReady: function(request) {
if (request.readyState !== 4)
return;
try {
if (request.status !== 200 )
throw new Error('HTTP: '+ request.statusText + ' ' + request.status);
var response = JSON.parse(request.responseText);
this.lastVersion = response[0].version
} catch (err) {
throw err;
}
},
openMdb: function() { openMdb: function() {
var notSignOut = !!this.$('notSignOut').checked; var notSignOut = !!this.$('notSignOut').checked;
this.regWrite(Conf.regPath, 'notSignOut', notSignOut); this.regWrite(Conf.regPath, 'notSignOut', notSignOut);
@ -580,7 +528,7 @@ var App = {
var clearPassword = err.name == 'BadLogin'; var clearPassword = err.name == 'BadLogin';
if (!this.$('notSignOut').checked || clearPassword) if (!this.$('notSignOut').checked || clearPassword)
this.regWrite(Conf.odbcPath + Conf.dsName, 'PWD', ''); this.regWrite(this.getOdbcPath(), 'PWD', '');
this.disableUi(false); this.disableUi(false);
this.showMessage(err.message, 'error'); this.showMessage(err.message, 'error');
@ -676,6 +624,51 @@ var App = {
this.shell.regDelete(path); this.shell.regDelete(path);
} catch (e) {} } catch (e) {}
}, },
request: function (method, url, data, cb) {
var fullUrl = this.getRemoteURL() +'/api/'+ url;
var isGet = method == 'GET';
if (isGet) {
var isFirst = true;
for (var param in data) {
fullUrl += isFirst ? '?' : '&';
isFirst = false;
var value = data[param];
if (typeof value == 'object')
value = JSON.stringify(value);
fullUrl += param +'='+ encodeURIComponent(value);
}
}
var req = new ActiveXObject('MSXML2.XMLHTTP.6.0');
req.open(method, fullUrl, false);
req.onreadystatechange = function() {
App.onRequestStateChange(req, cb)
};
if (isGet) {
req.setRequestHeader('Content-Type', 'application/json');
req.send(JSON.stringify(data));
} else
req.send();
},
onRequestStateChange: function(req, cb) {
if (req.readyState !== 4)
return;
var status = req.status;
if (status >= 100 && status < 400) {
var res = JSON.parse(req.responseText);
cb(null, res);
} else {
err = new Error(req.statusText);
err.name = 'HttpError';
err.status = status;
err.req = req;
if (status >= 400 && status < 600)
err.error = JSON.parse(req.responseText);
cb(err);
}
},
/** /**
* Gets information about the branch config in access * Gets information about the branch config in access
* *
@ -698,6 +691,7 @@ var App = {
Conf.regPath, Conf.regPath,
'currentDatasource' 'currentDatasource'
); );
return datasource || Conf.defaultDatasource; return datasource || Conf.defaultDatasource;
}, },
/** /**
@ -713,42 +707,36 @@ var App = {
return remoteURL || Conf.defaultRemoteURL; return remoteURL || Conf.defaultRemoteURL;
}, },
/** /**
* Get the current datasource path * Get the odbc path
* *
* @return {string} Datasource path * @return {string} Remote server
*/ */
getDatasourcePath: function() { getOdbcPath: function() {
var datasourcePath = Conf.regPath + '\\datasources\\' + this.getDatasource(); var odbcPath = Conf.odbcPath +
(this.$("datasource").value || Conf.defaultDatasource) +
return datasourcePath; Conf.identifier
return odbcPath;
}, },
/** EnumValues: function(RegKey) {
* Update the datasource var RootKey = new Object()
* RootKey["HKCR"] = RootKey["HKEY_CLASSES_ROOT"] = 0x80000000;
* @param {String} datasource The datasource RootKey["HKCU"] = RootKey["HKEY_CURRENT_USER"] = 0x80000001;
*/ RootKey["HKLM"] = RootKey["HKEY_LOCAL_MACHINE"] = 0x80000002;
updateDatasource: function(datasource) { RootKey["HKUS"] = RootKey["HKEY_USERS"] = 0x80000003;
this.regWrite(Conf.regPath, 'currentDatasource', datasource); RootKey["HKCC"] = RootKey["HKEY_CURRENT_CONFIG"] = 0x80000005;
}, var RootVal = RootKey[RegKey.substr(0, RegKey.indexOf("\\"))]
/** if (RootVal != undefined) {
* Create all datasources structure Locator = new ActiveXObject("WbemScripting.SWbemLocator");
*/ ServerConn = Locator.ConnectServer(null, "root\\default");
createDatasources: function() { Registry = ServerConn.Get("StdRegProv");
var params = { Method = Registry.Methods_.Item("EnumValues");
'UID': null, p_In = Method.InParameters.SpawnInstance_();
'PWD': null p_In.hDefKey = RootVal;
p_In.sSubKeyName = RegKey.substr(RegKey.indexOf("\\") + 1)
p_Out = Registry.ExecMethod_(Method.Name, p_In);
return p_Out.sNames.toArray();
} }
for (var datasource in Conf.datasources) {
var myPath = Conf.regPath + '\\datasources\\' + datasource
for (var stringValues in Conf.datasources[datasource]) {
this.regWrite(myPath,
stringValues,
Conf.datasources[datasource][stringValues]
);
} }
this.regWrites(myPath, params);
};
},
}; };
App.init(); App.init();

View File

@ -123,6 +123,7 @@ button:hover {
display: none; display: none;
padding-left: .3em; padding-left: .3em;
padding-right: .8em; padding-right: .8em;
max-width: 133px;
} }
#branchButton { #branchButton {
float: left; float: left;
@ -184,6 +185,7 @@ select.dev {
padding-right: .8em; padding-right: .8em;
margin-right: .5em; margin-right: .5em;
margin-top: -1.91em; margin-top: -1.91em;
max-width: 133px;
} }
#datasourceButton { #datasourceButton {
float: right; float: right;

View File

@ -61,11 +61,7 @@
App.onShowDatasourceOptionsClick()" App.onShowDatasourceOptionsClick()"
alt="Change branch"/> alt="Change branch"/>
<div id="branchSelector"> <div id="branchSelector">
<select id="branch" onchange="App.onChangeBranch()"> <select id="branch" onchange="App.onChangeBranch()"></select>
<option value="master">master</option>
<option value="test">test</option>
<option value="dev">dev</option>
</select>
</div> </div>
</div> </div>
</div> </div>
@ -79,10 +75,6 @@
alt="Change datasource"/> alt="Change datasource"/>
<div id="datasourceSelector"> <div id="datasourceSelector">
<select id="datasource" onchange="App.onChangeDatasource(false, true)"> <select id="datasource" onchange="App.onChangeDatasource(false, true)">
<option value="production">production</option>
<option value="test">test</option>
<option value="dev">dev</option>
<option value="localhost">localhost</option>
</select> </select>
</div> </div>
</div> </div>