2018-06-01 Fred Gleason <fredg@paravelsystems.com>

* Stubbed out rddbmgr(8).
	* Implemented the '--create' command in rddbmgr(8).
	* Fixed a bug in 'RDStation::create()' that generated corrupt records
	in the 'AUDIO_INPUT' and 'AUDIO_OUTPUTS' tables when creating a
	new host with no exemplar.
This commit is contained in:
Fred Gleason 2018-06-01 23:23:58 +00:00
parent fec324abd8
commit 7133d0f388
16 changed files with 3191 additions and 3 deletions

1
.gitignore vendored
View File

@ -117,6 +117,7 @@ utils/rdsoftkeys/rdsoftkeys
utils/rddbcheck/rddbcheck
utils/rdalsaconfig/rdalsaconfig
utils/rdpopup/rdpopup
utils/rddbmgr/rddbmgr
utils/rddelete/rddelete
utils/rdgpimon/rdgpimon
utils/rdimport/rdimport

View File

@ -17010,3 +17010,9 @@
* Incremented the package version to 2.19.2vlog03.
2018-05-31 Fred Gleason <fredg@paravelsystems.com>
* Fixed a bug that broke the build on RHEL 6.
2018-06-01 Fred Gleason <fredg@paravelsystems.com>
* Stubbed out rddbmgr(8).
* Implemented the '--create' command in rddbmgr(8).
* Fixed a bug in 'RDStation::create()' that generated corrupt records
in the 'AUDIO_INPUT' and 'AUDIO_OUTPUTS' tables when creating a
new host with no exemplar.

View File

@ -511,6 +511,7 @@ AC_CONFIG_FILES([rivendell.spec \
utils/rdcollect/Makefile \
utils/rdconvert/Makefile \
utils/rddbcheck/Makefile \
utils/rddbmgr/Makefile \
utils/rddelete/Makefile \
utils/rddgimport/Makefile \
utils/rddiscimport/Makefile \

View File

@ -587,9 +587,14 @@ void RDConfig::load()
profile->stringValue("mySQL","Charset",DEFAULT_MYSQL_CHARSET);
conf_mysql_collation=
profile->stringValue("mySQL","Collation",DEFAULT_MYSQL_COLLATION);
/*
conf_create_table_postfix=QString(" engine ")+conf_mysql_engine+" "+
"character set "+conf_mysql_charset+" "+
"collate "+conf_mysql_collation;
*/
conf_create_table_postfix=
RDConfig::createTablePostfix(conf_mysql_engine,conf_mysql_charset,
conf_mysql_collation);
facility=profile->stringValue("Logs","Facility",DEFAULT_LOG_FACILITY).lower();
if(facility=="syslog") {
@ -759,3 +764,12 @@ QString RDConfig::userAgent(const QString &modname)
}
return QString("Mozilla/5.0 rivendell/")+VERSION+" ("+modname+")";
}
QString RDConfig::createTablePostfix(const QString &engine,
const QString &charset,
const QString &collation)
{
return QString(" engine ")+engine+" "+"character set "+charset+" "+
"collate "+collation;
}

View File

@ -119,6 +119,9 @@ class RDConfig
void load();
void clear();
static QString userAgent(const QString &modname);
static QString createTablePostfix(const QString &engine,
const QString &charset,
const QString &collation);
private:
QString conf_filename;

View File

@ -120,6 +120,38 @@ RDSqlQuery::RDSqlQuery(const QString &query,bool reconnect):
}
QVariant RDSqlQuery::run(const QString &sql,bool *ok)
{
QVariant ret;
RDSqlQuery *q=new RDSqlQuery(sql);
if(ok!=NULL) {
*ok=q->isActive();
}
delete q;
q=new RDSqlQuery("select LAST_INSERT_ID()",false);
if(q->first()) {
ret=q->value(0);
}
delete q;
return ret;
}
int RDSqlQuery::rows(const QString &sql)
{
int ret=0;
RDSqlQuery *q=new RDSqlQuery(sql);
ret=q->size();
delete q;
return ret;
}
void RDSqlDatabaseStatus::sendRecon()
{
if (discon){

View File

@ -49,6 +49,8 @@ class RDSqlQuery : public QSqlQuery
{
public:
RDSqlQuery(const QString &query=QString::null,bool reconnect=true);
static QVariant run(const QString &sql,bool *ok=NULL);
static int rows(const QString &sql);
};
// Setup the default database, returns true on success.

View File

@ -736,14 +736,14 @@ bool RDStation::create(const QString &name,QString *err_msg,
sql=QString("insert into AUDIO_INPUTS set ")+
"STATION_NAME=\""+RDEscapeString(name)+"\","+
QString().sprintf("CARD_NUMBER=%d,",i)+
QString().sprintf("PORT_NUMBER=%d",i);
QString().sprintf("PORT_NUMBER=%d",j);
q=new RDSqlQuery(sql);
delete q;
sql=QString("insert into AUDIO_OUTPUTS set ")+
"STATION_NAME=\""+RDEscapeString(name)+"\","+
QString().sprintf("CARD_NUMBER=%d,",i)+
QString().sprintf("PORT_NUMBER=%d",i);
QString().sprintf("PORT_NUMBER=%d",j);
q=new RDSqlQuery(sql);
delete q;
}

View File

@ -1463,7 +1463,7 @@ bool CreateDb(QString name,QString pwd,RDConfig *config)
"DEFAULT_SERVICE char(10),"+
"SKIN_PATH char(255) default \""+
RDEscapeString(RD_DEFAULT_RDPANEL_SKIN)+"\","+
"index STATION_IDX (STATION,INSTANCE))"+
"index STATION_IDX (STATION))"+
config->createTablePostfix();
if(!RunQuery(sql)) {
return false;

View File

@ -32,6 +32,7 @@ SUBDIRS = $(ALSACONFIG_RD_OPT)\
rdclilogedit\
rdcollect\
rdconvert\
rddbmgr\
rddelete\
rddiscimport\
rdexport\

53
utils/rddbmgr/Makefile.am Normal file
View File

@ -0,0 +1,53 @@
## Makefile.am
##
## MAkefile.am for rivendell/utils/rddbmgr
##
## (C) Copyright 2018 Fred Gleason <fredg@paravelsystems.com>
##
## This program is free software; you can redistribute it and/or modify
## it under the terms of the GNU General Public License version 2 as
## published by the Free Software Foundation.
##
## This program is distributed in the hope that it will be useful,
## but WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU General Public License for more details.
##
## You should have received a copy of the GNU General Public
## License along with this program; if not, write to the Free Software
## Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
##
## Use automake to process this into a Makefile.in
AM_CPPFLAGS = -Wall -DPREFIX=\"$(prefix)\" -DQTDIR=\"@QT_DIR@\" @QT_CXXFLAGS@ -I$(top_srcdir)/lib
LIBS = @QT_LIBS@ -L$(top_srcdir)/lib
MOC = @QT_MOC@
# The dependency for qt's Meta Object Compiler (moc)
moc_%.cpp: %.h
$(MOC) $< -o $@
sbin_PROGRAMS = rddbmgr
dist_rddbmgr_SOURCES = check.cpp\
create.cpp\
modify.cpp\
rddbmgr.cpp rddbmgr.h
rddbmgr_LDADD = @LIB_RDLIBS@ @LIBVORBIS@
CLEANFILES = *~\
*.exe\
*.idb\
*ilk\
*.obj\
*.pdb\
*.qm\
moc_*
MAINTAINERCLEANFILES = *~\
*.tar.gz\
aclocal.m4\
configure\
Makefile.in\
moc_*

27
utils/rddbmgr/check.cpp Normal file
View File

@ -0,0 +1,27 @@
// check.cpp
//
// Routines for --check for rddbmgr(8)
//
// (C) Copyright 2018 Fred Gleason <fredg@paravelsystems.com>
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 2 as
// published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this program; if not, write to the Free Software
// Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//
#include "rddbmgr.h"
bool MainObject::Check(QString *err_msg) const
{
*err_msg="ok";
return true;
}

2699
utils/rddbmgr/create.cpp Normal file

File diff suppressed because it is too large Load Diff

28
utils/rddbmgr/modify.cpp Normal file
View File

@ -0,0 +1,28 @@
// modify.cpp
//
// Routines for --modify for rddbmgr(8)
//
// (C) Copyright 2018 Fred Gleason <fredg@paravelsystems.com>
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 2 as
// published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this program; if not, write to the Free Software
// Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//
#include "rddbmgr.h"
bool MainObject::Modify(QString *err_msg,int set_schema,
const QString &set_version) const
{
*err_msg="ok";
return true;
}

259
utils/rddbmgr/rddbmgr.cpp Normal file
View File

@ -0,0 +1,259 @@
// rddbmgr.cpp
//
// Rivendell database management utility
//
// (C) Copyright 2018 Fred Gleason <fredg@paravelsystems.com>
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 2 as
// published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this program; if not, write to the Free Software
// Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <qapplication.h>
#include <qsqldatabase.h>
#include <qstringlist.h>
#include <rdcmd_switch.h>
#include "rddbmgr.h"
MainObject::MainObject(QObject *parent)
: QObject(parent)
{
bool ok=false;
db_command=MainObject::NoCommand;
int set_schema=0;
QString set_version="";
QString station_name;
bool generate_audio=false;
db_verbose=false;
//
// Check that we're 'root'
//
if(geteuid()!=0) {
fprintf(stderr,"rddbmgr: this utility requires root privileges\n");
exit(1);
}
//
// Load default DB credentials
//
db_config=new RDConfig();
db_config->load();
db_mysql_hostname=db_config->mysqlHostname();
db_mysql_loginname=db_config->mysqlUsername();
db_mysql_password=db_config->mysqlPassword();
db_mysql_database=db_config->mysqlDbname();
db_mysql_driver=db_config->mysqlDriver();
db_mysql_engine=db_config->mysqlEngine();
db_mysql_charset=db_config->mysqlCharset();
db_mysql_collation=db_config->mysqlCollation();
station_name=db_config->stationName();
//
// Process Command Switches
//
RDCmdSwitch *cmd=
new RDCmdSwitch(qApp->argc(),qApp->argv(),"rddbmgr",RDDBMGR_USAGE);
for(unsigned i=0;i<cmd->keys();i++) {
if(cmd->key(i)=="--check") {
MainObject::Command command=MainObject::CheckCommand;
if((db_command!=MainObject::NoCommand)&&
(db_command!=MainObject::CheckCommand)) {
fprintf(stderr,"rddbmgr: exactly one command must be specified\n");
exit(1);
}
db_command=command;
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--create") {
MainObject::Command command=MainObject::CreateCommand;
if((db_command!=MainObject::NoCommand)&&
(db_command!=MainObject::CreateCommand)) {
fprintf(stderr,"rddbmgr: exactly one command must be specified\n");
exit(1);
}
db_command=command;
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--modify") {
MainObject::Command command=MainObject::ModifyCommand;
if((db_command!=MainObject::NoCommand)&&
(db_command!=MainObject::ModifyCommand)) {
fprintf(stderr,"rddbmgr: exactly one command must be specified\n");
exit(1);
}
db_command=command;
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--generate-audio") {
generate_audio=true;
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-hostname") {
db_mysql_hostname=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-loginname") {
db_mysql_loginname=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-password") {
db_mysql_password=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-database") {
db_mysql_database=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-driver") {
db_mysql_driver=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-engine") {
db_mysql_engine=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-charset") {
db_mysql_charset=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--mysql-collation") {
db_mysql_collation=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--set-schema") {
set_schema=cmd->value(i).toInt(&ok);
if((!ok)||(set_schema<=0)) {
fprintf(stderr,"rddbmgr: invalid schema\n");
exit(1);
}
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--set-version") {
bool ok2=false;
set_version=cmd->value(i);
QStringList f0=f0.split(".",set_version);
if(f0.size()==3) {
ok2=true;
for(int i=0;i<3;i++) {
f0[i].toInt(&ok);
ok2=ok2&&ok;
}
}
if(!ok2) {
fprintf(stderr,"rddbmgr: invalid version\n");
exit(1);
}
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--station-name") {
station_name=cmd->value(i);
cmd->setProcessed(i,true);
}
if(cmd->key(i)=="--verbose") {
db_verbose=true;
cmd->setProcessed(i,true);
}
if(!cmd->processed(i)) {
fprintf(stderr,"rddbmgr: unrecognized option \"%s\"\n",
(const char *)cmd->key(i));
exit(1);
}
}
delete cmd;
//
// Sanity Checks
//
if(db_command==MainObject::NoCommand) {
fprintf(stderr,"rddbmgr: exactly one command must be specified\n");
exit(1);
}
if(db_verbose) {
fprintf(stderr,"Using DB Credentials:\n");
fprintf(stderr," Hostname: %s\n",(const char *)db_mysql_hostname);
fprintf(stderr," Loginname: %s\n",(const char *)db_mysql_loginname);
fprintf(stderr," Password: %s\n",(const char *)db_mysql_password);
fprintf(stderr," Database: %s\n",(const char *)db_mysql_database);
fprintf(stderr," Driver: %s\n",(const char *)db_mysql_driver);
fprintf(stderr," Engine: %s\n",(const char *)db_mysql_engine);
fprintf(stderr," Charset: %s\n",(const char *)db_mysql_charset);
fprintf(stderr," Collation: %s\n",(const char *)db_mysql_collation);
}
//
// Open Database
//
QSqlDatabase *db=QSqlDatabase::addDatabase(db_mysql_driver);
if(!db) {
fprintf(stderr,"rddbmgr: unable to connect to database server\n");
exit(1);
}
db->setDatabaseName(db_mysql_database);
db->setUserName(db_mysql_loginname);
db->setPassword(db_mysql_password);
db->setHostName(db_mysql_hostname);
if(!db->open()) {
fprintf(stderr,"rddbmgr: unable to open database [%s]\n",
(const char *)db->lastError().text());
db->removeDatabase(db_mysql_database);
exit(1);
}
db_table_create_postfix=
RDConfig::createTablePostfix(db_mysql_engine,db_mysql_charset,
db_mysql_collation);
//
// Run the Command
//
QString err_msg;
switch(db_command) {
case MainObject::CheckCommand:
ok=Check(&err_msg);
break;
case MainObject::CreateCommand:
ok=Create(station_name,generate_audio,&err_msg);
break;
case MainObject::ModifyCommand:
ok=Modify(&err_msg,set_schema,set_version);
break;
case MainObject::NoCommand:
break;
}
if(!ok) {
fprintf(stderr,"rddbmgr: %s\n",(const char *)err_msg);
exit(1);
}
exit(0);
}
int main(int argc,char *argv[])
{
QApplication a(argc,argv,false);
new MainObject();
return a.exec();
}

62
utils/rddbmgr/rddbmgr.h Normal file
View File

@ -0,0 +1,62 @@
// rddbmgr.h
//
// Rivendell database management utility
//
// (C) Copyright 2018 Fred Gleason <fredg@paravelsystems.com>
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 2 as
// published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public
// License along with this program; if not, write to the Free Software
// Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
//
#ifndef RDDBMGR_H
#define RDDBMGR_H
#include <qobject.h>
#include <rdconfig.h>
#define RDDBMGR_USAGE "[options]\n"
class MainObject : public QObject
{
public:
enum Command {NoCommand=0,ModifyCommand=1,CreateCommand=2,CheckCommand=3};
MainObject(QObject *parent=0);
private:
bool Check(QString *err_msg) const;
bool Create(const QString &station_name,bool gen_audio,
QString *err_msg) const;
bool CreateNewDb(QString *err_msg) const;
bool InititalizeNewDb(const QString &station_name,bool gen_audio,
QString *err_msg) const;
bool RunQuery(QString sql) const;
void InsertImportFormats() const;
bool InsertRDAirplayHotkeys(const QString &station_name) const;
bool Modify(QString *err_msg,int set_schema,const QString &set_version) const;
Command db_command;
QString db_mysql_hostname;
QString db_mysql_loginname;
QString db_mysql_password;
QString db_mysql_database;
QString db_mysql_driver;
QString db_mysql_engine;
QString db_mysql_charset;
QString db_mysql_collation;
bool db_verbose;
QString db_table_create_postfix;
RDConfig *db_config;
};
#endif // RDDBMGR_H