#include "postgres.h"
#include "funcapi.h"
#include "catalog/namespace.h"
#include "catalog/pg_type.h"
#include "commands/defrem.h"
#include "tsearch/ts_cache.h"
#include "tsearch/ts_utils.h"
#include "utils/builtins.h"
Go to the source code of this file.
Data Structures | |
struct | TSTokenTypeStorage |
struct | LexemeEntry |
struct | PrsStorage |
Functions | |
static void | tt_setup_firstcall (FuncCallContext *funcctx, Oid prsid) |
static Datum | tt_process_call (FuncCallContext *funcctx) |
Datum | ts_token_type_byid (PG_FUNCTION_ARGS) |
Datum | ts_token_type_byname (PG_FUNCTION_ARGS) |
static void | prs_setup_firstcall (FuncCallContext *funcctx, Oid prsid, text *txt) |
static Datum | prs_process_call (FuncCallContext *funcctx) |
Datum | ts_parse_byid (PG_FUNCTION_ARGS) |
Datum | ts_parse_byname (PG_FUNCTION_ARGS) |
Datum | ts_headline_byid_opt (PG_FUNCTION_ARGS) |
Datum | ts_headline_byid (PG_FUNCTION_ARGS) |
Datum | ts_headline (PG_FUNCTION_ARGS) |
Datum | ts_headline_opt (PG_FUNCTION_ARGS) |
static Datum prs_process_call | ( | FuncCallContext * | funcctx | ) | [static] |
Definition at line 211 of file wparser.c.
References FuncCallContext::attinmeta, BuildTupleFromCStrings(), PrsStorage::cur, HeapTupleGetDatum, PrsStorage::len, LexemeEntry::lexeme, PrsStorage::list, pfree(), LexemeEntry::type, FuncCallContext::user_fctx, and values.
Referenced by ts_parse_byid(), and ts_parse_byname().
{ PrsStorage *st; st = (PrsStorage *) funcctx->user_fctx; if (st->cur < st->len) { Datum result; char *values[2]; char tid[16]; HeapTuple tuple; values[0] = tid; sprintf(tid, "%d", st->list[st->cur].type); values[1] = st->list[st->cur].lexeme; tuple = BuildTupleFromCStrings(funcctx->attinmeta, values); result = HeapTupleGetDatum(tuple); pfree(values[1]); st->cur++; return result; } else { if (st->list) pfree(st->list); pfree(st); } return (Datum) 0; }
static void prs_setup_firstcall | ( | FuncCallContext * | funcctx, | |
Oid | prsid, | |||
text * | txt | |||
) | [static] |
Definition at line 155 of file wparser.c.
References FuncCallContext::attinmeta, CreateTemplateTupleDesc(), PrsStorage::cur, DatumGetInt32, DatumGetPointer, FunctionCall1, FunctionCall2, FunctionCall3, Int32GetDatum, INT4OID, PrsStorage::len, LexemeEntry::lexeme, PrsStorage::list, lookup_ts_parser_cache(), MemoryContextSwitchTo(), FuncCallContext::multi_call_memory_ctx, palloc(), PointerGetDatum, TSParserCacheEntry::prsend, TSParserCacheEntry::prsstart, TSParserCacheEntry::prstoken, repalloc(), TEXTOID, TupleDescGetAttInMetadata(), TupleDescInitEntry(), LexemeEntry::type, FuncCallContext::user_fctx, VARDATA, and VARSIZE.
Referenced by ts_parse_byid(), and ts_parse_byname().
{ TupleDesc tupdesc; MemoryContext oldcontext; PrsStorage *st; TSParserCacheEntry *prs = lookup_ts_parser_cache(prsid); char *lex = NULL; int llen = 0, type = 0; void *prsdata; oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx); st = (PrsStorage *) palloc(sizeof(PrsStorage)); st->cur = 0; st->len = 16; st->list = (LexemeEntry *) palloc(sizeof(LexemeEntry) * st->len); prsdata = (void *) DatumGetPointer(FunctionCall2(&prs->prsstart, PointerGetDatum(VARDATA(txt)), Int32GetDatum(VARSIZE(txt) - VARHDRSZ))); while ((type = DatumGetInt32(FunctionCall3(&prs->prstoken, PointerGetDatum(prsdata), PointerGetDatum(&lex), PointerGetDatum(&llen)))) != 0) { if (st->cur >= st->len) { st->len = 2 * st->len; st->list = (LexemeEntry *) repalloc(st->list, sizeof(LexemeEntry) * st->len); } st->list[st->cur].lexeme = palloc(llen + 1); memcpy(st->list[st->cur].lexeme, lex, llen); st->list[st->cur].lexeme[llen] = '\0'; st->list[st->cur].type = type; st->cur++; } FunctionCall1(&prs->prsend, PointerGetDatum(prsdata)); st->len = st->cur; st->cur = 0; funcctx->user_fctx = (void *) st; tupdesc = CreateTemplateTupleDesc(2, false); TupleDescInitEntry(tupdesc, (AttrNumber) 1, "tokid", INT4OID, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 2, "token", TEXTOID, -1, 0); funcctx->attinmeta = TupleDescGetAttInMetadata(tupdesc); MemoryContextSwitchTo(oldcontext); }
Datum ts_headline | ( | PG_FUNCTION_ARGS | ) |
Definition at line 347 of file wparser.c.
References DirectFunctionCall3, getTSCurrentConfig(), ObjectIdGetDatum, PG_GETARG_DATUM, PG_RETURN_DATUM, and ts_headline_byid_opt().
Datum ts_headline_byid | ( | PG_FUNCTION_ARGS | ) |
Definition at line 338 of file wparser.c.
References DirectFunctionCall3, PG_GETARG_DATUM, PG_RETURN_DATUM, and ts_headline_byid_opt().
Referenced by tsa_headline_byname().
Datum ts_headline_byid_opt | ( | PG_FUNCTION_ARGS | ) |
Definition at line 289 of file wparser.c.
References TSConfigCacheEntry::cfgId, deserialize_deflist(), ereport, errcode(), errmsg(), ERROR, FunctionCall3, generateHeadline(), TSParserCacheEntry::headlineOid, hlparsetext(), HeadlineParsedText::lenwords, lookup_ts_config_cache(), lookup_ts_parser_cache(), OidIsValid, palloc(), pfree(), PG_FREE_IF_COPY, PG_GETARG_OID, PG_GETARG_POINTER, PG_GETARG_TEXT_P, PG_GETARG_TSQUERY, PG_NARGS, PG_RETURN_POINTER, PointerGetDatum, TSParserCacheEntry::prsheadline, TSConfigCacheEntry::prsId, HeadlineParsedText::startsel, HeadlineParsedText::stopsel, VARDATA, VARHDRSZ, VARSIZE, and HeadlineParsedText::words.
Referenced by ts_headline(), ts_headline_byid(), ts_headline_opt(), and tsa_headline_byname().
{ text *in = PG_GETARG_TEXT_P(1); TSQuery query = PG_GETARG_TSQUERY(2); text *opt = (PG_NARGS() > 3 && PG_GETARG_POINTER(3)) ? PG_GETARG_TEXT_P(3) : NULL; HeadlineParsedText prs; List *prsoptions; text *out; TSConfigCacheEntry *cfg; TSParserCacheEntry *prsobj; cfg = lookup_ts_config_cache(PG_GETARG_OID(0)); prsobj = lookup_ts_parser_cache(cfg->prsId); if (!OidIsValid(prsobj->headlineOid)) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), errmsg("text search parser does not support headline creation"))); memset(&prs, 0, sizeof(HeadlineParsedText)); prs.lenwords = 32; prs.words = (HeadlineWordEntry *) palloc(sizeof(HeadlineWordEntry) * prs.lenwords); hlparsetext(cfg->cfgId, &prs, query, VARDATA(in), VARSIZE(in) - VARHDRSZ); if (opt) prsoptions = deserialize_deflist(PointerGetDatum(opt)); else prsoptions = NIL; FunctionCall3(&(prsobj->prsheadline), PointerGetDatum(&prs), PointerGetDatum(prsoptions), PointerGetDatum(query)); out = generateHeadline(&prs); PG_FREE_IF_COPY(in, 1); PG_FREE_IF_COPY(query, 2); if (opt) PG_FREE_IF_COPY(opt, 3); pfree(prs.words); pfree(prs.startsel); pfree(prs.stopsel); PG_RETURN_POINTER(out); }
Datum ts_headline_opt | ( | PG_FUNCTION_ARGS | ) |
Definition at line 356 of file wparser.c.
References DirectFunctionCall4, getTSCurrentConfig(), ObjectIdGetDatum, PG_GETARG_DATUM, PG_RETURN_DATUM, and ts_headline_byid_opt().
{ PG_RETURN_DATUM(DirectFunctionCall4(ts_headline_byid_opt, ObjectIdGetDatum(getTSCurrentConfig(true)), PG_GETARG_DATUM(0), PG_GETARG_DATUM(1), PG_GETARG_DATUM(2))); }
Datum ts_parse_byid | ( | PG_FUNCTION_ARGS | ) |
Definition at line 243 of file wparser.c.
References PG_FREE_IF_COPY, PG_GETARG_OID, PG_GETARG_TEXT_P, prs_process_call(), prs_setup_firstcall(), SRF_FIRSTCALL_INIT, SRF_IS_FIRSTCALL, SRF_PERCALL_SETUP, SRF_RETURN_DONE, and SRF_RETURN_NEXT.
Referenced by tsa_parse_current().
{ FuncCallContext *funcctx; Datum result; if (SRF_IS_FIRSTCALL()) { text *txt = PG_GETARG_TEXT_P(1); funcctx = SRF_FIRSTCALL_INIT(); prs_setup_firstcall(funcctx, PG_GETARG_OID(0), txt); PG_FREE_IF_COPY(txt, 1); } funcctx = SRF_PERCALL_SETUP(); if ((result = prs_process_call(funcctx)) != (Datum) 0) SRF_RETURN_NEXT(funcctx, result); SRF_RETURN_DONE(funcctx); }
Datum ts_parse_byname | ( | PG_FUNCTION_ARGS | ) |
Definition at line 265 of file wparser.c.
References get_ts_parser_oid(), PG_GETARG_TEXT_P, prs_process_call(), prs_setup_firstcall(), SRF_FIRSTCALL_INIT, SRF_IS_FIRSTCALL, SRF_PERCALL_SETUP, SRF_RETURN_DONE, SRF_RETURN_NEXT, and textToQualifiedNameList().
{ FuncCallContext *funcctx; Datum result; if (SRF_IS_FIRSTCALL()) { text *prsname = PG_GETARG_TEXT_P(0); text *txt = PG_GETARG_TEXT_P(1); Oid prsId; funcctx = SRF_FIRSTCALL_INIT(); prsId = get_ts_parser_oid(textToQualifiedNameList(prsname), false); prs_setup_firstcall(funcctx, prsId, txt); } funcctx = SRF_PERCALL_SETUP(); if ((result = prs_process_call(funcctx)) != (Datum) 0) SRF_RETURN_NEXT(funcctx, result); SRF_RETURN_DONE(funcctx); }
Datum ts_token_type_byid | ( | PG_FUNCTION_ARGS | ) |
Definition at line 99 of file wparser.c.
References PG_GETARG_OID, SRF_FIRSTCALL_INIT, SRF_IS_FIRSTCALL, SRF_PERCALL_SETUP, SRF_RETURN_DONE, SRF_RETURN_NEXT, tt_process_call(), and tt_setup_firstcall().
Referenced by tsa_token_type_current().
{ FuncCallContext *funcctx; Datum result; if (SRF_IS_FIRSTCALL()) { funcctx = SRF_FIRSTCALL_INIT(); tt_setup_firstcall(funcctx, PG_GETARG_OID(0)); } funcctx = SRF_PERCALL_SETUP(); if ((result = tt_process_call(funcctx)) != (Datum) 0) SRF_RETURN_NEXT(funcctx, result); SRF_RETURN_DONE(funcctx); }
Datum ts_token_type_byname | ( | PG_FUNCTION_ARGS | ) |
Definition at line 118 of file wparser.c.
References get_ts_parser_oid(), PG_GETARG_TEXT_P, SRF_FIRSTCALL_INIT, SRF_IS_FIRSTCALL, SRF_PERCALL_SETUP, SRF_RETURN_DONE, SRF_RETURN_NEXT, textToQualifiedNameList(), tt_process_call(), and tt_setup_firstcall().
{ FuncCallContext *funcctx; Datum result; if (SRF_IS_FIRSTCALL()) { text *prsname = PG_GETARG_TEXT_P(0); Oid prsId; funcctx = SRF_FIRSTCALL_INIT(); prsId = get_ts_parser_oid(textToQualifiedNameList(prsname), false); tt_setup_firstcall(funcctx, prsId); } funcctx = SRF_PERCALL_SETUP(); if ((result = tt_process_call(funcctx)) != (Datum) 0) SRF_RETURN_NEXT(funcctx, result); SRF_RETURN_DONE(funcctx); }
static Datum tt_process_call | ( | FuncCallContext * | funcctx | ) | [static] |
Definition at line 67 of file wparser.c.
References LexDescr::alias, FuncCallContext::attinmeta, BuildTupleFromCStrings(), TSTokenTypeStorage::cur, LexDescr::descr, HeapTupleGetDatum, LexDescr::lexid, TSTokenTypeStorage::list, pfree(), FuncCallContext::user_fctx, and values.
Referenced by ts_token_type_byid(), and ts_token_type_byname().
{ TSTokenTypeStorage *st; st = (TSTokenTypeStorage *) funcctx->user_fctx; if (st->list && st->list[st->cur].lexid) { Datum result; char *values[3]; char txtid[16]; HeapTuple tuple; sprintf(txtid, "%d", st->list[st->cur].lexid); values[0] = txtid; values[1] = st->list[st->cur].alias; values[2] = st->list[st->cur].descr; tuple = BuildTupleFromCStrings(funcctx->attinmeta, values); result = HeapTupleGetDatum(tuple); pfree(values[1]); pfree(values[2]); st->cur++; return result; } if (st->list) pfree(st->list); pfree(st); return (Datum) 0; }
static void tt_setup_firstcall | ( | FuncCallContext * | funcctx, | |
Oid | prsid | |||
) | [static] |
Definition at line 34 of file wparser.c.
References FuncCallContext::attinmeta, CreateTemplateTupleDesc(), TSTokenTypeStorage::cur, DatumGetPointer, elog, ERROR, INT4OID, TSParserCacheEntry::lextypeOid, TSTokenTypeStorage::list, lookup_ts_parser_cache(), MemoryContextSwitchTo(), FuncCallContext::multi_call_memory_ctx, OidFunctionCall1, OidIsValid, palloc(), TEXTOID, TupleDescGetAttInMetadata(), TupleDescInitEntry(), and FuncCallContext::user_fctx.
Referenced by ts_token_type_byid(), and ts_token_type_byname().
{ TupleDesc tupdesc; MemoryContext oldcontext; TSTokenTypeStorage *st; TSParserCacheEntry *prs = lookup_ts_parser_cache(prsid); if (!OidIsValid(prs->lextypeOid)) elog(ERROR, "method lextype isn't defined for text search parser %u", prsid); oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx); st = (TSTokenTypeStorage *) palloc(sizeof(TSTokenTypeStorage)); st->cur = 0; /* lextype takes one dummy argument */ st->list = (LexDescr *) DatumGetPointer(OidFunctionCall1(prs->lextypeOid, (Datum) 0)); funcctx->user_fctx = (void *) st; tupdesc = CreateTemplateTupleDesc(3, false); TupleDescInitEntry(tupdesc, (AttrNumber) 1, "tokid", INT4OID, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 2, "alias", TEXTOID, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 3, "description", TEXTOID, -1, 0); funcctx->attinmeta = TupleDescGetAttInMetadata(tupdesc); MemoryContextSwitchTo(oldcontext); }