qsf-xml.h File Reference

Private QSF header - not for use by applications. More...

#include <stdio.h>
#include <stdlib.h>
#include <regex.h>
#include <time.h>
#include "qof.h"
#include <libintl.h>

Go to the source code of this file.

Data Structures

struct  QsfObject_s
 Holds a description of the QofObject. More...
struct  QsfMetadata_s
 QSF Parameters. More...
struct  QsfValidates_s
 Validation metadata. More...
struct  QsfNodeIterate
 One iterator, two typedefs. More...

Defines

#define _(String)   dgettext (GETTEXT_PACKAGE, String)
#define QSF_QOF_VERSION   QOF_OBJECT_VERSION
#define QSF_XSD_TIME   QOF_UTC_DATE_FORMAT
#define QSF_XML_BOOLEAN_TEST   "true"
#define QSF_OBJECT_SCHEMA   "qsf-object.xsd.xml"
#define QSF_MAP_SCHEMA   "qsf-map.xsd.xml"
QSF Object XML
#define QSF_ROOT_TAG   "qof-qsf"
#define QSF_DEFAULT_NS   "http://qof.sourceforge.net/"
#define QSF_DATE_LENGTH   MAX_DATE_LENGTH
#define QSF_BOOK_TAG   "book"
#define QSF_BOOK_GUID   "book-guid"
#define QSF_BOOK_COUNT   "count"
#define QSF_OBJECT_TAG   "object"
#define QSF_OBJECT_TYPE   "type"
#define QSF_OBJECT_COUNT   "count"
#define QSF_XML_VERSION   "1.0"
Representing KVP as XML
<kvp type="kvp" path="/from-sched-xaction" value="guid">c858b9a3235723b55bc1179f0e8c1322</kvp> A kvp type KVP parameter located at $path containing a GUID $value.

The relevance of type="kvp" won't be evident in GnuCash, they all use "kvp".

A non-GnuCash example helps: <kvp type="pilot_addr_kvp" path="/user/name" value="guid">c858b9a3235723b55bc1179f0e8c1322</kvp> A pilot_addr_kvp type KVP parameter located at /user/name containing a guid value.

#define QSF_OBJECT_KVP   "path"
#define QSF_OBJECT_VALUE   "value"
QSF Map XML
#define MAP_ROOT_TAG   "qsf-map"
#define MAP_DEFINITION_TAG   "definition"
#define MAP_DEFINE_TAG   "define"
#define MAP_ITERATE_ATTR   "foreach"
#define MAP_DEFAULT_TAG   "default"
#define MAP_OBJECT_TAG   "object"
#define MAP_CALCULATE_TAG   "calculate"
#define MAP_QOF_VERSION   "qof_version"
#define MAP_NAME_ATTR   "name"
#define MAP_TYPE_ATTR   "type"
#define MAP_VALUE_ATTR   "value"
#define MAP_OBJECT_ATTR   "object"
#define MAP_E_TYPE   "e_type"
#define MAP_ENUM_TYPE   "enum"
#define QSF_BOOLEAN_DEFAULT   "boolean"
 A specific boolean default for this map.
#define QSF_CONDITIONAL   "if"
#define QSF_CONDITIONAL_SET   "set"
#define QSF_CONDITIONAL_ELSE   "else"
#define QSF_OPTION   "option"
#define QSF_FORMATTING_OPTION   "format"

Typedefs

typedef struct QsfObject_s QsfObject
 Holds a description of the QofObject.
typedef struct QsfMetadata_s QsfParam
 QSF Parameters.
typedef struct QsfValidates_s QsfValidator
 Validation metadata.

Enumerations

enum  QsfType {
  QSF_UNDEF = 0, IS_QSF_MAP, IS_QSF_OBJ, HAVE_QSF_MAP,
  OUR_QSF_OBJ
}
enum  QsfStatus {
  QSF_NO_OBJECT = 0, QSF_DEFINED_OBJECT, QSF_REGISTERED_OBJECT, QSF_CALCULATED_OBJECT,
  QSF_INVALID_OBJECT
}
 Status of various object during mapping. More...

Functions

gint qsf_compare_tag_strings (const xmlChar *node_name, gchar *tag_name)
 shorthand function
gint qsf_strings_equal (const xmlChar *node_name, gchar *tag_name)
 shorthand function
gint qsf_is_element (xmlNodePtr a, xmlNsPtr ns, gchar *c)
 shorthand function
gint qsf_check_tag (QsfParam *params, gchar *qof_type)
 shorthand function
void qsf_object_validation_handler (xmlNodePtr child, xmlNsPtr ns, QsfValidator *valid)
 Checks all incoming objects for QOF registration.
gboolean qsf_is_valid (const gchar *schema_dir, const gchar *schema_filename, xmlDocPtr doc)
 Compares an xmlDoc in memory against the schema file.
GList ** qsf_map_prepare_list (GList **maps)
 Prepare the default list of maps.
void qsf_book_node_handler (xmlNodePtr child, xmlNsPtr qsf_ns, QsfParam *params)
 Book and book-guid node handler.
KvpValuestring_to_kvp_value (const gchar *content, KvpValueType type)
 Convert a string value into KvpValue.
void qsf_valid_foreach (xmlNodePtr parent, QsfValidCB cb, struct QsfNodeIterate *qsfiter, QsfValidator *valid)
void qsf_node_foreach (xmlNodePtr parent, QsfNodeCB cb, struct QsfNodeIterate *qsfiter, QsfParam *params)
xmlDocPtr qsf_object_convert (xmlDocPtr mapDoc, xmlNodePtr qsf_root, QsfParam *params)
 Convert between QSF objects.
void qsf_object_node_handler (xmlNodePtr child, xmlNsPtr qsf_ns, QsfParam *params)

Why two sets of functions and typedefs?

These functions are in pairs, one to use in an existing session and one to use when deciding which backend should be selected for a new session.
  • When there is an existing QofSession, the qsf_param context will be available, so set error codes in the backend. Use the *_be functions.
  • When just determining the type of file, qsf_param is not necessary and no backend is available (it has not been selected yet). Use the twin function. e.g. in qsf_file_type()


typedef void(* QsfNodeCB )(xmlNodePtr, xmlNsPtr, QsfParam *)
 map and qsf object callback
typedef void(* QsfValidCB )(xmlNodePtr, xmlNsPtr, QsfValidator *)
 validator callback
gboolean is_qsf_object_be (QsfParam *params)
 Validate a QSF file and identify a suitable QSF map.
gboolean is_qsf_object (const gchar *path)
 Validate a QSF file and identify a suitable QSF map.
gboolean is_our_qsf_object_be (QsfParam *params)
 Validate a QSF file and determine type.
gboolean is_our_qsf_object (const gchar *path)
 Validate a QSF file.
gboolean is_qsf_map_be (QsfParam *params)
 Validate a QSF map file.
gboolean is_qsf_map (const gchar *path)
 Validate a QSF map file.
gboolean is_qsf_object_with_map_be (gchar *map_path, QsfParam *params)
 Validate a QSF file and a selected QSF map.
gboolean is_qsf_object_with_map (const gchar *path, gchar *map_file)
 Validate a QSF file and a selected QSF map.


Detailed Description

Private QSF header - not for use by applications.

Author:
Copyright (C) 2004-2005 Neil Williams <linux@codehelp.co.uk>

Definition in file qsf-xml.h.


Define Documentation

#define MAP_CALCULATE_TAG   "calculate"

One calculation for every parameter that needs to be set.

QSF follows the same rule as qof_book_merge. Only if a getter and a setter function are defined for a parameter is it available to QSF. If a QofAccessFunc and QofSetterFunc are both defined for any QofObject parameter, that parameter MUST be calculated in any map that defines that object.

Definition at line 248 of file qsf-xml.h.

#define MAP_DEFAULT_TAG   "default"

User editable defaults for data not available within the available QSF objects.

Some defaults will relate to how to format descriptive dates, whether discount should be considered, which account to use for certain QSF data from applications that do not use accounts.

Some defaults are pre-defined and cannot be over-written:

  • qsf_time_now
  • qsf_time_string

Attributes (All are mandatory):

name The text name for this default. Certain pre-defined defaults exist but user- or map-defined defaults can have any unique text name. Spaces are NOT allowed, use undersccores instead. The value of name must not duplicate any existing default, define, object or parameter unless the special type, enum, is used.

type QOF_TYPE - must be one of the recognised QOF data types for the qof_version in use or the special type, enum.

value Text representation of the required value. For numeric, use the format [0-9]?/[0-9]?

Attention:
Using boolean defaults
A boolean default is not output in the QSF directly, instead the value is used in the calculations to modify certain values. If the boolean default is set to true, the if statement containing the boolean name will be evaluated. If the boolean default is set to false, the corresponding else will be evaluted. Make sure your calculations contain an appropriate else statement so that the boolean value can be adjusted without invalidating the map!

QSF deals with partial QofBooks - each object is fully described but the book does not have to contain any specific object types or have any particular structure. To merge partial books into usual QofBook data sources, the map must deal with entities that need to be referenced in the target QofBook but which simply do not exist in the QofBook used to generate the QSF. e.g. pilot-link knows nothing of Accounts yet when QSF creates a gncInvoice from qof-datebook, gncInvoice needs to know the GUID of certain accounts in the target QofBook. This is handled in the map by specifying the name of the account as a default for that map. When imported, the QSF QofBackend looks up the object required using the name of the parameter to obtain the parameter type. This is the only situation where QSF converts between QOF data types. A string description of the required object is converted to the GUID for that specific entity. The map cannot contain the GUID as it is generic and used by multiple users.

Attention:
Using enumerators
  • enum types are the only defaults that are allowed to use the same name value more than once.
  • enum types are used to increase the readability of a QSF map.
  • The enum name acts to group the enum values together - in a similar fashion to radio buttons in HTML forms.
  • enum types are used only where the QOF object itself uses an enum type.
e.g. the tax_included enum type allows maps to use the full name of the enum value GNC_TAXINCLUDED_YES, instead of the cryptic digit value, 1.

Definition at line 226 of file qsf-xml.h.

#define MAP_DEFINE_TAG   "define"

defines each object supported by this QSF map

Attributes: e_type Copied directly from the QofObject definition. Content: The full QofObject description for the defined QOF object.

Definition at line 151 of file qsf-xml.h.

#define MAP_DEFINITION_TAG   "definition"

Second level container for defined objects

Attributes: qof_version - Taken from the QOF_OBJECT_VERSION macro in QOF. At the time of QSF development, QOF_OBJECT_VERSION is defined as 3. All QSF maps and QSF objects must use the same qof_version which in turn must match the QOF_OBJECT_VERSION for the QOF library in use by the calling process.

No text content allowed.

Definition at line 144 of file qsf-xml.h.

#define MAP_E_TYPE   "e_type"

Validates the objects defined in the map

The e_type will be used to match incoming QSF objects with the relevant QSF map. The value of the e_type must be the value of the e_type for that object in the originating QOF application. The define tag must contain the value of the description of the same object in the same originating QOF application.

Definition at line 300 of file qsf-xml.h.

#define MAP_ENUM_TYPE   "enum"

Todo:
enum is an attempt to make enumerator values descriptive in the maps and QSF (possibly). Not working yet.

Definition at line 304 of file qsf-xml.h.

#define MAP_ITERATE_ATTR   "foreach"

Dictate which object type is the basis for iteration in a hierarchical object set.

Definition at line 155 of file qsf-xml.h.

#define MAP_NAME_ATTR   "name"

The name of the default setting.

Use this name to refer to the value of this default in the map calculations.

Make sure that the type of this default matches the type of the parameter being set by the parent calculation!

Definition at line 267 of file qsf-xml.h.

#define MAP_OBJECT_ATTR   "object"

The object to use to provide the data being set using the map.

Definition at line 290 of file qsf-xml.h.

#define MAP_OBJECT_TAG   "object"

Contains all the calculations to make one object from others.

Note that creating an object for the import application can involve using data from more than one QSF object, as well as defaults and lookups in the import application itself. Conditionals, simple arithmetic and date/time formatting options are also available.

Definition at line 237 of file qsf-xml.h.

#define MAP_QOF_VERSION   "qof_version"

This is the QOF_OBJECT_VERSION from QOF.

QSF maps may need to be updated if QOF itself is upgraded. This setting is coded into QOF and maps for one version cannot necessarily be used by other versions. At the first release of QSF, QOF_OBJECT_VERSION = 3.

Definition at line 257 of file qsf-xml.h.

#define MAP_ROOT_TAG   "qsf-map"

Top level root tag for QSF Maps

Definition at line 133 of file qsf-xml.h.

#define MAP_TYPE_ATTR   "type"

QSF will NOT convert between QOF types.

QSF will allow a conditional to use a parameter of one type to determine the value from a parameter of another type, but the final value assigned MUST be of the same type as the parent calculation.

Definition at line 276 of file qsf-xml.h.

#define MAP_VALUE_ATTR   "value"

The value of the tag, used in defaults and calculations.

The value of a default is a string representation of the value to be inserted into the calculation where the default is used.

The value of a calculation is the name of the parameter that will be set by that calculation.

Definition at line 286 of file qsf-xml.h.

#define QSF_BOOK_COUNT   "count"

Sequential counter of each book in this file

Definition at line 96 of file qsf-xml.h.

#define QSF_BOOK_GUID   "book-guid"

QOF GUID tag for the QofBook described by this QSF object file

Definition at line 94 of file qsf-xml.h.

#define QSF_BOOK_TAG   "book"

First level child: book tag - the QofBook.

Definition at line 91 of file qsf-xml.h.

#define QSF_CONDITIONAL   "if"

child of calculate.

Conditionals can reference objects as if within the original application. In operation, the map is overlaid across both sets of defined objects, an import object in the source application and an output object for the destination object. The current import and output QSF objects are therefore always available to the map. Conditionals can reference parameter as well as object values.

Definition at line 319 of file qsf-xml.h.

#define QSF_CONDITIONAL_ELSE   "else"

Alternative

if(){} else{} is also supported. Nesting of conditionals causes problems for validating the final map against any sensible XML Schema and a map that does not validate will be rejected. When editing conditionals in a QSF map, ALWAYS validate the map using xmllint. If necessary, define a variable at the foot of the definitions block, using a similar syntax to a default, then use that variable in another conditional

variable name="my_rate" type="numeric" value="0/1"

The syntax for xmllint is:

xmllint --schema <schema file> <qsf-file>

Use the qsf-object.xsd.xml schema for objects and qsf-map.xsd.xml for map files.

e.g. xmllint --schema qsf-object.xsd.xml --noout qof-qsf.xml

Definition at line 355 of file qsf-xml.h.

#define QSF_CONDITIONAL_SET   "set"

Assignment statement

Map assignments can use the native values within the output object. The output object must support setting the relevant parameter using the value exactly as given in the map because the relevant set() function will be called using this value. This may reduce the readability of the map but the relevant application could also be modified to support a more readable set function.

Definition at line 331 of file qsf-xml.h.

#define QSF_DATE_LENGTH   MAX_DATE_LENGTH

Max length of QSF_XSD_TIME.

MAX_DATE_LENGTH itself is defined in qof-time.h

Definition at line 88 of file qsf-xml.h.

#define QSF_DEFAULT_NS   "http://qof.sourceforge.net/"

Default namespace for QSF root tag

The map namespace is not included as maps are not currently written out by QOF.

Definition at line 84 of file qsf-xml.h.

#define QSF_FORMATTING_OPTION   "format"

How to format dates/times

When the QSF map uses a date/time value as a string, the formatting can be adjusted to personal preference. format will only be evaluated if the calculated parameter is a QOF_TYPE_STRING - any format attributes on other data types will be ignored.

Definition at line 373 of file qsf-xml.h.

#define QSF_MAP_SCHEMA   "qsf-map.xsd.xml"

Name of the QSF Map Schema.

Definition at line 420 of file qsf-xml.h.

#define QSF_OBJECT_COUNT   "count"

Sequential counter for each QSF object in this file

Definition at line 102 of file qsf-xml.h.

#define QSF_OBJECT_KVP   "path"

The path to this KVP value in the entity frame.

Definition at line 124 of file qsf-xml.h.

#define QSF_OBJECT_SCHEMA   "qsf-object.xsd.xml"

Name of the QSF Object Schema.

Definition at line 417 of file qsf-xml.h.

#define QSF_OBJECT_TAG   "object"

Second level child: object tag

Definition at line 98 of file qsf-xml.h.

#define QSF_OBJECT_TYPE   "type"

QSF parameter name for object type specifiers

Definition at line 100 of file qsf-xml.h.

#define QSF_OBJECT_VALUE   "value"

The KVP Value.

Definition at line 126 of file qsf-xml.h.

#define QSF_OPTION   "option"

enum operator

Not implemented yet - may need to change once work starts. Theoretically, option will specify when an enumerator value is in use - it is quite possible that it will be unnecessary.

Definition at line 363 of file qsf-xml.h.

#define QSF_QOF_VERSION   QOF_OBJECT_VERSION

QOF Version check.

Make sure the same version of QOF is in use in both applications.

Definition at line 70 of file qsf-xml.h.

#define QSF_ROOT_TAG   "qof-qsf"

The top level root tag

Definition at line 78 of file qsf-xml.h.

#define QSF_XML_BOOLEAN_TEST   "true"

needs to be lowercase for XML validation

Definition at line 414 of file qsf-xml.h.

#define QSF_XML_VERSION   "1.0"

The current XML version.

Definition at line 104 of file qsf-xml.h.

#define QSF_XSD_TIME   QOF_UTC_DATE_FORMAT

xsd:dateTime format in coordinated universal time, UTC.

You can reproduce the string from the GNU/Linux command line using the date utility:

date -u +Y-m-dTH:M:SZ

2004-12-12T23:39:11Z

The datestring must be timezone independent and include all specified fields.

Remember to use gmtime() NOT localtime()!. From the command line, use the -u switch with the date command: date -u

To generate a timestamp based on a real time, use the qsf_time_now and qsf_time_string defaults.

qsf_time_now : Format: QOF_TYPE_DATE. The current time taken from the moment the default is read into a QSF object at runtime.

qsf_time_string : Format: QOF_TYPE_STRING. The current timestamp taken from the moment the default is read into a QSF object at runtime. This form is used when the output parameter needs a formatted date string, not an actual date object. The format is determined by the optional format attribute of the set tag which takes the same operators as the GNU C Library for strftime() and output may therefore be dependent on the locale of the calling process - take care. Default value is F, used when qsf_time_string is set without the format attribute.

Both defaults use UTC.

Definition at line 411 of file qsf-xml.h.


Typedef Documentation

typedef void(* QsfNodeCB)(xmlNodePtr, xmlNsPtr, QsfParam *)

map and qsf object callback

This callback cannot do both the map and the validation tasks because validation sometimes needs to be done without qsf_params.

e.g. when selecting which backend should be used for a particular data source where two or more backends share the same access_method.

Definition at line 674 of file qsf-xml.h.

typedef struct QsfObject_s QsfObject

Holds a description of the QofObject.

Used when converting QOF objects from another application. The incoming, unknown, objects need to be stored prior to conversion. This allows many-to-many conversions where an invoice can receive data from an incoming expense AND datebook and use data from an incoming contacts object to lookup the customer for the invoice.

typedef struct QsfMetadata_s QsfParam

QSF Parameters.

This struct is a catch-all for all parameters required for various stages of the process. There are lots of elements here that will finally be removed.

typedef struct QsfValidates_s QsfValidator

Validation metadata.

The validation is a separate parse with separate data. This is used to determine which backend should load the data.

typedef void(* QsfValidCB)(xmlNodePtr, xmlNsPtr, QsfValidator *)

validator callback

Todo:
The need for separate metadata means a separate callback typedef is needed for the validator, but this should be fixed to only need one.

Definition at line 681 of file qsf-xml.h.


Enumeration Type Documentation

enum QsfStatus

Status of various object during mapping.

When handling a map, the incoming QSF objects are not registered with this instance of QOF - they originate from another QOF user. Each object in a map needs to be defined. If the object is registered, the map is checked to locate a calculation that can be used to generate this object. If the object is not registered, the incoming QSF is checked to ensure it provides the object data for the calculation. If anything goes wrong, QSF_INVALID_OBJECT is used.

Maps can be unidirectional or bidirectional so QOF registration is used to determine which calculations should be used and which should be ignored.

All QSF_REGISTERED_OBJECT types need a calculation - if any types remain tagged as QSF_REGISTERED_OBJECT when the map validation is complete, the validation must fail. The only acceptable end values for QsfStatus are QSF_DEFINED_OBJECT, QSF_CALCULATED_OBJECT or QSF_INVALID_OBJECT.

Enumerator:
QSF_NO_OBJECT  Init value.
QSF_DEFINED_OBJECT  The object is unregistered but defined. Objects of this type must exist in the incoming QSF and must provide data for the calculation of registered objects.
QSF_REGISTERED_OBJECT  Temporary value. The object is registered and defined - a calculation is needed but has not been found, yet.
QSF_CALCULATED_OBJECT  The object is registered, defined and can be calculated.
QSF_INVALID_OBJECT  Oops value.

Definition at line 443 of file qsf-xml.h.

enum QsfType

Enumerator:
QSF_UNDEF  Initial undefined value.
IS_QSF_MAP  A QSF map
IS_QSF_OBJ  A QSF object without a map - it may or may not need one.
HAVE_QSF_MAP  A QSF object with the map it needs.
OUR_QSF_OBJ  A QSF object that can be loaded without a map.

Definition at line 41 of file qsf-xml.h.

00042 {
00044     QSF_UNDEF = 0,
00046     IS_QSF_MAP,
00048     IS_QSF_OBJ,
00050     HAVE_QSF_MAP,
00052     OUR_QSF_OBJ,
00053 } QsfType;


Function Documentation

gboolean is_our_qsf_object ( const gchar *  path  ) 

Validate a QSF file.

Parameters:
path Absolute or relative path to the file to be validated
The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to see if it is registered with QOF within the QOF environment of the calling process.

Files that pass the test can be imported into the QOF application without the need for a QSF map.

Returns:
TRUE if the file validates and all objects pass, otherwise FALSE.

Definition at line 179 of file qsf-xml.c.

00180 {
00181     xmlDocPtr doc;
00182     struct QsfNodeIterate qsfiter;
00183     xmlNodePtr object_root;
00184     QsfValidator valid;
00185     gint table_count;
00186 
00187     g_return_val_if_fail ((path != NULL), FALSE);
00188     doc = xmlParseFile (path);
00189     if (doc == NULL)
00190     {
00191         return FALSE;
00192     }
00193     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00194     {
00195         PINFO (" validation failed %s %s %s", QSF_SCHEMA_DIR,
00196             QSF_OBJECT_SCHEMA, path);
00197         return FALSE;
00198     }
00199     object_root = xmlDocGetRootElement (doc);
00200     /* check that all objects in the file are already registered in QOF */
00201     valid.object_table = g_hash_table_new (g_str_hash, g_str_equal);
00202     valid.qof_registered_count = 0;
00203     valid.valid_object_count = 0;
00204     qsfiter.ns = object_root->ns;
00205     qsf_valid_foreach (object_root, qsf_object_validation_handler, 
00206         &qsfiter, &valid);
00207     table_count = g_hash_table_size (valid.object_table);
00208     g_hash_table_destroy (valid.object_table);
00209     xmlFreeDoc (doc);
00210     if (table_count == valid.qof_registered_count)
00211     {
00212         return TRUE;
00213     }
00214     return FALSE;
00215 }

gboolean is_our_qsf_object_be ( QsfParam params  ) 

Validate a QSF file and determine type.

Parameters:
params Pointer to qsf_param context
The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to see if it is registered with QOF within the QOF environment of the calling process.

Files that pass the test can be imported into the QOF appliction without the need for a QSF map.

Returns:
TRUE if the file validates and all objects pass, otherwise FALSE.

Definition at line 242 of file qsf-xml.c.

00243 {
00244     xmlDocPtr doc;
00245     struct QsfNodeIterate qsfiter;
00246     xmlNodePtr object_root;
00247     QsfValidator valid;
00248     gint table_count;
00249 
00250     g_return_val_if_fail ((params != NULL), FALSE);
00251     if (params->filepath == NULL)
00252     {
00253         qof_error_set_be (params->be, qof_error_register
00254         (_("The QSF XML file '%s' could not be found."), TRUE));
00255         return FALSE;
00256     }
00257     if (params->file_type != QSF_UNDEF)
00258     {
00259         return FALSE;
00260     }
00261     doc = xmlParseFile (params->filepath);
00262     if (doc == NULL)
00263     {
00264         qof_error_set_be (params->be, qof_error_register
00265         (_("There was an error parsing the file '%s'."), TRUE));
00266         return FALSE;
00267     }
00268     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00269     {
00270         qof_error_set_be (params->be, qof_error_register
00271         (_("Invalid QSF Object file! The QSF object file '%s' "
00272         " failed to validate  against the QSF object schema. "
00273         "The XML structure of the file is either not well-formed "
00274         "or the file contains illegal data."), TRUE));
00275         xmlFreeDoc (doc);
00276         return FALSE;
00277     }
00278     params->file_type = IS_QSF_OBJ;
00279     object_root = xmlDocGetRootElement (doc);
00280     xmlFreeDoc (doc);
00281     valid.object_table = g_hash_table_new (g_str_hash, g_str_equal);
00282     valid.qof_registered_count = 0;
00283     qsfiter.ns = object_root->ns;
00284     qsf_valid_foreach (object_root, qsf_object_validation_handler, 
00285         &qsfiter, &valid);
00286     table_count = g_hash_table_size (valid.object_table);
00287     if (table_count == valid.qof_registered_count)
00288     {
00289         g_hash_table_destroy (valid.object_table);
00290         return TRUE;
00291     }
00292     g_hash_table_destroy (valid.object_table);
00293     qof_error_set_be (params->be, params->err_nomap);
00294     return FALSE;
00295 }

gboolean is_qsf_map ( const gchar *  path  ) 

Validate a QSF map file.

Parameters:
path Absolute or relative path to the file to be validated
These functions are in pairs. When called from within a QofSession, the qsf_param context will be available. When just determining the type of file, qsf_param is not necessary. Use the *_be functions from within the QofBackend and the corresponding function in other code.

The file is validated aginst the QSF map schema, qsf-map.xsd.xsml. This function is called by is_qsf_object. If called directly, the map file is validated and closed, no data is retrieved. QSF maps do not contain user data but are used to import QSF object files from other applications.

Returns:
TRUE if the map validates, otherwise FALSE.

Definition at line 371 of file qsf-xml-map.c.

00372 {
00373     xmlDocPtr doc;
00374     struct QsfNodeIterate qsfiter;
00375     QsfValidator valid;
00376     xmlNodePtr map_root;
00377     xmlNsPtr map_ns;
00378 
00379     g_return_val_if_fail ((path != NULL), FALSE);
00380     if (path == NULL)
00381     {
00382         return FALSE;
00383     }
00384     doc = xmlParseFile (path);
00385     if (doc == NULL)
00386     {
00387         return FALSE;
00388     }
00389     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_MAP_SCHEMA, doc))
00390     {
00391         return FALSE;
00392     }
00393     map_root = xmlDocGetRootElement (doc);
00394     map_ns = map_root->ns;
00395     qsfiter.ns = map_ns;
00396     valid.error_state = QOF_SUCCESS;
00397     valid.map_table = g_hash_table_new (g_str_hash, g_str_equal);
00398     qsf_valid_foreach (map_root, qsf_map_validation_handler, 
00399         &qsfiter, &valid);
00400     if (valid.error_state != QOF_SUCCESS)
00401     {
00402         g_hash_table_destroy (valid.map_table);
00403         return FALSE;
00404     }
00405     g_hash_table_destroy (valid.map_table);
00406     return TRUE;
00407 }

gboolean is_qsf_map_be ( QsfParam params  ) 

Validate a QSF map file.

Parameters:
params Pointer to qsf_param context
The file is validated aginst the QSF map schema, qsf-map.xsd.xsml. This function is called by is_qsf_object. If called directly, the map file is validated and closed with a QofBackend error. QSF maps do not contain user data and are used to import QSF object files.

Returns:
TRUE if the map validates, otherwise FALSE.

Definition at line 319 of file qsf-xml-map.c.

00320 {
00321     xmlDocPtr doc;
00322     struct QsfNodeIterate qsfiter;
00323     QsfValidator valid;
00324     xmlNodePtr map_root;
00325     xmlNsPtr map_ns;
00326     gchar *path;
00327 
00328     g_return_val_if_fail ((params != NULL), FALSE);
00329     path = g_strdup (params->filepath);
00330     if (path == NULL)
00331     {
00332         qof_error_set_be (params->be, qof_error_register
00333         (_("The QSF XML file '%s' could not be found."), TRUE));
00334         return FALSE;
00335     }
00336     doc = xmlParseFile (path);
00337     if (doc == NULL)
00338     {
00339         qof_error_set_be (params->be, qof_error_register
00340         (_("There was an error parsing the file '%s'."), TRUE));
00341         return FALSE;
00342     }
00343     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_MAP_SCHEMA, doc))
00344     {
00345         qof_error_set_be (params->be, 
00346             qof_error_register (
00347             _("Invalid QSF Map file! The QSF map file "
00348               "failed to validate against the QSF map schema. "
00349               "The XML structure of the file is either not well-formed "
00350               "or the file contains illegal data."), FALSE));
00351         return FALSE;
00352     }
00353     map_root = xmlDocGetRootElement (doc);
00354     map_ns = map_root->ns;
00355     qsfiter.ns = map_ns;
00356     valid.object_table = g_hash_table_new (g_str_hash, g_str_equal);
00357     valid.map_table = g_hash_table_new (g_str_hash, g_str_equal);
00358     valid.error_state = QOF_SUCCESS;
00359     qsf_valid_foreach (map_root, qsf_map_validation_handler, 
00360         &qsfiter, &valid);
00361     if (valid.error_state != QOF_SUCCESS)
00362     {
00363         g_hash_table_destroy (valid.object_table);
00364         return FALSE;
00365     }
00366     g_hash_table_destroy (valid.object_table);
00367     return TRUE;
00368 }

gboolean is_qsf_object ( const gchar *  path  ) 

Validate a QSF file and identify a suitable QSF map.

Parameters:
path Absolute or relative path to the file to be validated.
These functions are in pairs. When called from within a QofSession, the qsf_param context will be available. When just determining the type of file, qsf_param is not necessary. Use the *_be functions from within the QofBackend and the corresponding function in other code.

The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to find out if a suitable QSF map exists. Map files are accepted if all objects described in the QSF object file are defined in the QSF map.

Returns:
TRUE if the file validates and a QSF map can be found, otherwise FALSE.

Definition at line 218 of file qsf-xml.c.

00219 {
00220     xmlDocPtr doc;
00221 
00222     g_return_val_if_fail ((path != NULL), FALSE);
00223     if (path == NULL)
00224     {
00225         return FALSE;
00226     }
00227     doc = xmlParseFile (path);
00228     if (doc == NULL)
00229     {
00230         return FALSE;
00231     }
00232     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00233     {
00234         return FALSE;
00235     }
00236     /* Note cannot test against a map here, so if the file is valid QSF,
00237        accept it and work out the details later. */
00238     return TRUE;
00239 }

gboolean is_qsf_object_be ( QsfParam params  ) 

Validate a QSF file and identify a suitable QSF map.

Parameters:
params Pointer to qsf_param context
These functions are in pairs. When called from within a QofSession, the qsf_param context will be available. When just determining the type of file, qsf_param is not necessary. Use the *_be functions from within the QofBackend and the corresponding function in other code.

The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to find out if a suitable QSF map exists. Map files are accepted if all objects described in the QSF object file are defined in the QSF map.

Returns:
TRUE if the file validates and a QSF map can be found, otherwise FALSE.

Definition at line 298 of file qsf-xml.c.

00299 {
00300     gboolean result;
00301     xmlDocPtr doc;
00302     GList *maps;
00303     gchar *path;
00304 
00305     g_return_val_if_fail ((params != NULL), FALSE);
00306     path = g_strdup (params->filepath);
00307     if (path == NULL)
00308     {
00309         qof_error_set_be (params->be, qof_error_register
00310         (_("The QSF XML file '%s' could not be found."), TRUE));
00311         return FALSE;
00312     }
00313     /* skip validation if is_our_qsf_object has already been called. */
00314 /*  if (ERR_QSF_INVALID_OBJ == qof_backend_get_error (params->be))
00315     {
00316         return FALSE;
00317     }*/
00318     if (params->file_type == QSF_UNDEF)
00319     {
00320         doc = xmlParseFile (path);
00321         if (doc == NULL)
00322         {
00323             qof_error_set_be (params->be, qof_error_register
00324             (_("There was an error parsing the file '%s'."), TRUE));
00325             return FALSE;
00326         }
00327         if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00328         {
00329             qof_error_set_be (params->be, qof_error_register
00330             (_("Invalid QSF Object file! The QSF object file '%s' "
00331             " failed to validate  against the QSF object schema. "
00332             "The XML structure of the file is either not well-formed "
00333             "or the file contains illegal data."), TRUE));
00334             return FALSE;
00335         }
00336     }
00337     result = FALSE;
00338     /* retrieve list of maps from config frame. */
00339     for (maps = params->map_files; maps; maps = maps->next)
00340     {
00341         QofErrorId err;
00342         result = is_qsf_object_with_map_be (maps->data, params);
00343         err = qof_error_check_be (params->be);
00344         if ((err == QOF_SUCCESS) && result)
00345         {
00346             params->map_path = maps->data;
00347             PINFO ("map chosen = %s", params->map_path);
00348             break;
00349         }
00350     }
00351     return result;
00352 }

gboolean is_qsf_object_with_map ( const gchar *  path,
gchar *  map_file 
)

Validate a QSF file and a selected QSF map.

Parameters:
path Absolute or relative path to the selected QSF object file
map_file Name of the QSF map file, located in QSF_SCHEMA_DIR.
The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to find out if the supplied QSF map is suitable. Map files are accepted if all objects described in the QSF object file are defined in the QSF map.

Returns:
TRUE if the file validates and the supplied QSF map is usable, otherwise FALSE.

Definition at line 289 of file qsf-xml-map.c.

00290 {
00291     xmlDocPtr doc, map_doc;
00292     QofErrorId result;
00293     gchar *map_path;
00294 
00295     map_path = g_strdup_printf ("%s/%s", QSF_SCHEMA_DIR, map_file);
00296     if (path == NULL)
00297     {
00298         return FALSE;
00299     }
00300     doc = xmlParseFile (path);
00301     if (doc == NULL)
00302     {
00303         return FALSE;
00304     }
00305     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00306     {
00307         return FALSE;
00308     }
00309     if (map_path == NULL)
00310     {
00311         return FALSE;
00312     }
00313     map_doc = xmlParseFile (map_path);
00314     result = check_qsf_object_with_map_internal (map_doc, doc);
00315     return (result == QOF_SUCCESS) ? TRUE : FALSE;
00316 }

gboolean is_qsf_object_with_map_be ( gchar *  map_path,
QsfParam params 
)

Validate a QSF file and a selected QSF map.

Parameters:
map_path Absolute or relative path to the selected QSF map file
params Pointer to qsf_param context
The file is validated against the QSF object schema, qsf-object.xsd.xml and each object described in the file is checked to find out if the supplied QSF map is suitable. Map files are accepted if all objects described in the QSF object file are defined in the QSF map.

This backend twin also sets QofErrorId codes.

Returns:
TRUE if the file validates and the supplied QSF map is usable, otherwise FALSE.

Definition at line 239 of file qsf-xml-map.c.

00240 {
00241     xmlDocPtr doc, map_doc;
00242     QofErrorId result;
00243     gchar *path, *map_path;
00244 
00245     g_return_val_if_fail ((params != NULL), FALSE);
00246     path = g_strdup (params->filepath);
00247     map_path = g_strdup_printf ("%s/%s", QSF_SCHEMA_DIR, map_file);
00248     PINFO (" checking map file '%s'", map_path);
00249     if (path == NULL)
00250     {
00251         qof_error_set_be (params->be, qof_error_register
00252         (_("The QSF XML file '%s' could not be found."), TRUE));
00253         return FALSE;
00254     }
00255     doc = xmlParseFile (path);
00256     if (doc == NULL)
00257     {
00258         qof_error_set_be (params->be, qof_error_register
00259         (_("There was an error parsing the file '%s'."), TRUE));
00260         return FALSE;
00261     }
00262     if (TRUE != qsf_is_valid (QSF_SCHEMA_DIR, QSF_OBJECT_SCHEMA, doc))
00263     {
00264         qof_error_set_be (params->be, qof_error_register
00265         (_("Invalid QSF Object file! The QSF object file '%s' "
00266         " failed to validate  against the QSF object schema. "
00267         "The XML structure of the file is either not well-formed "
00268         "or the file contains illegal data."), TRUE));
00269         return FALSE;
00270     }
00271     if (map_path == NULL)
00272     {
00273         qof_error_set_be (params->be, qof_error_register
00274         (_("The QSF map file '%s' could not be found."), TRUE));
00275         return FALSE;
00276     }
00277     map_doc = xmlParseFile (map_path);
00278     if (map_doc == NULL)
00279     {
00280         qof_error_set_be (params->be, qof_error_register
00281         (_("There was an error parsing the file '%s'."), TRUE));
00282         return FALSE;
00283     }
00284     result = check_qsf_object_with_map_internal (map_doc, doc);
00285     return (result == QOF_SUCCESS) ? TRUE : FALSE;
00286 }

void qsf_book_node_handler ( xmlNodePtr  child,
xmlNsPtr  qsf_ns,
QsfParam params 
)

Book and book-guid node handler.

Reads the book count="" attribute (currently only 1 QofBook is supported per QSF object file). Sets the book-guid as the GUID of the current QofBackend QofBook in qsf_param. Calls the next handler, qsf_object_node_handler, with the child of the book tag.

Definition at line 423 of file qsf-xml.c.

00424 {
00425     gchar *book_count_s, *tail;
00426     gint book_count;
00427     xmlNodePtr child_node;
00428     struct QsfNodeIterate qsfiter;
00429     gchar *buffer;
00430     GUID book_guid;
00431 
00432     g_return_if_fail (child);
00433     g_return_if_fail (params);
00434     ENTER (" child=%s", child->name);
00435     if (qsf_is_element (child, ns, QSF_BOOK_TAG))
00436     {
00437         book_count_s =
00438             (gchar *) xmlGetProp (child, BAD_CAST QSF_BOOK_COUNT);
00439         if (book_count_s)
00440         {
00441             book_count = (gint) strtol (book_count_s, &tail, 0);
00442             /* More than one book not currently supported. */
00443             g_free (book_count_s);
00444             g_return_if_fail (book_count == 1);
00445         }
00446         qsfiter.ns = ns;
00447         child_node = child->children->next;
00448         if (qsf_is_element (child_node, ns, QSF_BOOK_GUID))
00449         {
00450             DEBUG (" trying to set book GUID");
00451             buffer = BAD_CAST xmlNodeGetContent (child_node);
00452             g_return_if_fail (TRUE == string_to_guid (buffer, &book_guid));
00453             qof_entity_set_guid ((QofEntity *) params->book, &book_guid);
00454             xmlNewChild (params->output_node, params->qsf_ns,
00455                 BAD_CAST QSF_BOOK_GUID, BAD_CAST buffer);
00456             xmlFree (buffer);
00457         }
00458         qsf_node_foreach (child, qsf_object_node_handler, &qsfiter, params);
00459     }
00460     LEAVE (" ");
00461 }

gint qsf_check_tag ( QsfParam params,
gchar *  qof_type 
)

shorthand function

This may look repetitive but each one is used separately as well as in a block.

Definition at line 68 of file qsf-xml.c.

00069 {
00070     return qsf_is_element (params->child_node, params->qsf_ns, qof_type);
00071 }

gint qsf_compare_tag_strings ( const xmlChar *  node_name,
gchar *  tag_name 
)

shorthand function

This may look repetitive but each one is used separately as well as in a block.

Definition at line 38 of file qsf-xml.c.

00039 {
00040     return xmlStrcmp (node_name, (const xmlChar *) tag_name);
00041 }

gint qsf_is_element ( xmlNodePtr  a,
xmlNsPtr  ns,
gchar *  c 
)

shorthand function

This may look repetitive but each one is used separately as well as in a block.

Definition at line 54 of file qsf-xml.c.

00055 {
00056     g_return_val_if_fail (a != NULL, 0);
00057     g_return_val_if_fail (ns != NULL, 0);
00058     g_return_val_if_fail (c != NULL, 0);
00059     if ((a->ns == ns) && (a->type == XML_ELEMENT_NODE) &&
00060         qsf_strings_equal (a->name, c))
00061     {
00062         return 1;
00063     }
00064     return 0;
00065 }

gboolean qsf_is_valid ( const gchar *  schema_dir,
const gchar *  schema_filename,
xmlDocPtr  doc 
)

Compares an xmlDoc in memory against the schema file.

Parameters:
schema_dir set at compile time to $prefix/share/qsf/
schema_filename Either the QSF Object Schema or the QSF Map Schema.
doc The xmlDoc read from the file using libxml2.
Ensure that you call the right schema_filename for the doc in question!

Incorrect validation will result in output to the terminal window.

Returns:
TRUE if the doc validates against the assigned schema, otherwise FALSE.

Definition at line 74 of file qsf-xml.c.

00076 {
00077     xmlSchemaParserCtxtPtr qsf_schema_file;
00078     xmlSchemaPtr qsf_schema;
00079     xmlSchemaValidCtxtPtr qsf_context;
00080     gchar *schema_path;
00081     gint result;
00082 
00083     g_return_val_if_fail (doc || schema_filename, FALSE);
00084     schema_path = g_strdup_printf ("%s/%s", schema_dir, schema_filename);
00085     qsf_schema_file = xmlSchemaNewParserCtxt (schema_path);
00086     qsf_schema = xmlSchemaParse (qsf_schema_file);
00087     qsf_context = xmlSchemaNewValidCtxt (qsf_schema);
00088     result = xmlSchemaValidateDoc (qsf_context, doc);
00089     xmlSchemaFreeParserCtxt (qsf_schema_file);
00090     xmlSchemaFreeValidCtxt (qsf_context);
00091     xmlSchemaFree (qsf_schema);
00092     g_free (schema_path);
00093     if (result == 0)
00094     {
00095         return TRUE;
00096     }
00097     return FALSE;
00098 }

GList** qsf_map_prepare_list ( GList **  maps  ) 

Prepare the default list of maps.

Prepend the default maps to the supplied GList.

The GList remains the property of the caller.

Todo:
Automate this once map support is stable

Definition at line 167 of file qsf-backend.c.

00168 {
00169     /* Add new map filenames here. */
00171     *maps = g_list_prepend (*maps, "pilot-qsf-GnuCashInvoice.xml");
00172     *maps = g_list_prepend (*maps, "pilot-qsf-gncCustomer.xml");
00173     return maps;
00174 }

void qsf_node_foreach ( xmlNodePtr  parent,
QsfNodeCB  cb,
struct QsfNodeIterate qsfiter,
QsfParam params 
)

Iterate over the children of the parent node.

Only iterates over the immediate children of the parent - this function is not recursive.

Definition at line 115 of file qsf-xml.c.

00117 {
00118     xmlNodePtr cur_node;
00119 
00120     if (!parent)
00121         return;
00122     g_return_if_fail (params);
00123     g_return_if_fail (qsfiter->ns);
00124     qsfiter->fcn = &cb;
00125     for (cur_node = parent->children; cur_node != NULL;
00126         cur_node = cur_node->next)
00127     {
00128         cb (cur_node, qsfiter->ns, params);
00129     }
00130 }

xmlDocPtr qsf_object_convert ( xmlDocPtr  mapDoc,
xmlNodePtr  qsf_root,
QsfParam params 
)

Convert between QSF objects.

This is the main workhorse of the conversion between QSF objects using maps.

Parameters:
mapDoc The map document, parsed by libxml2.
qsf_root The top node of the QSF object to be converted using the map.
params The QSF backend parameters.
Each calculation in the map is performed over the child nodes of the object tree. A new xmlDoc is created and this is made available to QOF to be loaded into the book.

Definition at line 953 of file qsf-xml-map.c.

00955 {
00956     /* mapDoc : map document. qsf_root: incoming QSF root node. */
00957     struct QsfNodeIterate qsfiter;
00958     xmlDocPtr output_doc;
00959     xmlNode *cur_node;
00960     xmlNode *map_root, *output_root;
00961 
00962     g_return_val_if_fail ((mapDoc && qsf_root && params), NULL);
00963     ENTER (" root=%s", qsf_root->name);
00964     /* prepare the intermediary document */
00965     qsfiter.ns = params->qsf_ns;
00966     output_doc = xmlNewDoc (BAD_CAST QSF_XML_VERSION);
00967     output_root = xmlNewNode (NULL, BAD_CAST QSF_ROOT_TAG);
00968     xmlDocSetRootElement (output_doc, output_root);
00969     xmlSetNs (output_root, params->qsf_ns);
00970     params->output_node = xmlNewChild (output_root, params->qsf_ns,
00971         BAD_CAST QSF_BOOK_TAG, NULL);
00972     xmlNewProp (params->output_node, BAD_CAST QSF_BOOK_COUNT,
00973         BAD_CAST "1");
00974     /* parse the incoming QSF */
00975     qsf_book_node_handler (qsf_root->children->next, params->qsf_ns,
00976         params);
00977     /* parse the map and calculate the values */
00978     map_root = xmlDocGetRootElement (mapDoc);
00979     params->foreach_limit = 0;
00980     qsfiter.ns = params->map_ns;
00981     /* sets qof_foreach iterator, defines and defaults. */
00982     qsf_node_foreach (map_root, qsf_map_top_node_handler, &qsfiter, params);
00983     /* identify the entities of iterator type. */
00984     qsfiter.ns = params->qsf_ns;
00985     qsf_node_foreach (qsf_root->children->next, iterator_cb, &qsfiter,
00986         params);
00987     PINFO (" counted %d records", params->foreach_limit);
00988     params->count = 0;
00989     for (cur_node = map_root->children; cur_node != NULL;
00990         cur_node = cur_node->next)
00991     {
00992         params->convert_node = cur_node;
00993         if (qsf_is_element (cur_node, params->map_ns, MAP_OBJECT_TAG))
00994         {
00995             gint i;
00996 
00997             params->lister = NULL;
00998             PINFO (" found an object tag. starting calculation");
00999             /* cur_node describes the target object */
01000             if (!qof_class_is_registered (BAD_CAST
01001                     xmlGetProp (cur_node, MAP_TYPE_ATTR)))
01002             {
01003                 continue;
01004             }
01005             qsf_add_object_tag (params, params->count);
01006             params->count++;
01007             qsfiter.ns = params->map_ns;
01008             PINFO (" params->foreach_limit=%d", params->foreach_limit);
01009             for (i = -1; i < params->foreach_limit; i++)
01010             {
01011                 qsf_node_foreach (cur_node, qsf_map_object_handler, 
01012                     &qsfiter, params);
01013                 params->qsf_object_list =
01014                     g_list_next (params->qsf_object_list);
01015                 params->count++;
01016             }
01017         }
01018     }
01019     params->file_type = OUR_QSF_OBJ;
01020     /* use for debugging */
01021     xmlSaveFormatFileEnc ("-", output_doc, "UTF-8", 1);
01022     LEAVE (" ");
01023     return output_doc;
01024 }

void qsf_object_node_handler ( xmlNodePtr  child,
xmlNsPtr  qsf_ns,
QsfParam params 
)

Despite the name, this function handles the QSF object book tag AND the object tags.

Used to parse object and map files.

Definition at line 384 of file qsf-xml.c.

00386 {
00387     struct QsfNodeIterate qsfiter;
00388     QsfObject *object_set;
00389     gchar *tail, *object_count_s;
00390     gint64 c;
00391 
00392     g_return_if_fail (child != NULL);
00393     g_return_if_fail (qsf_ns != NULL);
00394     params->qsf_ns = qsf_ns;
00395     if (qsf_is_element (child, qsf_ns, QSF_OBJECT_TAG))
00396     {
00397         params->qsf_parameter_hash = NULL;
00398         c = 0;
00399         object_set = g_new (QsfObject, 1);
00400         params->object_set = object_set;
00401         object_set->object_count = 0;
00402         object_set->parameters =
00403             g_hash_table_new (g_str_hash, g_str_equal);
00404         object_set->object_type = ((gchar *) xmlGetProp (child,
00405                 BAD_CAST QSF_OBJECT_TYPE));
00406         object_count_s = ((gchar *) xmlGetProp (child,
00407                 BAD_CAST QSF_OBJECT_COUNT));
00408         if (object_count_s)
00409         {
00410             c = (gint64) strtol (object_count_s, &tail, 0);
00411             object_set->object_count = (gint) c;
00412             g_free (object_count_s);
00413         }
00414         params->qsf_object_list =
00415             g_list_prepend (params->qsf_object_list, object_set);
00416         qsfiter.ns = qsf_ns;
00417         params->qsf_parameter_hash = object_set->parameters;
00418         qsf_node_foreach (child, qsf_parameter_handler, &qsfiter, params);
00419     }
00420 }

void qsf_object_validation_handler ( xmlNodePtr  child,
xmlNsPtr  ns,
QsfValidator valid 
)

Checks all incoming objects for QOF registration.

Sums all existing objects in the QSF and counts the number of those objects that are also registered with QOF in the host application.

Definition at line 133 of file qsf-xml.c.

00135 {
00136     xmlNodePtr cur_node;
00137     xmlChar *object_declaration;
00138     guint count;
00139     QsfStatus type;
00140     gboolean is_registered;
00141 
00142     count = 0;
00143     type = QSF_NO_OBJECT;
00144     is_registered = FALSE;
00145     for (cur_node = child->children; cur_node != NULL;
00146         cur_node = cur_node->next)
00147     {
00148         if (qsf_is_element (cur_node, ns, QSF_OBJECT_TAG))
00149         {
00150             object_declaration =
00151                 xmlGetProp (cur_node, BAD_CAST QSF_OBJECT_TYPE);
00152             is_registered = qof_class_is_registered (object_declaration);
00153             if (is_registered)
00154             {
00155                 type = QSF_REGISTERED_OBJECT;
00156             }
00157             else
00158             {
00159                 type = QSF_DEFINED_OBJECT;
00160             }
00161             xmlFree (object_declaration);
00162             count = g_hash_table_size (valid->object_table);
00163             g_hash_table_insert (valid->object_table, object_declaration,
00164                 GINT_TO_POINTER (type));
00165             /* if insert was successful - i.e. object is unique so far */
00166             if (g_hash_table_size (valid->object_table) > count)
00167             {
00168                 valid->valid_object_count++;
00169                 if (is_registered)
00170                 {
00171                     valid->qof_registered_count++;
00172                 }
00173             }
00174         }
00175     }
00176 }

gint qsf_strings_equal ( const xmlChar *  node_name,
gchar *  tag_name 
)

shorthand function

This may look repetitive but each one is used separately as well as in a block.

Definition at line 44 of file qsf-xml.c.

00045 {
00046     if (0 == qsf_compare_tag_strings (node_name, tag_name))
00047     {
00048         return 1;
00049     }
00050     return 0;
00051 }

void qsf_valid_foreach ( xmlNodePtr  parent,
QsfValidCB  cb,
struct QsfNodeIterate qsfiter,
QsfValidator valid 
)

Validate the children of the parent node.

Note:
Slightly different to qsf_node_foreach because the validation can be run without qsf_param being initialized.

Definition at line 101 of file qsf-xml.c.

00103 {
00104     xmlNodePtr cur_node;
00105 
00106     qsfiter->v_fcn = &cb;
00107     for (cur_node = parent->children; cur_node != NULL;
00108         cur_node = cur_node->next)
00109     {
00110         cb (cur_node, qsfiter->ns, valid);
00111     }
00112 }

KvpValue* string_to_kvp_value ( const gchar *  content,
KvpValueType  type 
)

Convert a string value into KvpValue.

Partner to kvp_value_to_string. Given the type of KvpValue required, attempts to convert the string into that type of value.

Parameters:
content A string representation of the value, ideally as output by kvp_value_to_string.
type KvpValueType of the intended KvpValue
Returns:
KvpValue* or NULL on failure.

Definition at line 1164 of file qsf-backend.c.

01165 {
01166     gchar *tail;
01167     gint64 cm_i64;
01168     gdouble cm_double;
01169     QofNumeric cm_numeric;
01170     GUID *cm_guid;
01171 
01172     switch (type)
01173     {
01174         case KVP_TYPE_GINT64:
01175         {
01176             errno = 0;
01177             cm_i64 = strtoll (content, &tail, 0);
01178             if (errno == 0)
01179             {
01180                 return kvp_value_new_gint64 (cm_i64);
01181             }
01182             break;
01183         }
01184         case KVP_TYPE_DOUBLE:
01185         {
01186             errno = 0;
01187             cm_double = strtod (content, &tail);
01188             if (errno == 0)
01189                 return kvp_value_new_double (cm_double);
01190             break;
01191         }
01192         case KVP_TYPE_NUMERIC:
01193         {
01194             qof_numeric_from_string (content, &cm_numeric);
01195             return kvp_value_new_numeric (cm_numeric);
01196             break;
01197         }
01198         case KVP_TYPE_STRING:
01199         {
01200             return kvp_value_new_string (content);
01201             break;
01202         }
01203         case KVP_TYPE_GUID:
01204         {
01205             cm_guid = g_new0 (GUID, 1);
01206             if (TRUE == string_to_guid (content, cm_guid))
01207                 return kvp_value_new_guid (cm_guid);
01208             break;
01209         }
01210         case KVP_TYPE_TIME :
01211         {
01212             QofDate *qd;
01213             QofTime *qt;
01214             KvpValue *retval;
01215 
01216             qd = qof_date_parse (content, QOF_DATE_FORMAT_UTC);
01217             if(qd)
01218             {
01219                 qt = qof_date_to_qtime (qd);
01220                 retval = kvp_value_new_time (qt);
01221                 qof_date_free (qd);
01222                 qof_time_free (qt);
01223                 return retval;
01224             }
01225             else
01226                 PERR (" failed to parse date");
01227         }
01228         case KVP_TYPE_BOOLEAN :
01229         {
01230             gboolean val;
01231             val = qof_util_bool_to_int (content);
01232             return kvp_value_new_boolean (val);
01233         }
01234         case KVP_TYPE_BINARY:
01235 //        return kvp_value_new_binary(value->value.binary.data,
01236 //                                  value->value.binary.datasize);
01237             break;
01238         case KVP_TYPE_GLIST:
01239 //          return kvp_value_new_glist(value->value.list);
01240             break;
01241         case KVP_TYPE_FRAME:
01242 //        return kvp_value_new_frame(value->value.frame);
01243             break;
01244     }
01245     return NULL;
01246 }


Generated on Mon Jul 13 05:15:15 2009 for QOF by  doxygen 1.5.9