mirror of
https://github.com/cookiengineer/audacity
synced 2025-05-06 14:52:34 +02:00
2315 lines
66 KiB
C
2315 lines
66 KiB
C
/* -*- Mode: c; c-basic-offset: 2 -*-
|
|
*
|
|
* rdf_model.c - RDF Graph (Model) interface
|
|
*
|
|
* Copyright (C) 2000-2008, David Beckett http://www.dajobe.org/
|
|
* Copyright (C) 2000-2005, University of Bristol, UK http://www.bristol.ac.uk/
|
|
*
|
|
* This package is Free Software and part of Redland http://librdf.org/
|
|
*
|
|
* It is licensed under the following three licenses as alternatives:
|
|
* 1. GNU Lesser General Public License (LGPL) V2.1 or any newer version
|
|
* 2. GNU General Public License (GPL) V2 or any newer version
|
|
* 3. Apache License, V2.0 or any newer version
|
|
*
|
|
* You may not use this file except in compliance with at least one of
|
|
* the above three licenses.
|
|
*
|
|
* See LICENSE.html or LICENSE.txt at the top of this package for the
|
|
* complete terms and further detail along with the license texts for
|
|
* the licenses in COPYING.LIB, COPYING and LICENSE-2.0.txt respectively.
|
|
*
|
|
*
|
|
*/
|
|
|
|
|
|
#ifdef HAVE_CONFIG_H
|
|
#include <rdf_config.h>
|
|
#endif
|
|
|
|
#ifdef WIN32
|
|
#include <win32_rdf_config.h>
|
|
#endif
|
|
|
|
#include <stdio.h>
|
|
#include <string.h>
|
|
#ifdef HAVE_STDLIB_H
|
|
#include <stdlib.h> /* for exit() */
|
|
#endif
|
|
|
|
#include <redland.h>
|
|
|
|
#ifndef STANDALONE
|
|
|
|
/**
|
|
* librdf_init_model:
|
|
* @world: redland world object
|
|
*
|
|
* INTERNAL - Initialise the model module.
|
|
*
|
|
**/
|
|
void
|
|
librdf_init_model(librdf_world *world)
|
|
{
|
|
/* Always have model storage - must always be the default model */
|
|
librdf_init_model_storage(world);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_finish_model:
|
|
* @world: redland world object
|
|
*
|
|
* INTERNAL - Terminate the model module.
|
|
*
|
|
**/
|
|
void
|
|
librdf_finish_model(librdf_world *world)
|
|
{
|
|
if(world->models) {
|
|
raptor_free_sequence(world->models);
|
|
world->models=NULL;
|
|
}
|
|
}
|
|
|
|
|
|
/*
|
|
* librdf_model_supports_contexts - helper function to determine if this model supports contexts
|
|
**/
|
|
static REDLAND_INLINE int
|
|
librdf_model_supports_contexts(librdf_model* model) {
|
|
return model->supports_contexts;
|
|
}
|
|
|
|
|
|
|
|
/* class methods */
|
|
|
|
static void
|
|
librdf_free_model_factory(librdf_model_factory* factory)
|
|
{
|
|
if(factory->name)
|
|
LIBRDF_FREE(librdf_model_factory, factory->name);
|
|
if(factory->label)
|
|
LIBRDF_FREE(librdf_model_factory, factory->label);
|
|
LIBRDF_FREE(librdf_model_factory, factory);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_register_factory:
|
|
* @world: redland world object
|
|
* @name: the model factory name
|
|
* @label: the storage factory label
|
|
* @factory: pointer to function to call to register the factory
|
|
*
|
|
* Register a model factory.
|
|
*
|
|
**/
|
|
void
|
|
librdf_model_register_factory(librdf_world *world,
|
|
const char *name, const char *label,
|
|
void (*factory) (librdf_model_factory*))
|
|
{
|
|
librdf_model_factory *model;
|
|
int i;
|
|
|
|
librdf_world_open(world);
|
|
|
|
#if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1
|
|
LIBRDF_DEBUG2("Received registration for model %s\n", name);
|
|
#endif
|
|
|
|
if(!world->models) {
|
|
world->models=raptor_new_sequence((raptor_sequence_free_handler *)librdf_free_model_factory, NULL);
|
|
if(!world->models)
|
|
goto oom;
|
|
}
|
|
|
|
for(i=0;
|
|
(model=(librdf_model_factory*)raptor_sequence_get_at(world->models, i));
|
|
i++) {
|
|
if(!strcmp(model->name, name)) {
|
|
librdf_log(world,
|
|
0, LIBRDF_LOG_ERROR, LIBRDF_FROM_MODEL, NULL,
|
|
"model %s already registered", model->name);
|
|
return;
|
|
}
|
|
}
|
|
|
|
model=(librdf_model_factory*)LIBRDF_CALLOC(librdf_model_factory, 1,
|
|
sizeof(librdf_model_factory));
|
|
if(!model)
|
|
goto oom;
|
|
|
|
model->name=(char*)LIBRDF_MALLOC(cstring, strlen(name)+1);
|
|
if(!model->name)
|
|
goto oom_tidy;
|
|
strcpy(model->name, name);
|
|
|
|
model->label=(char*)LIBRDF_MALLOC(cstring, strlen(label)+1);
|
|
if(!model->label)
|
|
goto oom_tidy;
|
|
strcpy(model->label, label);
|
|
|
|
if(raptor_sequence_push(world->models, model))
|
|
goto oom;
|
|
|
|
/* Call the model registration function on the new object */
|
|
(*factory)(model);
|
|
|
|
#if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1
|
|
LIBRDF_DEBUG3("%s has context size %d\n", name, model->context_length);
|
|
#endif
|
|
|
|
return;
|
|
|
|
oom_tidy:
|
|
librdf_free_model_factory(model);
|
|
oom:
|
|
LIBRDF_FATAL1(world, LIBRDF_FROM_MODEL, "Out of memory");
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_get_model_factory:
|
|
* @world: redland world object
|
|
* @name: the factory name or NULL for the default factory
|
|
*
|
|
* Get a model factory by name.
|
|
*
|
|
* Return value: the factory object or NULL if there is no such factory
|
|
**/
|
|
librdf_model_factory*
|
|
librdf_get_model_factory(librdf_world* world, const char *name)
|
|
{
|
|
librdf_model_factory *factory;
|
|
|
|
librdf_world_open(world);
|
|
|
|
/* return 1st model if no particular one wanted - why? */
|
|
if(!name) {
|
|
factory=(librdf_model_factory *)raptor_sequence_get_at(world->models, 0);
|
|
if(!factory) {
|
|
LIBRDF_DEBUG1("No (default) models registered\n");
|
|
return NULL;
|
|
}
|
|
} else {
|
|
int i;
|
|
|
|
for(i=0;
|
|
(factory=(librdf_model_factory*)raptor_sequence_get_at(world->models, i));
|
|
i++) {
|
|
if(!strcmp(factory->name, name))
|
|
break;
|
|
}
|
|
/* else FACTORY name not found */
|
|
if(!factory) {
|
|
LIBRDF_DEBUG2("No model with name %s found\n", name);
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
return factory;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_enumerate:
|
|
* @world: redland world object
|
|
* @counter: index into the list of models
|
|
* @name: pointer to store the name of the model (or NULL)
|
|
* @label: pointer to store syntax readable label (or NULL)
|
|
*
|
|
* Get information on models.
|
|
*
|
|
* Return value: non 0 on failure of if counter is out of range
|
|
**/
|
|
int
|
|
librdf_model_enumerate(librdf_world* world,
|
|
const unsigned int counter,
|
|
const char **name, const char **label)
|
|
{
|
|
librdf_model_factory *factory;
|
|
|
|
librdf_world_open(world);
|
|
|
|
factory=(librdf_model_factory*)raptor_sequence_get_at(world->models,
|
|
counter);
|
|
if(!factory)
|
|
return 1;
|
|
|
|
if(name)
|
|
*name=factory->name;
|
|
if(label)
|
|
*label=factory->label;
|
|
return 0;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_new_model:
|
|
* @world: redland world object
|
|
* @storage: #librdf_storage to use
|
|
* @options_string: options to initialise model
|
|
*
|
|
* Constructor - create a new storage #librdf_model object.
|
|
*
|
|
* The options are encoded as described in librdf_hash_from_string()
|
|
* and can be NULL if none are required.
|
|
*
|
|
* Return value: a new #librdf_model object or NULL on failure
|
|
*/
|
|
librdf_model*
|
|
librdf_new_model (librdf_world *world,
|
|
librdf_storage *storage, const char *options_string) {
|
|
librdf_hash* options_hash;
|
|
librdf_model *model;
|
|
|
|
librdf_world_open(world);
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(storage, librdf_storage, NULL);
|
|
|
|
if(!storage)
|
|
return NULL;
|
|
|
|
options_hash=librdf_new_hash(world, NULL);
|
|
if(!options_hash)
|
|
return NULL;
|
|
|
|
if(librdf_hash_from_string(options_hash, options_string)) {
|
|
librdf_free_hash(options_hash);
|
|
return NULL;
|
|
}
|
|
|
|
model=librdf_new_model_with_options(world, storage, options_hash);
|
|
librdf_free_hash(options_hash);
|
|
return model;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_new_model_with_options:
|
|
* @world: redland world object
|
|
* @storage: #librdf_storage storage to use
|
|
* @options: #librdf_hash of options to use
|
|
*
|
|
* Constructor - Create a new #librdf_model with storage.
|
|
*
|
|
* Options are presently not used.
|
|
*
|
|
* Return value: a new #librdf_model object or NULL on failure
|
|
**/
|
|
librdf_model*
|
|
librdf_new_model_with_options(librdf_world *world,
|
|
librdf_storage *storage, librdf_hash* options)
|
|
{
|
|
librdf_model *model;
|
|
librdf_uri *uri;
|
|
|
|
librdf_world_open(world);
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(storage, librdf_storage, NULL);
|
|
|
|
if(!storage)
|
|
return NULL;
|
|
|
|
model=(librdf_model*)LIBRDF_CALLOC(librdf_model, 1, sizeof(librdf_model));
|
|
if(!model)
|
|
return NULL;
|
|
|
|
model->world=world;
|
|
|
|
model->factory=librdf_get_model_factory(world, "storage");
|
|
if(!model->factory) {
|
|
LIBRDF_FREE(librdf_model, model);
|
|
return NULL;
|
|
}
|
|
|
|
model->context=LIBRDF_CALLOC(data, 1, model->factory->context_length);
|
|
|
|
if(!model->context || model->factory->create(model, storage, options)) {
|
|
if(model->context)
|
|
LIBRDF_FREE(data, model->context);
|
|
LIBRDF_FREE(librdf_model, model);
|
|
return NULL;
|
|
}
|
|
|
|
uri=librdf_new_uri(world, (const unsigned char*)LIBRDF_MODEL_FEATURE_CONTEXTS);
|
|
if(uri) {
|
|
librdf_node *node=librdf_model_get_feature(model, uri);
|
|
if(node) {
|
|
model->supports_contexts=atoi((const char*)librdf_node_get_literal_value(node));
|
|
librdf_free_node(node);
|
|
}
|
|
librdf_free_uri(uri);
|
|
}
|
|
|
|
model->usage=1;
|
|
|
|
return model;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_new_model_from_model:
|
|
* @model: the existing #librdf_model
|
|
*
|
|
* Copy constructor - create a new librdf_model from an existing one.
|
|
*
|
|
* Creates a new model as a copy of the existing model in the same
|
|
* storage context.
|
|
*
|
|
* Return value: a new #librdf_model or NULL on failure
|
|
**/
|
|
librdf_model*
|
|
librdf_new_model_from_model(librdf_model* model)
|
|
{
|
|
librdf_model *new_model;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
|
|
new_model=model->factory->clone(model);
|
|
if(new_model) {
|
|
new_model->supports_contexts=model->supports_contexts;
|
|
new_model->usage=1;
|
|
}
|
|
return new_model;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_free_model:
|
|
* @model: #librdf_model model to destroy
|
|
*
|
|
* Destructor - Destroy a #librdf_model object.
|
|
*
|
|
**/
|
|
void
|
|
librdf_free_model(librdf_model *model)
|
|
{
|
|
librdf_iterator* iterator;
|
|
librdf_model* m;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN(model, librdf_model);
|
|
|
|
if(--model->usage)
|
|
return;
|
|
|
|
if(model->sub_models) {
|
|
iterator=librdf_list_get_iterator(model->sub_models);
|
|
if(iterator) {
|
|
while(!librdf_iterator_end(iterator)) {
|
|
m=(librdf_model*)librdf_iterator_get_object(iterator);
|
|
if(m)
|
|
librdf_free_model(m);
|
|
librdf_iterator_next(iterator);
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
}
|
|
librdf_free_list(model->sub_models);
|
|
} else {
|
|
model->factory->destroy(model);
|
|
}
|
|
LIBRDF_FREE(data, model->context);
|
|
|
|
LIBRDF_FREE(librdf_model, model);
|
|
}
|
|
|
|
|
|
void
|
|
librdf_model_add_reference(librdf_model *model)
|
|
{
|
|
model->usage++;
|
|
}
|
|
|
|
void
|
|
librdf_model_remove_reference(librdf_model *model)
|
|
{
|
|
model->usage--;
|
|
}
|
|
|
|
|
|
/* methods */
|
|
|
|
/**
|
|
* librdf_model_size:
|
|
* @model: #librdf_model object
|
|
*
|
|
* Get the number of statements in the model.
|
|
*
|
|
* WARNING: Not all underlying stores can return the size of the graph
|
|
* In which case the return value will be negative.
|
|
*
|
|
* Return value: the number of statements or <0 if not possible
|
|
**/
|
|
int
|
|
librdf_model_size(librdf_model* model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, -1);
|
|
|
|
return model->factory->size(model);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add_statement:
|
|
* @model: model object
|
|
* @statement: statement object
|
|
*
|
|
* Add a statement to the model.
|
|
*
|
|
* The passed-in statement is copied when added to the model, not
|
|
* shared with the model. It must be a complete statement - all
|
|
* of subject, predicate, object parts must be present.
|
|
*
|
|
* Only statements that are legal RDF can be added: URI or blank subject,
|
|
* URI predicate and URI or blank or literal object (i.e. anything).
|
|
*
|
|
* If the statement already exists in the model, it is not added.
|
|
* Duplicate statements can be added when used with Redland Contexts
|
|
* such as with #librdf_model_context_add_statement
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add_statement(librdf_model* model, librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, 1);
|
|
|
|
if(!librdf_statement_is_complete(statement))
|
|
return 1;
|
|
|
|
return model->factory->add_statement(model, statement);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add_statements:
|
|
* @model: model object
|
|
* @statement_stream: stream of statements to use
|
|
*
|
|
* Add a stream of statements to the model.
|
|
*
|
|
* If any of the statements are illegal RDF statements they will
|
|
* be skipped and not added. See #librdf_model_add_statement for the detail.
|
|
*
|
|
* If any of the statements already exists in the store, they are not
|
|
* added unless Redland contexts are being used. See also
|
|
* #librdf_model_context_add_statements
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add_statements(librdf_model* model, librdf_stream* statement_stream)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement_stream, librdf_statement, 1);
|
|
|
|
return model->factory->add_statements(model, statement_stream);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add:
|
|
* @model: model object
|
|
* @subject: #librdf_node of subject
|
|
* @predicate: #librdf_node of predicate
|
|
* @object: #librdf_node of object (literal or resource)
|
|
*
|
|
* Create and add a new statement about a resource to the model.
|
|
*
|
|
* After this method, the #librdf_node objects become owned by the model.
|
|
* All of subject, predicate and object must be non-NULL.
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add(librdf_model* model, librdf_node* subject,
|
|
librdf_node* predicate, librdf_node* object)
|
|
{
|
|
librdf_statement *statement;
|
|
int result;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(subject, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(predicate, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(object, librdf_node, 1);
|
|
|
|
if(!subject ||
|
|
(!librdf_node_is_resource(subject) && !librdf_node_is_blank(subject)))
|
|
return 1;
|
|
|
|
if(!predicate || !librdf_node_is_resource(predicate))
|
|
return 1;
|
|
|
|
if(!object)
|
|
return 1;
|
|
|
|
statement=librdf_new_statement(model->world);
|
|
if(!statement)
|
|
return 1;
|
|
|
|
librdf_statement_set_subject(statement, subject);
|
|
librdf_statement_set_predicate(statement, predicate);
|
|
librdf_statement_set_object(statement, object);
|
|
|
|
result=librdf_model_add_statement(model, statement);
|
|
librdf_free_statement(statement);
|
|
|
|
return result;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add_typed_literal_statement:
|
|
* @model: model object
|
|
* @subject: #librdf_node of subject
|
|
* @predicate: #librdf_node of predicate
|
|
* @literal: string literal content
|
|
* @xml_language: language of literal
|
|
* @datatype_uri: datatype #librdf_uri
|
|
*
|
|
* Create and add a new statement about a typed literal to the model.
|
|
*
|
|
* After this method, the #librdf_node subject and predicate become
|
|
* owned by the model.
|
|
*
|
|
* The language can be set to NULL if not used.
|
|
* All of subject, predicate and literal must be non-NULL.
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add_typed_literal_statement(librdf_model* model,
|
|
librdf_node* subject,
|
|
librdf_node* predicate,
|
|
const unsigned char* literal,
|
|
const char *xml_language,
|
|
librdf_uri *datatype_uri)
|
|
{
|
|
librdf_node* object;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(subject, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(predicate, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(literal, string, 1);
|
|
|
|
if(!subject ||
|
|
(!librdf_node_is_resource(subject) && !librdf_node_is_blank(subject)))
|
|
return 1;
|
|
|
|
if(!predicate || !librdf_node_is_resource(predicate))
|
|
return 1;
|
|
|
|
if(!literal)
|
|
return 1;
|
|
|
|
object=librdf_new_node_from_typed_literal(model->world,
|
|
literal, xml_language,
|
|
datatype_uri);
|
|
if(!object)
|
|
return 1;
|
|
|
|
return librdf_model_add(model, subject, predicate, object);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add_string_literal_statement:
|
|
* @model: model object
|
|
* @subject: #librdf_node of subject
|
|
* @predicate: #librdf_node of predicate
|
|
* @literal: string literal conten
|
|
* @xml_language: language of literal
|
|
* @is_wf_xml: literal is XML
|
|
*
|
|
* Create and add a new statement about a literal to the model.
|
|
*
|
|
* The language can be set to NULL if not used.
|
|
* All of subject, predicate and literal must be non-NULL.
|
|
*
|
|
* 0.9.12: xml_space argument deleted
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add_string_literal_statement(librdf_model* model,
|
|
librdf_node* subject,
|
|
librdf_node* predicate,
|
|
const unsigned char* literal,
|
|
const char *xml_language,
|
|
int is_wf_xml)
|
|
{
|
|
librdf_node* object;
|
|
int result;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(subject, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(predicate, librdf_node, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(literal, string, 1);
|
|
|
|
if(!subject ||
|
|
(!librdf_node_is_resource(subject) && !librdf_node_is_blank(subject)))
|
|
return 1;
|
|
|
|
if(!predicate || !librdf_node_is_resource(predicate))
|
|
return 1;
|
|
|
|
if(!literal)
|
|
return 1;
|
|
|
|
object=librdf_new_node_from_literal(model->world,
|
|
literal, xml_language,
|
|
is_wf_xml);
|
|
if(!object)
|
|
return 1;
|
|
|
|
result=librdf_model_add(model, subject, predicate, object);
|
|
if(result)
|
|
librdf_free_node(object);
|
|
|
|
return result;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_remove_statement:
|
|
* @model: the model object
|
|
* @statement: the statement
|
|
*
|
|
* Remove a known statement from the model.
|
|
*
|
|
* It must be a complete statement - all of subject, predicate, object
|
|
* parts must be present and a legal RDF triple.
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_remove_statement(librdf_model* model, librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, 1);
|
|
|
|
if(!librdf_statement_is_complete(statement))
|
|
return 1;
|
|
|
|
return model->factory->remove_statement(model, statement);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_contains_statement:
|
|
* @model: the model object
|
|
* @statement: the statement
|
|
*
|
|
* Check for a statement in the model.
|
|
*
|
|
* It must be a complete statement - all of subject, predicate,
|
|
* object parts must be present and a legal RDF triple. Use
|
|
* librdf_model_find_statements to search for partial statement
|
|
* matches.
|
|
*
|
|
* WARNING: librdf_model_contains_statement may not work correctly
|
|
* with stores using contexts. In this case, a search using
|
|
* librdf_model_find_statements for a non-empty list will
|
|
* return the correct result.
|
|
*
|
|
* Return value: non 0 if the model contains the statement (>0 if the statement is illegal)
|
|
**/
|
|
int
|
|
librdf_model_contains_statement(librdf_model* model, librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 0);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, 0);
|
|
|
|
if(!librdf_statement_is_complete(statement))
|
|
return 1;
|
|
|
|
return model->factory->contains_statement(model, statement);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_as_stream:
|
|
* @model: the model object
|
|
*
|
|
* List the model contents as a stream of statements.
|
|
*
|
|
* Return value: a #librdf_stream or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_as_stream(librdf_model* model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
|
|
return model->factory->serialise(model);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_serialise:
|
|
* @model: the model object
|
|
*
|
|
* Serialise the entire model as a stream (DEPRECATED).
|
|
*
|
|
* DEPRECATED to reduce confusion with the librdf_serializer class.
|
|
* Please use librdf_model_as_stream.
|
|
*
|
|
* Return value: a #librdf_stream or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_serialise(librdf_model* model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
|
|
return model->factory->serialise(model);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_find_statements:
|
|
* @model: the model object
|
|
* @statement: the partial statement to match
|
|
*
|
|
* Find matching statements in the model.
|
|
*
|
|
* The partial statement is a statement where the subject, predicate
|
|
* and/or object can take the value NULL which indicates a match with
|
|
* any value in the model
|
|
*
|
|
* Return value: a #librdf_stream of statements (can be empty) or NULL
|
|
* on failure.
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_find_statements(librdf_model* model,
|
|
librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, NULL);
|
|
|
|
return model->factory->find_statements(model, statement);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_sources:
|
|
* @model: #librdf_model object
|
|
* @arc: #librdf_node arc
|
|
* @target: #librdf_node target
|
|
*
|
|
* Return the sources (subjects) of arc in an RDF graph given arc (predicate) and target (object).
|
|
*
|
|
* Searches the model for arcs matching the given arc and target
|
|
* and returns a list of the source #librdf_node objects as an iterator
|
|
*
|
|
* Return value: #librdf_iterator of #librdf_node objects (may be empty) or NULL on failure
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_sources(librdf_model *model,
|
|
librdf_node *arc, librdf_node *target)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(arc, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(target, librdf_node, NULL);
|
|
|
|
return model->factory->get_sources(model, arc, target);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_arcs:
|
|
* @model: #librdf_model object
|
|
* @source: #librdf_node source
|
|
* @target: #librdf_node target
|
|
*
|
|
* Return the arcs (predicates) of an arc in an RDF graph given source (subject) and target (object).
|
|
*
|
|
* Searches the model for arcs matching the given source and target
|
|
* and returns a list of the arc #librdf_node objects as an iterator
|
|
*
|
|
* Return value: #librdf_iterator of #librdf_node objects (may be empty) or NULL on failure
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_arcs(librdf_model *model,
|
|
librdf_node *source, librdf_node *target)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(source, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(target, librdf_node, NULL);
|
|
|
|
return model->factory->get_arcs(model, source, target);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_targets:
|
|
* @model: #librdf_model object
|
|
* @source: #librdf_node source
|
|
* @arc: #librdf_node arc
|
|
*
|
|
* Return the targets (objects) of an arc in an RDF graph given source (subject) and arc (predicate).
|
|
*
|
|
* Searches the model for targets matching the given source and arc
|
|
* and returns a list of the source #librdf_node objects as an iterator
|
|
*
|
|
* Return value: #librdf_iterator of #librdf_node objects (may be empty) or NULL on failure
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_targets(librdf_model *model,
|
|
librdf_node *source, librdf_node *arc)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(source, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(arc, librdf_node, NULL);
|
|
|
|
return model->factory->get_targets(model, source, arc);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_source:
|
|
* @model: #librdf_model object
|
|
* @arc: #librdf_node arc
|
|
* @target: #librdf_node target
|
|
*
|
|
* Return one source (subject) of arc in an RDF graph given arc (predicate) and target (object).
|
|
*
|
|
* Searches the model for arcs matching the given arc and target
|
|
* and returns one #librdf_node object
|
|
*
|
|
* Return value: a new #librdf_node object or NULL on failure
|
|
**/
|
|
librdf_node*
|
|
librdf_model_get_source(librdf_model *model,
|
|
librdf_node *arc, librdf_node *target)
|
|
{
|
|
librdf_iterator *iterator;
|
|
librdf_node *node;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(arc, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(target, librdf_node, NULL);
|
|
|
|
iterator=librdf_model_get_sources(model, arc, target);
|
|
if(!iterator)
|
|
return NULL;
|
|
|
|
node=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
if(node)
|
|
node=librdf_new_node_from_node(node);
|
|
librdf_free_iterator(iterator);
|
|
return node;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_arc:
|
|
* @model: #librdf_model object
|
|
* @source: #librdf_node source
|
|
* @target: #librdf_node target
|
|
*
|
|
* Return one arc (predicate) of an arc in an RDF graph given source (subject) and target (object).
|
|
*
|
|
* Searches the model for arcs matching the given source and target
|
|
* and returns one #librdf_node object
|
|
*
|
|
* Return value: a new #librdf_node object or NULL on failure
|
|
**/
|
|
librdf_node*
|
|
librdf_model_get_arc(librdf_model *model,
|
|
librdf_node *source, librdf_node *target)
|
|
{
|
|
librdf_iterator *iterator;
|
|
librdf_node *node;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(source, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(target, librdf_node, NULL);
|
|
|
|
iterator=librdf_model_get_arcs(model, source, target);
|
|
if(!iterator)
|
|
return NULL;
|
|
|
|
node=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
if(node)
|
|
node=librdf_new_node_from_node(node);
|
|
librdf_free_iterator(iterator);
|
|
return node;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_target:
|
|
* @model: #librdf_model object
|
|
* @source: #librdf_node source
|
|
* @arc: #librdf_node arc
|
|
*
|
|
* Return one target (object) of an arc in an RDF graph given source (subject) and arc (predicate).
|
|
*
|
|
* Searches the model for targets matching the given source and arc
|
|
* and returns one #librdf_node object
|
|
*
|
|
* Return value: a new #librdf_node object or NULL on failure
|
|
**/
|
|
librdf_node*
|
|
librdf_model_get_target(librdf_model *model,
|
|
librdf_node *source, librdf_node *arc)
|
|
{
|
|
librdf_iterator *iterator;
|
|
librdf_node *node;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(source, librdf_node, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(arc, librdf_node, NULL);
|
|
|
|
iterator=librdf_model_get_targets(model, source, arc);
|
|
if(!iterator)
|
|
return NULL;
|
|
|
|
node=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
if(node)
|
|
node=librdf_new_node_from_node(node);
|
|
librdf_free_iterator(iterator);
|
|
return node;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_add_submodel:
|
|
* @model: the model object
|
|
* @sub_model: the sub model to add
|
|
*
|
|
* Add a sub-model to the model.
|
|
*
|
|
* FIXME: Not tested
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_add_submodel(librdf_model* model, librdf_model* sub_model)
|
|
{
|
|
librdf_list *l=model->sub_models;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(sub_model, librdf_model, 1);
|
|
|
|
if(!l) {
|
|
l=librdf_new_list(model->world);
|
|
if(!l)
|
|
return 1;
|
|
model->sub_models=l;
|
|
}
|
|
|
|
if(librdf_list_add(l, sub_model))
|
|
return 1;
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
* librdf_model_remove_submodel:
|
|
* @model: the model object
|
|
* @sub_model: the sub model to remove
|
|
*
|
|
* Remove a sub-model from the model.
|
|
*
|
|
* FIXME: Not tested
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_remove_submodel(librdf_model* model, librdf_model* sub_model)
|
|
{
|
|
librdf_list *l=model->sub_models;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(sub_model, librdf_model, 1);
|
|
|
|
if(!l)
|
|
return 1;
|
|
if(!librdf_list_remove(l, sub_model))
|
|
return 1;
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
* librdf_model_get_arcs_in:
|
|
* @model: #librdf_model object
|
|
* @node: #librdf_node resource node
|
|
*
|
|
* Return the properties pointing to the given resource.
|
|
*
|
|
* Return value: #librdf_iterator of #librdf_node objects (may be empty) or NULL on failure
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_arcs_in(librdf_model *model, librdf_node *node)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(node, librdf_node, NULL);
|
|
|
|
return model->factory->get_arcs_in(model, node);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_arcs_out:
|
|
* @model: #librdf_model object
|
|
* @node: #librdf_node resource node
|
|
*
|
|
* Return the properties pointing from the given resource.
|
|
*
|
|
* Return value: #librdf_iterator of #librdf_node objects (may be empty) or NULL on failure
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_arcs_out(librdf_model *model, librdf_node *node)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(node, librdf_node, NULL);
|
|
|
|
return model->factory->get_arcs_out(model, node);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_has_arc_in:
|
|
* @model: #librdf_model object
|
|
* @node: #librdf_node resource node
|
|
* @property: #librdf_node property node
|
|
*
|
|
* Check if a node has a given property pointing to it.
|
|
*
|
|
* Return value: non 0 if arc property does point to the resource node
|
|
**/
|
|
int
|
|
librdf_model_has_arc_in(librdf_model *model, librdf_node *node,
|
|
librdf_node *property)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 0);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(node, librdf_node, 0);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(property, librdf_node, 0);
|
|
|
|
return model->factory->has_arc_in(model, node, property);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_has_arc_out:
|
|
* @model: #librdf_model object
|
|
* @node: #librdf_node resource node
|
|
* @property: #librdf_node property node
|
|
*
|
|
* Check if a node has a given property pointing from it.
|
|
*
|
|
* Return value: non 0 if arc property does point from the resource node
|
|
**/
|
|
int
|
|
librdf_model_has_arc_out(librdf_model *model, librdf_node *node,
|
|
librdf_node *property)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 0);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(node, librdf_node, 0);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(property, librdf_node, 0);
|
|
|
|
return model->factory->has_arc_out(model, node, property);
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
* librdf_model_print:
|
|
* @model: the model object
|
|
* @fh: the FILE stream to print to
|
|
*
|
|
* Print the model.
|
|
*
|
|
* This method is for debugging and the format of the output should
|
|
* not be relied on.
|
|
**/
|
|
void
|
|
librdf_model_print(librdf_model *model, FILE *fh)
|
|
{
|
|
librdf_stream* stream;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN(model, librdf_model);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN(fh, FILE*);
|
|
|
|
stream=librdf_model_as_stream(model);
|
|
if(!stream)
|
|
return;
|
|
fputs("[[\n", fh);
|
|
librdf_stream_print(stream, fh);
|
|
fputs("]]\n", fh);
|
|
librdf_free_stream(stream);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_context_add_statement:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
* @statement: #librdf_statement statement object
|
|
*
|
|
* Add a statement to a model with a context.
|
|
*
|
|
* It must be a complete statement - all
|
|
* of subject, predicate, object parts must be present.
|
|
*
|
|
* If @context is NULL, this is equivalent to librdf_model_add_statement
|
|
*
|
|
* Return value: Non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_context_add_statement(librdf_model* model,
|
|
librdf_node* context,
|
|
librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, 1);
|
|
|
|
if(!librdf_statement_is_complete(statement))
|
|
return 1;
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return 1;
|
|
}
|
|
|
|
return model->factory->context_add_statement(model, context, statement);
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
* librdf_model_context_add_statements:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
* @stream: #librdf_stream stream object
|
|
*
|
|
* Add statements to a model with a context.
|
|
*
|
|
* If @context is NULL, this is equivalent to librdf_model_add_statements
|
|
*
|
|
* Return value: Non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_context_add_statements(librdf_model* model,
|
|
librdf_node* context,
|
|
librdf_stream* stream)
|
|
{
|
|
int status=0;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(stream, librdf_stream, 1);
|
|
|
|
if(!stream)
|
|
return 1;
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return 1;
|
|
}
|
|
|
|
if(model->factory->context_add_statements)
|
|
return model->factory->context_add_statements(model, context, stream);
|
|
|
|
while(!librdf_stream_end(stream)) {
|
|
librdf_statement* statement=librdf_stream_get_object(stream);
|
|
if(!statement)
|
|
break;
|
|
status=librdf_model_context_add_statement(model, context, statement);
|
|
if(status)
|
|
break;
|
|
librdf_stream_next(stream);
|
|
}
|
|
|
|
return status;
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
* librdf_model_context_remove_statement:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
* @statement: #librdf_statement statement
|
|
*
|
|
* Remove a statement from a model in a context.
|
|
*
|
|
* It must be a complete statement - all of subject, predicate, object
|
|
* parts must be present.
|
|
*
|
|
* If @context is NULL, this is equivalent to librdf_model_remove_statement
|
|
*
|
|
* Return value: Non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_context_remove_statement(librdf_model* model,
|
|
librdf_node* context,
|
|
librdf_statement* statement)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, 1);
|
|
|
|
if(!librdf_statement_is_complete(statement))
|
|
return 1;
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return 1;
|
|
}
|
|
|
|
return model->factory->context_remove_statement(model, context, statement);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_context_remove_statements:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
*
|
|
* Remove statements from a model with the given context.
|
|
*
|
|
* Return value: Non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_context_remove_statements(librdf_model* model,
|
|
librdf_node* context)
|
|
{
|
|
librdf_stream *stream;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(context, librdf_node, 1);
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return 1;
|
|
}
|
|
|
|
if(model->factory->context_remove_statements)
|
|
return model->factory->context_remove_statements(model, context);
|
|
|
|
stream=librdf_model_context_as_stream(model, context);
|
|
if(!stream)
|
|
return 1;
|
|
|
|
while(!librdf_stream_end(stream)) {
|
|
librdf_statement *statement=librdf_stream_get_object(stream);
|
|
if(!statement)
|
|
break;
|
|
librdf_model_context_remove_statement(model, context, statement);
|
|
librdf_stream_next(stream);
|
|
}
|
|
librdf_free_stream(stream);
|
|
return 0;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_context_as_stream:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
*
|
|
* List all statements in a model context.
|
|
*
|
|
* Return value: #librdf_stream of statements or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_context_as_stream(librdf_model* model, librdf_node* context)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(context, librdf_node, NULL);
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return NULL;
|
|
}
|
|
|
|
return model->factory->context_serialize(model, context);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_context_serialize:
|
|
* @model: #librdf_model object
|
|
* @context: #librdf_node context
|
|
*
|
|
* List all statements in a model context.
|
|
*
|
|
* DEPRECATED to reduce confusion with the librdf_serializer class.
|
|
* Please use librdf_model_context_as_stream.
|
|
*
|
|
* Return value: #librdf_stream of statements or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_context_serialize(librdf_model* model, librdf_node* context)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(context, librdf_node, NULL);
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return NULL;
|
|
}
|
|
|
|
return model->factory->context_serialize(model, context);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_query_execute:
|
|
* @model: #librdf_model object
|
|
* @query: #librdf_query object
|
|
*
|
|
* Execute a query against the model.
|
|
*
|
|
* Run the given query against the model and return a #librdf_stream of
|
|
* matching #librdf_statement objects
|
|
*
|
|
* Return value: #librdf_query_results or NULL on failure
|
|
**/
|
|
librdf_query_results*
|
|
librdf_model_query_execute(librdf_model* model, librdf_query* query)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(query, librdf_query, NULL);
|
|
|
|
return model->factory->query_execute(model, query);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_sync:
|
|
* @model: #librdf_model object
|
|
*
|
|
* Synchronise the model to the model implementation.
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
int
|
|
librdf_model_sync(librdf_model* model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, 1);
|
|
|
|
if(model->factory->sync)
|
|
return model->factory->sync(model);
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_storage:
|
|
* @model: #librdf_model object
|
|
*
|
|
* Return the storage of this model.
|
|
*
|
|
* Note: this can only return one storage, so model implementations
|
|
* that have multiple #librdf_storage internally may chose not to
|
|
* implement this.
|
|
*
|
|
* Return value: #librdf_storage or NULL if this has no store
|
|
**/
|
|
librdf_storage*
|
|
librdf_model_get_storage(librdf_model *model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
|
|
if(model->factory->get_storage)
|
|
return model->factory->get_storage(model);
|
|
else
|
|
return NULL;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_find_statements_in_context:
|
|
* @model: #librdf_model object
|
|
* @statement: #librdf_statement partial statement to find
|
|
* @context_node: context #librdf_node (or NULL)
|
|
*
|
|
* Search the model for matching statements in a given context.
|
|
*
|
|
* Searches the model for a (partial) statement as described in
|
|
* librdf_statement_match() in the given context and returns a
|
|
* #librdf_stream of matching #librdf_statement objects. If
|
|
* context is NULL, this is equivalent to librdf_model_find_statements.
|
|
*
|
|
* Return value: #librdf_stream of matching statements (may be empty) or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_find_statements_in_context(librdf_model* model, librdf_statement* statement, librdf_node* context_node)
|
|
{
|
|
librdf_stream *stream;
|
|
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(statement, librdf_statement, NULL);
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return NULL;
|
|
}
|
|
|
|
if(model->factory->find_statements_in_context)
|
|
return model->factory->find_statements_in_context(model, statement, context_node);
|
|
|
|
statement=librdf_new_statement_from_statement(statement);
|
|
if(!statement)
|
|
return NULL;
|
|
|
|
stream=librdf_model_context_as_stream(model, context_node);
|
|
if(!stream) {
|
|
librdf_free_statement(statement);
|
|
return librdf_new_empty_stream(model->world);
|
|
}
|
|
|
|
librdf_stream_add_map(stream,
|
|
&librdf_stream_statement_find_map,
|
|
(librdf_stream_map_free_context_handler)&librdf_free_statement, (void*)statement);
|
|
|
|
return stream;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_contexts:
|
|
* @model: #librdf_model object
|
|
*
|
|
* Return the list of contexts in the graph.
|
|
*
|
|
* Returns an iterator of #librdf_node context nodes for each
|
|
* context in the graph.
|
|
*
|
|
* Return value: #librdf_iterator of context nodes or NULL on failure or if contexts are not supported
|
|
**/
|
|
librdf_iterator*
|
|
librdf_model_get_contexts(librdf_model* model)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
|
|
if(!librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return NULL;
|
|
}
|
|
|
|
if(model->factory->get_contexts)
|
|
return model->factory->get_contexts(model);
|
|
else
|
|
return NULL;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_get_feature:
|
|
* @model: #librdf_model object
|
|
* @feature: #librdf_uri feature property
|
|
*
|
|
* Get the value of a graph feature .
|
|
*
|
|
* Return value: new #librdf_node feature value or NULL if no such feature
|
|
* exists or the value is empty.
|
|
**/
|
|
librdf_node*
|
|
librdf_model_get_feature(librdf_model* model, librdf_uri* feature)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, NULL);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(feature, librdf_uri, NULL);
|
|
|
|
if(model->factory->get_feature)
|
|
return model->factory->get_feature(model, feature);
|
|
return NULL;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_set_feature:
|
|
* @model: #librdf_model object
|
|
* @feature: #librdf_uri feature property
|
|
* @value: #librdf_node feature property value
|
|
*
|
|
* Set the value of a graph feature.
|
|
*
|
|
* Return value: non 0 on failure (negative if no such feature)
|
|
**/
|
|
int
|
|
librdf_model_set_feature(librdf_model* model, librdf_uri* feature,
|
|
librdf_node* value)
|
|
{
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(model, librdf_model, -1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(feature, librdf_uri, -1);
|
|
LIBRDF_ASSERT_OBJECT_POINTER_RETURN_VALUE(value, librdf_node, -1);
|
|
|
|
if(model->factory->set_feature)
|
|
return model->factory->set_feature(model, feature, value);
|
|
return -1;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_find_statements_with_options:
|
|
* @model: #librdf_model object
|
|
* @statement: #librdf_statement partial statement to find
|
|
* @context_node: #librdf_node context node or NULL.
|
|
* @options: #librdf_hash of matching options or NULL
|
|
*
|
|
* Search the model for matching statements with match options.
|
|
*
|
|
* Searches the model for a (partial) statement as described in
|
|
* librdf_statement_match() and returns a #librdf_stream of
|
|
* matching #librdf_statement objects.
|
|
*
|
|
* If options is given then the match is made according to
|
|
* the given options. If options is NULL, this is equivalent
|
|
* to librdf_model_find_statements_in_context.
|
|
*
|
|
* Return value: #librdf_stream of matching statements (may be empty) or NULL on failure
|
|
**/
|
|
librdf_stream*
|
|
librdf_model_find_statements_with_options(librdf_model* model,
|
|
librdf_statement* statement,
|
|
librdf_node* context_node,
|
|
librdf_hash* options)
|
|
{
|
|
if(context_node && !librdf_model_supports_contexts(model)) {
|
|
librdf_log(model->world, 0, LIBRDF_LOG_WARN, LIBRDF_FROM_MODEL, NULL,
|
|
"Model does not support contexts");
|
|
return NULL;
|
|
}
|
|
|
|
if(model->factory->find_statements_with_options)
|
|
return model->factory->find_statements_with_options(model, statement, context_node, options);
|
|
else
|
|
return librdf_model_find_statements_in_context(model, statement, context_node);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_load:
|
|
* @model: #librdf_model object
|
|
* @uri: the URI to read the content
|
|
* @name: the name of the parser (or NULL)
|
|
* @mime_type: the MIME type of the syntax (NULL if not used)
|
|
* @type_uri: URI identifying the syntax (NULL if not used)
|
|
*
|
|
* Load content from a URI into the model.
|
|
*
|
|
* If the name field is NULL, the library will try to guess
|
|
* the parser to use from the uri, mime_type and type_uri fields.
|
|
* This is done via the raptor_guess_parser_name function.
|
|
*
|
|
* Return value: non 0 on failure
|
|
**/
|
|
int
|
|
librdf_model_load(librdf_model* model, librdf_uri *uri,
|
|
const char *name, const char *mime_type,
|
|
librdf_uri *type_uri)
|
|
{
|
|
int rc=0;
|
|
librdf_parser* parser;
|
|
|
|
if(name && !*name)
|
|
name=NULL;
|
|
if(mime_type && !*mime_type)
|
|
mime_type=NULL;
|
|
|
|
if(!name)
|
|
name=raptor_guess_parser_name((raptor_uri*)type_uri, mime_type,
|
|
NULL, 0, librdf_uri_as_string(uri));
|
|
parser=librdf_new_parser(model->world, name, NULL, NULL);
|
|
if(!parser)
|
|
return 1;
|
|
|
|
rc=librdf_parser_parse_into_model(parser, uri, NULL, model);
|
|
librdf_free_parser(parser);
|
|
return rc;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_to_counted_string:
|
|
* @model: #librdf_model object
|
|
* @uri: base URI to use in serializing (or NULL if not used)
|
|
* @name: the name of the serializer (or NULL for default)
|
|
* @mime_type: the MIME type of the syntax (NULL if not used)
|
|
* @type_uri: URI identifying the syntax (NULL if not used)
|
|
* @string_length_p: pointer to location to store string length (or NULL)
|
|
*
|
|
* Write serialized model to a string.
|
|
*
|
|
* If the name field is NULL, the default serializer will be used.
|
|
*
|
|
* Note: the returned string must be freed by the caller.
|
|
*
|
|
* Return value: new string or NULL on failure
|
|
**/
|
|
unsigned char*
|
|
librdf_model_to_counted_string(librdf_model* model, librdf_uri *uri,
|
|
const char *name, const char *mime_type,
|
|
librdf_uri *type_uri, size_t* string_length_p)
|
|
{
|
|
unsigned char *string=NULL;
|
|
librdf_serializer* serializer;
|
|
|
|
if(name && !*name)
|
|
name=NULL;
|
|
if(mime_type && !*mime_type)
|
|
mime_type=NULL;
|
|
|
|
serializer=librdf_new_serializer(model->world, name, mime_type, type_uri);
|
|
if(!serializer)
|
|
return NULL;
|
|
|
|
string=librdf_serializer_serialize_model_to_counted_string(serializer,
|
|
uri, model,
|
|
string_length_p);
|
|
librdf_free_serializer(serializer);
|
|
return string;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_to_string:
|
|
* @model: #librdf_model object
|
|
* @uri: base URI to use in serializing (or NULL if not used)
|
|
* @name: the name of the serializer (or NULL for default)
|
|
* @mime_type: the MIME type of the syntax (NULL if not used)
|
|
* @type_uri: URI identifying the syntax (NULL if not used)
|
|
*
|
|
* Write serialized model to a string.
|
|
*
|
|
* If the name field is NULL, the default serializer will be used.
|
|
*
|
|
* Note: the returned string must be freed by the caller.
|
|
*
|
|
* Return value: new string or NULL on failure
|
|
**/
|
|
unsigned char*
|
|
librdf_model_to_string(librdf_model* model, librdf_uri *uri,
|
|
const char *name, const char *mime_type,
|
|
librdf_uri *type_uri) {
|
|
return librdf_model_to_counted_string(model, uri,
|
|
name, mime_type, type_uri,
|
|
NULL);
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_contains_context:
|
|
* @model: the model object
|
|
* @context: the contest
|
|
*
|
|
* Check for a context in the model.
|
|
*
|
|
* Return value: non 0 if the model contains the context node
|
|
**/
|
|
int
|
|
librdf_model_contains_context(librdf_model* model, librdf_node* context) {
|
|
librdf_stream* stream;
|
|
int result;
|
|
|
|
stream=librdf_model_context_as_stream(model, context);
|
|
if(!stream)
|
|
return 0;
|
|
|
|
result=!librdf_stream_end(stream);
|
|
librdf_free_stream(stream);
|
|
|
|
return result;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_transaction_start:
|
|
* @model: the model object
|
|
*
|
|
* Start a transaction
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
int
|
|
librdf_model_transaction_start(librdf_model* model)
|
|
{
|
|
if(model->factory->transaction_start)
|
|
return model->factory->transaction_start(model);
|
|
else
|
|
return 1;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_transaction_start_with_handle:
|
|
* @model: the model object
|
|
* @handle: the transaction object
|
|
*
|
|
* Start a transaction using an existing external transaction object.
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
int
|
|
librdf_model_transaction_start_with_handle(librdf_model* model, void* handle)
|
|
{
|
|
if(model->factory->transaction_start_with_handle)
|
|
return model->factory->transaction_start_with_handle(model, handle);
|
|
else
|
|
return 1;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_transaction_commit:
|
|
* @model: the model object
|
|
*
|
|
* Commit a transaction.
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
int
|
|
librdf_model_transaction_commit(librdf_model* model)
|
|
{
|
|
if(model->factory->transaction_commit)
|
|
return model->factory->transaction_commit(model);
|
|
else
|
|
return 1;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_transaction_rollback:
|
|
* @model: the model object
|
|
*
|
|
* Rollback a transaction.
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
int
|
|
librdf_model_transaction_rollback(librdf_model* model)
|
|
{
|
|
if(model->factory->transaction_rollback)
|
|
return model->factory->transaction_rollback(model);
|
|
else
|
|
return 1;
|
|
}
|
|
|
|
|
|
/**
|
|
* librdf_model_transaction_get_handle:
|
|
* @model: the model object
|
|
*
|
|
* Get the current transaction handle.
|
|
*
|
|
* Return value: non-0 on failure
|
|
**/
|
|
void*
|
|
librdf_model_transaction_get_handle(librdf_model* model)
|
|
{
|
|
if(model->factory->transaction_get_handle)
|
|
return model->factory->transaction_get_handle(model);
|
|
else
|
|
return NULL;
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
/* TEST CODE */
|
|
|
|
|
|
#ifdef STANDALONE
|
|
|
|
/* one more prototype */
|
|
int main(int argc, char *argv[]);
|
|
|
|
#define EX1_CONTENT \
|
|
"<?xml version=\"1.0\"?>\n" \
|
|
"<rdf:RDF xmlns:rdf=\"http://www.w3.org/1999/02/22-rdf-syntax-ns#\"\n" \
|
|
" xmlns:dc=\"http://purl.org/dc/elements/1.1/\">\n" \
|
|
" <rdf:Description rdf:about=\"http://purl.org/net/dajobe/\">\n" \
|
|
" <dc:title>Dave Beckett's Home Page</dc:title>\n" \
|
|
" <dc:creator>Dave Beckett</dc:creator>\n" \
|
|
" <dc:description>The generic home page of Dave Beckett.</dc:description>\n" \
|
|
" </rdf:Description>\n" \
|
|
"</rdf:RDF>"
|
|
|
|
#define EX2_CONTENT \
|
|
"<?xml version=\"1.0\"?>\n" \
|
|
"<rdf:RDF xmlns:rdf=\"http://www.w3.org/1999/02/22-rdf-syntax-ns#\"\n" \
|
|
" xmlns:dc=\"http://purl.org/dc/elements/1.1/\">\n" \
|
|
" <rdf:Description rdf:about=\"http://purl.org/net/dajobe/\">\n" \
|
|
" <dc:title>Dave Beckett's Home Page</dc:title>\n" \
|
|
" <dc:creator>Dave Beckett</dc:creator>\n" \
|
|
" <dc:description>I do development-based research on RDF, metadata and web searching.</dc:description>\n" \
|
|
" <dc:rights>Copyright © 2002 Dave Beckett</dc:rights>\n" \
|
|
" </rdf:Description>\n" \
|
|
"</rdf:RDF>"
|
|
|
|
int test_model_cloning(char const *program, librdf_world *);
|
|
|
|
int
|
|
main(int argc, char *argv[])
|
|
{
|
|
librdf_storage* storage;
|
|
librdf_model* model;
|
|
librdf_statement *statement;
|
|
librdf_parser* parser;
|
|
librdf_stream* stream;
|
|
const char *parser_name="rdfxml";
|
|
#define URI_STRING_COUNT 2
|
|
const unsigned char *file_uri_strings[URI_STRING_COUNT]={(const unsigned char*)"http://example.org/test1.rdf", (const unsigned char*)"http://example.org/test2.rdf"};
|
|
const unsigned char *file_content[URI_STRING_COUNT]={(const unsigned char*)EX1_CONTENT, (const unsigned char*)EX2_CONTENT};
|
|
librdf_uri* uris[URI_STRING_COUNT];
|
|
librdf_node* nodes[URI_STRING_COUNT];
|
|
int i;
|
|
const char *program=librdf_basename((const char*)argv[0]);
|
|
/* initialise dependent modules - all of them! */
|
|
librdf_world *world=librdf_new_world();
|
|
librdf_iterator *iterator, *second_iterator;
|
|
librdf_node *n1, *n2;
|
|
int count;
|
|
int expected_count;
|
|
#define EXPECTED_BAD_STRING_LENGTH 317
|
|
librdf_uri* base_uri;
|
|
unsigned char *string;
|
|
size_t string_length=0;
|
|
int remove_count=0;
|
|
int status=0;
|
|
const char* storage_type;
|
|
const char* storage_name;
|
|
const char* storage_options;
|
|
|
|
librdf_world_open(world);
|
|
|
|
/* Test model cloning first */
|
|
if(test_model_cloning(program, world))
|
|
return(1);
|
|
|
|
/* Get storage configuration */
|
|
storage_type=getenv("REDLAND_TEST_STORAGE_TYPE");
|
|
storage_name=getenv("REDLAND_TEST_STORAGE_NAME");
|
|
storage_options=getenv("REDLAND_TEST_STORAGE_OPTIONS");
|
|
if(!(storage_type && storage_name && storage_options)) {
|
|
/* default is to test in memory */
|
|
storage_type="memory";
|
|
storage_name=NULL;
|
|
storage_options="write='yes',new='yes',contexts='yes'";
|
|
}
|
|
|
|
fprintf(stderr, "%s: Creating new %s storage\n", program, storage_type);
|
|
storage=librdf_new_storage(world, storage_type, storage_name, storage_options);
|
|
if(!storage) {
|
|
fprintf(stderr, "%s: Failed to create new %s storage name %s with options %s\n", program, storage_type, storage_name, storage_options);
|
|
return(1);
|
|
}
|
|
|
|
fprintf(stderr, "%s: Creating model\n", program);
|
|
model=librdf_new_model(world, storage, NULL);
|
|
if(!model) {
|
|
fprintf(stderr, "%s: Failed to create new model\n", program);
|
|
return(1);
|
|
}
|
|
|
|
statement=librdf_new_statement(world);
|
|
/* after this, nodes become owned by model */
|
|
librdf_statement_set_subject(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://www.dajobe.org/"));
|
|
librdf_statement_set_predicate(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator"));
|
|
|
|
if(!librdf_model_add_statement(model, statement)) {
|
|
fprintf(stderr, "%s: librdf_model_add_statement unexpectedly succeeded adding a partial statement\n", program);
|
|
return(1);
|
|
}
|
|
|
|
librdf_statement_set_object(statement, librdf_new_node_from_literal(world, (const unsigned char*)"Dave Beckett", NULL, 0));
|
|
|
|
librdf_model_add_statement(model, statement);
|
|
librdf_free_statement(statement);
|
|
|
|
/* make it illegal */
|
|
statement=librdf_new_statement(world);
|
|
librdf_statement_set_subject(statement, librdf_new_node_from_literal(world, (const unsigned char*)"Bad Subject", NULL, 0));
|
|
librdf_statement_set_predicate(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://example.org/pred"));
|
|
librdf_statement_set_object(statement, librdf_new_node_from_literal(world, (const unsigned char*)"Good Object", NULL, 0));
|
|
|
|
if(!librdf_model_add_statement(model, statement)) {
|
|
fprintf(stderr, "%s: librdf_model_add_statement unexpectedly succeeded adding an illegal triple\n", program);
|
|
return(1);
|
|
}
|
|
librdf_free_statement(statement);
|
|
|
|
fprintf(stderr, "%s: Printing model\n", program);
|
|
librdf_model_print(model, stderr);
|
|
|
|
parser=librdf_new_parser(world, parser_name, NULL, NULL);
|
|
if(!parser) {
|
|
fprintf(stderr, "%s: Failed to create new parser type %s\n", program,
|
|
parser_name);
|
|
exit(1);
|
|
}
|
|
|
|
for (i=0; i<URI_STRING_COUNT; i++) {
|
|
uris[i]=librdf_new_uri(world, file_uri_strings[i]);
|
|
nodes[i]=librdf_new_node_from_uri_string(world, file_uri_strings[i]);
|
|
|
|
fprintf(stderr, "%s: Adding content from %s into statement context\n", program,
|
|
librdf_uri_as_string(uris[i]));
|
|
if(!(stream=librdf_parser_parse_string_as_stream(parser,
|
|
file_content[i], uris[i]))) {
|
|
fprintf(stderr, "%s: Failed to parse RDF from %s as stream\n", program,
|
|
librdf_uri_as_string(uris[i]));
|
|
exit(1);
|
|
}
|
|
librdf_model_context_add_statements(model, nodes[i], stream);
|
|
librdf_free_stream(stream);
|
|
|
|
fprintf(stderr, "%s: Printing model\n", program);
|
|
librdf_model_print(model, stderr);
|
|
}
|
|
|
|
|
|
fprintf(stderr, "%s: Freeing Parser\n", program);
|
|
librdf_free_parser(parser);
|
|
|
|
|
|
/* sync - probably a NOP */
|
|
librdf_model_sync(model);
|
|
|
|
|
|
/* sources */
|
|
n1=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator");
|
|
n2=librdf_new_node_from_literal(world, (const unsigned char*)"Dave Beckett", NULL, 0);
|
|
|
|
fprintf(stderr, "%s: Looking for sources of arc=", program);
|
|
librdf_node_print(n1, stderr);
|
|
fputs(" target=", stderr);
|
|
librdf_node_print(n2, stderr);
|
|
fputs("\n", stderr);
|
|
|
|
iterator=librdf_model_get_sources(model, n1, n2);
|
|
if(!iterator) {
|
|
fprintf(stderr, "%s: librdf_model_get_sources failed\n", program);
|
|
status=1;
|
|
}
|
|
|
|
expected_count=3;
|
|
for(count=0; !librdf_iterator_end(iterator); librdf_iterator_next(iterator), count++) {
|
|
librdf_node* n=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
fputs(" ", stderr);
|
|
librdf_node_print(n, stderr);
|
|
fputs("\n", stderr);
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
if(count != expected_count) {
|
|
fprintf(stderr, "%s: librdf_model_get_sources returned %d nodes, expected %d\n", program, count, expected_count);
|
|
status=1;
|
|
}
|
|
librdf_free_node(n1);
|
|
librdf_free_node(n2);
|
|
|
|
|
|
/* targets */
|
|
n1=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/net/dajobe/");
|
|
n2=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/description");
|
|
|
|
fprintf(stderr, "%s: Looking for targets of source=", program);
|
|
librdf_node_print(n1, stderr);
|
|
fputs(" arc=", stderr);
|
|
librdf_node_print(n2, stderr);
|
|
fputs("\n", stderr);
|
|
|
|
iterator=librdf_model_get_targets(model, n1, n2);
|
|
if(!iterator) {
|
|
fprintf(stderr, "%s: librdf_model_get_targets failed\n", program);
|
|
status=1;
|
|
}
|
|
|
|
expected_count=2;
|
|
for(count=0; !librdf_iterator_end(iterator); librdf_iterator_next(iterator), count++) {
|
|
librdf_node* n=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
fputs(" ", stderr);
|
|
librdf_node_print(n, stderr);
|
|
fputs("\n", stderr);
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
if(count != expected_count) {
|
|
fprintf(stderr, "%s: librdf_model_get_targets returned %d nodes, expected %d\n", program, count, expected_count);
|
|
status=1;
|
|
}
|
|
librdf_free_node(n1);
|
|
librdf_free_node(n2);
|
|
|
|
|
|
/* arcs */
|
|
n1=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/net/dajobe/");
|
|
n2=librdf_new_node_from_literal(world, (const unsigned char*)"Dave Beckett", NULL, 0);
|
|
|
|
fprintf(stderr, "%s: Looking for arcs of source=", program);
|
|
librdf_node_print(n1, stderr);
|
|
fputs(" target=", stderr);
|
|
librdf_node_print(n2, stderr);
|
|
fputs("\n", stderr);
|
|
|
|
iterator=librdf_model_get_arcs(model, n1, n2);
|
|
if(!iterator) {
|
|
fprintf(stderr, "%s: librdf_model_get_arcs failed\n", program);
|
|
status=1;
|
|
}
|
|
|
|
expected_count=2;
|
|
for(count=0; !librdf_iterator_end(iterator); librdf_iterator_next(iterator), count++) {
|
|
librdf_node* n=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
fputs(" ", stderr);
|
|
librdf_node_print(n, stderr);
|
|
fputs("\n", stderr);
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
if(count != expected_count) {
|
|
fprintf(stderr, "%s: librdf_model_get_arcs returned %d nodes, expected %d\n", program, count, expected_count);
|
|
status=1;
|
|
}
|
|
librdf_free_node(n1);
|
|
librdf_free_node(n2);
|
|
|
|
|
|
fprintf(stderr, "%s: Listing contexts\n", program);
|
|
iterator=librdf_model_get_contexts(model);
|
|
if(!iterator) {
|
|
fprintf(stderr, "%s: librdf_model_get_contexts failed (optional method)\n", program);
|
|
} else {
|
|
expected_count=2;
|
|
for(count=0; !librdf_iterator_end(iterator); librdf_iterator_next(iterator), count++) {
|
|
librdf_node* n=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
fputs(" ", stderr);
|
|
librdf_node_print(n, stderr);
|
|
fputs("\n", stderr);
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
if(count != expected_count) {
|
|
fprintf(stderr, "%s: librdf_model_get_contexts returned %d context nodes, expected %d\n", program, count, expected_count);
|
|
status=1;
|
|
}
|
|
}
|
|
|
|
#define TEST_CONTEXT_URI_INDEX 0
|
|
|
|
if(librdf_model_contains_context(model, nodes[TEST_CONTEXT_URI_INDEX])) {
|
|
fprintf(stderr, "%s: Model contains context %s\n", program,
|
|
librdf_uri_as_string(uris[TEST_CONTEXT_URI_INDEX]));
|
|
} else {
|
|
fprintf(stderr, "%s: librdf_model_contains_contexts failed to find context URI %s\n",
|
|
program, librdf_uri_as_string(uris[TEST_CONTEXT_URI_INDEX]));
|
|
status=1;
|
|
}
|
|
|
|
|
|
for (i=0; i<URI_STRING_COUNT; i++) {
|
|
fprintf(stderr, "%s: Removing statement context %s\n", program,
|
|
librdf_uri_as_string(uris[i]));
|
|
librdf_model_context_remove_statements(model, nodes[i]);
|
|
|
|
fprintf(stderr, "%s: Printing model\n", program);
|
|
librdf_model_print(model, stderr);
|
|
}
|
|
|
|
fprintf(stderr, "%s: Serializing model\n", program);
|
|
base_uri=librdf_new_uri(world, (const unsigned char*)"http://example.org/base#");
|
|
string=librdf_model_to_counted_string(model, base_uri,
|
|
"rdfxml",
|
|
NULL, NULL,
|
|
&string_length);
|
|
if(string_length != EXPECTED_BAD_STRING_LENGTH) {
|
|
fprintf(stderr, "%s: Serialising to RDF/XML returned string size %d, expected %d\n", program,
|
|
(int)string_length, EXPECTED_BAD_STRING_LENGTH);
|
|
return 1;
|
|
}
|
|
librdf_free_uri(base_uri);
|
|
free(string);
|
|
fprintf(stderr, "%s: Serialized OK\n", program);
|
|
|
|
|
|
#define TEST_SIMILAR_COUNT 9
|
|
|
|
/* add some similar statements */
|
|
fprintf(stderr, "%s: Adding %d similar statements\n", program, TEST_SIMILAR_COUNT);
|
|
for(i=0; i < TEST_SIMILAR_COUNT; i++) {
|
|
char literal[6];
|
|
strncpy(literal, "DaveX", 6);
|
|
literal[4]='0'+i;
|
|
statement=librdf_new_statement(world);
|
|
librdf_statement_set_subject(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://example.org/"));
|
|
librdf_statement_set_predicate(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator"));
|
|
librdf_statement_set_object(statement, librdf_new_node_from_literal(world, (const unsigned char*)literal, NULL, 0));
|
|
|
|
librdf_model_add_statement(model, statement);
|
|
librdf_free_statement(statement);
|
|
}
|
|
|
|
/* targets */
|
|
fprintf(stderr, "%s: iterating similar statements\n", program);
|
|
n1=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://example.org/");
|
|
n2=librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator");
|
|
iterator=librdf_model_get_targets(model, n1, n2);
|
|
if(!iterator) {
|
|
fprintf(stderr, "%s: librdf_model_get_targets failed\n", program);
|
|
status=1;
|
|
}
|
|
|
|
fprintf(stderr, "%s: iterating similar statements again\n", program);
|
|
second_iterator=librdf_model_get_targets(model, n1, n2);
|
|
|
|
/* Deleting 2 statements but only 1 before counting */
|
|
expected_count= TEST_SIMILAR_COUNT - 1;
|
|
for(count=0;
|
|
!librdf_iterator_end(iterator);
|
|
librdf_iterator_next(iterator), librdf_iterator_next(second_iterator), count++) {
|
|
librdf_node* n;
|
|
char literal[6];
|
|
|
|
if(count == 2 ) {
|
|
strncpy(literal, "DaveX", 6);
|
|
literal[4]='0'+count;
|
|
statement=librdf_new_statement(world);
|
|
librdf_statement_set_subject(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://example.org/"));
|
|
librdf_statement_set_predicate(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator"));
|
|
librdf_statement_set_object(statement, librdf_new_node_from_literal(world, (const unsigned char*)literal, NULL, 0));
|
|
|
|
fprintf(stderr, "%s: Removing statement with literal '%s'\n",
|
|
program, literal);
|
|
|
|
librdf_model_remove_statement(model, statement);
|
|
librdf_free_statement(statement);
|
|
remove_count++;
|
|
}
|
|
|
|
n=(librdf_node*)librdf_iterator_get_object(iterator);
|
|
fputs(" ", stderr);
|
|
librdf_node_print(n, stderr);
|
|
fputs("\n", stderr);
|
|
|
|
if(count == 5 ) {
|
|
strncpy(literal, "DaveX", 6);
|
|
literal[4]='0'+count+remove_count;
|
|
statement=librdf_new_statement(world);
|
|
librdf_statement_set_subject(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://example.org/"));
|
|
librdf_statement_set_predicate(statement, librdf_new_node_from_uri_string(world, (const unsigned char*)"http://purl.org/dc/elements/1.1/creator"));
|
|
librdf_statement_set_object(statement, librdf_new_node_from_literal(world, (const unsigned char*)literal, NULL, 0));
|
|
|
|
fprintf(stderr, "%s: Removing statement with literal '%s'\n",
|
|
program, literal);
|
|
|
|
librdf_model_remove_statement(model, statement);
|
|
librdf_free_statement(statement);
|
|
remove_count++;
|
|
}
|
|
|
|
}
|
|
librdf_free_iterator(iterator);
|
|
if(count != expected_count) {
|
|
fprintf(stderr, "%s: librdf_model_get_targets returned %d nodes, expected %d\n", program, count, expected_count);
|
|
status=1;
|
|
}
|
|
librdf_free_node(n1);
|
|
librdf_free_node(n2);
|
|
|
|
|
|
librdf_free_iterator(second_iterator);
|
|
|
|
fprintf(stderr, "%s: Freeing URIs and Nodes\n", program);
|
|
for (i=0; i<URI_STRING_COUNT; i++) {
|
|
librdf_free_uri(uris[i]);
|
|
librdf_free_node(nodes[i]);
|
|
}
|
|
|
|
fprintf(stderr, "%s: Freeing model\n", program);
|
|
librdf_free_model(model);
|
|
|
|
fprintf(stderr, "%s: Freeing storage\n", program);
|
|
librdf_free_storage(storage);
|
|
|
|
librdf_free_world(world);
|
|
|
|
return status;
|
|
}
|
|
|
|
int test_model_cloning(char const *program, librdf_world *world) {
|
|
librdf_storage *storage;
|
|
librdf_model *model1;
|
|
librdf_model *model2;
|
|
librdf_model *model3;
|
|
const char* storage_type;
|
|
const char* storage_name;
|
|
const char* storage_options;
|
|
|
|
fprintf(stderr, "%s: Testing model cloning\n", program);
|
|
|
|
/* Get storage configuration */
|
|
storage_type=getenv("REDLAND_TEST_CLONING_STORAGE_TYPE");
|
|
storage_name=getenv("REDLAND_TEST_CLONING_STORAGE_NAME");
|
|
storage_options=getenv("REDLAND_TEST_CLONING_STORAGE_OPTIONS");
|
|
if(!(storage_type && storage_name && storage_options)) {
|
|
/* default is to test bdb disk hashes for cloning */
|
|
storage_type="hashes";
|
|
storage_name="test";
|
|
storage_options="hash-type='bdb',dir='.',write='yes',new='yes',contexts='yes'";
|
|
}
|
|
|
|
fprintf(stderr, "%s: Creating new %s storage\n", program, storage_type);
|
|
storage=librdf_new_storage(world, storage_type, storage_name, storage_options);
|
|
if(!storage) {
|
|
fprintf(stderr, "%s: Failed to create new %s storage name %s with options %s\n", program, storage_type, storage_name, storage_options);
|
|
return 1;
|
|
}
|
|
|
|
fprintf(stderr, "%s: Creating new model for cloning\n", program);
|
|
model1=librdf_new_model(world, storage, NULL);
|
|
if(!model1) {
|
|
fprintf(stderr, "%s: Failed to create new model\n", program);
|
|
/* ok to leak memory */
|
|
return 1;
|
|
}
|
|
|
|
fprintf(stderr, "%s: Cloning model\n", program);
|
|
model2=librdf_new_model_from_model(model1);
|
|
if(!model2) {
|
|
fprintf(stderr, "%s: Failed to clone model\n", program);
|
|
/* ok to leak memory */
|
|
return 1;
|
|
}
|
|
|
|
/* Free original model now so we can test whether the clone is self-sufficient */
|
|
fprintf(stderr, "%s: Freeing original model\n", program);
|
|
librdf_free_model(model1);
|
|
|
|
fprintf(stderr, "%s: Cloning cloned model\n", program);
|
|
model3=librdf_new_model_from_model(model2);
|
|
if(!model3) {
|
|
fprintf(stderr, "%s: Failed to clone cloned model\n", program);
|
|
/* ok to leak memory */
|
|
return 1;
|
|
}
|
|
|
|
fprintf(stderr, "%s: Freeing cloned models\n", program);
|
|
librdf_free_model(model3);
|
|
librdf_free_model(model2);
|
|
|
|
fprintf(stderr, "%s: Freeing %s storage\n", program, storage_type);
|
|
librdf_free_storage(storage);
|
|
|
|
return 0;
|
|
}
|
|
|
|
#endif
|
|
|