Entities
[Entity: Types, Identity and Instance Framework]


Detailed Description

This file defines an API that adds types to the GUID's. GUID's with types can be used to identify and reference typed entities.

The idea here is that a GUID can be used to uniquely identify some thing. By adding a type, one can then talk about the type of thing identified. By adding a collection, one can then work with a handle to a collection of things of a given type, each uniquely identified by a given ID. QOF Entities can be used independently of any other part of the system. In particular, Entities can be useful even if one is not using the Query ond Object parts of the QOF system.

Identifiers are globally-unique and permanent, i.e., once an entity has been assigned an identifier, it retains that same identifier for its lifetime. Identifiers can be encoded as hex strings.

GUID Identifiers are 'typed' with strings. The native ids used by QOF are defined below.

  1. An id with type QOF_ID_NONE does not refer to any entity.
  2. An id with type QOF_ID_NULL does not refer to any entity, and will never refer to any entity. =# An identifier with any other type may refer to an actual entity, but that is not guaranteed as that entity does not have to exist within the current book. (See PARTIAL_QOFBOOK). Also, creating a new entity from a data source involves creating a temporary GUID and then setting the value from the data source. If an id does refer to an entity, the type of the entity will match the type of the identifier.

If you have a type name, and you want to have a way of finding a collection that is associated with that type, then you must use Books.

Entities can refer to other entities as well as to the basic QOF types, using the qofclass parameters.


Files

file  qofid.h
 QOF entity type identification system.

Data Structures

struct  QofEntity_s

Collections of Entities

typedef void(* QofEntityForeachCB )(QofEntity *, gpointer user_data)
QofCollectionqof_collection_new (QofIdType type)
guint qof_collection_count (QofCollection *col)
void qof_collection_destroy (QofCollection *col)
QofIdType qof_collection_get_type (QofCollection *)
QofEntityqof_collection_lookup_entity (QofCollection *, const GUID *)
void qof_collection_foreach (QofCollection *, QofEntityForeachCB, gpointer user_data)
gpointer qof_collection_get_data (QofCollection *col)
void qof_collection_set_data (QofCollection *col, gpointer user_data)
gboolean qof_collection_is_dirty (QofCollection *col)

QOF Entity Initialization & Shutdown

void qof_entity_init (QofEntity *, QofIdType, QofCollection *)
void qof_entity_release (QofEntity *)

QOF_TYPE_COLLECT: Linking one entity to many of one type

Note:
These are NOT the same as the main collections in the book.
QOF_TYPE_COLLECT is a secondary collection, used to select entities of one object type as references of another entity.
See also:
QOF_TYPE_CHOICE.


gboolean qof_collection_add_entity (QofCollection *coll, QofEntity *ent)
 Add an entity to a QOF_TYPE_COLLECT.
gboolean qof_collection_merge (QofCollection *target, QofCollection *merge)
 Merge two QOF_TYPE_COLLECT of the same type.
gint qof_collection_compare (QofCollection *target, QofCollection *merge)
 Compare two secondary collections.
QofCollectionqof_collection_from_glist (QofIdType type, GList *glist)
 Create a secondary collection from a GList.

Defines

#define QOF_ID_NONE   NULL
#define QOF_ID_NULL   "null"
#define QOF_ID_BOOK   "Book"
#define QOF_ID_SESSION   "Session"
#define QOF_ENTITY(object)   ((QofEntity *)(object))
#define QSTRCMP(da, db)
#define QOF_CHECK_TYPE(obj, type)   (0 == QSTRCMP((type),(((QofEntity *)(obj))->e_type)))
#define QOF_CHECK_CAST(obj, e_type, c_type)

Typedefs

typedef const char * QofIdType
typedef const char * QofIdTypeConst
typedef const gchar * QofLogModule
typedef QofEntity_s QofEntity
typedef QofCollection_s QofCollection

Functions

const GUIDqof_entity_get_guid (QofEntity *)


Define Documentation

#define QOF_CHECK_CAST obj,
e_type,
c_type   ) 
 

Value:

(                   \
  QOF_CHECK_TYPE((obj),(e_type)) ?                            \
  (c_type *) (obj) :                                          \
  (c_type *) ({                                               \
     g_log (G_LOG_DOMAIN, G_LOG_LEVEL_CRITICAL,               \
       "Error: Bad QofEntity at %s:%d", __FILE__, __LINE__);  \
     (obj);                                                   \
  }))
cast object to the indicated type, print error message if its bad

Definition at line 118 of file qofid.h.

#define QOF_CHECK_TYPE obj,
type   )     (0 == QSTRCMP((type),(((QofEntity *)(obj))->e_type)))
 

return TRUE if object is of the given type

Definition at line 113 of file qofid.h.

#define QOF_ENTITY object   )     ((QofEntity *)(object))
 

simple,cheesy cast but holds water for now

Definition at line 93 of file qofid.h.

#define QSTRCMP da,
db   ) 
 

Value:

({                \
  int val = 0;                           \
  if ((da) && (db)) {                    \
    if ((da) != (db)) {                  \
      val = strcmp ((da), (db));         \
    }                                    \
  } else                                 \
  if ((!(da)) && (db)) {                 \
    val = -1;                            \
  } else                                 \
  if ((da) && (!(db))) {                 \
    val = 1;                             \
  }                                      \
  val; /* block assumes value of last statment */  \
})
Inline string comparision; compiler will optimize away most of this

Definition at line 96 of file qofid.h.


Typedef Documentation

typedef struct QofCollection_s QofCollection
 

QofCollection declaration

Parameters:
e_type QofIdType
is_dirty gboolean
hash_of_entities GHashTable
data gpointer, place where object class can hang arbitrary data

Definition at line 137 of file qofid.h.

typedef struct QofEntity_s QofEntity
 

QofEntity declaration

Definition at line 128 of file qofid.h.

typedef void(* QofEntityForeachCB)(QofEntity *, gpointer user_data)
 

Callback type for qof_entity_foreach

Definition at line 185 of file qofid.h.

typedef const char* QofIdType
 

QofIdType declaration

Definition at line 80 of file qofid.h.

typedef const char* QofIdTypeConst
 

QofIdTypeConst declaration

Definition at line 82 of file qofid.h.

typedef const gchar* QofLogModule
 

QofLogModule declaration

Definition at line 84 of file qofid.h.


Function Documentation

gboolean qof_collection_add_entity QofCollection coll,
QofEntity ent
 

Add an entity to a QOF_TYPE_COLLECT.

Note:
These are NOT the same as the main collections in the book.
Entities can be freely added and merged across these secondary collections, they will not be removed from the original collection as they would by using qof_entity_insert_entity or qof_entity_remove_entity.

Definition at line 202 of file qofid.c.

00203 {
00204         QofEntity *e;
00205 
00206         e = NULL;
00207         if (!coll || !ent) { return FALSE; }
00208         if (guid_equal(&ent->guid, guid_null())) { return FALSE; }
00209         g_return_val_if_fail (coll->e_type == ent->e_type, FALSE);
00210         e = qof_collection_lookup_entity(coll, &ent->guid);
00211         if ( e != NULL ) { return FALSE; }
00212         g_hash_table_insert (coll->hash_of_entities, &ent->guid, ent);
00213         return TRUE;
00214 }

gint qof_collection_compare QofCollection target,
QofCollection merge
 

Compare two secondary collections.

Performs a deep comparision of the collections. Each QofEntity in each collection is looked up in the other collection, via the GUID.

Returns:
0 if the collections are identical or both are NULL otherwise -1 if target is NULL or either collection contains an entity with an invalid GUID or if the types of the two collections do not match, or +1 if merge is NULL or if any entity exists in one collection but not in the other.

Definition at line 265 of file qofid.c.

00266 {
00267         gint value;
00268 
00269         value = 0;
00270         if (!target && !merge) { return 0; }
00271         if (target == merge) { return 0; }
00272         if (!target && merge) { return -1; }
00273         if (target && !merge) { return 1; }
00274         if(target->e_type != merge->e_type) { return -1; }
00275         qof_collection_set_data(target, &value);
00276         qof_collection_foreach(merge, collection_compare_cb, target);
00277         value = *(gint*)qof_collection_get_data(target);
00278         if(value == 0) {
00279                 qof_collection_set_data(merge, &value);
00280                 qof_collection_foreach(target, collection_compare_cb, merge);
00281                 value = *(gint*)qof_collection_get_data(merge);
00282         }
00283         return value;
00284 }

guint qof_collection_count QofCollection col  ) 
 

return the number of entities in the collection.

Definition at line 316 of file qofid.c.

00317 {
00318         guint c;
00319 
00320         c = g_hash_table_size(col->hash_of_entities);
00321         return c;
00322 }

void qof_collection_destroy QofCollection col  ) 
 

XXX there should be a destroy notifier for this

Definition at line 158 of file qofid.c.

00159 {
00160   CACHE_REMOVE (col->e_type);
00161   g_hash_table_destroy(col->hash_of_entities);
00162   col->e_type = NULL;
00163   col->hash_of_entities = NULL;
00164   col->data = NULL;   
00165   g_free (col);
00166 }

void qof_collection_foreach QofCollection ,
QofEntityForeachCB  ,
gpointer  user_data
 

Call the callback for each entity in the collection.

Definition at line 379 of file qofid.c.

00381 {
00382   struct _iterate iter;
00383 
00384   g_return_if_fail (col);
00385   g_return_if_fail (cb_func);
00386 
00387   iter.fcn = cb_func;
00388   iter.data = user_data;
00389 
00390   g_hash_table_foreach (col->hash_of_entities, foreach_cb, &iter);
00391 }

QofCollection* qof_collection_from_glist QofIdType  type,
GList *  glist
 

Create a secondary collection from a GList.

Parameters:
type The QofIdType of the QofCollection and of all entities in the GList.
glist GList of entities of the same QofIdType.
Returns:
NULL if any of the entities fail to match the QofCollection type, else a pointer to the collection on success.

Definition at line 297 of file qofid.c.

00298 {
00299         QofCollection *coll;
00300         QofEntity *ent;
00301         GList *list;
00302 
00303         coll = qof_collection_new(type);
00304         for(list = glist; list != NULL; list = list->next)
00305         {
00306                 ent = (QofEntity*)list->data;
00307                 if(FALSE == qof_collection_add_entity(coll, ent))
00308                 {
00309                         return NULL;
00310                 }
00311         }
00312         return coll;
00313 }

gpointer qof_collection_get_data QofCollection col  ) 
 

Store and retreive arbitrary object-defined data

XXX We need to add a callback for when the collection is being destroyed, so that the user has a chance to clean up anything that was put in the 'data' member here.

Definition at line 350 of file qofid.c.

00351 {
00352    if (!col) return NULL;
00353    return col->data;
00354 }

QofIdType qof_collection_get_type QofCollection  ) 
 

return the type that the collection stores

Definition at line 172 of file qofid.c.

00173 {
00174   return col->e_type;
00175 }

gboolean qof_collection_is_dirty QofCollection col  ) 
 

Return value of 'dirty' flag on collection

Definition at line 327 of file qofid.c.

00328 {
00329    if (!col) return FALSE;
00330    return col->is_dirty;
00331 }

QofEntity* qof_collection_lookup_entity QofCollection ,
const GUID
 

Find the entity going only from its guid

Definition at line 287 of file qofid.c.

00288 {
00289   QofEntity *ent;
00290   g_return_val_if_fail (col, NULL);
00291   if (guid == NULL) return NULL;
00292   ent = g_hash_table_lookup (col->hash_of_entities, guid->data);
00293   return ent;
00294 }

gboolean qof_collection_merge QofCollection target,
QofCollection merge
 

Merge two QOF_TYPE_COLLECT of the same type.

Note:
NOT the same as the main collections in the book.
QOF_TYPE_COLLECT uses a secondary collection, independent of those in the book. Entities will not be removed from the original collection as when using qof_entity_insert_entity or qof_entity_remove_entity.

Definition at line 226 of file qofid.c.

00227 {
00228         if(!target || !merge) { return FALSE; }
00229         g_return_val_if_fail (target->e_type == merge->e_type, FALSE);
00230         qof_collection_foreach(merge, collection_merge_cb, target);
00231         return TRUE;
00232 }

QofCollection* qof_collection_new QofIdType  type  ) 
 

create a new collection of entities of type

Definition at line 147 of file qofid.c.

00148 {
00149   QofCollection *col;
00150   col = g_new0(QofCollection, 1);
00151   col->e_type = CACHE_INSERT (type);
00152   col->hash_of_entities = g_hash_table_new (id_hash, id_compare);
00153   col->data = NULL;
00154   return col;
00155 }

const GUID* qof_entity_get_guid QofEntity  ) 
 

Return the GUID of this entity

Definition at line 103 of file qofid.c.

00104 {
00105   if (!ent) return guid_null();
00106   return &ent->guid;
00107 }

void qof_entity_init QofEntity ,
QofIdType  ,
QofCollection
 

Initialise the memory associated with an entity

Definition at line 51 of file qofid.c.

00052 {
00053   g_return_if_fail (NULL != tab);
00054   
00055   /* XXX We passed redundant info to this routine ... but I think that's
00056         * OK, it might eliminate programming errors. */
00057   if (safe_strcmp(tab->e_type, type))
00058   {
00059     PERR ("attempt to insert \"%s\" into \"%s\"", type, tab->e_type);
00060          return;
00061   }
00062   ent->e_type = CACHE_INSERT (type);
00063 
00064   do
00065   {
00066     guid_new(&ent->guid);
00067 
00068     if (NULL == qof_collection_lookup_entity (tab, &ent->guid)) break;
00069 
00070     PWARN("duplicate id created, trying again");
00071   } while(1);
00072  
00073   ent->collection = tab;
00074 
00075   qof_collection_insert_entity (tab, ent);
00076 }

void qof_entity_release QofEntity  ) 
 

Release the data associated with this entity. Dont actually free the memory associated with the instance.

Definition at line 79 of file qofid.c.

00080 {
00081   if (!ent->collection) return;
00082   qof_collection_remove_entity (ent);
00083   CACHE_REMOVE (ent->e_type);
00084   ent->e_type = NULL;
00085 }


Generated on Fri Oct 21 15:50:00 2005 for QOF by  doxygen 1.4.5