Assume we’re creating a web application for a seat reservation system that users can use to reserve seats for an event. The application must be highly sensitive to available seats for an event and must reflect changes in available seats in real time for a given event. To create such an application, we must ensure that the result set for a query is always available in the cache in order to serve data faster to users, and that any change in the backend (a seat reserved or canceled) is immediately reflected across the cache so that users can see the updated data.
What exactly are Continuous Queries?
Continuous Queries is a technique for efficiently keeping our application cache in sync with the underlying data source. It enables you to monitor and react to changes in cached data in real time, ensuring that the cache always contains the most recent information.
The Benefits of Continuous Queries
Continuous querying in a cache provides various benefits, making it a desirable method when developing apps.
Data Synchronization in Real Time
Live dashboards and analytics cut latency and maximize resource utilization.
Providers of Caching that Support Continuous Querying
Continuous Querying is a complicated yet powerful feature that is supported by a wide range of prominent cache providers, including NCache, Redis, Hazelcast, Apache Ignite, Memcached, Couchbase, and others.
NCache is a feature-rich,.NET-based caching solution that allows continuous querying right out of the box.
Let us explore how to build continuous querying with NCache in this detailed article.
Using NCache to Implement Continuous Querying
So, how exactly does Continuous Querying function?
Continuous querying can be implemented in four simple steps.
- Query Specification: Create a query that describes the conditions for the data in the cache that we are interested in. This query can be based on any number of criteria, including keys, attributes, and even complicated data patterns.
- Subscription: Add the query to the cache provider’s list. The cache starts looking for changes that match the query in the cached data.
- Notifications of Change: When data in the cache that meets the criteria we established changes, the cache provider notifies the subscribed application in real time.
- Response: The program can then promptly respond to these messages, ensuring that it always works with the most up-to-date data.
Changes in the result set of a query can be triggered by the following operations.
- Adding an item in the cache or updating any existing item that brings it into the query result set
- Updating any existing cache item but remains in the query result set
- Removing an item from the cache or updating any existing cached item such that it causes item removal from the query result set. It can also happen due to expiration, eviction, dependency change, or explicit API removal.
Query Indexing
One prerequisite to using continuous queries is that you need to configure query indexes over the data on which the querying will be applied. A Query Index is similar to why you use indexes over an SQL table – for performance and faster querying. In NCache, you will create a query index over the type of objects you are storing in the cache or a specific attribute of that type.
This will be created at the cache level – using the NCache Management Dashboard or by Powershell.
You can find more information about how to create Query Indexes here – https://www.alachisoft.com/resources/docs/ncache/admin-guide/configure-query-index.html
Implementing Continuous Querying with NCache with an Example
As mentioned above, implementing Continuous queries involves four steps.
- Create a Query specification
- Create a Subscription based on the Query
- Receive Notifications
- Unsubscribe to the Notifications
We can follow the above steps and create continuous queries as below.
1. Install the necessary packages required for the NCache Client libraries. You can follow this link for the prerequisite packages – https://www.alachisoft.com/resources/docs/ncache/prog-guide/client-side-api-pre-reqs.html?tabs =net
2. Once the packages are installed and libraries are ready to use, we will first create a query that filters out the data in the cache and for which we are interested in receiving notifications on any change. Then we create a continuous query for that particular query over the cache.
The below code creates a continuous query on the cached dataset over an indexed property of the records called category. It returns the created continuous query instance.
3. When any change over the data that matches with the specified query happens, the continuous query calls the OnChangeInQueryResultSet callback method that is registered via the QueryDataNotificationCallback object. This callback function looks like below.
Since we have registered this callback for all the event types – Add, Update, and Remove; we will handle each of these based on the CQEventArg parameter value.
4. When we are no longer interested in receiving notifications about a particular event type within a continuous query, we can do so by unregistering for the callback. In the below code block, we will pass the continuous query instance that we have received after calling the RegisterCQ method along with the EventType enum that we wish to unregister.
5. If we are no longer interested in the continuous query itself, we can also unregister from it, by which we will no longer receive notifications for any notifications under that continuous query. The below code block shows us how to do so.
The total sequence of calls can happen as below.
The complete class is as below.