From: Shigeru Hanada Date: Tue, 9 Nov 2010 06:07:36 +0000 (+0900) Subject: Add new FdwRoutine function BeginScan which is called just after Open X-Git-Url: http://git.postgresql.org/gitweb/static/gitweb.js?a=commitdiff_plain;h=84e508d574dc9faef48bc71b8d7bf85d33870209;p=users%2Fhanada%2Fpostgres.git Add new FdwRoutine function BeginScan which is called just after Open if the execution if for real query or EXPLAIN ANALYZE. --- diff --git a/contrib/postgresql_fdw/postgresql_fdw.c b/contrib/postgresql_fdw/postgresql_fdw.c index 288830430b..f327a298f1 100644 --- a/contrib/postgresql_fdw/postgresql_fdw.c +++ b/contrib/postgresql_fdw/postgresql_fdw.c @@ -43,6 +43,7 @@ extern Datum postgresql_fdw_handler(PG_FUNCTION_ARGS); static FSConnection* pgConnectServer(ForeignServer *server, UserMapping *user); static void pgFreeFSConnection(FSConnection *conn); static void pgOpen(ForeignScanState *scanstate); +static void pgBeginScan(ForeignScanState *scanstate); static void pgIterate(ForeignScanState *scanstate); static void pgClose(ForeignScanState *scanstate); static void pgReOpen(ForeignScanState *scanstate); @@ -74,6 +75,7 @@ static FdwRoutine postgresql_fdw_routine = pgFreeFSConnection, pgEstimateCosts, pgOpen, + pgBeginScan, pgIterate, pgClose, pgReOpen, @@ -491,6 +493,16 @@ pgOpen(ForeignScanState *scanstate) scanstate->reply = (FdwReply *) reply; } +/* + * Initiate actual scan on a foreign table. + * This function is called just after pgOpen() if the exexution was for real + * query or EXPLAIN ANALYZE. + */ +static void +pgBeginScan(ForeignScanState *scanstate) +{ +} + /* * return tuples one by one. * - execute SQL statement which was deparsed in pgOpen() diff --git a/src/backend/executor/nodeForeignscan.c b/src/backend/executor/nodeForeignscan.c index f8c305a6ae..c9634c6b46 100644 --- a/src/backend/executor/nodeForeignscan.c +++ b/src/backend/executor/nodeForeignscan.c @@ -170,12 +170,20 @@ ExecInitForeignScan(ForeignScan *node, EState *estate, int eflags) scanstate->wrapper = GetForeignDataWrapper(scanstate->server->fdwid); scanstate->user = GetUserMapping(userid, scanstate->server->serverid); scanstate->routine = GetFdwRoutine(scanstate->wrapper->fdwhandler); - - /* connect to the foreign server and prepare to execute scan */ - scanstate->conn = scanstate->routine->ConnectServer(scanstate->server, - scanstate->user); scanstate->routine->Open(scanstate); + /* + * If this execution was not for EXPLAIN w/o ANALYZE flag, initiate the + * foreign scan. + */ + if (!(eflags & EXEC_FLAG_EXPLAIN_ONLY)) + { + /* connect to the foreign server and prepare to execute scan */ + scanstate->conn = scanstate->routine->ConnectServer(scanstate->server, + scanstate->user); + scanstate->routine->BeginScan(scanstate); + } + return scanstate; } diff --git a/src/backend/foreign/file_fdw.c b/src/backend/foreign/file_fdw.c index 729f4692d0..707a3eeedc 100644 --- a/src/backend/foreign/file_fdw.c +++ b/src/backend/foreign/file_fdw.c @@ -70,6 +70,7 @@ extern Datum file_fdw_handler(PG_FUNCTION_ARGS); static FSConnection* ConnectServer(ForeignServer *server, UserMapping *user); static void FreeFSConnection(FSConnection *conn); static void Open(ForeignScanState *scanstate); +static void BeginScan(ForeignScanState *scanstate); static void Iterate(ForeignScanState *scanstate); static void Close(ForeignScanState *scanstate); static void ReOpen(ForeignScanState *scanstate); @@ -253,6 +254,7 @@ file_fdw_handler(PG_FUNCTION_ARGS) FreeFSConnection, EstimateCosts, Open, + BeginScan, Iterate, Close, ReOpen, @@ -302,6 +304,16 @@ Open(ForeignScanState *scanstate) scanstate->reply = (FdwReply *) fstate; } +/* + * BeginScan() + * - initiate access to the file, but we have nothing to do + */ +static void +BeginScan(ForeignScanState *scanstate) +{ + elog(DEBUG2, "%s called", __FUNCTION__); +} + /* * Iterate() * - create HeapTuple from the record in the file. diff --git a/src/include/nodes/execnodes.h b/src/include/nodes/execnodes.h index 70cfb1084b..2abda678bc 100644 --- a/src/include/nodes/execnodes.h +++ b/src/include/nodes/execnodes.h @@ -1430,10 +1430,15 @@ struct FdwRoutine RelOptInfo *baserel); /* - * Deparse query request and open a cursor for the foreign scan. + * Prepare to execute foreign access. */ void (*Open)(ForeignScanState *scanstate); + /* + * Initiate scanning of a foreign table. + */ + void (*BeginScan)(ForeignScanState *scanstate); + /* * Fetch the next record and fill tupleslot with it. */