#include "executor/spi.h"
#include "utils/builtins.h"
#include "utils/datum.h"
+#include "utils/syscache.h"
PG_MODULE_MAGIC;
{
plan = SPI_prepare(query_ensuredbtransummary, 0, NULL);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_ensuredbtransummary);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_ensuredbtransummary);
plan_ensuredbtransummary = SPI_saveplan(plan);
}
argtypes[1] = TEXTOID;
plan = SPI_prepare(query_insertop, 2, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertop);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertop);
plan_insertop = SPI_saveplan(plan);
}
argtypes[3] = TEXTOID;
plan = SPI_prepare(query_insertvaltext, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvaltext);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvaltext);
plan_insertvaltext = SPI_saveplan(plan);
}
argtypes[3] = INT8OID;
plan = SPI_prepare(query_insertvalint, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvalint);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvalint);
plan_insertvalint = SPI_saveplan(plan);
}
argtypes[3] = NUMERICOID;
plan = SPI_prepare(query_insertvalnumeric, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvalnumeric);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvalnumeric);
plan_insertvalnumeric = SPI_saveplan(plan);
}
argtypes[3] = BYTEAOID;
plan = SPI_prepare(query_insertvalbinary, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvalbinary);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvalbinary);
plan_insertvalbinary = SPI_saveplan(plan);
}
argtypes[3] = BOOLOID;
plan = SPI_prepare(query_insertvalboolean, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvalboolean);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvalboolean);
plan_insertvalboolean = SPI_saveplan(plan);
}
argtypes[3] = DATEOID;
plan = SPI_prepare(query_insertvaldate, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvaldate);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvaldate);
plan_insertvaldate = SPI_saveplan(plan);
}
argtypes[3] = TIMEOID;
plan = SPI_prepare(query_insertvaltime, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvaltime);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvaltime);
plan_insertvaltime = SPI_saveplan(plan);
}
argtypes[3] = TIMESTAMPTZOID;
plan = SPI_prepare(query_insertvaltimestamp, 4, argtypes);
if (plan == NULL)
- elog(ERROR, "SPI_prepare failed for \"%s\"", query_insertvaltimestamp);
+ elog(ERROR, "capture_replication_data: SPI_prepare failed for \"%s\"", query_insertvaltimestamp);
plan_insertvaltimestamp = SPI_saveplan(plan);
}
}
write_one_dbtran_value(Datum value, const TupleDesc tupdesc, int i,
Datum *args, const char *nulls)
{
- int spirc;
+ int spirc;
+ HeapTuple tuple;
+ Form_pg_type typeTup;
+ Oid typid = tupdesc->attrs[i]->atttypid;
- switch (tupdesc->attrs[i]->atttypid)
+ tuple = SearchSysCache1(TYPEOID, ObjectIdGetDatum(typid));
+ if (!HeapTupleIsValid(tuple))
+ elog(ERROR, "capture_replication_data: cache lookup failed for type %u", typid);
+
+ typeTup = (Form_pg_type) GETSTRUCT(tuple);
+ if (typeTup->typbasetype != 0)
+ typid = typeTup->typbasetype;
+
+ ReleaseSysCache(tuple);
+
+ switch (typid)
{
case TEXTOID:
args[3] = value;
spirc = SPI_execp(plan_insertvaltimestamp, args, nulls, 4);
break;
default:
- elog(ERROR, "unrecognized type");
+ elog(ERROR, "capture_replication_data: unrecognized type");
+ spirc = -1; /* quiet compiler */
}
+
+ if (spirc < 0)
+ elog(ERROR, "capture_replication_data: SPI error %i while writing value", spirc);
}
/* Make sure we've got a summary row. */
spirc = SPI_execp(plan_ensuredbtransummary, 0, NULL, 0);
if (spirc != SPI_OK_SELECT)
- elog(ERROR, "failed to insert transaction summary");
+ elog(ERROR, "capture_replication_data: failed to insert transaction summary");
/* Insert a new operation row. */
args[0] = CStringGetTextDatum(operation);
args[1] = CStringGetTextDatum(RelationGetRelationName(rel));
spirc = SPI_execp(plan_insertop, args, NULL, 2);
if (spirc != SPI_OK_SELECT || SPI_processed != 1)
- elog(ERROR, "failed to insert transaction operation");
+ elog(ERROR, "capture_replication_data: failed to insert transaction operation");
/* Set those things which will be the same for all value roes below. */
args[0] = SPI_getbinval(SPI_tuptable->vals[0], SPI_tuptable->tupdesc, 1, &isnull);