Hello all,

I've been working on an extension that tightly integrates
postgres with underlying filesystem . I need to customize
how postgres copies directories for new databases.

I first looked at the ProcessUtility_hook. This would require
me to copy or rewrite most of the createdb() function. This is
less than ideal of course. Someone on the IRC channel
suggested I could add a hook for copydir().

I implemented the hook similar to how the
ProcessUtility_hook is implemented. I couldn't find any tests
for any of the existing hooks. I've been looking at the regression
tests, but I am not entirely sure how to proceed on that front.

I tested my patch extensively against master and
the REL_12_STABLE branch. All tests pass and the patch has
been working great with my extension.

I attached a first draft of the patch against master.

---
Swen Kooij
diff --git a/src/backend/storage/file/copydir.c b/src/backend/storage/file/copydir.c
index ca1c9cd765..e44bebf947 100644
--- a/src/backend/storage/file/copydir.c
+++ b/src/backend/storage/file/copydir.c
@@ -27,6 +27,9 @@
 #include "miscadmin.h"
 #include "pgstat.h"
 
+/* Hook for plugins to get control in copydir() */
+copydir_hook_type copydir_hook = NULL;
+
 /*
  * copydir: copy a directory
  *
@@ -36,6 +39,22 @@
 void
 copydir(char *fromdir, char *todir, bool recurse)
 {
+	if (copydir_hook)
+		(*copydir_hook) (fromdir, todir, recurse);
+	else
+		standard_copydir(fromdir, todir, recurse);
+}
+
+/*
+ * copydir: copy a directory
+ *
+ * If recurse is false, subdirectories are ignored.  Anything that's not
+ * a directory or a regular file is ignored.
+ */
+void
+standard_copydir(char *fromdir, char *todir, bool recurse)
+{
+
 	DIR		   *xldir;
 	struct dirent *xlde;
 	char		fromfile[MAXPGPATH * 2];
diff --git a/src/include/storage/copydir.h b/src/include/storage/copydir.h
index 525cc6203e..8b73184177 100644
--- a/src/include/storage/copydir.h
+++ b/src/include/storage/copydir.h
@@ -13,7 +13,12 @@
 #ifndef COPYDIR_H
 #define COPYDIR_H
 
+/* Hook for plugins to get control in copydir() */
+typedef void (*copydir_hook_type) (char *fromdir, char *todir, bool recurse);
+extern PGDLLIMPORT copydir_hook_type copydir_hook;
+
 extern void copydir(char *fromdir, char *todir, bool recurse);
+extern void standard_copydir(char *fromdir, char *todir, bool recurse);
 extern void copy_file(char *fromfile, char *tofile);
 
 #endif							/* COPYDIR_H */

Reply via email to