Closed
Description
Ashot Golovenko opened SPR-10958 and commented
Currently you can evict only one or all elements in a single cache region.
Allowing something like
@CacheEvict(value = "userCache", key = {"key1", "key2"})
would be really handful.
Affects: 3.2.4
12 votes, 14 watchers
Metadata
Metadata
Assignees
Labels
Type
Projects
Milestone
Relationships
Development
No branches or pull requests
Activity
spring-projects-issues commentedon Oct 11, 2013
Phil Webb commented
Usually the
key
attribute is a SpEL expression that obtains the key from an input parameter.e.g.:
What use-case do you have in mind where two keys would need to be evicted?
spring-projects-issues commentedon Oct 20, 2013
Ashot Golovenko commented
Well, let's say I have the following logic:
The update method changes the database so that calculations of both getFoo1 and getFoo2 methods are obsolete. Now I can evict only one key or all. Ideally I'd really love to have a keymask support so I could evict all keys starting like "#userId*" but array of keys is also fine.
spring-projects-issues commentedon Oct 23, 2013
Phil Webb commented
You could consider using different cache stores rather than using the key:
You can then use:
spring-projects-issues commentedon Feb 14, 2014
Lives commented
This would be very helpful in different use cases.
For eg : I have a city master which is cached.
The service for city master can accept a collection of cities for creation / modification
Since currently cache evict does not support multiple keys , developer ends up with clearing the entire cache.
Using SPEL developers can pass the list of keys to be removed from cache.If the cache evict aspect can handle it, it would be very useful.
spring-projects-issues commentedon Nov 25, 2014
shirish commented
This is a really good feature request. One such use case that I have encountered is to update user messages. Ideally an user can have messages in multiple locales I would like to evict all the messages with key= "{#userid_en, #userid_de}" instead of maintaining a separate cache for each locale.
Also if eviction is possible using regex of the key that would solve this entirely, how ever I am not sure about how big a task this is. some thing like key={"#userid_*"} should evict every thing under that key regex.
spring-projects-issues commentedon Apr 10, 2015
Stéphane Nicoll commented
My own personal feeling about it is that if you need to do this you probably reached the boundaries of what's safe to do declaratively. If we're talking about multiple keys and spel then it starts to be awkward for several reasons:
KeyGenerator
returns an object so we'll have to deal with the return type and handle a collection of something explicitly (which means you can't use that as a single key anywhere even though I doubt someone was doing that)Since this adds a lot of complexity I want to be sure that this is really needed so please cast your vote (and add your use case please).
spring-projects-issues commentedon Oct 20, 2015
Johannes Kuhs commented
For more advanced caching scenarios, some concept of having multiple keys is definitely necessary in my opinion. I'm not sure it needs to be in the form of allowing multiple
key
values though. Thekey
is used for retrieving a cache entry but really we just need a way to evict specific entries. So instead, it might make more sense to add a newevictKeys
parameter.evictKeys
simply point to thekey
and can thus be used to evict the actual entry.Another use-case for this kind of functionality would be the caching of different product information. A product might have skus, images, prices, features, facets, and other information attached to it that require more expensive operations (e.g. looping through all images to find a certain image type + view, getting a specific customer price, creating a distinct set of facets across skus, etc.). It would be nice to be able to cache the results of these kind of operations and simply evict them based on the product ID when the product is updated.
Updating the existing annotations to support this could look like this:
spring-projects-issues commentedon Jan 20, 2016
Kyle Lieber commented
We could really use this functionality as well. I think the suggestions made by
@jkuhs
would work. Here my scenario if it helps:We have a
Policy
and aProduct
.I have a
Policy
which is identified by apolicyId
and eachPolicy
can have multipleProducts
which are identified by thepolicyId
and theproductCode
.So I have a
ProductService
with a method for getting a product bypolicyId
andproductCode
.Then I have a
PolicyService
which has a method for deleting aPolicy
when given thepolicyId
.The
PolicyService#deletePolicy
will also delete all products for that policy but I have no way to clear theproducts
cache for that policy.My workaround options are:
spring-projects-issues commentedon Jan 21, 2016
Johannes Kuhs commented
To add to my previous comment, it would be nice to also have a
evictKeysGenerator
parameter on theCacheable
annotation. It would follow the same concept askeyGenerator
but have a return type ofString[]
(or evenObject[]
- the point being that multiple evict keys are supported).I'm really hoping some support for multiple evict keys will be implemented. In it's current form, the cache invalidation is quite limited for more advanced scenarios.
spring-projects-issues commentedon Feb 11, 2016
Stéphane Nicoll commented
We discussed this internally and decided to reject this feature. This is mostly programming by annotations and it would make the API and implementation much more complex. This idea of a separate
KeysGenerator
interface for evictions is an obvious example.While we could implement a simpler solution for some cases, the solution would become inconsistent overall as all the other annotation attributes and interface method handle a single value for the key.
spring-projects-issues commentedon Feb 11, 2016
Johannes Kuhs commented
It's disappointing to hear that. Would you mind elaborating on why you think this would make the API and implementation "much more complex"? Not sure I understand the argument for a
KeysGenerator
adding that much complexity. The concept for key generators is not a new one after all.If this decision is mostly based on not wanting to change the current interfaces, would you consider alternative solutions to support multiple evict keys in some capacity? I haven't thought about alternative solutions a lot, but maybe a separate set of annotations for advanced use, or some hooks that would allow for a more programmatic approach after the logic behind the
@Cacheable
and@CacheEvict
annotations has been executed?spring-projects-issues commentedon Feb 11, 2016
Sarath Akula commented
As
@jkuhs
mentioned, can it be a separate set of annotations for advanced use.It would avoid writing custom code for clearing up the cache in our application.spring-projects-issues commentedon Apr 10, 2016
Ranadeep Sharma Hidangmayum commented
Hi Team,
The use cases mentioned by everyone here are very common ones, infact.
Here is another usecase -
Let's consider an application where insurance plans for participants belonging to various clients are being read/updated in DB. This application has lots of methods where numerous plan objects have been pumped to cache(s), no matter how many.
Now, I want to delete items from applicable cache(s) where the item's key is matching partially with the collective *clientId * used for deleting all relevant data from DB for a particular client.
In short, I would like the above _CacheEvict_to be able to convey to cache handler that all the objects for this specific clientId be cleared, including the List and PlanInfo objects from participantCache and clientCache respectively.
spring-projects-issues commentedon Apr 10, 2016
Ranadeep Sharma Hidangmayum commented
Kindly review this feature against my use case (mentioned in comments) for possible enhancement.
spring-projects-issues commentedon Apr 11, 2016
Stéphane Nicoll commented
As I already explained above, we've made up our mind on this feature and decided not to implement it.
14 remaining items