--- trunk/pgest.c 2005/05/20 12:19:05 1 +++ trunk/pgest.c 2005/05/20 19:44:09 5 @@ -34,12 +34,16 @@ #define GET_STR(textp) DatumGetCString(DirectFunctionCall1(textout, PointerGetDatum(textp))) #define GET_TEXT(cstrp) DatumGetTextP(DirectFunctionCall1(textin, CStringGetDatum(cstrp))) +/* prototype */ +char *attr2text(ESTDOC *doc, char *attr); ESTDB *db; ESTCOND *cond; ESTDOC *doc; const CBLIST *texts; int ecode, *est_result, resnum, i, j; +int limit = 0; +int offset = 0; /* define PostgreSQL v1 function */ PG_FUNCTION_INFO_V1(pgest); @@ -53,6 +57,7 @@ AttInMetadata *attinmeta; char *index_path; char *query; + char *attr; /* stuff done only on the first call of the function */ if (SRF_IS_FIRSTCALL()) { @@ -62,6 +67,9 @@ //index_path = _textout(PG_GETARG_TEXT_P(0)); index_path = _textout(PG_GETARG_TEXT_P(0)); query = _textout(PG_GETARG_TEXT_P(1)); + attr = _textout(PG_GETARG_TEXT_P(2)); + limit = PG_GETARG_INT32(3); + offset = PG_GETARG_INT32(4); /* create a function context for cross-call persistence */ funcctx = SRF_FIRSTCALL_INIT(); @@ -77,7 +85,7 @@ SRF_RETURN_DONE(funcctx); } - elog(DEBUG2, "pgest: query=%s", query); + elog(INFO, "pgest: query[%s] attr[%s] limit %d offset %d", query, attr, limit, offset); /* create a search condition object */ if (!(cond = est_cond_new())) { @@ -88,17 +96,27 @@ /* set the search phrase to the search condition object */ est_cond_set_phrase(cond, query); + /* minimum valid attribute length is 10: @a STREQ a */ + if (attr != NULL && strlen(attr) >= 10) { + elog(INFO,"est_cond_add_attr(%s)", attr); + est_cond_add_attr(cond, attr); + } + /* get the result of search */ est_result = est_db_search(db, cond, &resnum, NULL); /* total number of tuples to be returned */ - funcctx->max_calls = resnum; + if (limit && limit < resnum) { + funcctx->max_calls = limit - offset; + } else { + funcctx->max_calls = resnum - offset; + } /* check if results exists */ if ( 0 == funcctx->max_calls ) elog(INFO, "pgest: no results for: %s", query ); - elog(INFO, "pgest: found %d hits for %s", funcctx->max_calls, query); + elog(DEBUG1, "pgest: found %d hits for %s", resnum, query); /* Build a tuple description for a __pgest tuple */ tupdesc = RelationNameGetTupleDesc("__pgest"); @@ -118,7 +136,7 @@ MemoryContextSwitchTo(oldcontext); - elog(INFO, "SRF_IS_FIRSTCALL done"); + elog(DEBUG1, "SRF_IS_FIRSTCALL done"); } /* stuff done on every call of the function */ @@ -128,13 +146,18 @@ max_calls = funcctx->max_calls; slot = funcctx->slot; attinmeta = funcctx->attinmeta; - + + if (limit && call_cntr > limit - 1) { + elog(INFO, "call_cntr: %d limit: %d", call_cntr, limit); + SRF_RETURN_DONE(funcctx); + } + if (call_cntr < max_calls) { char **values; HeapTuple tuple; Datum result; - elog(INFO, "pgest: loop count %d", call_cntr); + elog(DEBUG1, "pgest: loop count %d", call_cntr); if (! est_result) { elog(ERROR, "pgest: no estraier results"); @@ -147,9 +170,9 @@ * be processed later by the type input functions. */ - if (doc = est_db_get_doc(db, est_result[call_cntr], 0)) { + if (doc = est_db_get_doc(db, est_result[call_cntr + offset], 0)) { - elog(INFO, "URI: %s\n Title: %s\n", + elog(DEBUG1, "URI: %s\n Title: %s\n", est_doc_attr(doc, "@uri"), est_doc_attr(doc, "@title") ); @@ -158,10 +181,10 @@ // values[0] = (char *) palloc(strlen(_estval) * sizeof(char)); - values[0] = attr2text(doc,"@id"); - values[1] = attr2text(doc,"@uri"); - values[2] = attr2text(doc,"@title"); - values[3] = attr2text(doc,"@type"); + values[0] = (char *) attr2text(doc,"@id"); + values[1] = (char *) attr2text(doc,"@uri"); + values[2] = (char *) attr2text(doc,"@title"); + values[3] = (char *) attr2text(doc,"@type"); /* destloy the document object */ elog(DEBUG2, "est_doc_delete"); @@ -197,7 +220,7 @@ SRF_RETURN_NEXT(funcctx, result); } else { - elog(INFO, "loop over"); + elog(DEBUG1, "loop over"); if(!est_db_close(db, &ecode)){ elog(INFO, "est_db_close error: %s", est_err_msg(ecode)); @@ -292,17 +315,18 @@ char *val; const char *attrval; int len; + int attrlen; - elog(INFO, "doc: %08x, attr: %s", doc, attr); + elog(DEBUG1, "doc: %08x, attr: %s", doc, attr); - if (attrval = est_doc_attr(doc, attr)) { - val = (char *) palloc(strlen(attrval) * sizeof(char)); + if ( (attrval = est_doc_attr(doc, attr)) && (attrlen = strlen(attrval)) ) { + val = (char *) palloc(attrlen * sizeof(char)); } else { return (Datum) NULL; } len = strlen(attrval); - elog(INFO, "attr2text(%s) = '%s' %d bytes", attr, attrval, len); + elog(DEBUG1, "attr2text(%s) = '%s' %d bytes", attr, attrval, len); len++; len *= sizeof(char);