"      !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~ None09;T "Resources data definition used by withSTMResources forces a retry*resources to be inserted back in the cacheAresources to be deleted from the cache and from permanent storageresult to be returned .Must be defined for every object to be cached. QImplements the database access and marshalling of the object. while the database access must be strict, the marshaling must be lazy if, as is often the case, some parts of the object are not really accesed. If the object contains DBRefs, this avoids unnecesary cache lookups. This method is called within  blocks. Since STM transactions retry, readResourceByKey may be called twice in strange situations. So it must be idempotent, not only in the result but also in the effect in the database . However, because it is executed by  safeIOToSTM8 it is guaranteed that the execution is not interrupted. 0hopefully optimized read of many objects by key.ZTo write into persistent storage. It must be strict. Since STM transactions may retry,  writeResourcez must be idempotent, not only in the result but also in the effect in the database. . However, because it is executed by  safeIOToSTM it is guaranteed that the execution is not interrupted. All the new obbects are writeen to the database on synchromization, so writeResource must not autocommit. Commit code must be located in the postcondition. (see  setConditions\) Since there is no provision for rollback from failure in writing to persistent storage,  must retry until success.multiple write (hopefully) in a single request. That is up to you and your backend . Defined by default as 'mapM_ writeResource'DDelete the resource. It is called syncronously. So it must commit Empty resources: resources= Resources [] [] ()     None09;T =a persist mechanism has to implement these three primitives / is the default file persistencedeleteread by key. It must be strictwrite. It must be strict-Used by IndexQuery for index persistence(see Data.TCache.IndexQuery.Serialize is an alternative to the IResource class for defining persistence in TCache. The deserialization must be as lazy as possible. serialization/deserialization are not performance critical in TCache=Read, Show, instances are implicit instances of Serializable 9 serialize = pack . show deserialize= read . unpack|Since write and read to disk of to/from the cache are not be very frequent The performance of serialization is not critical. CIndexable is an utility class used to derive instances of IResourceExample: data Person= Person{ pname :: String, cars :: [DBRef Car]} deriving (Show, Read, Typeable) data Car= Car{owner :: DBRef Person , cname:: String} deriving (Show, Read, Eq, Typeable) &Since Person and Car are instances of  ans , by defining the  M instance will implicitly define the IResource instance for file persistence: instance Indexable Person where key Person{pname=n} = "Person " ++ n instance Indexable Car where key Car{cname= n} = "Car " ++ n /WImplements default default-persistence of objects in files with their keys as filenames1-Set the default persistence mechanism of all  serializable objects that have setPersist= const Nothing. By default it is /Athis statement must be the first one before any other TCache call;:Strict read from file, needed for default file persistence- !"#$%&'()*+,-./0123456789:;<=>?) !"#$%&'()*+,-./0123456789:;--,()*+&'%#$. !"?>=</0123456789:; !"#$%&'()*+,-./0123456789:;<=>?None0AT@Add an user defined trigger to the list of triggers Trriggers are called just before an object of the given type is created, modified or deleted. The DBRef to the object and the new value is passed to the trigger. The called trigger function has two parameters: the DBRef being accesed (which still contains the old value), and the new value. If the DBRef is being deleted, the second parameter is A. if the DBRef contains Nothing, then the object is being createdA*internally called when a DBRef is modifieddeletedcreated @A #$&'()*+@A #$&'()*+@A@ANone09;AT$C%sync state to permanent storage when c is invokedEuse a to write the stateF0number of seconds between saves when asyncronousG?The user-defined check-for-cleanup-from-cache for each object. e is an exampleHsize of the cache when asyncJeSet the cache. this is useful for hot loaded modules that will update an existing cache. Experimental'The cache holder. stablished by defaultK!Creates a new cache. ExperimentalLReturn the total number of DBRefs in the cache. For debug purposes. This does not count the number of objects in the cache since many of the DBRef may not have the pointed object loaded. It's O(n).MXReturn the reference value. If it is not in the cache, it is fetched from the database.N7Read multiple DBRefs in a single request using the new  OWrite in the reference a value The new key must be the same than the old key of the previous object stored otherwise, an error "law of key conservation broken" will be raisedWARNING: the value to be written in the DBRef must be fully evaluated. Delayed evaluations at serialization time can cause inconsistencies in the database. In future releases this will be enforced.P4Return the key of the object pointed to by the DBRefQxGet the reference to the object in the cache. if it does not exist, the reference is created empty. Every execution of Q returns the same unique reference to this key, so it can be safely considered pure. This is a property useful because deserialization of objects with unused embedded DBRef's do not need to marshall them eagerly. Tbis also avoid unnecesary cache lookups of the pointed objects.RCreate the object passed as parameter (if it does not exist) and -- return its reference in the IO monad. -- If an object with the same key already exists, it is returned as is -- If not, the reference is created with the new value. -- If you like to update in any case, use Q and O combined newDBRefIO :: (IResource a,Typeable a) => a -> IO (DBRef a) newDBRefIO x= do let key = keyResource x mdbref <- mDBRefIO key case mdbref of Right dbref -> return dbref Left cache -> do tv<- newTVarIO DoNotExist let dbref= DBRef key tv w <- mkWeakPtr dbref . Just $ fixToCache dbref H.insert cache key (CacheElem Nothing w) t <- timeInteger atomically $ do applyTriggers [dbref] [Just x] --debugO ("before "++key) writeTVar tv . Exist $ Elem x t t return dbref Create the object passed as parameter (if it does not exist) and return its reference in the STM monad. If an object with the same key already exists, it is returned as is If not, the reference is created with the new value. If you like to update in any case, use Q and OO combined if you need to create the reference and the reference content, use RSIDelete the content of the DBRef form the cache and from permanent storageTbHandles Nothing cases in a simpler way than runMaybeT. it is used in infix notation. for example: Jresult <- readDBRef ref `onNothing` error ("Not found "++ keyObjDBRef ref)or ;result <- readDBRef ref `onNothing` return someDefaultValueUADeletes the pointed object from the cache, not the database (see SO) useful for cache invalidation when the database is modified by other processV$flush the element with the given keyW,label the object as not existent in databaseXdrops the entire cache.YThis is the main function for the *Resource(s) calls. All the rest derive from it. The results are kept in the STM monad so it can be part of a larger STM transaction involving other DBRefs. The I register returned by the user-defined function is interpreted as such:?: the content of this field will be added/updated to the cacheU: the content of this field will be removed from the cache and from permanent storage0: the content of this field will be returned by YWARNING: To catch evaluations errors at the right place, the values to be written must be fully evaluated. Errors in delayed evaluations at serialization time can cause inconsistencies in the database.Z&Update of a single object in the cache withResource r f= [ [r] ([mr]-> [f mr])[2To atomically add/modify many objects in the cache # withResources rs f= atomically $ YH rs f1 >> return() where f1 mrs= let as= f mrs in Resources as [] ()\"To read a resource from the cache. getResource r= do{mr<- ] [r];return $! head mr}]8To read a list of resources from the cache if they exist| getResources rs= atomically $ Y* rs f1 where f1 mrs= Resources [] [] mrs^=Delete the resource from cache and from persistent storage.  deleteResource r= _ [r]_DDelete the list of resources from cache and from persistent storage. # deleteResources rs= atomically $ Y7 rs f1 where f1 mrs = Resources [] (catMaybes mrs) ()`(Start the thread that periodically call dQ to clean and writes on the persistent storage. it is indirecly set by means of bK, since it is more higuer level. I recommend to use the latter Otherwise, a or d or ce must be invoked explicitly or no persistence will exist. Cache writes allways save a coherent stateaForce the atomic write of all cached objects modified since the last save into permanent storage. Cache writes allways save a coherent state. As allways, only the modified objects are written.bESpecify the cache synchronization policy with permanent storage. See B for detailscfPerform a synchronization of the cache with permanent storage once executed the STM transaction when b policy is Cd\Saves the unsaved elems of the cache. Cache writes allways save a coherent state. Unlike  syncChaceG this call deletes some elems of the cache when the number of elems >  sizeObjectsT. The deletion depends on the check criteria, expressed by the first parameter. e` is the one implemented to be passed by default. Look at it to understand the clearing criteria.e(This is a default cache clearance check. It forces to drop from the cache all the elems not accesed since half the time between now and the last sync if it returns True, the object will be discarded from the cache it is invoked when the cache size exceeds the number of objects configured in ` or df?stablishes the procedures to call before and after saving with a, d or `@. The postcondition of database persistence should be a commit.gAssures that the IO computation finalizes no matter if the STM transaction is aborted or retried. The IO computation run in a different thread. The STM transaction wait until the completion of the IO procedure (or retry as usual).It can be retried if the embedding STM computation is retried so the IO computation must be idempotent. Exceptions are bubbled up to the STM transactionCBCDEFGHIJKLMNOPQRSTUVWXY%the list of resources to be retrievedNThe function that process the resources found and return a Resources structure"The return value in the STM monad.Z[\]^_`Hnumber of seconds betwen checks. objects not written to disk are written?The user-defined check-for-cleanup-from-cache for each object. e is an exampleDThe max number of objects in the cache, if more, the cleanup starts Identifier of the thread createdabcdecurrent time in seconds#last access time for a given object6last cache syncronization (with the persisten storage)[return true for all the elems not accesed since half the time between now and the last syncfghijk; #@BCDEGFHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefg;cg#QPRMNOS Y[Z]\_^@UVWXIJKafdLbBCDEFGH`eT9BCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijkNone 09;<=?ATlBy default the index of a  data persist with the data.lm !"/12 !"12/lmNone 09;<=?TCimplement the relational-like operators, operating on record fieldswRegister a trigger for indexing the values of the field passed as parameter. the indexed field can be used to perform relational-like searchesxZreturn all the (indexed) values which this field has and a DBRef pointer to the register(nopqrstuvwxyz{|}~ noprstuqvwxy wqutsrxyponvnopqrstuvwxyz{|}~o3p4q5r5s5t5u5None 09;<=T9start a trigger to index the contents of a register fieldGtrigger the indexation of list fields with elements convertible to Textsreturn the DBRefs of the registers whose field (first parameter, usually a container) contains the requested value.Dreturn all the values of a given field (if it has been indexed with w)return the DBRefs whose fields include all the words in the requested text contents.Except the words with less than three characters that are not digits or uppercase, that are filtered out before making the queryfield to index>method to convert the field content to lazy Text (for example D in case of String fields). This permits to index non Textual fieldsfield to indexlmethod to convert a field element to Text (for example `pack . show` in case of elemets with Show instances)  field to search intext to search      None09;AT:to execute a monad for the purpose of memoizing its resultgiven a string, return a key that can be used in Indexable instances Of non persistent objects, such are cached objects (it changes fron execution to execution) . It uses  memoize the result of a computation for a certain time. This is useful for caching costly data such web pages composed on the fly.time == 0 means infiniteAMemoize the result of a computation for a certain time. A string ! is used to index the resultThe Int parameter is the timeout, in second after the last evaluation, after which the cached value will be discarded and the expression will be evaluated again if demanded . Time == 0 means no timeouta pure version of cached None 09;<=?AT\check if a (possibly polimorphic) value within a IDynamic value has the given serialization" None 09;<=?ATA queue reference'push an element at the top of the queueCheck if the queue is empty:Get the reference to new or existing queue trough its name*Empty the queue (factually, it is deleted)Version in the STM monad8Read the first element in the queue and delete it (pop)Version in the STM monadPush an element in the queueVersion in the STM monadIReturn the list of all elements in the queue. The queue remains unchangedVersion in the STM monad<Return the first element in the queue that has the given keyVersion in the STM monadJUpdate the first element of the queue with a new element with the same keyVersion in the STM monad9Return the list of all elements in the queue and empty itA version in the STM monadMDelete all the elements of the queue that has the key of the parameter passedVerison in the STM monad" Queue namethe returned elems Queue namethe returned elems   !"#$%&'()*+,-../00123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~                       ! " #$$TCache-0.12.1-FGWSF6OxF9qJoAKBBPABWF Data.TCacheData.TCache.IResourceData.TCache.DefsData.TCache.TriggersData.TCache.DefaultPersistenceData.TCache.IndexQueryData.TCache.IndexTextData.TCache.MemoizationData.Persistent.IDynamicData.Persistent.Collectionbase GHC.Conc.Sync atomically unsafeIOToSTMSTM ResourcesRetrytoAddtoDeletetoReturn IResource keyResourcereadResourceByKeyreadResourcesByKey readResource writeResourcewriteResources delResource delResources resourcesPersist readByKeywritedeleteKey PersistIndex persistIndex Serializable serialize deserialize deserialKey setPersist IndexablekeydefPathDBRefTPVarElemStatusNotRead DoNotExistExist ModifTime AccessTimecastErr filePersistdefaultPersistIORefsetDefaultPersistgetDefaultPersist getPersistdefaultReadByKey defaultWrite safeWrite defaultDeletedefReadResourceByKeydefWriteResourcedefDelResourcereadFileStrict $fIndexable()$fIndexableInteger$fIndexableInt $fIndexable[] addTrigger applyTriggersSyncMode Synchronous Asyncronous SyncManual frecuencycheck cacheSizeCachesetCachenewCachenumElems readDBRef readDBRefs writeDBRef keyObjDBRefgetDBRefnewDBRefdelDBRef onNothing flushDBRefflushKey invalidateKeyflushAllwithSTMResources withResource withResources getResource getResourcesdeleteResourcedeleteResourcesclearSyncCacheProc syncCache syncWriteatomicallySyncclearSyncCache defaultCheck setConditions safeIOToSTM $fOrdDBRef $fEqDBRef $fReadDBRef $fShowDBRef$fPersistIndexa $fIResourceaselect.||..&&..==..>..>=..<=..<. QueriableindexindexOf recordsWith$fSelect(,)STMSTM$fSelect(,,,)STMSTM$fSelect(,,)STMSTM$fSelect(,)STMSTM0$fSelect(->)STMSTM$fSetOperations[][][]$fSetOperations[][][]0$fSetOperations[][][]1$fSetOperations[][][]2$fRelationOps(->)(->)[]$fRelationOps(->)a[]$fIndexableIndex$fSerializableIndex $fReadIndex$fIResourceIndex$fQueriablerega $fShowIndex indexText indexList containsElem allElemsOfcontains$fIResourceIndexText$fIndexableIndexText$fSerializableIndexText$fReadIndexText$fShowIndexText ExecutableexecuteaddrStr writeCached cachedByKeycachedByKeySTM flushCachedcachedp$fIResourceCached$fMonadIOIdentity$fExecutableIdentity$fExecutableIOSaveIDynTypeDRightDLeftIDynamicIDyntosave errorfied dynPrefix dynPrefixSp notreifiedtoIDynserializedEqualfromIDyn safeFromIDynreifyM$fShowIDynamic$fSerializeIDynamic$fSerializeSaveRefQueue unreadSTMisEmpty isEmptySTMgetQRefflushflushSTMpoppopSTMpickpushpushSTMpickAll pickAllSTMpickElem pickElemSTM updateElem updateElemSTMreadAll readAllSTM deleteElem deleteElemSTM$fSerializableQueue$fSerializeQueue$fIndexableQueueGHC.ReadReadGHC.ShowShowGHC.BaseNothing CMTrigger TriggerType cmtriggersmbToListmapM2_refcacheFilteredCheckTPVarFlags AddToHash NoAddToHashHt CacheElem deRefWeakSTM fixToCache getRefFlag takeDBRefs takeDBRef timeInteger releaseTPVars releaseTPVardelListFromHashupdateListToHashcriticalSection tvSyncWrite refConditionssavingsaveextract RelationOpsSelect SetOperationsJoinDataIndexkeyIndexgetIndex getIndexr selectorIndexjoinretrieve IndexText fieldTypelastDoc mapDocKeyInt mapIntDocKeymapTextInteger readInitDBRefadddelopbytestring-0.10.8.1Data.ByteString.Lazy.Char8packindextwords1 filterWordt filterWord)RefSerialize-0.4.0-2IqFUb9iVTF770g98DtVQwData.RefSerialize.SerializeaddrHashCachedcontextcachedKeyPrefixcached cachedSTMQueuenameimpout!> queuePrefix lenQPrefixreadQRef