Skip to content

Commit

Permalink
Properly escape username/roles in web interface (#3570)
Browse files Browse the repository at this point in the history
* Escaping username component to allow usernames with slash.
* Allowing to handle deletion/updates of roles with special characters.
* Allowing editing/updating/deleting users with special characters in name
* Using proper route methods, escaping username in CurrentUserStore.

Fixes #3569
  • Loading branch information
dennisoelkers authored and joschi committed Mar 7, 2017
1 parent bbeefdd commit 34446c2
Show file tree
Hide file tree
Showing 6 changed files with 16 additions and 18 deletions.
Expand Up @@ -118,7 +118,7 @@ const AuthenticationComponent = React.createClass({

if (authenticators.length === 0) {
// special case, this is a user editing their own profile
authenticators = [<LinkContainer key="profile-edit" to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(this.state.currentUser.username)}>
authenticators = [<LinkContainer key="profile-edit" to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(encodeURIComponent(this.state.currentUser.username))}>
<NavItem title="Edit User">Edit User</NavItem>
</LinkContainer>];
}
Expand Down
Expand Up @@ -24,7 +24,7 @@ const UserMenu = React.createClass({
render() {
return (
<NavDropdown navItem title={this.props.fullName} id="user-menu-dropdown">
<LinkContainer to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(this.props.loginName)}>
<LinkContainer to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(encodeURIComponent(this.props.loginName))}>
<MenuItem>Edit profile</MenuItem>
</LinkContainer>
<MenuItem divider />
Expand Down
2 changes: 1 addition & 1 deletion graylog2-web-interface/src/components/users/UserList.jsx
Expand Up @@ -126,7 +126,7 @@ const UserList = React.createClass({
);

const editAction = (
<LinkContainer to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(user.username)}>
<LinkContainer to={Routes.SYSTEM.AUTHENTICATION.USERS.edit(encodeURIComponent(user.username))}>
<Button bsStyle="info" bsSize="xs" title={`Edit user ${user.username}`}>
Edit
</Button>
Expand Down
12 changes: 5 additions & 7 deletions graylog2-web-interface/src/stores/users/CurrentUserStore.jsx
Expand Up @@ -2,17 +2,15 @@ import Reflux from 'reflux';

import URLUtils from 'util/URLUtils';
import fetch from 'logic/rest/FetchProvider';
import ApiRoutes from 'routing/ApiRoutes';

import StoreProvider from 'injection/StoreProvider';
const SessionStore = StoreProvider.getStore('Session');
const StartpageStore = StoreProvider.getStore('Startpage');
import CombinedProvider from 'injection/CombinedProvider';

import ActionsProvider from 'injection/ActionsProvider';
const SessionActions = ActionsProvider.getActions('Session');
const { SessionStore, SessionActions } = CombinedProvider.get('Session');
const { StartpageStore } = CombinedProvider.get('Startpage');

const CurrentUserStore = Reflux.createStore({
listenables: [SessionActions],
sourceUrl: '/users',
currentUser: undefined,

init() {
Expand Down Expand Up @@ -45,7 +43,7 @@ const CurrentUserStore = Reflux.createStore({
},

update(username) {
fetch('GET', URLUtils.qualifyUrl(this.sourceUrl + '/' + username))
fetch('GET', URLUtils.qualifyUrl(ApiRoutes.UsersApiController.load(encodeURIComponent(username)).url))
.then((resp) => {
this.currentUser = resp;
this.trigger({ currentUser: this.currentUser });
Expand Down
6 changes: 3 additions & 3 deletions graylog2-web-interface/src/stores/users/RolesStore.ts
Expand Up @@ -51,7 +51,7 @@ const RolesStore = {
},

updateRole(rolename: string, role: Role): Promise<Role> {
const promise = fetch('PUT', URLUtils.qualifyUrl(ApiRoutes.RolesApiController.updateRole(rolename).url), role);
const promise = fetch('PUT', URLUtils.qualifyUrl(ApiRoutes.RolesApiController.updateRole(encodeURIComponent(rolename)).url), role);

promise.then((newRole) => {
UserNotification.success("Role \"" + newRole.name + "\" was updated successfully");
Expand All @@ -66,7 +66,7 @@ const RolesStore = {
},

deleteRole(rolename: string): Promise<string[]> {
const url = URLUtils.qualifyUrl(ApiRoutes.RolesApiController.deleteRole(rolename).url);
const url = URLUtils.qualifyUrl(ApiRoutes.RolesApiController.deleteRole(encodeURIComponent(rolename)).url);
const promise = fetch('DELETE', url);

promise.then(() => {
Expand All @@ -80,7 +80,7 @@ const RolesStore = {
return promise;
},
getMembers(rolename: string): Promise<RoleMembership[]> {
const url = URLUtils.qualifyUrl(ApiRoutes.RolesApiController.loadMembers(rolename).url);
const url = URLUtils.qualifyUrl(ApiRoutes.RolesApiController.loadMembers(encodeURIComponent(rolename)).url);
const promise = fetch('GET', url);
promise.catch((error) => {
if (error.additional.status !== 404) {
Expand Down
10 changes: 5 additions & 5 deletions graylog2-web-interface/src/stores/users/UsersStore.ts
Expand Up @@ -58,7 +58,7 @@ export const UsersStore = {
},

load(username: string): Promise<User> {
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.load(username).url);
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.load(encodeURIComponent(username)).url);
const promise = fetch('GET', url);
promise.catch((error) => {
UserNotification.error("Loading user failed with status: " + error,
Expand All @@ -69,7 +69,7 @@ export const UsersStore = {
},

deleteUser(username: string): Promise<string[]> {
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.delete(username).url);
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.delete(encodeURIComponent(username)).url);
const promise = fetch('DELETE', url);

promise.then(() => {
Expand All @@ -85,21 +85,21 @@ export const UsersStore = {
},

updateRoles(username: string, roles: string[]): void {
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.update(username).url);
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.update(encodeURIComponent(username)).url);
const promise = fetch('PUT', url, {roles: roles});

return promise;
},

changePassword(username: string, request: ChangePasswordRequest): void {
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.changePassword(username).url);
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.changePassword(encodeURIComponent(username)).url);
const promise = fetch('PUT', url, request);

return promise;
},

update(username: string, request: any): void {
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.update(username).url);
const url = URLUtils.qualifyUrl(ApiRoutes.UsersApiController.update(encodeURIComponent(username)).url);
const promise = fetch('PUT', url, request);

return promise;
Expand Down

0 comments on commit 34446c2

Please sign in to comment.