Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.92) (envelope-from ) id 1jAMV2-0001vC-BF for pgsql-hackers@arkaria.postgresql.org; Fri, 06 Mar 2020 23:35:25 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.89) (envelope-from ) id 1jAMV0-000536-TY for pgsql-hackers@arkaria.postgresql.org; Fri, 06 Mar 2020 23:35:22 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1jAMV0-00052z-Ey for pgsql-hackers@lists.postgresql.org; Fri, 06 Mar 2020 23:35:22 +0000 Received: from mail-yw1-xc42.google.com ([2607:f8b0:4864:20::c42]) by magus.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.92) (envelope-from ) id 1jAMUq-0008FH-NQ for pgsql-hackers@postgresql.org; Fri, 06 Mar 2020 23:35:21 +0000 Received: by mail-yw1-xc42.google.com with SMTP id v138so3901909ywa.9 for ; Fri, 06 Mar 2020 15:35:11 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=telsasoft-com.20150623.gappssmtp.com; s=20150623; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:in-reply-to:user-agent; bh=P4jq3zWOjMK5/rcw6bqmn1M5nytjf66+peF0iYKbC6k=; b=EJrvhogs+h+7fKFnFltSajw/4B1DprfF+Vj/PFbfAJydM2dV5xVl7AEfTbl8TqVgDZ cYilXW7zqscKYvbzpO8a8QgXU97oJRyKpIdi7jjMJntGkpn7h9gWK8tDWcKBFaA23UEX tUxh8bHRWVNSZRtXmlsjTiAoIK/Clv69evjhVGWnZWycWccqe/W181k0sCjci3VIXVk/ O3QYXONtPCONXrbHPn1/rBjCIqxnje3Is9gCyD7AMaHYY0l0EDkP+vNALi1G9C4Foh0R jdEHXvIn5LnkHiFmqWy4GWE8T71am2fwr5H1eftvNCM1TGQ5n1qnL1fqv3IdvLQWCsNh Egdg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:in-reply-to:user-agent; bh=P4jq3zWOjMK5/rcw6bqmn1M5nytjf66+peF0iYKbC6k=; b=lGRl5AqKWSu8lEDiGPlm+882ePxinQqedPHEt0f5toIl6JBbLIY5QmmS2yUNIYGDm8 P6B5d5FxgqfDhldbuJGyo/5ecyOJKHsfK8OJ6QPRq76eSmdZvoZO/DGceIx2g3GpvYbF oZdLrCaGo0kCHrUYRPmLltsu/5fQuSzPeDEBpfFRv0ntWc3BRj7lulw1nLKXTNpLt1cR Y8DwhgasPBSl2tgn4q0K2rS5FW0oyRX4iu4eeEUhGFx6bQEZEKq0GgAXfSAohFEKIsAG FSmoErWgFCGJX+ckKrG8E3PVd4SJgw3rCW8QLVgQtiKF92JEkt8pJy22ZMMiOZnWPiKP GGvw== X-Gm-Message-State: ANhLgQ0i95qXSOiusH/xB03BxY8RCJaN9ocKOa1wysB51qrTQ6gvYGnE O228VR5jaiPA+me8x0w0KFKvVg== X-Google-Smtp-Source: ADFU+vu4Ju4cnrlV+IexuXJyNh/PCtREbmOSOSyiTD1EiRhwfG63ahMoAve8PpoLNkpOC43985mlfA== X-Received: by 2002:a81:66d6:: with SMTP id a205mr5562185ywc.39.1583537710155; Fri, 06 Mar 2020 15:35:10 -0800 (PST) Received: from pryzbyj (charmander.telsasoft.com. [50.244.222.1]) by smtp.gmail.com with ESMTPSA id m128sm10903763ywc.89.2020.03.06.15.35.08 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Fri, 06 Mar 2020 15:35:08 -0800 (PST) Received: by pryzbyj (Postfix, from userid 1000) id 73DE98007F2; Fri, 6 Mar 2020 17:35:07 -0600 (CST) Date: Fri, 6 Mar 2020 17:35:07 -0600 From: Justin Pryzby To: Alvaro Herrera Cc: David Steele , Fabien COELHO , pgsql-hackers@postgresql.org, "Bossart, Nathan" , Thomas Munro Subject: Re: pg_ls_tmpdir to show directories and shared filesets Message-ID: <20200306233507.GN684@telsasoft.com> References: <20200303200117.GI684@telsasoft.com> <20200303202313.GA28076@alvherre.pgsql> <20200305161838.GJ684@telsasoft.com> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="jKBxcB1XkHIR0Eqt" Content-Disposition: inline In-Reply-To: <20200305161838.GJ684@telsasoft.com> User-Agent: Mutt/1.5.24 (2015-08-30) List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk --jKBxcB1XkHIR0Eqt Content-Type: text/plain; charset=us-ascii Content-Disposition: inline On Thu, Mar 05, 2020 at 10:18:38AM -0600, Justin Pryzby wrote: > I'm not sure if prefer the 0002 patch alone (which recurses into dirs all at > once during the initial call), or 0002+3+4, which incrementally reads the dirs > on each call (but requires keeping dirs opened). I fixed an issue that leading dirs were being shown which should not have been, which was easier in the 0004 patch, so squished. And fixed a bug that "special" files weren't excluded, and "missing_ok" wasn't effective. > > I don't understand what purpose is served by having pg_ls_waldir() hide > > directories. > > We could talk about whether the other functions should show dirs, if it's worth > breaking their return type. Or if they should show hidden or special files, > which doesn't require breaking the return. But until then I am to leave the > behavior alone. I don't see why any of the functions would exclude dirs, but ls_tmpdir deserves to be fixed since core postgres dynamically creates dirs there. Also ... I accidentally changed the behavior: master not only doesn't decend into dirs, it hides them - that was my original complaint. I propose to *also* change at least tmpdir and logdir to show dirs, but don't decend. I left waldir alone for now. Since v12 ls_tmpdir and since v10 logdir and waldir exclude dirs, I think we should backpatch documentation to say so. ISTM pg_ls_tmpdir and ls_logdir should be called with missing_ok=true, since they're not created until they're used. -- Justin --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0001-BUG-in-errmsg.patch" From a5b9a03445d1c768662cafebd8ab3bd7a62890aa Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 27 Dec 2019 23:34:14 -0600 Subject: [PATCH v7 1/6] BUG: in errmsg Note there's two changes here. Should backpatch to v12, where pg_ls_tmpdir was added. --- src/backend/utils/adt/genfile.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/backend/utils/adt/genfile.c b/src/backend/utils/adt/genfile.c index 3741b87486..897b11a77d 100644 --- a/src/backend/utils/adt/genfile.c +++ b/src/backend/utils/adt/genfile.c @@ -590,7 +590,7 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) if (stat(path, &attrib) < 0) ereport(ERROR, (errcode_for_file_access(), - errmsg("could not stat directory \"%s\": %m", dir))); + errmsg("could not stat file \"%s\": %m", path))); /* Ignore anything but regular files */ if (!S_ISREG(attrib.st_mode)) -- 2.17.0 --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0002-Document-historic-behavior-about-hiding-directori.patch" From 6ea85ec0a267930320b8454a33bca368a8544a2d Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 6 Mar 2020 16:50:07 -0600 Subject: [PATCH v7 2/6] Document historic behavior about hiding directories and special files Should backpatch to v10: tmpdir, waldir and archive_statusdir --- doc/src/sgml/func.sgml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/doc/src/sgml/func.sgml b/doc/src/sgml/func.sgml index 323366feb6..4c0ea5ab3f 100644 --- a/doc/src/sgml/func.sgml +++ b/doc/src/sgml/func.sgml @@ -21450,6 +21450,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); (mtime) of each file in the log directory. By default, only superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. + Filenames beginning with a dot, directories, and other special files are not shown. @@ -21461,6 +21462,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); default only superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. + Filenames beginning with a dot, directories, and other special files are not shown. @@ -21473,6 +21475,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. + Filenames beginning with a dot, directories, and other special files are not shown. -- 2.17.0 --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0003-Document-historic-behavior-about-hiding-directori.patch" From 5250d637493627f1ff3587bc73dd598bc1ca3ffc Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 6 Mar 2020 17:12:04 -0600 Subject: [PATCH v7 3/6] Document historic behavior about hiding directories and special files Should backpatch to v12: tmpdir --- doc/src/sgml/func.sgml | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/src/sgml/func.sgml b/doc/src/sgml/func.sgml index 4c0ea5ab3f..fc4d7f0f78 100644 --- a/doc/src/sgml/func.sgml +++ b/doc/src/sgml/func.sgml @@ -21489,6 +21489,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); default only superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. + Filenames beginning with a dot, directories, and other special files are not shown. -- 2.17.0 --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0004-pg_ls_tmpdir-to-show-directories.patch" From 8d00a1c80679d9a754a3988786e70c0385b46b30 Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Sat, 14 Dec 2019 16:22:15 -0600 Subject: [PATCH v7 4/6] pg_ls_tmpdir to show directories See also 9cd92d1a33699f86aa53d44ab04cc3eb50c18d11 --- doc/src/sgml/func.sgml | 14 +-- src/backend/utils/adt/genfile.c | 167 +++++++++++++++++++++++--------- src/include/catalog/pg_proc.dat | 8 +- 3 files changed, 134 insertions(+), 55 deletions(-) diff --git a/doc/src/sgml/func.sgml b/doc/src/sgml/func.sgml index fc4d7f0f78..15f4908924 100644 --- a/doc/src/sgml/func.sgml +++ b/doc/src/sgml/func.sgml @@ -21382,8 +21382,9 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); setof record - List the name, size, and last modification time of files in the - temporary directory for tablespace. If + For the temporary directory for tablespace, + list each file's name, size, last modification time, and boolean + indicating if it is a directory. Directories are shown recursively. If tablespace is not provided, the pg_default tablespace is used. Access is granted to members of the pg_monitor role and may be @@ -21482,14 +21483,15 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); pg_ls_tmpdir - pg_ls_tmpdir returns the name, size, and last modified - time (mtime) of each file in the temporary file directory for the specified - tablespace. If tablespace is + pg_ls_tmpdir lists each file in the temporary file + directory for the specified tablespace, along with + its size, last modified time (mtime) and boolean indicating if it is a + directory. Directories are used for temporary files used by parallel + processes, and are shown recursively. If tablespace is not provided, the pg_default tablespace is used. By default only superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. - Filenames beginning with a dot, directories, and other special files are not shown. diff --git a/src/backend/utils/adt/genfile.c b/src/backend/utils/adt/genfile.c index 897b11a77d..0207ac6be8 100644 --- a/src/backend/utils/adt/genfile.c +++ b/src/backend/utils/adt/genfile.c @@ -35,11 +35,23 @@ #include "utils/syscache.h" #include "utils/timestamp.h" +enum dir_action { + DIR_HIDE, + DIR_ONLY, + DIR_DESCEND, +}; + typedef struct { - char *location; - DIR *dirdesc; + /* Stack of opened dirs */ + List *location; + List *dirdesc; bool include_dot_dirs; + + /* Used in ls_dir_files: */ + enum dir_action dir_action; + char *path; + struct stat stat; } directory_fctx; @@ -469,10 +481,9 @@ pg_ls_dir(PG_FUNCTION_ARGS) oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx); fctx = palloc(sizeof(directory_fctx)); - fctx->location = convert_and_check_filename(PG_GETARG_TEXT_PP(0)); - + fctx->location = lappend(NIL, convert_and_check_filename(PG_GETARG_TEXT_PP(0))); + fctx->dirdesc = lappend(NIL, AllocateDir(linitial(fctx->location))); fctx->include_dot_dirs = include_dot_dirs; - fctx->dirdesc = AllocateDir(fctx->location); if (!fctx->dirdesc) { @@ -485,7 +496,7 @@ pg_ls_dir(PG_FUNCTION_ARGS) ereport(ERROR, (errcode_for_file_access(), errmsg("could not open directory \"%s\": %m", - fctx->location))); + (char*)linitial(fctx->location)))); } funcctx->user_fctx = fctx; MemoryContextSwitchTo(oldcontext); @@ -494,7 +505,7 @@ pg_ls_dir(PG_FUNCTION_ARGS) funcctx = SRF_PERCALL_SETUP(); fctx = (directory_fctx *) funcctx->user_fctx; - while ((de = ReadDir(fctx->dirdesc, fctx->location)) != NULL) + while ((de = ReadDir(linitial(fctx->dirdesc), linitial(fctx->location))) != NULL) { if (!fctx->include_dot_dirs && (strcmp(de->d_name, ".") == 0 || @@ -504,7 +515,9 @@ pg_ls_dir(PG_FUNCTION_ARGS) SRF_RETURN_NEXT(funcctx, CStringGetTextDatum(de->d_name)); } - FreeDir(fctx->dirdesc); + FreeDir(linitial(fctx->dirdesc)); + list_free(fctx->dirdesc); + list_free_deep(fctx->location); SRF_RETURN_DONE(funcctx); } @@ -522,12 +535,84 @@ pg_ls_dir_1arg(PG_FUNCTION_ARGS) return pg_ls_dir(fcinfo); } -/* Generic function to return a directory listing of files */ +/* + * Update fctx->path and stat with next filename. + * Directories are descended into. + * The current dir to read from is at fctx[fctx->depth]. + */ +static int +populate_paths(directory_fctx *fctx, FuncCallContext *funcctx) +{ + struct dirent *de; + + for (;;) + { + char path[MAXPGPATH]; + DIR *dirdesc = llast(fctx->dirdesc); + char *location = llast(fctx->location); + + Assert(list_length(fctx->dirdesc) == list_length(fctx->location)); + + if ((de = ReadDir(dirdesc, location)) == NULL) + { + /* + * Read to the end of the dir on the top of the stack, now move to + * the next dir. + */ + if (list_length(fctx->dirdesc) == 1) + return 0; + FreeDir(llast(fctx->dirdesc)); + fctx->dirdesc = list_delete_last(fctx->dirdesc); + pfree(location); + fctx->location = list_delete_last(fctx->location); + continue; + } + + /* Skip hidden files */ + if (de->d_name[0] == '.') + continue; + + /* Get the file info */ + snprintf(path, sizeof(path), "%s/%s", location, de->d_name); + if (stat(path, &fctx->stat) < 0) + ereport(ERROR, + (errcode_for_file_access(), + errmsg("could not stat file \"%s\": %m", path))); + + /* Ignore anything but regular files, or dirs, if requested */ + if (S_ISDIR(fctx->stat.st_mode)) + { + if (fctx->dir_action == DIR_HIDE) + continue; + else if (fctx->dir_action == DIR_DESCEND) + { + /* Reallocate location and dirdesc whenever descending */ + MemoryContext oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx); + fctx->location = lappend(fctx->location, pstrdup(path)); + fctx->dirdesc = lappend(fctx->dirdesc, AllocateDir(path)); + MemoryContextSwitchTo(oldcontext); + } + } else if (!S_ISREG(fctx->stat.st_mode)) + continue; + + /* Do not show the initial dir or slash */ + fctx->path = pstrdup(path + 1 + strlen(linitial(fctx->location))); + return 1; + } +} + +/* + * Generic function to return a directory listing of files + * + * if missing_ok, then fail silently if the dir doesn't exist, else error. + * + * if dir_action!=DIR_HIDE, then include a 4th column indicating whether path + * is a directory, and recurse if DIR_DESCEND. + */ static Datum -pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) +pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok, enum dir_action dir_action) { FuncCallContext *funcctx; - struct dirent *de; directory_fctx *fctx; if (SRF_IS_FIRSTCALL()) @@ -540,19 +625,24 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) fctx = palloc(sizeof(directory_fctx)); - tupdesc = CreateTemplateTupleDesc(3); + tupdesc = CreateTemplateTupleDesc(dir_action == DIR_HIDE ? 3 : 4); TupleDescInitEntry(tupdesc, (AttrNumber) 1, "name", TEXTOID, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 2, "size", INT8OID, -1, 0); TupleDescInitEntry(tupdesc, (AttrNumber) 3, "modification", TIMESTAMPTZOID, -1, 0); + if (dir_action != DIR_HIDE) + TupleDescInitEntry(tupdesc, (AttrNumber) 4, "isdir", + BOOLOID, -1, 0); + funcctx->tuple_desc = BlessTupleDesc(tupdesc); - fctx->location = pstrdup(dir); - fctx->dirdesc = AllocateDir(fctx->location); + fctx->location = lappend(NIL, pstrdup(dir)); + fctx->dirdesc = lappend(NIL, AllocateDir(dir)); + fctx->dir_action = dir_action; - if (!fctx->dirdesc) + if (!linitial(fctx->dirdesc)) { if (missing_ok && errno == ENOENT) { @@ -563,7 +653,7 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) ereport(ERROR, (errcode_for_file_access(), errmsg("could not open directory \"%s\": %m", - fctx->location))); + dir))); } funcctx->user_fctx = fctx; @@ -573,39 +663,26 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) funcctx = SRF_PERCALL_SETUP(); fctx = (directory_fctx *) funcctx->user_fctx; - while ((de = ReadDir(fctx->dirdesc, fctx->location)) != NULL) + if (populate_paths(fctx, funcctx)) { - Datum values[3]; - bool nulls[3]; - char path[MAXPGPATH * 2]; - struct stat attrib; + Datum values[4]; + bool nulls[4] = {0}; HeapTuple tuple; - /* Skip hidden files */ - if (de->d_name[0] == '.') - continue; - - /* Get the file info */ - snprintf(path, sizeof(path), "%s/%s", fctx->location, de->d_name); - if (stat(path, &attrib) < 0) - ereport(ERROR, - (errcode_for_file_access(), - errmsg("could not stat file \"%s\": %m", path))); - - /* Ignore anything but regular files */ - if (!S_ISREG(attrib.st_mode)) - continue; - - values[0] = CStringGetTextDatum(de->d_name); - values[1] = Int64GetDatum((int64) attrib.st_size); - values[2] = TimestampTzGetDatum(time_t_to_timestamptz(attrib.st_mtime)); - memset(nulls, 0, sizeof(nulls)); + values[0] = CStringGetTextDatum(fctx->path); + values[1] = Int64GetDatum((int64) fctx->stat.st_size); + values[2] = TimestampTzGetDatum(time_t_to_timestamptz(fctx->stat.st_mtime)); + if (dir_action != DIR_HIDE) + values[3] = BoolGetDatum(S_ISDIR(fctx->stat.st_mode)); tuple = heap_form_tuple(funcctx->tuple_desc, values, nulls); + pfree(fctx->path); SRF_RETURN_NEXT(funcctx, HeapTupleGetDatum(tuple)); } - FreeDir(fctx->dirdesc); + FreeDir(linitial(fctx->dirdesc)); + list_free(fctx->dirdesc); + list_free_deep(fctx->location); SRF_RETURN_DONE(funcctx); } @@ -613,14 +690,14 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok) Datum pg_ls_logdir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, Log_directory, false); + return pg_ls_dir_files(fcinfo, Log_directory, false, false); } /* Function to return the list of files in the WAL directory */ Datum pg_ls_waldir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, XLOGDIR, false); + return pg_ls_dir_files(fcinfo, XLOGDIR, false, DIR_HIDE); } /* @@ -638,7 +715,7 @@ pg_ls_tmpdir(FunctionCallInfo fcinfo, Oid tblspc) tblspc))); TempTablespacePath(path, tblspc); - return pg_ls_dir_files(fcinfo, path, true); + return pg_ls_dir_files(fcinfo, path, true, DIR_DESCEND); } /* @@ -667,5 +744,5 @@ pg_ls_tmpdir_1arg(PG_FUNCTION_ARGS) Datum pg_ls_archive_statusdir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, XLOGDIR "/archive_status", true); + return pg_ls_dir_files(fcinfo, XLOGDIR "/archive_status", true, false); } diff --git a/src/include/catalog/pg_proc.dat b/src/include/catalog/pg_proc.dat index 07a86c7b7b..0dbce4ba09 100644 --- a/src/include/catalog/pg_proc.dat +++ b/src/include/catalog/pg_proc.dat @@ -10739,13 +10739,13 @@ { oid => '5029', descr => 'list files in the pgsql_tmp directory', proname => 'pg_ls_tmpdir', procost => '10', prorows => '20', proretset => 't', provolatile => 'v', prorettype => 'record', proargtypes => '', - proallargtypes => '{text,int8,timestamptz}', proargmodes => '{o,o,o}', - proargnames => '{name,size,modification}', prosrc => 'pg_ls_tmpdir_noargs' }, + proallargtypes => '{text,int8,timestamptz,bool}', proargmodes => '{o,o,o,o}', + proargnames => '{name,size,modification,isdir}', prosrc => 'pg_ls_tmpdir_noargs' }, { oid => '5030', descr => 'list files in the pgsql_tmp directory', proname => 'pg_ls_tmpdir', procost => '10', prorows => '20', proretset => 't', provolatile => 'v', prorettype => 'record', proargtypes => 'oid', - proallargtypes => '{oid,text,int8,timestamptz}', proargmodes => '{i,o,o,o}', - proargnames => '{tablespace,name,size,modification}', + proallargtypes => '{oid,text,int8,timestamptz,bool}', proargmodes => '{i,o,o,o,o}', + proargnames => '{tablespace,name,size,modification,isdir}', prosrc => 'pg_ls_tmpdir_1arg' }, # hash partitioning constraint function -- 2.17.0 --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0005-Change-logdir-and-archive_statusdir-to-include-di.patch" From 30a6473462e84ae700fb63269bb5669c3d1925be Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Thu, 5 Mar 2020 15:17:28 -0600 Subject: [PATCH v7 5/6] Change logdir and archive_statusdir to include dirs.. *and* add a column indicating *whether* a path is a dir.. The previous commit changes to always *show* directories (and optionally recurse). XXX: also need to update docs for new column --- doc/src/sgml/func.sgml | 4 ++-- src/backend/utils/adt/genfile.c | 4 ++-- src/include/catalog/pg_proc.dat | 8 ++++---- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/doc/src/sgml/func.sgml b/doc/src/sgml/func.sgml index 15f4908924..2b920ebd12 100644 --- a/doc/src/sgml/func.sgml +++ b/doc/src/sgml/func.sgml @@ -21451,7 +21451,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); (mtime) of each file in the log directory. By default, only superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. - Filenames beginning with a dot, directories, and other special files are not shown. + Filenames beginning with a dot and special file types are not shown. @@ -21476,7 +21476,7 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup()); superusers and members of the pg_monitor role can use this function. Access may be granted to others using GRANT. - Filenames beginning with a dot, directories, and other special files are not shown. + Filenames beginning with a dot and special file types are not shown. diff --git a/src/backend/utils/adt/genfile.c b/src/backend/utils/adt/genfile.c index 0207ac6be8..9d99528aa5 100644 --- a/src/backend/utils/adt/genfile.c +++ b/src/backend/utils/adt/genfile.c @@ -690,7 +690,7 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok, enum Datum pg_ls_logdir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, Log_directory, false, false); + return pg_ls_dir_files(fcinfo, Log_directory, false, DIR_ONLY); } /* Function to return the list of files in the WAL directory */ @@ -744,5 +744,5 @@ pg_ls_tmpdir_1arg(PG_FUNCTION_ARGS) Datum pg_ls_archive_statusdir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, XLOGDIR "/archive_status", true, false); + return pg_ls_dir_files(fcinfo, XLOGDIR "/archive_status", true, DIR_ONLY); } diff --git a/src/include/catalog/pg_proc.dat b/src/include/catalog/pg_proc.dat index 0dbce4ba09..fdf86e1eaf 100644 --- a/src/include/catalog/pg_proc.dat +++ b/src/include/catalog/pg_proc.dat @@ -10723,8 +10723,8 @@ { oid => '3353', descr => 'list files in the log directory', proname => 'pg_ls_logdir', procost => '10', prorows => '20', proretset => 't', provolatile => 'v', prorettype => 'record', proargtypes => '', - proallargtypes => '{text,int8,timestamptz}', proargmodes => '{o,o,o}', - proargnames => '{name,size,modification}', prosrc => 'pg_ls_logdir' }, + proallargtypes => '{text,int8,timestamptz,bool}', proargmodes => '{o,o,o,o}', + proargnames => '{name,size,modification,isdir}', prosrc => 'pg_ls_logdir' }, { oid => '3354', descr => 'list of files in the WAL directory', proname => 'pg_ls_waldir', procost => '10', prorows => '20', proretset => 't', provolatile => 'v', prorettype => 'record', proargtypes => '', @@ -10733,8 +10733,8 @@ { oid => '5031', descr => 'list of files in the archive_status directory', proname => 'pg_ls_archive_statusdir', procost => '10', prorows => '20', proretset => 't', provolatile => 'v', prorettype => 'record', - proargtypes => '', proallargtypes => '{text,int8,timestamptz}', - proargmodes => '{o,o,o}', proargnames => '{name,size,modification}', + proargtypes => '', proallargtypes => '{text,int8,timestamptz,bool}', + proargmodes => '{o,o,o,o}', proargnames => '{name,size,modification,isdir}', prosrc => 'pg_ls_archive_statusdir' }, { oid => '5029', descr => 'list files in the pgsql_tmp directory', proname => 'pg_ls_tmpdir', procost => '10', prorows => '20', proretset => 't', -- 2.17.0 --jKBxcB1XkHIR0Eqt Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="v7-0006-Change-pg_ls_logdir-to-ignore-error-if-initial-to.patch" From 458da7d43d5dcd91a1345a3a25ecc07f3274dade Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Fri, 6 Mar 2020 17:23:51 -0600 Subject: [PATCH v7 6/6] Change pg_ls_logdir to ignore error if initial/top dir is missing --- src/backend/utils/adt/genfile.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/backend/utils/adt/genfile.c b/src/backend/utils/adt/genfile.c index 9d99528aa5..e15ad1827c 100644 --- a/src/backend/utils/adt/genfile.c +++ b/src/backend/utils/adt/genfile.c @@ -690,7 +690,7 @@ pg_ls_dir_files(FunctionCallInfo fcinfo, const char *dir, bool missing_ok, enum Datum pg_ls_logdir(PG_FUNCTION_ARGS) { - return pg_ls_dir_files(fcinfo, Log_directory, false, DIR_ONLY); + return pg_ls_dir_files(fcinfo, Log_directory, true, DIR_ONLY); } /* Function to return the list of files in the WAL directory */ -- 2.17.0 --jKBxcB1XkHIR0Eqt--