-
Notifications
You must be signed in to change notification settings - Fork 123
rename updates #593
rename updates #593
Changes from 2 commits
9b9fa9d
888412a
28cf3c1
42c993e
63c7e9f
4a56424
a4a3791
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,9 +1,9 @@ | ||
/** | ||
* @file | ||
* \file | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @ is the correct one, see doc/CODING.md |
||
* | ||
* @brief A plugin that converts keys to metakeys and vice versa | ||
* \brief A plugin that converts keys to metakeys and vice versa | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. please change, it should be |
||
* | ||
* @copyright BSD License (see doc/COPYING or http://www.libelektra.org) | ||
* \copyright BSD License (see doc/COPYING or http://www.libelektra.org) | ||
* | ||
*/ | ||
|
||
|
@@ -21,15 +21,15 @@ | |
#include <stdio.h> | ||
#include <stdlib.h> | ||
|
||
#include <kdbprivate.h> // for access to sync bit (keyClearSync) | ||
|
||
#define ELEKTRA_ORIGINAL_NAME_META "origname" | ||
#define TOLOWER (-1) | ||
#define TOUPPER 1 | ||
#define UNCHNGD 0 | ||
#define KEYNAME 2 | ||
// TODO defined privately in keyhelpers.c, API break possible.. | ||
char * keyNameGetOneLevel (const char * name, size_t * size); | ||
|
||
static void doConversion (char * newName, int levels, int toCase) | ||
static void doConversion (char * newName, int levels, const int toCase) | ||
{ | ||
int (*conversion) (int); | ||
|
||
|
@@ -74,7 +74,7 @@ static void doConversion (char * newName, int levels, int toCase) | |
} | ||
|
||
Key * elektraKeyCreateNewName (const Key * key, const Key * parentKey, const char * cutPath, const char * replaceWith, | ||
const char * toUpperPath, const char * toLowerPath) | ||
const char * toUpperPath, const char * toLowerPath, const int initialConversion) | ||
{ | ||
size_t addToLen = 0; | ||
if (replaceWith != NULL) addToLen = strlen (replaceWith); | ||
|
@@ -89,9 +89,15 @@ Key * elektraKeyCreateNewName (const Key * key, const Key * parentKey, const cha | |
char * curKeyName = elektraMalloc (keyGetFullNameSize (key)); | ||
keyGetFullName (key, curKeyName, keyGetFullNameSize (key)); | ||
|
||
const char * afterParentString = curKeyName + (strlen (parentKeyName)); | ||
char * afterParentString = curKeyName + (strlen (parentKeyName)); | ||
char * ptr; | ||
|
||
if (initialConversion != UNCHNGD) | ||
{ | ||
doConversion (afterParentString, 0, initialConversion); | ||
replace = 1; | ||
} | ||
|
||
if (cutPath && (cutPath[0] != '/') && ((ptr = strstr (afterParentString, cutPath)) != NULL)) | ||
{ | ||
strncpy (newName, afterParentString, (ptr - afterParentString)); | ||
|
@@ -165,7 +171,8 @@ static void keyAddUnescapedBasePath (Key * key, const char * path) | |
} | ||
} | ||
|
||
static Key * renameGet (Key * key, Key * parentKey, Key * cutConfig, Key * replaceWithConfig, Key * toUpperConfig, Key * toLowerConfig) | ||
static Key * renameGet (Key * key, Key * parentKey, Key * cutConfig, Key * replaceWithConfig, Key * toUpperConfig, Key * toLowerConfig, | ||
Key * getCase) | ||
{ | ||
char * cutPath = 0; | ||
char * replaceWith = 0; | ||
|
@@ -175,6 +182,24 @@ static Key * renameGet (Key * key, Key * parentKey, Key * cutConfig, Key * repla | |
const Key * toMeta = keyGetMeta (key, "rename/to"); | ||
const Key * toUpperMeta = keyGetMeta (key, "rename/toupper"); | ||
const Key * toLowerMeta = keyGetMeta (key, "rename/tolower"); | ||
|
||
int initialConversion = 0; | ||
if (getCase) | ||
{ | ||
const char * str = keyString (getCase); | ||
if (!strcmp (str, "toupper")) | ||
{ | ||
initialConversion = TOUPPER; | ||
} | ||
else if (!strcmp (str, "tolower")) | ||
{ | ||
initialConversion = TOLOWER; | ||
} | ||
else | ||
{ | ||
initialConversion = UNCHNGD; | ||
} | ||
} | ||
/* if the meta config exists, it takes precedence over the global config */ | ||
if (cutMeta) | ||
cutPath = (char *)keyString (cutMeta); | ||
|
@@ -193,7 +218,7 @@ static Key * renameGet (Key * key, Key * parentKey, Key * cutConfig, Key * repla | |
else if (toLowerConfig) | ||
toLowerPath = (char *)keyString (toLowerConfig); | ||
|
||
return elektraKeyCreateNewName (key, parentKey, cutPath, replaceWith, toUpperPath, toLowerPath); | ||
return elektraKeyCreateNewName (key, parentKey, cutPath, replaceWith, toUpperPath, toLowerPath, initialConversion); | ||
} | ||
|
||
static Key * restoreKeyName (Key * key, const Key * parentKey, const Key * configKey) | ||
|
@@ -203,23 +228,16 @@ static Key * restoreKeyName (Key * key, const Key * parentKey, const Key * confi | |
{ | ||
if (strcmp (keyString (origNameKey), keyName (key))) | ||
{ | ||
int hasSync = keyNeedSync (key); // test_bit(key->flags, KEY_FLAG_SYNC); | ||
Key * result = keyDup (key); | ||
keySetName (result, keyString (origNameKey)); | ||
keySetMeta (result, ELEKTRA_ORIGINAL_NAME_META, 0); | ||
|
||
if (!hasSync) | ||
{ | ||
keyClearSync (result); | ||
} | ||
return result; | ||
} | ||
} | ||
else | ||
{ | ||
if (configKey) | ||
{ | ||
int hasSync = keyNeedSync (key); // test_bit(key->flags, KEY_FLAG_SYNC); | ||
Key * result = keyDup (key); | ||
keySetName (result, keyName (parentKey)); | ||
keyAddUnescapedBasePath (result, keyString (configKey)); | ||
|
@@ -231,10 +249,6 @@ static Key * restoreKeyName (Key * key, const Key * parentKey, const Key * confi | |
keyAddUnescapedBasePath (result, relativePath); | ||
} | ||
|
||
if (!hasSync) | ||
{ | ||
keyClearSync (result); | ||
} | ||
return result; | ||
} | ||
} | ||
|
@@ -265,10 +279,14 @@ int elektraRenameGet (Plugin * handle, KeySet * returned, Key * parentKey) | |
Key * toUpper = ksLookupByName (config, "/toupper", KDB_O_NONE); | ||
Key * toLower = ksLookupByName (config, "/tolower", KDB_O_NONE); | ||
Key * replaceWith = ksLookupByName (config, "/replacewith", KDB_O_NONE); | ||
Key * getCase = ksLookupByName (config, "/get/case", KDB_O_NONE); | ||
|
||
|
||
Key * key; | ||
while ((key = ksNext (iterateKs)) != 0) | ||
{ | ||
Key * renamedKey = renameGet (key, parentKey, cutConfig, replaceWith, toUpper, toLower); | ||
|
||
Key * renamedKey = renameGet (key, parentKey, cutConfig, replaceWith, toUpper, toLower, getCase); | ||
|
||
if (renamedKey) | ||
{ | ||
|
@@ -315,29 +333,77 @@ int elektraRenameSet (Plugin * handle, KeySet * returned, Key * parentKey) | |
KeySet * config = elektraPluginGetConfig (handle); | ||
Key * cutConfig = ksLookupByName (config, "/cut", KDB_O_NONE); | ||
|
||
Key * setCase = ksLookupByName (config, "/set/case", KDB_O_NONE); | ||
|
||
int writeConversion = 0; | ||
if (setCase) | ||
{ | ||
const char * str = keyString (setCase); | ||
if (!strcmp (str, "toupper")) | ||
{ | ||
writeConversion = TOUPPER; | ||
} | ||
else if (!strcmp (str, "tolower")) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think its nicer when you leave this customized formatted, don't you agree? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i honestly have no idea why that line always disappears... |
||
{ | ||
writeConversion = TOLOWER; | ||
} | ||
else if (!strcmp (str, "keyname")) | ||
{ | ||
writeConversion = KEYNAME; | ||
} | ||
else | ||
{ | ||
writeConversion = UNCHNGD; | ||
} | ||
} | ||
ksRewind (iterateKs); | ||
Key * key; | ||
char * parentKeyName = elektraMalloc (keyGetFullNameSize (parentKey)); | ||
keyGetFullName (parentKey, parentKeyName, keyGetFullNameSize (parentKey)); | ||
while ((key = ksNext (iterateKs)) != 0) | ||
{ | ||
Key * renamedKey = restoreKeyName (key, parentKey, cutConfig); | ||
|
||
if (renamedKey) | ||
Key * renamedKey = NULL; | ||
if (writeConversion != KEYNAME) | ||
{ | ||
renamedKey = restoreKeyName (key, parentKey, cutConfig); | ||
|
||
if (!renamedKey) renamedKey = keyDup (key); | ||
if (writeConversion == TOUPPER || writeConversion == TOLOWER) | ||
{ | ||
char * curKeyName = elektraMalloc (keyGetFullNameSize (renamedKey)); | ||
keyGetFullName (renamedKey, curKeyName, keyGetFullNameSize (renamedKey)); | ||
|
||
char * afterParentString = curKeyName + (strlen (parentKeyName)); | ||
|
||
doConversion (afterParentString, 0, writeConversion); | ||
|
||
keySetName (renamedKey, curKeyName); | ||
elektraFree (curKeyName); | ||
} | ||
/* | ||
* if something is restored from the parentKey, do | ||
* not delete the parentKey (might cause troubles) | ||
*/ | ||
if (keyCmp (key, parentKey) != 0) | ||
{ | ||
ksLookup (returned, key, KDB_O_POP); | ||
keyDel (key); | ||
keyDel (ksLookup (returned, key, KDB_O_POP)); | ||
} | ||
ksAppendKey (returned, renamedKey); | ||
keyDel (renamedKey); | ||
} | ||
else | ||
{ | ||
if (keyCmp (key, parentKey) != 0) | ||
{ | ||
keyDel (ksLookupByName (returned, keyString (keyGetMeta (key, ELEKTRA_ORIGINAL_NAME_META)), KDB_O_POP)); | ||
} | ||
ksAppendKey (returned, key); | ||
} | ||
} | ||
|
||
ksDel (iterateKs); | ||
|
||
ksRewind (returned); | ||
elektraFree (parentKeyName); | ||
return 1; /* success */ | ||
} | ||
|
||
|
@@ -349,4 +415,3 @@ Plugin * ELEKTRA_PLUGIN_EXPORT (rename) | |
ELEKTRA_PLUGIN_SET, &elektraRenameSet, | ||
ELEKTRA_PLUGIN_END); | ||
} | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -225,28 +225,28 @@ static void test_metaConfigTakesPrecedence () | |
static void test_keyCutNamePart () | ||
{ | ||
Key * parentKey = keyNew ("user/tests/rename", KEY_END); | ||
Key * result = elektraKeyCreateNewName (parentKey, parentKey, "wont/cut/this", NULL, NULL, NULL); | ||
Key * result = elektraKeyCreateNewName (parentKey, parentKey, "wont/cut/this", NULL, NULL, NULL, 0); | ||
succeed_if (!result, "parentKey was modified although it should have been ignored"); | ||
|
||
/* cutting works correctly without trailing slash */ | ||
Key * testKey = keyNew ("user/tests/rename/will/cut/this/key1", KEY_END); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "will/cut/this", NULL, NULL, NULL); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "will/cut/this", NULL, NULL, NULL, 0); | ||
succeed_if (result, "key1 was not cut") | ||
succeed_if (!strcmp (keyName (result), "user/tests/rename/key1"), "cutting key1 did not yield the expected result"); | ||
keyDel (testKey); | ||
keyDel (result); | ||
|
||
/* cutting works correctly with trailing slash */ | ||
testKey = keyNew ("user/tests/rename/will/cut/this/key1", KEY_END); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "will/cut/this/", NULL, NULL, NULL); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "will/cut/this/", NULL, NULL, NULL, 0); | ||
succeed_if (result, "key1 was not cut") | ||
succeed_if (!strcmp (keyName (result), "user/tests/rename/key1"), "cutting key1 did not yield the expected result"); | ||
keyDel (testKey); | ||
keyDel (result); | ||
|
||
/* disallow leading slashes */ | ||
testKey = keyNew ("user/tests/rename/wont/cut/this/key1", KEY_END); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "/wont/cut/this", NULL, NULL, NULL); | ||
result = elektraKeyCreateNewName (testKey, parentKey, "/wont/cut/this", NULL, NULL, NULL, 0); | ||
succeed_if (!result, "key was cut although it the cutpath contained a leading slash"); | ||
keyDel (testKey); | ||
keyDel (parentKey); | ||
|
@@ -395,6 +395,26 @@ static void test_mixCase () | |
PLUGIN_CLOSE (); | ||
} | ||
|
||
static void test_write () | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. can you also test the other direction (upper/lower) |
||
{ | ||
Key * parentKey = keyNew ("user/tests/rename", KEY_END); | ||
KeySet * conf = | ||
ksNew (20, keyNew ("system/tolower", KEY_VALUE, "1", KEY_END), keyNew ("system/get/case", KEY_VALUE, "toupper", KEY_END), | ||
keyNew ("system/set/case", KEY_VALUE, "keyname"), KS_END); | ||
KeySet * ks = ksNew (20, keyNew ("user/tests/rename/uppercase/uppercase/uppercase/LOWERCASE", KEY_VALUE, "test", KEY_END), KS_END); | ||
ksAppendKey (ks, parentKey); | ||
PLUGIN_OPEN ("rename"); | ||
succeed_if (plugin->kdbGet (plugin, ks, parentKey) >= 1, "call to kdbGet was not successful"); | ||
Key * key = ksLookupByName (ks, "user/tests/rename/UPPERCASE/UPPERCASE/UPPERCASE/lowercase", KDB_O_NONE); | ||
succeed_if (key, "key1 was not correctly rename"); | ||
succeed_if (plugin->kdbSet (plugin, ks, parentKey) == 1, "call to kdbSet was not successful"); | ||
key = ksLookupByName (ks, "user/tests/rename/UPPERCASE/UPPERCASE/UPPERCASE/lowercase", KDB_O_NONE); | ||
succeed_if (key, "key1s name was not correctly saved"); | ||
keyDel (parentKey); | ||
ksDel (ks); | ||
PLUGIN_CLOSE (); | ||
} | ||
|
||
int main (int argc, char ** argv) | ||
{ | ||
printf ("RENAME TESTS\n"); | ||
|
@@ -415,7 +435,7 @@ int main (int argc, char ** argv) | |
test_toLower (); | ||
test_mixCase (); | ||
test_replaceString (); | ||
|
||
test_write (); | ||
printf ("\ntest_rename RESULTS: %d test(s) done. %d error(s).\n", nbTest, nbError); | ||
|
||
return nbError; | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should not be here?