Age Owner Branch data TLA Line data Source code
1 : : /*-------------------------------------------------------------------------
2 : : *
3 : : * dropuser
4 : : *
5 : : * Portions Copyright (c) 1996-2025, PostgreSQL Global Development Group
6 : : * Portions Copyright (c) 1994, Regents of the University of California
7 : : *
8 : : * src/bin/scripts/dropuser.c
9 : : *
10 : : *-------------------------------------------------------------------------
11 : : */
12 : :
13 : : #include "postgres_fe.h"
14 : : #include "common.h"
15 : : #include "common/logging.h"
16 : : #include "common/string.h"
17 : : #include "fe_utils/option_utils.h"
18 : : #include "fe_utils/string_utils.h"
19 : :
20 : :
21 : : static void help(const char *progname);
22 : :
23 : :
24 : : int
8208 peter_e@gmx.net 25 :CBC 5 : main(int argc, char *argv[])
26 : : {
27 : : static int if_exists = 0;
28 : :
29 : : static struct option long_options[] = {
30 : : {"host", required_argument, NULL, 'h'},
31 : : {"port", required_argument, NULL, 'p'},
32 : : {"username", required_argument, NULL, 'U'},
33 : : {"no-password", no_argument, NULL, 'w'},
34 : : {"password", no_argument, NULL, 'W'},
35 : : {"echo", no_argument, NULL, 'e'},
36 : : {"interactive", no_argument, NULL, 'i'},
37 : : {"if-exists", no_argument, &if_exists, 1},
38 : : {NULL, 0, NULL, 0}
39 : : };
40 : :
41 : : const char *progname;
42 : : int optindex;
43 : : int c;
44 : :
45 : 5 : char *dropuser = NULL;
46 : 5 : char *host = NULL;
47 : 5 : char *port = NULL;
48 : 5 : char *username = NULL;
6036 49 : 5 : enum trivalue prompt_password = TRI_DEFAULT;
50 : : ConnParams cparams;
8208 51 : 5 : bool echo = false;
52 : 5 : bool interactive = false;
53 : :
54 : : PQExpBufferData sql;
55 : :
56 : : PGconn *conn;
57 : : PGresult *result;
58 : :
2350 peter@eisentraut.org 59 : 5 : pg_logging_init(argv[0]);
8208 peter_e@gmx.net 60 : 5 : progname = get_progname(argv[0]);
6113 61 : 5 : set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pgscripts"));
62 : :
8208 63 : 5 : handle_help_version_opts(argc, argv, "dropuser", help);
64 : :
999 peter@eisentraut.org 65 [ + + ]: 3 : while ((c = getopt_long(argc, argv, "eh:ip:U:wW", long_options, &optindex)) != -1)
66 : : {
8208 peter_e@gmx.net 67 [ - - - - : 1 : switch (c)
- - - -
+ ]
68 : : {
999 peter@eisentraut.org 69 :UBC 0 : case 'e':
70 : 0 : echo = true;
71 : 0 : break;
8208 peter_e@gmx.net 72 : 0 : case 'h':
4712 bruce@momjian.us 73 : 0 : host = pg_strdup(optarg);
8208 peter_e@gmx.net 74 : 0 : break;
999 peter@eisentraut.org 75 : 0 : case 'i':
76 : 0 : interactive = true;
77 : 0 : break;
8208 peter_e@gmx.net 78 : 0 : case 'p':
4712 bruce@momjian.us 79 : 0 : port = pg_strdup(optarg);
8208 peter_e@gmx.net 80 : 0 : break;
81 : 0 : case 'U':
4712 bruce@momjian.us 82 : 0 : username = pg_strdup(optarg);
8208 peter_e@gmx.net 83 : 0 : break;
6036 84 : 0 : case 'w':
85 : 0 : prompt_password = TRI_NO;
86 : 0 : break;
8208 87 : 0 : case 'W':
6036 88 : 0 : prompt_password = TRI_YES;
8208 89 : 0 : break;
5121 rhaas@postgresql.org 90 : 0 : case 0:
91 : : /* this covers the long options */
92 : 0 : break;
8208 peter_e@gmx.net 93 :CBC 1 : default:
94 : : /* getopt_long already emitted a complaint */
1247 tgl@sss.pgh.pa.us 95 : 1 : pg_log_error_hint("Try \"%s --help\" for more information.", progname);
8208 peter_e@gmx.net 96 : 1 : exit(1);
97 : : }
98 : : }
99 : :
100 [ - + - ]: 2 : switch (argc - optind)
101 : : {
8208 peter_e@gmx.net 102 :UBC 0 : case 0:
103 : 0 : break;
8208 peter_e@gmx.net 104 :CBC 2 : case 1:
105 : 2 : dropuser = argv[optind];
106 : 2 : break;
8208 peter_e@gmx.net 107 :UBC 0 : default:
2350 peter@eisentraut.org 108 : 0 : pg_log_error("too many command-line arguments (first is \"%s\")",
109 : : argv[optind + 1]);
1247 tgl@sss.pgh.pa.us 110 : 0 : pg_log_error_hint("Try \"%s --help\" for more information.", progname);
8208 peter_e@gmx.net 111 : 0 : exit(1);
112 : : }
113 : :
8208 peter_e@gmx.net 114 [ - + ]:CBC 2 : if (dropuser == NULL)
115 : : {
4960 peter_e@gmx.net 116 [ # # ]:UBC 0 : if (interactive)
117 : : {
1829 tgl@sss.pgh.pa.us 118 : 0 : dropuser = simple_prompt("Enter name of role to drop: ", true);
119 : : }
120 : : else
121 : : {
2350 peter@eisentraut.org 122 : 0 : pg_log_error("missing required argument role name");
1247 tgl@sss.pgh.pa.us 123 : 0 : pg_log_error_hint("Try \"%s --help\" for more information.", progname);
4960 peter_e@gmx.net 124 : 0 : exit(1);
125 : : }
126 : : }
127 : :
8208 peter_e@gmx.net 128 [ - + ]:CBC 2 : if (interactive)
129 : : {
7327 tgl@sss.pgh.pa.us 130 :UBC 0 : printf(_("Role \"%s\" will be permanently removed.\n"), dropuser);
6924 peter_e@gmx.net 131 [ # # ]: 0 : if (!yesno_prompt("Are you sure?"))
8208 132 : 0 : exit(0);
133 : : }
134 : :
1783 tgl@sss.pgh.pa.us 135 :CBC 2 : cparams.dbname = NULL; /* this program lacks any dbname option... */
136 : 2 : cparams.pghost = host;
137 : 2 : cparams.pgport = port;
138 : 2 : cparams.pguser = username;
139 : 2 : cparams.prompt_password = prompt_password;
140 : 2 : cparams.override_dbname = NULL;
141 : :
142 : 2 : conn = connectMaintenanceDatabase(&cparams, progname, echo);
143 : :
8208 peter_e@gmx.net 144 : 2 : initPQExpBuffer(&sql);
4226 145 : 4 : appendPQExpBuffer(&sql, "DROP ROLE %s%s;",
208 andres@anarazel.de 146 [ - + ]: 2 : (if_exists ? "IF EXISTS " : ""),
147 : : fmtIdEnc(dropuser, PQclientEncoding(conn)));
148 : :
8208 peter_e@gmx.net 149 [ - + ]: 2 : if (echo)
4226 peter_e@gmx.net 150 :UBC 0 : printf("%s\n", sql.data);
8208 peter_e@gmx.net 151 :CBC 2 : result = PQexec(conn, sql.data);
152 : :
153 [ + + ]: 2 : if (PQresultStatus(result) != PGRES_COMMAND_OK)
154 : : {
2350 peter@eisentraut.org 155 : 1 : pg_log_error("removal of role \"%s\" failed: %s",
156 : : dropuser, PQerrorMessage(conn));
8208 peter_e@gmx.net 157 : 1 : PQfinish(conn);
158 : 1 : exit(1);
159 : : }
160 : :
7040 bruce@momjian.us 161 : 1 : PQclear(result);
8208 peter_e@gmx.net 162 : 1 : PQfinish(conn);
163 : 1 : exit(0);
164 : : }
165 : :
166 : :
167 : : static void
168 : 1 : help(const char *progname)
169 : : {
7281 170 : 1 : printf(_("%s removes a PostgreSQL role.\n\n"), progname);
8208 171 : 1 : printf(_("Usage:\n"));
7281 172 : 1 : printf(_(" %s [OPTION]... [ROLENAME]\n"), progname);
8208 173 : 1 : printf(_("\nOptions:\n"));
8123 bruce@momjian.us 174 : 1 : printf(_(" -e, --echo show the commands being sent to the server\n"));
4960 peter_e@gmx.net 175 : 1 : printf(_(" -i, --interactive prompt before deleting anything, and prompt for\n"
176 : : " role name if not specified\n"));
4828 177 : 1 : printf(_(" -V, --version output version information, then exit\n"));
5121 rhaas@postgresql.org 178 : 1 : printf(_(" --if-exists don't report error if user doesn't exist\n"));
4828 peter_e@gmx.net 179 : 1 : printf(_(" -?, --help show this help, then exit\n"));
6037 180 : 1 : printf(_("\nConnection options:\n"));
8123 bruce@momjian.us 181 : 1 : printf(_(" -h, --host=HOSTNAME database server host or socket directory\n"));
8208 peter_e@gmx.net 182 : 1 : printf(_(" -p, --port=PORT database server port\n"));
183 : 1 : printf(_(" -U, --username=USERNAME user name to connect as (not the one to drop)\n"));
6036 184 : 1 : printf(_(" -w, --no-password never prompt for password\n"));
6479 tgl@sss.pgh.pa.us 185 : 1 : printf(_(" -W, --password force password prompt\n"));
2017 peter@eisentraut.org 186 : 1 : printf(_("\nReport bugs to <%s>.\n"), PACKAGE_BUGREPORT);
187 : 1 : printf(_("%s home page: <%s>\n"), PACKAGE_NAME, PACKAGE_URL);
8208 peter_e@gmx.net 188 : 1 : }
|