org.activityinfo.ui.client.page.config.DbUserEditor.java Source code

Java tutorial

Introduction

Here is the source code for org.activityinfo.ui.client.page.config.DbUserEditor.java

Source

package org.activityinfo.ui.client.page.config;

/*
 * #%L
 * ActivityInfo Server
 * %%
 * Copyright (C) 2009 - 2013 UNICEF
 * %%
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as
 * published by the Free Software Foundation, either version 3 of the 
 * License, or (at your option) any later version.
 * 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public 
 * License along with this program.  If not, see
 * <http://www.gnu.org/licenses/gpl-3.0.html>.
 * #L%
 */

import com.extjs.gxt.ui.client.core.El;
import com.extjs.gxt.ui.client.data.*;
import com.extjs.gxt.ui.client.event.GridEvent;
import com.extjs.gxt.ui.client.event.Listener;
import com.extjs.gxt.ui.client.event.SelectionChangedEvent;
import com.extjs.gxt.ui.client.event.SelectionChangedListener;
import com.extjs.gxt.ui.client.store.ListStore;
import com.extjs.gxt.ui.client.store.Record;
import com.extjs.gxt.ui.client.store.Store;
import com.extjs.gxt.ui.client.store.StoreEvent;
import com.extjs.gxt.ui.client.widget.ContentPanel;
import com.extjs.gxt.ui.client.widget.grid.*;
import com.extjs.gxt.ui.client.widget.layout.FitLayout;
import com.extjs.gxt.ui.client.widget.toolbar.PagingToolBar;
import com.google.gwt.core.client.GWT;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.inject.Inject;
import org.activityinfo.i18n.shared.I18N;
import org.activityinfo.legacy.client.Dispatcher;
import org.activityinfo.legacy.client.monitor.MaskingAsyncMonitor;
import org.activityinfo.legacy.client.state.StateProvider;
import org.activityinfo.legacy.shared.command.BatchCommand;
import org.activityinfo.legacy.shared.command.GetUsers;
import org.activityinfo.legacy.shared.command.UpdateUserPermissions;
import org.activityinfo.legacy.shared.command.result.BatchResult;
import org.activityinfo.legacy.shared.command.result.UserResult;
import org.activityinfo.legacy.shared.command.result.VoidResult;
import org.activityinfo.legacy.shared.model.PartnerDTO;
import org.activityinfo.legacy.shared.model.UserDatabaseDTO;
import org.activityinfo.legacy.shared.model.UserPermissionDTO;
import org.activityinfo.ui.client.EventBus;
import org.activityinfo.ui.client.page.NavigationCallback;
import org.activityinfo.ui.client.page.PageId;
import org.activityinfo.ui.client.page.PageState;
import org.activityinfo.ui.client.page.common.dialog.FormDialogCallback;
import org.activityinfo.ui.client.page.common.dialog.FormDialogImpl;
import org.activityinfo.ui.client.page.common.toolbar.ActionListener;
import org.activityinfo.ui.client.page.common.toolbar.ActionToolBar;
import org.activityinfo.ui.client.page.common.toolbar.UIActions;
import org.activityinfo.ui.client.page.config.form.UserForm;
import org.activityinfo.ui.client.style.legacy.icon.IconImageBundle;

import java.util.ArrayList;
import java.util.List;

public class DbUserEditor extends ContentPanel implements DbPage, ActionListener {
    public static final PageId PAGE_ID = new PageId("dbusers");

    private final EventBus eventBus;
    private final Dispatcher dispatcher;

    private PagingLoader<UserResult> loader;
    private ListStore<UserPermissionDTO> store;
    private Grid<UserPermissionDTO> grid;

    private UserDatabaseDTO db;

    private ActionToolBar toolBar;

    @Inject
    public DbUserEditor(EventBus eventBus, Dispatcher service, StateProvider stateMgr) {
        this.eventBus = eventBus;
        this.dispatcher = service;

        setHeadingText(I18N.CONSTANTS.users());
        setLayout(new FitLayout());

        createToolBar();
        createGrid();
        createPagingToolBar();
    }

    @Override
    public void go(UserDatabaseDTO db) {
        this.db = db;
        store.removeAll();

        toolBar.setActionEnabled(UIActions.SAVE, false);
        toolBar.setActionEnabled(UIActions.ADD, db.isManageUsersAllowed());
        toolBar.setActionEnabled(UIActions.DELETE, false);

        grid.getColumnModel().getColumnById("allowViewAll").setHidden(!db.isManageUsersAllowed());
        grid.getColumnModel().getColumnById("allowEditAll").setHidden(!db.isManageUsersAllowed());
        grid.getColumnModel().getColumnById("allowManageUsers").setHidden(!db.isManageAllUsersAllowed());
        grid.getColumnModel().getColumnById("allowManageAllUsers").setHidden(!db.isManageAllUsersAllowed());
        grid.getColumnModel().getColumnById("allowDesign").setHidden(!db.isDesignAllowed());

        loader.load();
    }

    private void createToolBar() {
        toolBar = new ActionToolBar(this);
        toolBar.addSaveSplitButton();
        toolBar.addButton(UIActions.ADD, I18N.CONSTANTS.addUser(), IconImageBundle.ICONS.addUser());
        toolBar.addButton(UIActions.DELETE, I18N.CONSTANTS.delete(), IconImageBundle.ICONS.deleteUser());
        toolBar.addButton(UIActions.EXPORT, I18N.CONSTANTS.export(), IconImageBundle.ICONS.excel());
        toolBar.addButton(UIActions.MAILING_LIST, I18N.CONSTANTS.CopyAddressToClipBoard(),
                IconImageBundle.ICONS.dataEntry());
        setTopComponent(toolBar);
    }

    private void createGrid() {

        loader = new BasePagingLoader<UserResult>(new UserProxy());

        store = new ListStore<UserPermissionDTO>(loader);
        store.setKeyProvider(new ModelKeyProvider<UserPermissionDTO>() {
            @Override
            public String getKey(UserPermissionDTO model) {
                return model.getEmail();
            }
        });
        store.addListener(Store.Update, new Listener<StoreEvent<UserPermissionDTO>>() {

            @Override
            public void handleEvent(StoreEvent<UserPermissionDTO> event) {
                toolBar.setDirty(!store.getModifiedRecords().isEmpty());
            }
        });

        final List<ColumnConfig> columns = new ArrayList<ColumnConfig>();

        columns.add(new ColumnConfig("name", I18N.CONSTANTS.name(), 100));
        columns.add(new ColumnConfig("email", I18N.CONSTANTS.email(), 150));
        columns.add(new ColumnConfig("partner", I18N.CONSTANTS.partner(), 150));

        PermissionCheckConfig allowView = new PermissionCheckConfig("allowViewSimple", I18N.CONSTANTS.allowView(),
                75);
        allowView.setDataIndex("allowView");
        allowView.setToolTip(I18N.CONSTANTS.allowViewLong());
        columns.add(allowView);

        PermissionCheckConfig allowEdit = new PermissionCheckConfig("allowEditSimple", I18N.CONSTANTS.allowEdit(),
                75);
        allowEdit.setDataIndex("allowEdit");
        allowEdit.setToolTip(I18N.CONSTANTS.allowEditLong());
        columns.add(allowEdit);

        PermissionCheckConfig allowViewAll = new PermissionCheckConfig("allowViewAll",
                I18N.CONSTANTS.allowViewAll(), 75);
        allowViewAll.setToolTip(I18N.CONSTANTS.allowViewAllLong());
        columns.add(allowViewAll);

        PermissionCheckConfig allowEditAll = new PermissionCheckConfig("allowEditAll",
                I18N.CONSTANTS.allowEditAll(), 75);
        allowEditAll.setToolTip(I18N.CONSTANTS.allowEditAllLong());
        columns.add(allowEditAll);

        PermissionCheckConfig allowManageUsers = null;
        allowManageUsers = new PermissionCheckConfig("allowManageUsers", I18N.CONSTANTS.allowManageUsers(), 150);
        columns.add(allowManageUsers);

        PermissionCheckConfig allowManageAllUsers = new PermissionCheckConfig("allowManageAllUsers",
                I18N.CONSTANTS.manageAllUsers(), 150);
        columns.add(allowManageAllUsers);

        // only users with the right to design them selves can change the design
        // attribute
        PermissionCheckConfig allowDesign = new PermissionCheckConfig("allowDesign", I18N.CONSTANTS.allowDesign(),
                75);
        allowDesign.setToolTip(I18N.CONSTANTS.allowDesignLong());
        columns.add(allowDesign);

        grid = new Grid<UserPermissionDTO>(store, new ColumnModel(columns));
        grid.setLoadMask(true);
        grid.setSelectionModel(new GridSelectionModel<UserPermissionDTO>());
        grid.getSelectionModel().addSelectionChangedListener(new SelectionChangedListener<UserPermissionDTO>() {

            @Override
            public void selectionChanged(SelectionChangedEvent<UserPermissionDTO> se) {
                onSelectionChanged(se.getSelectedItem());
            }
        });
        grid.addPlugin(allowEdit);
        grid.addPlugin(allowViewAll);
        grid.addPlugin(allowEditAll);
        grid.addPlugin(allowManageUsers);
        grid.addPlugin(allowManageAllUsers);
        grid.addPlugin(allowDesign);
        add(grid);
    }

    private void createPagingToolBar() {
        PagingToolBar pagingToolBar = new PagingToolBar(100);
        pagingToolBar.bind(loader);
        setBottomComponent(pagingToolBar);
    }

    @Override
    public void shutdown() {
    }

    @Override
    public boolean navigate(PageState place) {
        return false;
    }

    private boolean validateChange(UserPermissionDTO user, String property) {

        // If the user doesn't have the manageUser permission, then it's
        // definitely
        // a no.
        if (!db.isManageUsersAllowed()) {
            return false;
        }

        // if the user is only allowed to manager their own partners, then make
        // sure they're changing someone from their own organisation
        if (!db.isManageAllUsersAllowed() && db.getMyPartner().getId() != user.getPartner().getId()) {
            return false;
        }

        // do not allow users to set rights they themselves do not have
        if ("allowViewAll".equals(property) && !db.isViewAllAllowed()) {
            return false;
        }
        if ("allowEdit".equals(property) && !db.isEditAllowed()) {
            return false;
        }
        if ("allowEditAll".equals(property) && !db.isEditAllAllowed()) {
            return false;
        }
        if ("allowDesign".equals(property) && !db.isDesignAllowed()) {
            return false;
        }
        if ("allowManageUsers".equals(property) && !db.isManageUsersAllowed()) {
            return false;
        }
        if ("allowManageAllUsers".equals(property) && !db.isManageAllUsersAllowed()) {
            return false;
        }

        return true;
    }

    @Override
    public PageId getPageId() {
        return PAGE_ID;
    }

    @Override
    public Object getWidget() {
        return this;
    }

    @Override
    public String beforeWindowCloses() {
        return null;
    }

    private void onRowEdit(String property, boolean value, Record record) {
        record.beginEdit();
        if (!value) {
            // Cascade remove permissions
            if ("allowViewAll".equals(property)) {
                record.set("allowEditAll", false);
            }
        } else {
            // cascade add permissions
            if ("allowEditAll".equals(property)) {
                record.set("allowEdit", true);
                record.set("allowViewAll", true);
            } else if ("allowManageAllUsers".equals(property)) {
                record.set("allowManageUsers", true);
            }
        }

        record.endEdit();
        toolBar.setDirty(store.getModifiedRecords().size() != 0);
    }

    private void onSelectionChanged(UserPermissionDTO selectedItem) {

        if (selectedItem != null) {
            PartnerDTO selectedPartner = selectedItem.getPartner();

            toolBar.setActionEnabled(UIActions.DELETE, db.isManageAllUsersAllowed()
                    || (db.isManageUsersAllowed() && db.getMyPartnerId() == selectedPartner.getId()));
        }
        toolBar.setActionEnabled(UIActions.DELETE, selectedItem != null);
    }

    @Override
    public void onUIAction(String actionId) {
        if (actionId.equals(UIActions.SAVE)) {
            save();
        } else if (actionId.equals(UIActions.ADD)) {
            add();
        } else if (actionId.equals(UIActions.DELETE)) {
            delete();
        } else if (actionId.equals(UIActions.EXPORT)) {
            export();
        } else if (UIActions.MAILING_LIST.equals(actionId)) {
            createMailingListPopup();
        }
    }

    private void save() {
        BatchCommand batch = new BatchCommand();
        for (Record record : store.getModifiedRecords()) {
            batch.add(new UpdateUserPermissions(db.getId(), (UserPermissionDTO) record.getModel()));
        }

        dispatcher.execute(batch, new MaskingAsyncMonitor(this, I18N.CONSTANTS.saving()),
                new AsyncCallback<BatchResult>() {

                    @Override
                    public void onFailure(Throwable caught) {
                        // handled by monitor
                    }

                    @Override
                    public void onSuccess(BatchResult result) {
                        store.commitChanges();
                    }
                });
    }

    private void createMailingListPopup() {
        new MailingListDialog(dispatcher, db.getId());
    }

    private void add() {
        final UserForm form = new UserForm(db);

        final FormDialogImpl dlg = new FormDialogImpl(form);
        dlg.setHeadingText(I18N.CONSTANTS.newUser());
        dlg.setWidth(400);
        dlg.setHeight(300);

        final String host = Window.Location.getHostName();

        dlg.show(new FormDialogCallback() {

            @Override
            public void onValidated() {
                dispatcher.execute(new UpdateUserPermissions(db, form.getUser(), host), dlg,
                        new AsyncCallback<VoidResult>() {

                            @Override
                            public void onFailure(Throwable caught) {
                            }

                            @Override
                            public void onSuccess(VoidResult result) {
                                loader.load();
                                dlg.hide();
                            }
                        });
            }
        });
    }

    private void delete() {
        final UserPermissionDTO model = grid.getSelectionModel().getSelectedItem();
        model.setAllowView(false);
        model.setAllowViewAll(false);
        model.setAllowEdit(false);
        model.setAllowEditAll(false);
        model.setAllowDesign(false);
        model.setAllowManageAllUsers(false);
        model.setAllowManageUsers(false);

        dispatcher.execute(new UpdateUserPermissions(db.getId(), model),
                new MaskingAsyncMonitor(this, I18N.CONSTANTS.deleting()), new AsyncCallback<VoidResult>() {
                    @Override
                    public void onFailure(Throwable caught) {
                    }

                    @Override
                    public void onSuccess(VoidResult result) {
                        store.remove(model);
                    }
                });
    }

    private void export() {
        Window.open(GWT.getModuleBaseURL() + "export/users?dbUsers=" + db.getId(), "_blank", null);
    }

    @Override
    public void requestToNavigateAway(PageState place, NavigationCallback callback) {
        callback.onDecided(true);
    }

    private class PermissionCheckConfig extends CheckColumnConfig {

        public PermissionCheckConfig(String id, String name, int width) {
            super(id, name, width);
        }

        @Override
        protected void onMouseDown(GridEvent<ModelData> ge) {
            El el = ge.getTargetEl();
            if (el != null && el.hasStyleName("x-grid3-cc-" + getId())
                    && !el.hasStyleName("x-grid3-check-col-disabled")) {
                ge.stopEvent();
                UserPermissionDTO m = (UserPermissionDTO) ge.getModel();
                String property = grid.getColumnModel().getColumnId(ge.getColIndex());
                Record r = store.getRecord(m);
                Boolean b = (Boolean) m.get(getDataIndex());
                if (validateChange(m, property)) {
                    boolean newValue = b == null ? true : !b;
                    r.set(getDataIndex(), newValue);
                    onRowEdit(property, newValue, r);
                }
            }
        }
    }

    private class UserProxy extends RpcProxy<UserResult> {

        @Override
        protected void load(Object loadConfig, final AsyncCallback<UserResult> callback) {

            PagingLoadConfig config = (PagingLoadConfig) loadConfig;
            GetUsers command = new GetUsers(db.getId());
            command.setOffset(config.getOffset());
            command.setLimit(config.getLimit());
            command.setSortInfo(config.getSortInfo());
            dispatcher.execute(command, callback);
        }
    }
}