Find namespace records in Redis - redis

How do I find all the records in Redis?
USER_EXCHANGE = table
USER_ID = User ID (primary key)
UID = relationship
The key is stored with the following structure
USER_EXCHANGE:USER_ID:4030:UID:63867a4c6948e9405f4dd73bd9eaf8782b7a6667063dbd85014bd02046f6cc2e
I am trying to find all the records of the user 4030...
using (var redisClient = new RedisClient ())
{
List<object> ALL_UID = redisClient.Get<List<object>>("USER_EXCHANGE:USER_ID:4030:UID:*");
}
What am I doing wrong? Thank you all for your help.

Hi as you're trying to fetch all keys matching a pattern you should use KEYS.
GET won't match patterns. by will retrieve complete full names.
Caution this is a debug function and not a production function.
doc: https://redis.io/commands/keys
Production simple solution, recommanded for you is :
store a list of your key in a LIST
USER_EXCHANGE:USER_ID:4030 => [ uid1, uid2, uid3 ....]
get list of uids for a specific user ID by getting the list.
This is a good practice in REDIS.

Related

Separate lists in Redis

Im bulding a game server where i'm holding a list of connected users and at the same time a list of battles, those 2 lists are seperate.
I'm holding the battles data in Redis db, with battle id as the key,
could I use the connected user list in the same Redis db and get a list of the connected users in a elegant way while avoining battles data ?
I couldn't find a solution for that and currently holding the connected users in JS dictionary in my nodeJs server
UPDATE:
to clarify queries,
connected user object is -
connectedUser = {
nickname: string, (key)
socketId: string,
status: string,
rating: number
}
i would like to query the data with getUser(nickname) which will fetch a specific user and getAllUsers() to fetch all connected users.
as for match it includes all match data and stats
match = {
id: string, (key)
nicknameOne: string,
nicknameTwo: string,
...
}
on matches I query with id and believed it works well with hash table and hset and hget complexity wize.
as for queries on connected user, I wonder if using a simple js dictionary might provide with faster query results.
the js dictionary looks like that -
connectedUsers = {}
adding user -
user = {
key: nickname,
value: {
socketId: string,
status: string,
rating: number
}
}
while getting a specific user like that -
connectedUsers[nickname]
and iterating all this way -
for(let key in connectedUsers) {
//value - connectedUsers[key];
}
Nothing will beat the JS dictionary in terms of performance. Even with something as fast as Redis you're adding the overhead of interprocess communication (if hosted on the same machine) or network latencies.
If you want to use Redis for persistence, one way to store connected users would be to have a hash where keys are nicknames and values are user objects. You can do HGET users-key userId to get 1 user and HGETALL users-key to fetch all users.

Sitefinity - Safely delete orphaned dynamic content records

I've been adding records to a dynamic module via the API and in the process during my experimentation I added a bunch of records that weren't associated correctly with any valid parent record.
I've checked and so far I can see that Sitefinity stores data about these records in a number of tables:
mydynamiccontenttype_table
sf_dynamic_content
sf_dynmc_cntnt_sf_lnguage_data
sf_dynmc_cntent_sf_permissions
I would like to clean up the database by deleting these records but I want to make sure I don't create more problems in the process.
Anyone know if there are more references to these dynamic content type records or a process to safely delete them?
There are probably other tables, so your safest option would be to delete the items using the Sitefinity API.
Just get the masterId of the item and use a code like this:
public static void DeleteDataItemOfType(this DynamicModuleManager manager, string type, Guid Id)
{
Type resolvedType = TypeResolutionService.ResolveType(type);
using (var region = new ElevatedModeRegion(manager))
{
manager.DeleteDataItem(resolvedType, Id);
manager.SaveChanges();
}
}

What is the best way to find out the candidate group a task?

After I loaded a List of tasks with a taskQuery
taskService.createTaskQuery()
.processDefinitionKey(PROCESSKEY)
.taskCandidateGroupIn(list).initializeFormKeys().list()
What is the best way to find out the candidate group of every task?
I want to display it in a JSF view, but the class Task has no corresponding field.
You can get a task's identity links using the task service. Among other relations, the candidate group relation is expressed as an identity link. The following code filters a task's identity links for those that represent candidate groups:
List<IdentityLink> identityLinks = taskService.getIdentityLinksForTask(task.getId());
for (IdentityLink identityLink : identityLinks) {
String type = identityLink.getType();
/* type corresponds to the constants defined in IdentityLinkType.
"candidate" identitifies a candidate relation */
String groupId = identityLink.getGroupId();
if (IdentityLinkType.CANDIDATE.equals(type) && groupId != null) {
// we have found a candidate group; do something
}
}
The best approach is to write a custom query that gives you all task information the way you need them with on select. You do not want to start looping over result lists and sending one or more query per item, especially not in a high performance application as your task list.
Check the custom query documentation for details.
Only select task which have a candidate groups.
List<Task> candidateGroupList = taskService.createTaskQuery().withCandidateGroups().list();

Problems understanding Redis ServiceStack Example

I am trying to get a grip on the ServiceStack Redis example and Redis itself and now have some questions.
Question 1:
I see some static indexes defined, eg:
static class TagIndex
{
public static string Questions(string tag) { return "urn:tags>q:" + tag.ToLower(); }
public static string All { get { return "urn:tags"; } }
}
What does that '>' (greater than) sign do? Is this some kind of convention?
Question 2:
public User GetOrCreateUser(User user)
{
var userIdAliasKey = "id:User:DisplayName:" + user.DisplayName.ToLower();
using (var redis = RedisManager.GetClient())
{
var redisUsers = redis.As<User>();
var userKey = redis.GetValue(userIdAliasKey);
if (userKey != null) return redisUsers.GetValue(userKey);
if (user.Id == default(long)) user.Id = redisUsers.GetNextSequence();
redisUsers.Store(user);
redis.SetEntry(userIdAliasKey, user.CreateUrn());
return redisUsers.GetById(user.Id);
}
}
As far as I can understand, first a user is stored with a unique id. Is this necessary when using the client (I know this is not for Redis necessary)? I have for my model a meaningful string id (like an email address) which I like to use. I also see a SetEntry is done. What does SetEntry do exactly? I think it is an extra key just to set a relation between the id and a searchable key. I guess this is not necessary when storing the object itself with a meaningful key, so user.id = "urn:someusername". And how is SetEntry stored as a Redis Set or just an extra key?
Question 3:
This is more Redis related but I am trying to figure out how everything is stored in Redis in order to get a grip on the example so I did:
Started redis-cli.exe in a console
Typed 'keys *' this shows all keys
Typed 'get id:User:DisplayName:joseph' this showed 'urn:user:1'
Typed 'get urn:user:1' this shows the user
Now I also see keys like 'urn:user>q:1' or 'urn:tags' if I do a 'get urn:tags' I get the error 'ERR Operation against a key holding the wrong kind of value'. And tried other Redis commands like smembers but I cannot find the right query commands.
Question 1: return "urn:tags>q:" + tag.ToLower(); gives you the key (a string) for a given tag; the ">" has no meaning for Redis, it's a convention of the developer of the example, and could have been any other character.
Question 3: use the TYPE command to determine the type of the key, then you'll find the right command in redis documentation to get the values.

Laravel Eloquent last inserted object wrong properties

I've got a problem while using Laravel Eloquent ORM:
When inserting a new Eloquent Model in the database, the data is corrupted.
To be concrete:
$newItem = new NotificationNewItem;
$newItem->item_id = $item->id; // item_id is the primary key (returned by getKeyName())
$newItem->save();
return NotificationNewItem::find($item->id);
This code does not return the same as
$newItem = new NotificationNewItem;
$newItem->item_id = $item->id;
$newItem->save();
return $newItem;
whereas the two items should be the same, shouldn't they ?
The weird part is that the returned JSON object (I show it directly in my browser) in the first case is exactly what is inserted in the database, and in the second case the JSON Object's primary key (here item_id) is equal to 0 even if in the database the corresponding entry has a primary key equal to 3 (or different values).
Here's the laravel code if you want to see that error again : http://pastebin.com/9wcsnvSq
There are two "returns" in the model function insertAndGetElement() and those return items with different primary keys (the first one in that pastebin is returning a primary key equal to 0).
Help will be much appreciated.
Thanks in advance,
Robin.
The solution to that problem (Primary key set to 0 after calling save()) is to precisely define the model as not auto_incrementing the primary key.
To do so, just use
public $incrementing = false;
in the model declaration. Thanks to AndreasLutro on #laravel!
i don't know what exactly you want, but to get last insert id use this:
$newItem = new NotificationNewItem;
$newItem->item_id = $item->id;
$newItem->save();
// $newItem->id; this is lastinsertedid
return $newItem->id;
//NotificationNewItem::find($newItem->id);