pg_ctl: Add idempotent option
authorPeter Eisentraut <peter_e@gmx.net>
Sun, 14 Apr 2013 03:42:42 +0000 (23:42 -0400)
committerPeter Eisentraut <peter_e@gmx.net>
Sun, 14 Apr 2013 03:42:42 +0000 (23:42 -0400)
This changes the behavior of the start and stop actions to exit
successfully if the server was already started or stopped.

This changes the default behavior of the start action:  Before, if the
server was already running, it would print a message and succeed.  Now,
that situation will result in an error.  When running in idempotent
mode, no message is printed and pg_ctl exits successfully.

It was considered to just make the idempotent behavior the default and
only option, but pg_upgrade needs the old behavior.

contrib/start-scripts/linux
doc/src/sgml/ref/pg_ctl-ref.sgml
src/bin/pg_ctl/pg_ctl.c

index b950cf512c3c519c1813f69af98a7a0ce7422769..03c6e503bc609d01b59cf9d2aeaa2658f48c703b 100644 (file)
@@ -84,17 +84,17 @@ case $1 in
    echo -n "Starting PostgreSQL: "
    test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
    test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
-   su - $PGUSER -c "$DAEMON -D '$PGDATA' &" >>$PGLOG 2>&1
+   su - $PGUSER -c "$DAEMON -I -D '$PGDATA' &" >>$PGLOG 2>&1
    echo "ok"
    ;;
   stop)
    echo -n "Stopping PostgreSQL: "
-   su - $PGUSER -c "$PGCTL stop -D '$PGDATA' -s -m fast"
+   su - $PGUSER -c "$PGCTL stop -I -D '$PGDATA' -s -m fast"
    echo "ok"
    ;;
   restart)
    echo -n "Restarting PostgreSQL: "
-   su - $PGUSER -c "$PGCTL stop -D '$PGDATA' -s -m fast -w"
+   su - $PGUSER -c "$PGCTL stop -I -D '$PGDATA' -s -m fast -w"
    test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
    test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
    su - $PGUSER -c "$DAEMON -D '$PGDATA' &" >>$PGLOG 2>&1
index 3107514901ce96463261596931b1721534ca9089..549730da6f9edd5aefb67973c5925aa1725d1cb9 100644 (file)
@@ -39,6 +39,7 @@ PostgreSQL documentation
    <arg choice="opt"><option>-o</option> <replaceable>options</replaceable></arg>
    <arg choice="opt"><option>-p</option> <replaceable>path</replaceable></arg>
    <arg choice="opt"><option>-c</option></arg>
+   <arg choice="opt"><option>-I</option></arg>
   </cmdsynopsis>
 
   <cmdsynopsis>
@@ -55,6 +56,7 @@ PostgreSQL documentation
        <arg choice="plain"><option>i[mmediate]</option></arg>
      </group>
    </arg>
+   <arg choice="opt"><option>-I</option></arg>
   </cmdsynopsis>
 
   <cmdsynopsis>
@@ -270,6 +272,25 @@ PostgreSQL documentation
       </listitem>
      </varlistentry>
 
+     <varlistentry>
+      <term><option>-I</option></term>
+      <term><option>--idempotent</option></term>
+      <listitem>
+       <para>
+        When used with the <literal>start</literal> or <literal>stop</literal>
+        actions, return exit code 0 if the server is already running or
+        stopped, respectively.  Otherwise, an error is raised and a nonzero
+        exit code is returned in these cases.
+       </para>
+
+       <para>
+        This option is useful for System-V-style init scripts, which require
+        the <literal>start</literal> and <literal>stop</literal> actions to be
+        idempotent.
+       </para>
+      </listitem>
+     </varlistentry>
+
      <varlistentry>
       <term><option>-l <replaceable class="parameter">filename</replaceable></option></term>
       <term><option>--log <replaceable class="parameter">filename</replaceable></option></term>
index 537d173e893b0a56d99e0015dd7764dc7c76c5af..a4e7922d687e2c67c5ed0898e3319ecb18c107c0 100644 (file)
@@ -85,6 +85,7 @@ static char *pg_config = NULL;
 static char *pgdata_opt = NULL;
 static char *post_opts = NULL;
 static const char *progname;
+static bool idempotent = false;
 static char *log_file = NULL;
 static char *exec_path = NULL;
 static char *register_servicename = "PostgreSQL";      /* FIXME: + version ID? */
@@ -773,9 +774,15 @@ do_start(void)
    {
        old_pid = get_pgpid();
        if (old_pid != 0)
-           write_stderr(_("%s: another server might be running; "
-                          "trying to start server anyway\n"),
-                        progname);
+       {
+           if (idempotent)
+               exit(0);
+           else
+           {
+               write_stderr(_("%s: another server might be running\n"), progname);
+               exit(1);
+           }
+       }
    }
 
    read_post_opts();
@@ -859,6 +866,8 @@ do_stop(void)
 
    if (pid == 0)               /* no pid file */
    {
+       if (idempotent)
+           exit(0);
        write_stderr(_("%s: PID file \"%s\" does not exist\n"), progname, pid_file);
        write_stderr(_("Is server running?\n"));
        exit(1);
@@ -1763,9 +1772,9 @@ do_help(void)
    printf(_("%s is a utility to initialize, start, stop, or control a PostgreSQL server.\n\n"), progname);
    printf(_("Usage:\n"));
    printf(_("  %s init[db]               [-D DATADIR] [-s] [-o \"OPTIONS\"]\n"), progname);
-   printf(_("  %s start   [-w] [-t SECS] [-D DATADIR] [-s] [-l FILENAME] [-o \"OPTIONS\"]\n"), progname);
-   printf(_("  %s stop    [-W] [-t SECS] [-D DATADIR] [-s] [-m SHUTDOWN-MODE]\n"), progname);
-   printf(_("  %s restart [-w] [-t SECS] [-D DATADIR] [-s] [-m SHUTDOWN-MODE]\n"
+   printf(_("  %s start   [-w] [-t SECS] [-D DATADIR] [-s] [-I] [-l FILENAME] [-o \"OPTIONS\"]\n"), progname);
+   printf(_("  %s stop    [-W] [-t SECS] [-D DATADIR] [-s] [-I] [-m SHUTDOWN-MODE]\n"), progname);
+   printf(_("  %s restart [-w] [-t SECS] [-D DATADIR] [-s]      [-m SHUTDOWN-MODE]\n"
             "                 [-o \"OPTIONS\"]\n"), progname);
    printf(_("  %s reload  [-D DATADIR] [-s]\n"), progname);
    printf(_("  %s status  [-D DATADIR]\n"), progname);
@@ -1798,6 +1807,8 @@ do_help(void)
    printf(_("  -o OPTIONS             command line options to pass to postgres\n"
     "                         (PostgreSQL server executable) or initdb\n"));
    printf(_("  -p PATH-TO-POSTGRES    normally not necessary\n"));
+   printf(_("\nOptions for start or stop:\n"));
+   printf(_("  -I, --idempotent       don't error if server already running or stopped\n"));
    printf(_("\nOptions for stop, restart, or promote:\n"));
    printf(_("  -m, --mode=MODE        MODE can be \"smart\", \"fast\", or \"immediate\"\n"));
 
@@ -1980,6 +1991,7 @@ main(int argc, char **argv)
        {"silent", no_argument, NULL, 's'},
        {"timeout", required_argument, NULL, 't'},
        {"core-files", no_argument, NULL, 'c'},
+       {"idempotent", no_argument, NULL, 'I'},
        {NULL, 0, NULL, 0}
    };
 
@@ -2045,7 +2057,7 @@ main(int argc, char **argv)
    /* process command-line options */
    while (optind < argc)
    {
-       while ((c = getopt_long(argc, argv, "cD:l:m:N:o:p:P:sS:t:U:wW", long_options, &option_index)) != -1)
+       while ((c = getopt_long(argc, argv, "cD:Il:m:N:o:p:P:sS:t:U:wW", long_options, &option_index)) != -1)
        {
            switch (c)
            {
@@ -2071,6 +2083,9 @@ main(int argc, char **argv)
                                 pgdata_D);
                        break;
                    }
+               case 'I':
+                   idempotent = true;
+                   break;
                case 'l':
                    log_file = pg_strdup(optarg);
                    break;