00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #include "config.h"
00025
00026 #include <glib.h>
00027
00028 #include "gnc-trace.h"
00029 #include "gnc-engine-util.h"
00030 #include "qofclass.h"
00031 #include "qofclass-p.h"
00032 #include "qofquery.h"
00033
00034 static QofLogModule log_module = QOF_MOD_CLASS;
00035
00036 static GHashTable *classTable = NULL;
00037 static GHashTable *sortTable = NULL;
00038 static gboolean initialized = FALSE;
00039
00040 static gboolean clear_table (gpointer key, gpointer value, gpointer user_data)
00041 {
00042 g_hash_table_destroy (value);
00043 return TRUE;
00044 }
00045
00046
00047
00048
00049 void
00050 qof_class_register (QofIdTypeConst obj_name,
00051 QofSortFunc default_sort_function,
00052 const QofParam *params)
00053 {
00054 GHashTable *ht;
00055 int i;
00056
00057 if (!obj_name) return;
00058
00059 if (default_sort_function)
00060 {
00061 g_hash_table_insert (sortTable, (char *)obj_name, default_sort_function);
00062 }
00063
00064 ht = g_hash_table_lookup (classTable, obj_name);
00065
00066
00067 if (!ht)
00068 {
00069 ht = g_hash_table_new (g_str_hash, g_str_equal);
00070 g_hash_table_insert (classTable, (char *)obj_name, ht);
00071 }
00072
00073
00074
00075
00076
00077 if (params)
00078 {
00079 for (i = 0; params[i].param_name; i++)
00080 g_hash_table_insert (ht,
00081 (char *)params[i].param_name,
00082 (gpointer)&(params[i]));
00083 }
00084 }
00085
00086 void
00087 qof_class_init(void)
00088 {
00089 if (initialized) return;
00090 initialized = TRUE;
00091
00092 classTable = g_hash_table_new (g_str_hash, g_str_equal);
00093 sortTable = g_hash_table_new (g_str_hash, g_str_equal);
00094 }
00095
00096 void
00097 qof_class_shutdown (void)
00098 {
00099 if (!initialized) return;
00100 initialized = FALSE;
00101
00102 g_hash_table_foreach_remove (classTable, clear_table, NULL);
00103 g_hash_table_destroy (classTable);
00104 g_hash_table_destroy (sortTable);
00105 }
00106
00107 gboolean
00108 qof_class_is_registered (QofIdTypeConst obj_name)
00109 {
00110 if (!obj_name) return FALSE;
00111
00112 if (g_hash_table_lookup (classTable, obj_name)) return TRUE;
00113
00114 return FALSE;
00115 }
00116
00117 const QofParam *
00118 qof_class_get_parameter (QofIdTypeConst obj_name,
00119 const char *parameter)
00120 {
00121 GHashTable *ht;
00122
00123 g_return_val_if_fail (obj_name, NULL);
00124 g_return_val_if_fail (parameter, NULL);
00125
00126 ht = g_hash_table_lookup (classTable, obj_name);
00127 if (!ht)
00128 {
00129 PWARN ("no object of type %s", obj_name);
00130 return NULL;
00131 }
00132
00133 return (g_hash_table_lookup (ht, parameter));
00134 }
00135
00136 QofAccessFunc
00137 qof_class_get_parameter_getter (QofIdTypeConst obj_name,
00138 const char *parameter)
00139 {
00140 const QofParam *prm;
00141
00142 g_return_val_if_fail (obj_name, NULL);
00143 g_return_val_if_fail (parameter, NULL);
00144
00145 prm = qof_class_get_parameter (obj_name, parameter);
00146 if (prm)
00147 return prm->param_getfcn;
00148
00149 return NULL;
00150 }
00151
00152 QofSetterFunc
00153 qof_class_get_parameter_setter (QofIdTypeConst obj_name,
00154 const char *parameter)
00155 {
00156 const QofParam *prm;
00157
00158 g_return_val_if_fail (obj_name, NULL);
00159 g_return_val_if_fail (parameter, NULL);
00160
00161 prm = qof_class_get_parameter (obj_name, parameter);
00162 if (prm)
00163 return prm->param_setfcn;
00164
00165 return NULL;
00166 }
00167
00168 QofType
00169 qof_class_get_parameter_type (QofIdTypeConst obj_name,
00170 const char *param_name)
00171 {
00172 const QofParam *prm;
00173
00174 if (!obj_name || !param_name) return NULL;
00175
00176 prm = qof_class_get_parameter (obj_name, param_name);
00177 if (!prm) return NULL;
00178
00179 return (prm->param_type);
00180 }
00181
00182 QofSortFunc
00183 qof_class_get_default_sort (QofIdTypeConst obj_name)
00184 {
00185 if (!obj_name) return NULL;
00186 return g_hash_table_lookup (sortTable, obj_name);
00187 }
00188
00189
00190
00191 struct class_iterate {
00192 QofClassForeachCB fcn;
00193 gpointer data;
00194 };
00195
00196 static void
00197 class_foreach_cb (gpointer key, gpointer item, gpointer arg)
00198 {
00199 struct class_iterate *iter = arg;
00200 QofIdTypeConst id = key;
00201
00202 iter->fcn (id, iter->data);
00203 }
00204
00205 void
00206 qof_class_foreach (QofClassForeachCB cb, gpointer user_data)
00207 {
00208 struct class_iterate iter;
00209
00210 if (!cb) return;
00211 if (!classTable) return;
00212
00213 iter.fcn = cb;
00214 iter.data = user_data;
00215
00216 g_hash_table_foreach (classTable, class_foreach_cb, &iter);
00217 }
00218
00219
00220
00221 struct parm_iterate {
00222 QofParamForeachCB fcn;
00223 gpointer data;
00224 };
00225
00226 static void
00227 param_foreach_cb (gpointer key, gpointer item, gpointer arg)
00228 {
00229 struct parm_iterate *iter = arg;
00230 QofParam *parm = item;
00231
00232 iter->fcn (parm, iter->data);
00233 }
00234
00235 void
00236 qof_class_param_foreach (QofIdTypeConst obj_name,
00237 QofParamForeachCB cb, gpointer user_data)
00238 {
00239 struct parm_iterate iter;
00240 GHashTable *param_ht;
00241
00242 if (!obj_name || !cb) return;
00243 if (!classTable) return;
00244 param_ht = g_hash_table_lookup (classTable, obj_name);
00245 if (!param_ht) return;
00246
00247 iter.fcn = cb;
00248 iter.data = user_data;
00249
00250 g_hash_table_foreach (param_ht, param_foreach_cb, &iter);
00251 }
00252
00253 struct param_ref_list
00254 {
00255 GList *list;
00256 };
00257
00258 static void
00259 find_reference_param_cb(QofParam *param, gpointer user_data)
00260 {
00261 struct param_ref_list *b;
00262
00263 b = (struct param_ref_list*)user_data;
00264 if((param->param_getfcn == NULL)||(param->param_setfcn == NULL)) { return; }
00265 if(0 == safe_strcmp(param->param_type, QOF_TYPE_STRING)) { return; }
00266 if(0 == safe_strcmp(param->param_type, QOF_TYPE_NUMERIC)) { return; }
00267 if(0 == safe_strcmp(param->param_type, QOF_TYPE_DATE)) { return; }
00268 if(0 == safe_strcmp(param->param_type, QOF_TYPE_CHAR)) { return; }
00269 if(0 == safe_strcmp(param->param_type, QOF_TYPE_DEBCRED)) { return; }
00270 if(0 == safe_strcmp(param->param_type, QOF_TYPE_GUID)) { return; }
00271 if(0 == safe_strcmp(param->param_type, QOF_TYPE_INT32)) { return; }
00272 if(0 == safe_strcmp(param->param_type, QOF_TYPE_INT64)) { return; }
00273 if(0 == safe_strcmp(param->param_type, QOF_TYPE_DOUBLE)) { return; }
00274 if(0 == safe_strcmp(param->param_type, QOF_TYPE_KVP)) { return; }
00275 if(0 == safe_strcmp(param->param_type, QOF_TYPE_BOOLEAN)) { return; }
00276 if(0 == safe_strcmp(param->param_type, QOF_ID_BOOK)) { return; }
00277 b->list = g_list_append(b->list, param);
00278 }
00279
00280 GList*
00281 qof_class_get_referenceList(QofIdTypeConst type)
00282 {
00283 GList *ref_list;
00284 struct param_ref_list b;
00285
00286 ref_list = NULL;
00287 b.list = NULL;
00288 qof_class_param_foreach(type, find_reference_param_cb, &b);
00289 ref_list = g_list_copy(b.list);
00290 return ref_list;
00291 }
00292
00293
00294