1(function(window) { 2 yomvi.addPackage('yomvi.system.store', function() { 3 4 5 6 this.StoreFactory= { 7 _defaults: { 8 persistenceLocal:'local', 9 persistenceSession :'session', 10 /** 11 * main() for flatDataStore (instance) 12 * This is the primary place that individual values are stored and retrieved. 13 * The main() method can be overridden with other desired behaviour, the primary 14 * purpose of which might be to provide special handling for certain fields. 15 * 16 * Received parameters and behaviours in the default main(): 17 * @param {object} data (Always set) The data object for this FDS. 18 * @param {string} property (Always set) Usually, the property name to get/set. 19 * @param {JSONcompat} value (Optional) If present, the value to set option to. If not 20 * present, main returns the current value of data[option] 21 * 22 * @return Either the specified property value or this FDS instance (for chaining). 23 */ 24 main: function(data, property, val){ 25 if( data._expires && ( data._expires - (new Date().getTime())) < 0 ) { 26 27 delete this; 28 this.unset(); 29 return null; 30 } 31 if (typeof val === 'undefined' || val === null) { 32 return data[property]; 33 } else { 34 data[property] = val; 35 this.save(); 36 } 37 return this; 38 }, 39 //Persistence a FALSE indica que debe ir en el sessionStorage en vez del local storage 40 41 private_api: { 42 /* load() 43 * Loads the data. Automatically called just once at instantiation. 44 */ 45 load: function(){ 46 var s = this.getStates(), data; 47 if (s.isTopLevel) { 48 49 var datastr; 50 s.persistence == yomvi.system.store.StoreFactory._defaults.persistenceLocal?datastr = localStorage.getItem(s.storageName):datastr = sessionStorage.getItem(s.storageName); 51 if (!datastr) { 52 if (s.persistence == yomvi.system.store.StoreFactory._defaults.persistenceLocal){ 53 // iPad has a bug with local storage - workaround by removing it first 54 localStorage.removeItem(s.storageName); 55 localStorage.setItem(s.storageName, {}); 56 } else { 57 // iPad has a bug with local storage - workaround by removing it first 58 sessionStorage.removeItem(s.storageName); 59 sessionStorage.setItem(s.storageName, {}); 60 } 61 62 } 63 try { 64 data = JSON.parse(datastr); 65 } catch(e){ 66 //ERROR: FlatDataStore.private_api.load: ERROR localStorage[' + s.storageName + '] is corrupted.', datastr 67 } 68 } else { 69 data = s.parentStore(s.storageName); 70 } 71 if (!data) { 72 //*should* only happen on first start-up, but could also be if the JSON got corrupted somehow 73 //need to do what we can to load info into this 74 data = this.getDefaultData(); 75 if( s.expires ) { 76 data._expires = ( new Date().getTime() ) + ( s.expires * 86400000 ); 77 } 78 } 79 this(data); 80 return this; 81 } 82 }, 83 default_api: { 84 /* save() 85 * Saves the data. If a child of another FDS, this will trigger a chain 86 * save through to the top level. 87 */ 88 save: function(){
89 var s = this.getStates(), data = this(); 90 if (s.isTopLevel) { 91 if (s.persistence == yomvi.system.store.StoreFactory._defaults.persistenceLocal){ 92 // iPad has a bug with local storage - workaround by removing it first 93 localStorage.removeItem(s.storageName); 94 localStorage.setItem(s.storageName, JSON.stringify(data)); 95 } 96 else { 97 sessionStorage.removeItem(s.storageName); 98 sessionStorage.setItem(s.storageName, JSON.stringify(data)); 99 } 100 } else { 101 s.parentStore(s.storageName, data); 102 } 103 return this; 104 }, 105 unset: function() { 106 var s = this.getStates(), data = this(); 107 if (s.isTopLevel) { 108 if (s.persistence == yomvi.system.store.StoreFactory._defaults.persistenceLocal){ 109 localStorage.removeItem(s.storageName); 110 } else { 111 sessionStorage.removeItem(s.storageName); 112 } 113 114 } else { 115 s.parentStore.remove(s.storageName); 116 } 117 return this; 118 }, 119 remove:function(key) { 120 var data = this(); 121 delete data[key]; 122 this.save(); 123 }, 124 /* getDefaultData() 125 * Method to generate the initial data when it does not exist in 126 * localStorage (or on the parent FDS). 127 * 128 * @return Object 129 */ 130 getDefaultData: function(){ 131 return {}; 132 } 133 } 134 }, 135 create: function(storageName, cfg, expires){ 136 cfg = cfg || {}; 137 cfg.main = cfg.main || yomvi.system.store.StoreFactory._defaults.main; 138 cfg.persistence = cfg.persistence || yomvi.system.store.StoreFactory._defaults.persistenceLocal; 139 var data, 140 private_api = yomvi.system.store.StoreFactory._defaults.private_api, 141 states = { 142 isTopLevel: !cfg.parentStore, 143 storageName: storageName, 144 persistence: cfg.persistence 145 }; 146 147 if (cfg.private_api) { 148 jQuery.extend(private_api, cfg.private_api); 149 } 150 if (!states.isTopLevel) { 151 states.parentStore = cfg.parentStore; 152 } 153 154 /** 155 * @method flatDataStore (instance) 156 * @return The data object 157 * The first parameter is an object: Sets the data to be that object 158 * Anything else: delegates to the main() function and returns a value from that 159 * 160 */ 161 /** 162 * @method flatDataStore (instance) 163 * @param {object} data Sets the data with this object 164 * @return The datastore instance 165 */ 166 /** 167 * @method flatDataStore (instance) 168 * @param {string} property The property to get. 169 * @return The property value. 170 * Note: this is the default behaviour, and can be changed by passing in a 171 * different main function 172 */ 173 /** 174 * @method flatDataStore (instance) 175 * @param {string} property The property to set. 176 * @param {JSON compatible type} value The value for the named property 177 * @return The datastore instance. 178 * Note: this is the default behaviour, and can be changed by passing in a 179 * different main function 180 */ 181 182 states.expires = expires; 183 184 var flatDataStore = function(){ 185 //unified 186 if (arguments.length === 0) { 187 if( isExpired(data) ) { 188 return flatDataStore.getDefaultData(); 189 } 190 return data; 191 } 192 if (arguments.length === 1 && typeof arguments[0] === 'object') { 193 var expires = states.expires; 194 data = arguments[0];//set whole object method 195 if( expires ) { 196 data._expires = ( new Date().getTime() ) + ( states.expires * 86400000 ); 197 data._expireTime = states.expires * 86400000; 198 } 199 flatDataStore.save(); 200 return flatDataStore; 201 } 202 if (arguments.length && data && data._expires ) { 203 if( isExpired(data) ) { 204 return; 205 } 206 } 207 var args = jQuery.makeArray(arguments); 208 args.unshift(data);
209 return cfg.main.apply(flatDataStore, args); 210 }; 211 212 function isExpired(data){ 213 if( !data._expires ) { 214 return false; 215 } 216 if( ( data._expires - (new Date().getTime())) < 0 ) { 217 // check for an expiration event 218 if( typeof flatDataStore.onExpiration === 'function' ) { 219 flatDataStore.onExpiration(); 220 } 221 return true; 222 } else { 223 data._expires = ( new Date().getTime() ) + ( data._expireTime ); 224 } 225 return false; 226 } 227 /** 228 * @method getStates 229 * @return An object containing the storageName, an isTopLevel boolean, and the parentStore (if any) 230 */ 231 flatDataStore.getStates = function(){ 232 return states; 233 }; 234 jQuery.extend(flatDataStore, yomvi.system.store.StoreFactory._defaults.default_api); 235 if (typeof cfg.custom_api === 'object') { 236 jQuery.extend(flatDataStore, cfg.custom_api); 237 } 238 private_api.load.call(flatDataStore); 239 return flatDataStore; 240 } 241 242 }; 243 244 }); 245})(window);
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.