Added 'remove user' to client API. New functions are
debugcmd.c : telnetdRemoveUser adminusers.c : admin_remove_user Also renamed admin_test_user to admin_search_user .
This commit is contained in:
parent
3357748aad
commit
ca3638ae2c
@ -18,6 +18,7 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#define _XOPEN_SOURCE
|
||||
#include <unistd.h>
|
||||
#include <crypt.h>
|
||||
@ -48,7 +49,15 @@ static int admin_init = 0;
|
||||
static char *ADMIN_ERR_NOMEM = "Out of memory";
|
||||
static char *ADMIN_ERR_FILEOPEN = "Unable to create password file";
|
||||
static char *ADMIN_ERR_DUPLICATE = "Duplicate username specified";
|
||||
static char *ADMIN_ERR_USERNOTFOUND = "User not found";
|
||||
static char *ADMIN_ERR_AUTHENTICATION = "Authentication failed";
|
||||
static char *ADMIN_ERR_FILEAPPEND = "Unable to append to password file";
|
||||
static char *ADMIN_ERR_PWDFILEOPEN = "Failed to open password file";
|
||||
static char *ADMIN_ERR_TMPFILEOPEN = "Failed to open temporary password file";
|
||||
static char *ADMIN_ERR_PWDFILEACCESS = "Failed to access password file";
|
||||
static char *ADMIN_SUCCESS = NULL;
|
||||
|
||||
static const int LINELEN=80;
|
||||
|
||||
/**
|
||||
* Admin Users initialisation
|
||||
@ -150,7 +159,7 @@ char fname[1024], *home, *cpasswd;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to create password file %s.\n",
|
||||
fname);
|
||||
return ADMIN_ERR_FILEOPEN;
|
||||
return ADMIN_ERR_PWDFILEOPEN;
|
||||
}
|
||||
fclose(fp);
|
||||
}
|
||||
@ -169,9 +178,145 @@ char fname[1024], *home, *cpasswd;
|
||||
}
|
||||
fprintf(fp, "%s:%s\n", uname, cpasswd);
|
||||
fclose(fp);
|
||||
return NULL;
|
||||
return ADMIN_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Remove maxscale user from in-memory structure and from password file
|
||||
*
|
||||
* @param uname Name of the new user
|
||||
* @param passwd Password for the new user
|
||||
* @return NULL on success or an error string on failure
|
||||
*/
|
||||
char* admin_remove_user(
|
||||
char* uname,
|
||||
char* passwd)
|
||||
{
|
||||
FILE* fp;
|
||||
FILE* fp_tmp;
|
||||
char fname[1024];
|
||||
char fname_tmp[1024];
|
||||
char* home;
|
||||
char fusr[LINELEN];
|
||||
char fpwd[LINELEN];
|
||||
char line[LINELEN];
|
||||
fpos_t rpos;
|
||||
|
||||
if (!admin_search_user(uname)) {
|
||||
skygw_log_write(NULL,
|
||||
LOGFILE_MESSAGE,
|
||||
"Couldn't find user %s. Removing user failed", uname);
|
||||
return ADMIN_ERR_USERNOTFOUND;
|
||||
}
|
||||
|
||||
if (admin_verify(uname, passwd) == 0) {
|
||||
skygw_log_write(NULL,
|
||||
LOGFILE_MESSAGE,
|
||||
"Authentication failed, wrong user/password combination.\n"
|
||||
"Removing user failed");
|
||||
return ADMIN_ERR_AUTHENTICATION;
|
||||
}
|
||||
|
||||
/** Remove user from in-memory structure */
|
||||
users_delete(users, uname);
|
||||
|
||||
/**
|
||||
* Open passwd file and remove user from the file.
|
||||
*/
|
||||
if ((home = getenv("MAXSCALE_HOME")) != NULL) {
|
||||
sprintf(fname, "%s/etc/passwd", home);
|
||||
sprintf(fname_tmp, "%s/etc/passwd_tmp", home);
|
||||
} else {
|
||||
sprintf(fname, "/usr/local/skysql/MaxScale/etc/passwd");
|
||||
sprintf(fname_tmp, "/usr/local/skysql/MaxScale/etc/passwd_tmp");
|
||||
}
|
||||
/**
|
||||
* Rewrite passwd file from memory.
|
||||
*/
|
||||
if ((fp = fopen(fname, "r")) == NULL)
|
||||
{
|
||||
int err = errno;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to open password file %s : errno %d.\n"
|
||||
"Removing user from file failed; it must be done manually.",
|
||||
fname,
|
||||
err);
|
||||
return ADMIN_ERR_PWDFILEOPEN;
|
||||
}
|
||||
/**
|
||||
* Open temporary passwd file.
|
||||
*/
|
||||
if ((fp_tmp = fopen(fname_tmp, "w")) == NULL)
|
||||
{
|
||||
int err = errno;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to open tmp file %s : errno %d.\n"
|
||||
"Removing user from passwd file failed; "
|
||||
"it must be done manually.",
|
||||
fname_tmp,
|
||||
err);
|
||||
fclose(fp);
|
||||
return ADMIN_ERR_TMPFILEOPEN;
|
||||
}
|
||||
|
||||
/**
|
||||
* Scan passwd and copy all but matching lines to temp file.
|
||||
*/
|
||||
if (fgetpos(fp, &rpos) != 0) {
|
||||
int err = errno;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to process passwd file %s : errno %d.\n"
|
||||
"Removing user from file failed, and must be done manually.",
|
||||
fname,
|
||||
err);
|
||||
return ADMIN_ERR_PWDFILEACCESS;
|
||||
}
|
||||
|
||||
while (fscanf(fp, "%[^:]:%s\n", fusr, fpwd) == 2)
|
||||
{
|
||||
/**
|
||||
* Compare username what was found from passwd file.
|
||||
* Unmatching lines are copied to tmp file.
|
||||
*/
|
||||
if (strncmp(uname, fusr, strlen(uname)+1) != 0) {
|
||||
fsetpos(fp, &rpos); /** one step back */
|
||||
fgets(line, LINELEN, fp);
|
||||
fputs(line, fp_tmp);
|
||||
}
|
||||
|
||||
if (fgetpos(fp, &rpos) != 0) {
|
||||
int err = errno;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to process passwd file %s : errno %d.\n"
|
||||
"Removing user from file failed, and must be "
|
||||
"done manually.",
|
||||
fname,
|
||||
err);
|
||||
return ADMIN_ERR_PWDFILEACCESS;
|
||||
}
|
||||
}
|
||||
fclose(fp);
|
||||
/**
|
||||
* Replace original passwd file with new.
|
||||
*/
|
||||
if (rename(fname_tmp, fname)) {
|
||||
int err = errno;
|
||||
skygw_log_write(NULL, LOGFILE_ERROR,
|
||||
"Unable to rename new passwd file %s : errno %d.\n"
|
||||
"Rename it to %s manually.",
|
||||
fname_tmp,
|
||||
err,
|
||||
fname);
|
||||
return ADMIN_ERR_PWDFILEACCESS;
|
||||
}
|
||||
|
||||
fclose(fp_tmp);
|
||||
return ADMIN_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Check for existance of the user
|
||||
*
|
||||
@ -179,7 +324,7 @@ char fname[1024], *home, *cpasswd;
|
||||
* @return Non-zero if the user exists
|
||||
*/
|
||||
int
|
||||
admin_test_user(char *user)
|
||||
admin_search_user(char *user)
|
||||
{
|
||||
initialise();
|
||||
if (users == NULL)
|
||||
|
@ -36,5 +36,7 @@ extern char *admin_add_user(char *, char *);
|
||||
extern int admin_test_user(char *);
|
||||
extern void dcb_PrintAdminUsers(DCB *dcb);
|
||||
|
||||
char* admin_remove_user(char* uname, char* passwd);
|
||||
|
||||
|
||||
#endif
|
||||
|
@ -81,7 +81,7 @@ static void telnetdShowUsers(DCB *);
|
||||
* The subcommands of the show command
|
||||
*/
|
||||
struct subcommand showoptions[] = {
|
||||
{ "dcbs", 0, dprintAllDCBs, "Show all descriptor control blocks (network connections)",
|
||||
{ "dcbs", 0, dprintAllDCBs, "Show all descriptor control blocks (network connections)",
|
||||
{0, 0, 0} },
|
||||
{ "dcb", 1, dprintDCB, "Show a single descriptor control block e.g. show dcb 0x493340",
|
||||
{ARG_TYPE_ADDRESS, 0, 0} },
|
||||
@ -191,6 +191,25 @@ struct subcommand addoptions[] = {
|
||||
{0, 0, 0} }
|
||||
};
|
||||
|
||||
|
||||
static void telnetdRemoveUser(DCB *, char *, char *);
|
||||
/**
|
||||
* The subcommands of the remove command
|
||||
*/
|
||||
struct subcommand removeoptions[] = {
|
||||
{
|
||||
"user",
|
||||
2,
|
||||
telnetdRemoveUser,
|
||||
"Remove existing maxscale user. Example : remove user john johnpwd",
|
||||
{ARG_TYPE_STRING, ARG_TYPE_STRING, 0}
|
||||
},
|
||||
{
|
||||
NULL, 0, NULL, NULL, {0, 0, 0}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* The debug command table
|
||||
*/
|
||||
@ -200,6 +219,7 @@ static struct {
|
||||
} cmds[] = {
|
||||
{ "add", addoptions },
|
||||
{ "clear", clearoptions },
|
||||
{ "remove", removeoptions },
|
||||
{ "restart", restartoptions },
|
||||
{ "set", setoptions },
|
||||
{ "show", showoptions },
|
||||
@ -513,7 +533,7 @@ reload_config(DCB *dcb)
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a new admin user
|
||||
* Add a new maxscale admin user
|
||||
*
|
||||
* @param dcb The DCB for messages
|
||||
* @param user The user name
|
||||
@ -524,7 +544,7 @@ telnetdAddUser(DCB *dcb, char *user, char *passwd)
|
||||
{
|
||||
char *err;
|
||||
|
||||
if (admin_test_user(user))
|
||||
if (admin_search_user(user))
|
||||
{
|
||||
dcb_printf(dcb, "User %s already exists.\n", user);
|
||||
return;
|
||||
@ -535,6 +555,39 @@ char *err;
|
||||
dcb_printf(dcb, "Failed to add new user. %s\n", err);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Remove a maxscale admin user
|
||||
*
|
||||
* @param dcb The DCB for messages
|
||||
* @param user The user name
|
||||
* @param passwd The Password of the user
|
||||
*/
|
||||
static void telnetdRemoveUser(
|
||||
DCB* dcb,
|
||||
char* user,
|
||||
char* passwd)
|
||||
{
|
||||
char* err;
|
||||
|
||||
if (!admin_search_user(user))
|
||||
{
|
||||
dcb_printf(dcb, "User %s doesn't exist.\n", user);
|
||||
return;
|
||||
}
|
||||
|
||||
if ((err = admin_remove_user(user, passwd)) == NULL)
|
||||
{
|
||||
dcb_printf(dcb, "User %s has been successfully removed.\n", user);
|
||||
}
|
||||
else
|
||||
{
|
||||
dcb_printf(dcb, "Failed to remove user %s. %s\n", user, err);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Print the adminsitration users
|
||||
*
|
||||
|
Loading…
x
Reference in New Issue
Block a user