Introduce new extended routines for FDW and foreign server lookups
authorMichael Paquier <[email protected]>
Thu, 13 Dec 2018 23:59:35 +0000 (08:59 +0900)
committerMichael Paquier <[email protected]>
Thu, 13 Dec 2018 23:59:35 +0000 (08:59 +0900)
The cache lookup routines for foreign-data wrappers and foreign servers
are extended with an extra argument to handle a set of flags.  The only
value which can be used now is to indicate if a missing object should
result in an error or not, and are designed to be extensible on need.
Those new routines are added into the existing set of user-visible
FDW APIs and documented in consequence.  They will be used for future
patches to improve the SQL interface for object addresses.

Author: Michael Paquier
Reviewed-by: Álvaro Herrera
Discussion: https://postgr.es/m/CAB7nPqSZxrSmdHK-rny7z8mi=EAFXJ5J-0RbzDw6aus=wB5azQ@mail.gmail.com

doc/src/sgml/fdwhandler.sgml
src/backend/foreign/foreign.c
src/include/foreign/foreign.h

index 4ce88dd77c19edefca0121e66d8ff4e584b8c07c..452b776b9e1995a271ea4a084e61fc9ded084a91 100644 (file)
@@ -1408,6 +1408,23 @@ ReparameterizeForeignPathByChild(PlannerInfo *root, List *fdw_private,
     <para>
 <programlisting>
 ForeignDataWrapper *
+GetForeignDataWrapperExtended(Oid fdwid, bits16 flags);
+</programlisting>
+
+     This function returns a <structname>ForeignDataWrapper</structname>
+     object for the foreign-data wrapper with the given OID.  A
+     <structname>ForeignDataWrapper</structname> object contains properties
+     of the FDW (see <filename>foreign/foreign.h</filename> for details).
+     <structfield>flags</structfield> is a bitwise-or'd bit mask indicating
+     an extra set of options.  It can take the value
+     <literal>FDW_MISSING_OK</literal>, in which case a <literal>NULL</literal>
+     result is returned to the caller instead of an error for an undefined
+     object.
+    </para>
+
+    <para>
+<programlisting>
+ForeignDataWrapper *
 GetForeignDataWrapper(Oid fdwid);
 </programlisting>
 
@@ -1420,6 +1437,23 @@ GetForeignDataWrapper(Oid fdwid);
     <para>
 <programlisting>
 ForeignServer *
+GetForeignServerExtended(Oid serverid, bits16 flags);
+</programlisting>
+
+     This function returns a <structname>ForeignServer</structname> object
+     for the foreign server with the given OID.  A
+     <structname>ForeignServer</structname> object contains properties
+     of the server (see <filename>foreign/foreign.h</filename> for details).
+     <structfield>flags</structfield> is a bitwise-or'd bit mask indicating
+     an extra set of options.  It can take the value
+     <literal>FSV_MISSING_OK</literal>, in which case a <literal>NULL</literal>
+     result is returned to the caller instead of an error for an undefined
+     object.
+    </para>
+
+    <para>
+<programlisting>
+ForeignServer *
 GetForeignServer(Oid serverid);
 </programlisting>
 
index 989a58ad78b94030ff1bf2485d75daeb76b744ac..79661526a3afc8653cba1b464a2d70ba470b264a 100644 (file)
  */
 ForeignDataWrapper *
 GetForeignDataWrapper(Oid fdwid)
+{
+       return GetForeignDataWrapperExtended(fdwid, 0);
+}
+
+
+/*
+ * GetForeignDataWrapperExtended -     look up the foreign-data wrapper
+ * by OID. If flags uses FDW_MISSING_OK, return NULL if the object cannot
+ * be found instead of raising an error.
+ */
+ForeignDataWrapper *
+GetForeignDataWrapperExtended(Oid fdwid, bits16 flags)
 {
        Form_pg_foreign_data_wrapper fdwform;
        ForeignDataWrapper *fdw;
@@ -43,7 +55,11 @@ GetForeignDataWrapper(Oid fdwid)
        tp = SearchSysCache1(FOREIGNDATAWRAPPEROID, ObjectIdGetDatum(fdwid));
 
        if (!HeapTupleIsValid(tp))
-               elog(ERROR, "cache lookup failed for foreign-data wrapper %u", fdwid);
+       {
+               if ((flags & FDW_MISSING_OK) == 0)
+                       elog(ERROR, "cache lookup failed for foreign-data wrapper %u", fdwid);
+               return NULL;
+       }
 
        fdwform = (Form_pg_foreign_data_wrapper) GETSTRUCT(tp);
 
@@ -91,6 +107,18 @@ GetForeignDataWrapperByName(const char *fdwname, bool missing_ok)
  */
 ForeignServer *
 GetForeignServer(Oid serverid)
+{
+       return GetForeignServerExtended(serverid, 0);
+}
+
+
+/*
+ * GetForeignServerExtended - look up the foreign server definition. If
+ * flags uses FSV_MISSING_OK, return NULL if the object cannot be found
+ * instead of raising an error.
+ */
+ForeignServer *
+GetForeignServerExtended(Oid serverid, bits16 flags)
 {
        Form_pg_foreign_server serverform;
        ForeignServer *server;
@@ -101,7 +129,11 @@ GetForeignServer(Oid serverid)
        tp = SearchSysCache1(FOREIGNSERVEROID, ObjectIdGetDatum(serverid));
 
        if (!HeapTupleIsValid(tp))
-               elog(ERROR, "cache lookup failed for foreign server %u", serverid);
+       {
+               if ((flags & FSV_MISSING_OK) == 0)
+                       elog(ERROR, "cache lookup failed for foreign server %u", serverid);
+               return NULL;
+       }
 
        serverform = (Form_pg_foreign_server) GETSTRUCT(tp);
 
index 3ca12e64d27d86694c41b3ddb06758f356c76a13..a7129b5fcb2b939b76f417fa5fbbc7bb277b2c8c 100644 (file)
@@ -68,11 +68,21 @@ typedef struct ForeignTable
        List       *options;            /* ftoptions as DefElem list */
 } ForeignTable;
 
+/* Flags for GetForeignServerExtended */
+#define FSV_MISSING_OK 0x01
+
+/* Flags for GetForeignDataWrapperExtended */
+#define FDW_MISSING_OK 0x01
+
 
 extern ForeignServer *GetForeignServer(Oid serverid);
+extern ForeignServer *GetForeignServerExtended(Oid serverid,
+                                                bits16 flags);
 extern ForeignServer *GetForeignServerByName(const char *name, bool missing_ok);
 extern UserMapping *GetUserMapping(Oid userid, Oid serverid);
 extern ForeignDataWrapper *GetForeignDataWrapper(Oid fdwid);
+extern ForeignDataWrapper *GetForeignDataWrapperExtended(Oid fdwid,
+                                                         bits16 flags);
 extern ForeignDataWrapper *GetForeignDataWrapperByName(const char *name,
                                                        bool missing_ok);
 extern ForeignTable *GetForeignTable(Oid relid);