import {
isFunction,
isNotArray,
isNotBoolean,
isNotObject,
isNotUndefined,
isNull,
isString,
isUndefined
} from 'itee-validators'
/**
* @class
* @classdesc TStore is a simple javascript object whose purpose is to store some ket/value data to future usage. It could be enable/disable.
*
* @example {@lang javascript}
* var cache = new TCache()
* cache.add( 'foo', 'bar' )
* TLogger.log( cache.get('foo') ) // 'bar'
*
* @author [Tristan Valcke]{@link https://github.com/Itee}
* @license [BSD-3-Clause]{@link https://opensource.org/licenses/BSD-3-Clause}
*/
class TStore {
/**
*
* @param value
* @param validators
* @private
*/
static _validate ( value, validators ) {
for ( let validatorIndex = 0, numberOfValidators = validators.length ; validatorIndex < numberOfValidators ; validatorIndex++ ) {
let validator = validators[ validatorIndex ]
if ( !validator.validator( value ) ) {
const error = validator.error
if ( isString( error ) ) {
throw new TypeError( error )
} else if ( isFunction( error ) ) {
throw new TypeError( error( value ) )
} else {
throw new TypeError( `${ value } is invalid.` )
}
}
}
}
/**
* @constructor
* @param {Object} [parameters={}]
* @param {Object} [parameters.collection={}]
* @param {Boolean} [parameters.allowOverride=false]
* @param {Array.<function>} [parameters.keyValidators=[]]
* @param {Array.<function>} [parameters.valueValidators=[]]
*/
constructor ( parameters = {} ) {
const _parameters = {
...{
collection: {},
allowOverride: false,
keyValidators: [],
valueValidators: []
}, ...parameters
}
this.collection = _parameters.collection
this.allowOverride = _parameters.allowOverride
this.keyValidators = _parameters.keyValidators
this.valueValidators = _parameters.valueValidators
}
/**
*
* @return {{}}
*/
get collection () {
return this._collection
}
set collection ( value ) {
const memberName = 'Collection'
const expect = 'Expect an object.'
if ( isNull( value ) ) { throw new TypeError( `${ memberName } cannot be null ! ${ expect }` ) }
if ( isUndefined( value ) ) { throw new TypeError( `${ memberName } cannot be undefined ! ${ expect }` ) }
if ( isNotObject( value ) ) { throw new TypeError( `${ memberName } cannot be an instance of ${ value.constructor.name } ! ${ expect }` ) }
this._collection = value
}
/**
*
* @return {*}
*/
get allowOverride () {
return this._allowOverride
}
set allowOverride ( value ) {
const memberName = 'Allow override'
const expect = 'Expect a boolean.'
if ( isNull( value ) ) { throw new TypeError( `${ memberName } cannot be null ! ${ expect }` ) }
if ( isUndefined( value ) ) { throw new TypeError( `${ memberName } cannot be undefined ! ${ expect }` ) }
if ( isNotBoolean( value ) ) { throw new TypeError( `${ memberName } cannot be an instance of ${ value.constructor.name } ! ${ expect }` ) }
this._allowOverride = value
}
/**
*
* @return {*}
*/
get keyValidators () {
return this._keyValidators
}
set keyValidators ( value ) {
const memberName = 'Keys validators'
const expect = 'Expect an array of TValidator or an empty array.'
if ( isNull( value ) ) { throw new TypeError( `${ memberName } cannot be null ! ${ expect }` ) }
if ( isUndefined( value ) ) { throw new TypeError( `${ memberName } cannot be undefined ! ${ expect }` ) }
if ( isNotArray( value ) ) { throw new TypeError( `${ memberName } cannot be an instance of ${ value.constructor.name } ! ${ expect }` ) }
this._keyValidators = value
}
/**
*
* @return {*}
*/
get valueValidators () {
return this._valueValidators
}
set valueValidators ( value ) {
const memberName = 'Values validators'
const expect = 'Expect an array of TValidator or an empty array.'
if ( isNull( value ) ) { throw new TypeError( `${ memberName } cannot be null ! ${ expect }` ) }
if ( isUndefined( value ) ) { throw new TypeError( `${ memberName } cannot be undefined ! ${ expect }` ) }
if ( isNotArray( value ) ) { throw new TypeError( `${ memberName } cannot be an instance of ${ value.constructor.name } ! ${ expect }` ) }
this._valueValidators = value
}
/**
*
* @return {string[]}
*/
get keys () {
return Object.keys( this._collection )
}
/**
*
* @return {unknown[] | any[]}
*/
get values () {
return Object.values( this._collection )
}
/**
*
* @param value
* @return {TStore} The current instance (this)
*/
setCollection ( value ) {
this.collection = value
return this
}
/**
*
* @param value
* @return {TStore} The current instance (this)
*/
setAllowOverride ( value ) {
this.allowOverride = value
return this
}
/**
*
* @param value
* @return {TStore} The current instance (this)
*/
setKeyValidators ( value ) {
this.keyValidators( value )
return this
}
/**
*
* @param value
* @return {TStore} The current instance (this)
*/
setValueValidators ( value ) {
this.valueValidators( value )
return this
}
/**
* Allow to add new key value pair, the key cannot be null, undefined, or an empty string.
* In case the key already exist, the value will be overwritten if force params is true or this
* allow overriding else it throw an TypeError.
*
* @param {*} key
* @param {*} value
* @param {Boolean} force
* @return {TStore} The current instance (this)
*/
add ( key, value, force = false ) {
if ( this.contain( key ) && ( !this._allowOverride && !force ) ) {
throw new TypeError( `Item with key (${ key }) already exist in collection !` )
}
TStore._validate( key, this._keyValidators )
TStore._validate( value, this._valueValidators )
this._collection[ key ] = value
return this
}
/**
*
* @param key
* @return {boolean}
*/
contain ( key ) {
return isNotUndefined( this._collection[ key ] )
}
/**
* Return the value associated to the key.
*
* @param key
* @returns {*}
*/
get ( key ) {
return this._collection[ key ]
}
/**
* Remove to value from the cache. Does nothing if the key does not exist.
*
* @param key
* @return {TStore} The current instance (this)
*/
remove ( key ) {
delete this._collection[ key ]
return this
}
/**
* Clear the cache and reset collection to an empty object.
* @return {TStore} The current instance (this)
*/
clear () {
this._collection = {}
return this
}
}
export { TStore }