Read-through, Write-through, Write-behind in NCache

NCache is an extremely fast and scalable In-Memory Distributed Cache for .NET and caches application data to reduce expensive database trips. Use NCache to remove performance bottlenecks related to your data storage and database.

The most common way to use the cache is where your application reads data from your database / data source and then caches it. Then, later when your application updates the data in your database, it also updates the cache to make sure the cache is in-sync with the database.

NCache provides another very powerful mechanism for reading and writing data called Read-through / Write-through / Write-behind features to let NCache read and write data from your database.

There are three ways you can use NCache in this context:

  1. Read-through: you develop Read-through handler that resides and runs on all cache servers in the cluster. Then, when your application fetches any data from the cache, NCache calls Read-through handler to go and read this data from your database / data source if that data is not already in the cache.
  2. Write-through (sync): you develop a Write-through Handler that also resides and runs on all cache servers in the cluster. And, when your application updates data in the cache, NCache first updates the cache and then calls the Write-though handler to immediately update your database with it too. And, your application waits until data is updated in the database as well.
  3. Write-behind (async): if you don’t want your application to wait until Write-through handler completes the updating of data in the database, you can choose Write-behind option where NCache updates your database asynchronously and your application does not have to wait for the database update. This speeds-up your application as database updates are usually much slower than cache updates.
Read-through, Write-through, Write-behind in NCache

Benefits of Read-through / Write-through / Write-behind

Here are some benefits for using Read-through, Write-through, and Write-behind capability in NCache.

  1. Better write performance with Write-behind: updating your database / data source is usually much slower than updating cache. When you use Write-behind, your application only updates the cache and moves on while NCache asynchronously updates your database / data source. This improves your application performance quite a bit.
  2. More database scalability with Write-behind Throttling: if your application is updating database quite frequently, your database is likely to choke. But, if you turn on throttling with Write-behind, then NCache keeps your updated data in the cache with replication and updates your database in a slower speed. This relieves a lot of pressure from your database / data source.
  3. Auto-refresh cache on expiration: if you have developed a Read-through handler, you can enable auto-refresh on expiration in NCache. This way, whenever any cached item expires, instead of removing it from the cache, NCache calls the Read-through handler to reload a fresh copy from your database / data source. This frees up a major responsibility from your application.
  4. Auto-refresh cache on database changes: if you have developed a Read-through handler, you can enable auto-refresh on SQL Dependency / Oracle Dependency in NCache. This way, whenever the corresponding data in the database changes, instead of removing the cached item from the cache, NCache calls the Read-through handler to reload a fresh copy from your database / data source. This frees up a major responsibility from your application.

Feature Highlights

Here are some highlights of Read-through, Write-through, and Write-behind capability in NCache.

  1. Server-side Code (.NET or Java): you can develop your Read-through / Write-through handlers in either .NET or Java. There is an interface for each handler that you develop and then deploy your code to all cache servers in the cluster. NCache is then able to call them at runtime when needed. Handlers developed in .NET are called natively by NCache since it is also developed in .NET. However, handlers developed in Java are called by NCache through Java Native Interface (JNI).
  2. Multiple Read-through / Write-through Handlers: you can develop multiple Read-through and multiple Write-through handlers and register them all with NCache. In that case, they’re all named and your application can ask for any of them by specifying its name.
  3. Default Read-through / Write-through Handler: if you have multiple handlers registered as named handlers, then NCache allows you to select one of them as default. This default handler is used when your application doesn’t specify a handler name.
  4. Read-through Highlights
    1. Forced Read-through: NCache provides an option where you can tell it to use Read-through even if the item exists in the cache (normally, Read-through is only called when item is not found in the cache). This allows you to refresh the item from your database if you feel data might have changed there.
    2. Bulk Get Read-through: NCache provides a Bulk Get API that allows your application to provide a list of keys against which to fetch data from the cache. Read-through works in this situation as well and fetches items in bulk from your database / data source.
    3. Data Structures Read-through (Counter, Dictionary, List, Queue, Set): NCache provides the ability for your application to fetch any data structure and NCache calls Read-through handler to go fetch its data from your database / data source. It supports Counter, Dictionary, List, Queue, and Set data structures.
  5. Write-through Highlights
    1. Remove Item Write-through: NCache also provides a Remove Item API that lets your application provide a key to remove from the cache. Write-through works in this situation as well and removes this item from your database / data source as well.
    2. Bulk Remove Items Write-through: NCache also provides a Bulk Remove API that lets your application provide a list of keys to remove from the cache. Write-through works in this situation as well and removes these items from your database / data source in bulk.
    3. Bulk Add/Update Write-through: NCache provides a Bulk Add/Update API that lets your application to provide a list of keys and their values to add/update the cache in bulk. Write-through works in this situation as well and adds/updates your database / data source with these items in bulk.
    4. Data Structures Write-through (Counter, Dictionary, List, Queue, Set): NCache provides the ability for your application to update any data structure and NCache calls Write-through handler to go update your database / data source with the changes. It supports Counter, Dictionary, List, Queue, and Set data structures.
    5. Async Add/Update/Remove Write-through: NCache API provides Async Add/Insert/Remove. Write-through supports this API and gets invoked whenever your application makes that API call. This is different from Write-behind where Write-though itself does things asynchronously. Here, Write-though thinks your application is waiting for the operation to complete and the asynchronous nature is known only at the client API level.
  6. Write-behind Highlights
    1. Async Operations Queue Replicated (high availability): Write-behind accepts client’s request to update the cache and immediately updates the cache but queues up the database / data source update portion for a later asynchronous execution. This queue is always replicated to more than one cache server depending on the caching topology to make sure these operations are never lost if any cache server ever goes down suddenly.
    2. Throttling (default: 500 ops/sec): you can specify a throttling level for Write-behind async operations. This allows you to slow down the updates and spread them over a longer period of time versus updates in the cache.
    3. Write-behind Modes (Non-Batch, Batch): Non-Batch mode means each operation in the Write-behind queue is executed separately whereas Batch mode means that you lump multiple operations together and execute them together.
    4. Batch Operation Delay: you can specify a delay in-between two batch mode operations. This allows you to slow down your updates to the database if you want.
    5. Failed Operations Queue: since Write-behind performs all operations asynchronously, when an operation fails, NCache can put it in a Failed Operations Queue so it can be executed again without interfering with fresh operations that have not failed. You can put a max size on this queue and also specify eviction ration to evict the most retried operations if the queue becomes full.
  7. Monitor Write-through / Write-behind through Counters: NCache provides a rich set of counters with which you can monitor what is happening in Write-through / Write-behind. These counters are visible in NCache Web Monitor, PerfMon SNMP, and Prometheus / Grafana.

Read-through / Write-through Code Interface

It is quite simple to develop Read-through and Write-through handler code. Below are examples of interfaces for both.

public interface IReadThruProvider
{
	void Init(IDictionary parameters, string cacheId);
	ProviderCacheItem LoadFromSource(string key);
	IDictionary<string, ProviderCacheItem> LoadFromSource(ICollection<string> keys);
	ProviderDataTypeItem<IEnumerable> LoadDataTypeFromSource(string key, DistributedDataType dataType);
	void Dispose();
}
public interface ReadThruProvider extends java.lang.AutoCloseable
{
void init(java.util.Map<java.lang.String,java.lang.String> parameters, java.lang.String cacheId) 
throws java.lang.Exception;
	ProviderCacheItem loadFromSource(java.lang.String key) throws java.lang.Exception;
	java.util.Map<java.lang.String,ProviderCacheItem> loadFromSource(java.util.Collection<java.lang.String> keys) 
throws java.lang.Exception;
	ProviderDataStructureItem loadDataStructureFromSource(java.lang.String key, 
DistributedDataStructureType distributedDataStructureType) throws java.lang.Exception;
}
public interface IWriteThruProvider
{
	void Init(IDictionary parameters, string cacheId);
	OperationResult WriteToDataSource(WriteOperation operation);
	ICollection<OperationResult> WriteToDataSource(ICollection<WriteOperation> operations);
	ICollection<OperationResult> WriteToDataSource(ICollection<DataTypeWriteOperation> dataTypeWriteOperations);
	void Dispose();
}
public interface WriteThruProvider extends java.lang.AutoCloseable
{
	void init(java.util.Map<java.lang.String,java.lang.String> parameters, java.lang.String cacheId) 
throws java.lang.Exception;
	OperationResult writeToDataSource(WriteOperation operation) throws java.lang.Exception;
	java.util.Collection<OperationResult> writeToDataSource(java.util.Collection<WriteOperation> operations) 
throws java.lang.Exception;
	java.util.Collection<OperationResult>
writeDataStructureToDataSource(java.util.Collection<DataStructureWriteOperation< dataStructureWriteOperations)
throws java.lang.Exception;
}

Signup for monthly email newsletter to get latest updates.

© Copyright Alachisoft 2002 - . All rights reserved.