Skip to content
This repository has been archived by the owner on Jun 11, 2024. It is now read-only.

Add filter to Accounts entity to allow searching in account.asset field #3990

Closed
yatki opened this issue Jul 22, 2019 · 3 comments · Fixed by #4078
Closed

Add filter to Accounts entity to allow searching in account.asset field #3990

yatki opened this issue Jul 22, 2019 · 3 comments · Fixed by #4078
Assignees
Milestone

Comments

@yatki
Copy link
Contributor

yatki commented Jul 22, 2019

Expected behavior

I should be able to search in asset (jsonb) field.

Example:

// file: lisk-framework/src/components/storage/entities/account.js

constructor(adapter, defaultFilters = {}) { 
// ...
  this.addFilter("asset_contains", ft.CUSTOM, {
      condition:
        'mem_accounts.asset @> \'{"packages": [{ "name":  "${asset_contains:value}" }]}\'::jsonb'
    });
// ...
}

The filter name could be something else like asset_matches etc.

Actual behavior

We don't have a filter at the moment.

Steps to reproduce

Which version(s) does this affect? (Environment, OS, etc...)

2.1.0+

@Tschakki
Copy link
Contributor

@lsilvs Would it be possible to provide a way for bApp developers to dynamically define new filters like this one? I think it could add a lot of flexibility to the sdk :)

@lsilvs
Copy link
Contributor

lsilvs commented Aug 1, 2019

I agree. It's not straightforward but we should work on it.

@lsilvs
Copy link
Contributor

lsilvs commented Aug 2, 2019

I did a quick research and one option would be create two extra filters for the asset field - contains and exists.

asset_contains

asset_contains will return when one json document is contained within another one.

Assuming we have the following accounts:

aliceAccount.asset = { "name":  "Alice", "company":  "Acme Corp" };
bobAccount.asset = { "name":  "Bob", "company":  "Acme Corp" };

The following calls will return aliceAccount:

storage.entities.Account.get({ asset_contains: '{ "name":  "Alice", "company":  "Acme Corp" }' });
storage.entities.Account.get({ asset_contains: '{ "name":  "Alice"' });

The following calls will return bobAccount:

storage.entities.Account.get({ asset_contains: '{ "name":  "Bob", "company":  "Acme Corp" }' });
storage.entities.Account.get({ asset_contains: '{ "name":  "Bob"' });

The following call will return aliceAccount and bobAccount:

storage.entities.Account.get({ asset_contains: '{ "company":  "Acme Corp" }' });

asset_exists

asset_exists will return when a string appears as an object key or array element at the top level of the json object.

Assuming we have the following accounts:

aliceAccount.asset = { "name":  "Alice", "height":  "1.79" };
bobAccount.asset = { "name":  "Bob", "weight":  "74" };

The following call will return aliceAccount:

storage.entities.Account.get({ asset_exists: 'height' });

The following call will return bobAccount:

storage.entities.Account.get({ asset_exists: 'weight' });

The following call will return aliceAccount and bobAccount:

storage.entities.Account.get({ asset_exists: 'name' });

Note that we can only assert for exact value. In order to allow searches with greater_than or less_than more research needs to be done.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
6 participants