The Data Access Object Pattern, also known as DAO pattern, is used to separate low-level data access APIs or operations from high-level business services. The Data Access Object Pattern does not belong to the categories of the 23 commonly defined design patterns, but it is generally regarded as a broad-spectrum technical design pattern.
The Data Access Object Pattern encapsulates access to and storage of data sources, providing a data access object class responsible for managing and manipulating the stored data, and standardizing the data storage format, similar to the backend's DAO layer. HTML5 provides two new methods for client-side data storage: localStorage and sessionStorage. They are two storage mechanisms provided by the Web Storage API, with the former being permanent storage and the latter being limited to the current session and data transfer in related windows. Since WebStorage uses a key-value approach to access data and can only store strings (any type of data will be converted to strings when stored and requires type conversion when read), we can standardize the format of the key, such as module name + Key, developer + Key, and also add a prefix to describe the data in the value, such as adding a timestamp for the expiration date of the data to manage the data lifecycle. The specific format can be defined by the project team itself, mainly for ease of management and prevention of conflicts. In the frontend, it mainly involves encapsulating local storage to standardize and define the data access object after the conventions are set.
/**
* LocalStorage data access class
* @param {string} prefix Key prefix
* @param {string} timeSplit Separator between timestamp and stored data
*/varDAO=function(prefix, timeSplit){this.prefix = prefix;this.timeSplit = timeSplit ||"|-|";}```javascript
// Prototype methodDAO.prototype ={constructor:DAO,// Operation statusstatus:{SUCCESS:0,// SuccessFAILURE:1,// FailureOVERFLOW:2,// OverflowTIMEOUT:3// Expired},// Local storage objectstorage: localStorage || window.localStorage,/**
* Get the real key value with prefix
* @param key Data field identifier
*/getKey:function(key){returnthis.prefix + key;},/**
* Add (or update) data
* @param key Data field identifier
* @param value Data value
* @param callback Callback function
* @param time Expiration time
*/set:function(oriKey, value, callback, time){let status =this.status.SUCCESS;// Default to successlet key =this.getKey(oriKey);try{ time =newDate(time).getTime()|| time.getTime();// Get expiration timestamp}catch(e){ time =newDate().getTime()+1000*60*60*24*30;// Default to one month if no expiration time is set}try{this.storage.setItem(key, time +this.timeSplit + value);// Add (or update) data to local storage}catch(e){ status =this.status.OVERFLOW;// Overflow occurred} callback &&callback.call(this, status, key, value);// Execute callback and pass in parameters},/**
* Get data
* @param key Data field identifier
* @param callback Callback function
*/get:function(oriKey, callback){let key =this.getKey(oriKey);let status =this.status.SUCCESS;// Get data statuslet value =null;// Get data valuetry{ value =this.storage.getItem(key);// Get data from local storage}catch(e){ status =this.status.FAILURE;// Failed to get data value =null;}// If data is successfully retrievedif(status !==this.status.FAILURE){let index = value.indexOf(this.timeSplit);let timeSplitLen =this.timeSplit.length;let time = value.slice(0, index);// Get the timestamp// Check if the data is not expiredif(newDate(1* time).getTime()>newDate().getTime()|| time ===0){ value = value.slice(index + timeSplitLen);// Get the data value}else{ value =null;// Data has expired, delete the data status =this.status.TIMEOUT;this.remove(key);}} callback &&callback.call(this, status, value);// Execute callbackreturn value;// Return the result value},/**
* Delete data
* @param key Data field identifier
* @param callback Callback function
*/remove:function(oriKey, callback){let status =this.status.FAILURE;// Set the default status to failurelet key =this.getKey(oriKey);let value =null;try{ value =this.storage.getItem(key);// Get the data value}catch(e){// Data does not exist, no operation is taken}if(value){// If the data existstry{// Delete the datathis.storage.removeItem(key); status =this.status.SUCCESS;}catch(e){// Data deletion failed, no operation is taken}}// Execute callback and pass in parameters, if successful, pass in the deleted data valuelet param = status >0?null: value.slice(value.indexOf(this.timeSplit)+this.timeSplit.length); callback &&callback.call(this, status, param);}};
(function(){let dao =newDAO("user-verify"); dao.set("token","111",(...args)=> console.log(args));// [0, "user-verifytoken", "111"]let value = dao.get("token",(...args)=> console.log(args));// [0, "111"] console.log(value);// 111 dao.remove("token",(...args)=> console.log(args));// [0, "111"]})();