/*
 * rdfconsturi.c
 * Redland nodes corresponding to commonly-used uris.
 *
 * Copyright (C) Leni Mayo 2002
 *
 *	This program is free software; you can redistribute it and/or modify
 *	it under the terms of the GNU General Public License, version 2, as
 *	published by the Free Software Foundation.
 *	
 *	This program is distributed in the hope that it will be useful,
 *	but WITHOUT ANY WARRANTY; without even the implied warranty of
 *	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *	GNU General Public License for more details.
 *	
 *	You should have received a copy of the GNU General Public License
 *	along with this program; if not, write to the Free Software
 *	Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */

#include <stdlib.h>
#include <string.h>
#include "servercommon.h"
#include "rdfcommon.h"
#include "rdfconsturi.h"

static librdf_node * newNodeFromCode(RdfProperty code);

static librdf_node * table[eRdfPropertyLast];
static int initialised = FALSE;

int rdfConstInitialise()
{
	int i;
	int ret = TRUE;

	assert(pWorld);
	assert(!initialised);

	initialised = TRUE;

	for (i = 0; i < eRdfPropertyLast && ret; i++)
	{
		table[i] = newNodeFromCode(i);

		ret = (table[i] != NULL);
	}

	return ret;
}

void rdfConstCleanup()
{
	int i;

	for (i = 0; i < eRdfPropertyLast; i++)
	{
		if (table[i])
		{
			librdf_free_node(table[i]);
		}
	}
}

librdf_node * nodeFromCode(RdfProperty code)
{
	assert(code < eRdfPropertyLast);

	return table[code];
}

librdf_node * newNodeFromCode(RdfProperty code)
{
	char buf[200];
	librdf_node *pReturn    = NULL;
	const char *pszSpace    = rdfPropertyNamespace(code);
	const char *pszFragment = rdfPropertyFragment(code);

	assert(strlen(pszSpace) + strlen(pszFragment) < sizeof(buf));

	sprintf(buf, "%s#%s", pszSpace, pszFragment);

	pReturn = librdf_new_node_from_uri_string(pWorld, buf);

	return pReturn;
}

int nodeHasPropertyName(librdf_model *pModel, librdf_node *pNode, RdfProperty code)
{
	return librdf_model_has_arc_out(pModel, pNode, nodeFromCode(code));
}

int addPropertyToNode(librdf_model *pModel, librdf_node *pNode, RdfProperty name, const char *pszLiteral)
{
	librdf_node *pSubject, *pPredicate, *pObject;
	int ret;

	pSubject   = librdf_new_node_from_node(pNode);
	pPredicate = librdf_new_node_from_node(nodeFromCode(name));
	pObject    = librdf_new_node_from_literal(pWorld, pszLiteral, NULL, 0, 0);

	ret = ! librdf_model_add(pModel, pSubject, pPredicate, pObject); 

	return ret;
}

int addPropertyToBaseAndFragment(librdf_model *pModel, const char *pszBase, const char *pszFragment, RdfProperty name, const char *pszLiteral)
{
	librdf_node *pNode;
	char *pszUri;
	int ret;

	pszUri = new_string_from_base_and_fragment(pszBase, pszFragment);

	pNode = librdf_new_node_from_uri_string(pWorld, pszUri);
	
	ret = addPropertyToNode(pModel, pNode, name, pszLiteral);

	librdf_free_node(pNode);
	free(pszUri);

	return ret;
}

/*
 * isNodeWithPropertyValue()
 *	Returns:
 *		TRUE if the node has the named RdfProperty and it's value matches,
 *		FALSE otherwise
 */
int isNodeWithPropertyValue(librdf_model *pModel, librdf_node *pNode, RdfProperty code, const char *pszValue)
{
	librdf_node *pSourceUriValue;
	int ret = FALSE;

	assert(pNode);

	pSourceUriValue = librdf_model_get_target(pModel, pNode, nodeFromCode(code));

	if (pSourceUriValue)
	{
		char *pszSourceUriValue = librdf_node_get_literal_value(pSourceUriValue);

		ret = strcmp(pszSourceUriValue, pszValue) == 0;
	}

	return ret;
}
