00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
#include "kconfigpropagator.h"
00023
00024
#include <kdebug.h>
00025
#include <kconfig.h>
00026
#include <kconfigskeleton.h>
00027
#include <kstandarddirs.h>
00028
#include <kstringhandler.h>
00029
#include <klocale.h>
00030
00031
#include <qfile.h>
00032
#include <qstringlist.h>
00033
00034 KConfigPropagator::Change::~Change()
00035 {
00036 }
00037
00038 KConfigPropagator::ChangeConfig::ChangeConfig()
00039 : KConfigPropagator::Change( i18n("Change Config Value") ),
00040 hideValue( false )
00041 {
00042 }
00043
00044
QString KConfigPropagator::ChangeConfig::arg1()
const
00045
{
00046
return file +
"/" + group +
"/" + name;
00047 }
00048
00049
QString KConfigPropagator::ChangeConfig::arg2()
const
00050
{
00051
if ( hideValue )
return "*";
00052
else return value;
00053 }
00054
00055
void KConfigPropagator::ChangeConfig::apply()
00056 {
00057 KConfig cfg( file );
00058 cfg.setGroup( group );
00059 cfg.writeEntry( name, value );
00060
00061 cfg.sync();
00062 }
00063
00064 KConfigPropagator::KConfigPropagator()
00065 : mSkeleton( 0 )
00066 {
00067 init();
00068 }
00069
00070 KConfigPropagator::KConfigPropagator( KConfigSkeleton *skeleton,
00071
const QString &kcfgFile )
00072 : mSkeleton( skeleton ), mKcfgFile( kcfgFile )
00073 {
00074 init();
00075
00076 readKcfgFile();
00077 }
00078
00079
void KConfigPropagator::init()
00080 {
00081 mChanges.setAutoDelete(
true );
00082 }
00083
00084
void KConfigPropagator::readKcfgFile()
00085 {
00086
QString filename = locate(
"kcfg", mKcfgFile );
00087
if ( filename.isEmpty() ) {
00088 kdError() <<
"Unable to find kcfg file '" << mKcfgFile <<
"'" << endl;
00089
return;
00090 }
00091
00092
QFile input( filename );
00093
QDomDocument doc;
00094
QString errorMsg;
00095
int errorRow;
00096
int errorCol;
00097
if ( !doc.setContent( &input, &errorMsg, &errorRow, &errorCol ) ) {
00098 kdError() <<
"Parse error in " << mKcfgFile <<
", line " << errorRow <<
", col " << errorCol <<
": " << errorMsg << endl;
00099
return;
00100 }
00101
00102
QDomElement cfgElement = doc.documentElement();
00103
00104
if ( cfgElement.isNull() ) {
00105 kdError() <<
"No document in kcfg file" << endl;
00106
return;
00107 }
00108
00109 mRules.clear();
00110
00111
QDomNode n;
00112
for ( n = cfgElement.firstChild(); !n.isNull(); n = n.nextSibling() ) {
00113
QDomElement e = n.toElement();
00114
00115
QString tag = e.tagName();
00116
00117
if ( tag ==
"propagation" ) {
00118 Rule rule = parsePropagation( e );
00119 mRules.append( rule );
00120 }
else if ( tag ==
"condition" ) {
00121 Condition condition = parseCondition( e );
00122
QDomNode n2;
00123
for( n2 = e.firstChild(); !n2.isNull(); n2 = n2.nextSibling() ) {
00124
QDomElement e2 = n2.toElement();
00125
if ( e2.tagName() ==
"propagation" ) {
00126 Rule rule = parsePropagation( e2 );
00127 rule.condition = condition;
00128 mRules.append( rule );
00129 }
else {
00130 kdError() <<
"Unknow tag: " << e2.tagName() << endl;
00131 }
00132 }
00133 }
00134 }
00135 }
00136
00137 KConfigPropagator::Rule KConfigPropagator::parsePropagation(
const QDomElement &e )
00138 {
00139 Rule r;
00140
00141
QString source = e.attribute(
"source" );
00142 parseConfigEntryPath( source, r.sourceFile, r.sourceGroup, r.sourceEntry );
00143
00144
QString target = e.attribute(
"target" );
00145 parseConfigEntryPath( target, r.targetFile, r.targetGroup, r.targetEntry );
00146
00147 r.hideValue = e.hasAttribute(
"hidevalue" ) &&
00148 e.attribute(
"hidevalue" ) ==
"true";
00149
00150
return r;
00151 }
00152
00153
void KConfigPropagator::parseConfigEntryPath(
const QString &path,
00154
QString &file,
00155
QString &group,
00156
QString &entry )
00157 {
00158
QStringList p = QStringList::split(
"/", path );
00159
00160
if ( p.count() != 3 ) {
00161 kdError() <<
"Path has to be of form file/group/entry" << endl;
00162 file = QString::null;
00163 group = QString::null;
00164 entry = QString::null;
00165
return;
00166 }
00167
00168 file = p[ 0 ];
00169 group = p[ 1 ];
00170 entry = p[ 2 ];
00171
00172
return;
00173 }
00174
00175 KConfigPropagator::Condition KConfigPropagator::parseCondition(
const QDomElement &e )
00176 {
00177 Condition c;
00178
00179
QString key = e.attribute(
"key" );
00180
00181 parseConfigEntryPath( key, c.file, c.group, c.key );
00182
00183 c.value = e.attribute(
"value" );
00184
00185 c.isValid =
true;
00186
00187
return c;
00188 }
00189
00190
void KConfigPropagator::commit()
00191 {
00192 updateChanges();
00193
00194 Change *c;
00195
for( c = mChanges.first(); c; c = mChanges.next() ) {
00196 c->apply();
00197 }
00198 }
00199
00200 KConfigSkeletonItem *KConfigPropagator::findItem(
const QString &group,
00201
const QString &name )
00202 {
00203
00204
00205
if ( !mSkeleton )
return 0;
00206
00207 KConfigSkeletonItem::List items = mSkeleton->items();
00208 KConfigSkeletonItem::List::ConstIterator it;
00209
for( it = items.begin(); it != items.end(); ++it ) {
00210
00211
00212
if ( (*it)->group() == group && (*it)->name() == name ) {
00213
break;
00214 }
00215 }
00216
if ( it == items.end() )
return 0;
00217
else return *it;
00218 }
00219
00220
QString KConfigPropagator::itemValueAsString( KConfigSkeletonItem *item )
00221 {
00222
QVariant p = item->property();
00223
00224
if ( p.type() == QVariant::Bool ) {
00225
if ( p.toBool() )
return "true";
00226
else return "false";
00227 }
00228
00229
return p.toString();
00230 }
00231
00232
void KConfigPropagator::updateChanges()
00233 {
00234 mChanges.clear();
00235
00236 Rule::List::ConstIterator it;
00237
for( it = mRules.begin(); it != mRules.end(); ++it ) {
00238 Rule r = *it;
00239 Condition c = r.condition;
00240
if ( c.isValid ) {
00241 KConfigSkeletonItem *item = findItem( c.group, c.key );
00242 kdDebug() <<
"Item " << c.group <<
"/" << c.key <<
":" << endl;
00243
if ( !item ) {
00244 kdError() <<
" Item not found." << endl;
00245 }
else {
00246
QString value = itemValueAsString( item );
00247 kdDebug() <<
" Value: " << value << endl;
00248
if ( value != c.value ) {
00249
continue;
00250 }
00251 }
00252 }
00253
00254 KConfigSkeletonItem *item = findItem( r.sourceGroup, r.sourceEntry );
00255
if ( !item ) {
00256 kdError() <<
"Item " << r.sourceGroup <<
"/" << r.sourceEntry
00257 <<
" not found." << endl;
00258
continue;
00259 }
00260
QString value = itemValueAsString( item );
00261
00262 KConfig target( r.targetFile );
00263 target.setGroup( r.targetGroup );
00264
QString targetValue = target.readEntry( r.targetEntry );
00265
if ( r.hideValue ) targetValue = KStringHandler::obscure( targetValue );
00266
if ( targetValue != value ) {
00267 ChangeConfig *change =
new ChangeConfig();
00268 change->file = r.targetFile;
00269 change->group = r.targetGroup;
00270 change->name = r.targetEntry;
00271
if ( r.hideValue ) value = KStringHandler::obscure( value );
00272 change->value = value;
00273 change->hideValue = r.hideValue;
00274 mChanges.append( change );
00275 }
00276 }
00277
00278 addCustomChanges( mChanges );
00279 }
00280
00281
KConfigPropagator::Change::List KConfigPropagator::changes()
00282 {
00283
return mChanges;
00284 }
00285
00286
KConfigPropagator::Rule::List KConfigPropagator::rules()
00287 {
00288
return mRules;
00289 }