Coverage Report - org.kuali.student.lum.program.client.major.edit.MajorEditController
 
Classes in this File Line Coverage Branch Coverage Complexity
MajorEditController
0%
0/78
0%
0/16
1.833
MajorEditController$1
0%
0/3
N/A
1.833
MajorEditController$10
0%
0/6
N/A
1.833
MajorEditController$10$1
0%
0/7
0%
0/2
1.833
MajorEditController$11
0%
0/33
0%
0/8
1.833
MajorEditController$2
0%
0/3
N/A
1.833
MajorEditController$3
0%
0/6
0%
0/2
1.833
MajorEditController$4
0%
0/3
N/A
1.833
MajorEditController$4$1
0%
0/10
0%
0/2
1.833
MajorEditController$4$1$1
0%
0/5
0%
0/2
1.833
MajorEditController$4$1$1$1
0%
0/5
0%
0/2
1.833
MajorEditController$5
0%
0/27
0%
0/10
1.833
MajorEditController$6
0%
0/9
N/A
1.833
MajorEditController$7
0%
0/12
0%
0/4
1.833
MajorEditController$8
0%
0/3
N/A
1.833
MajorEditController$9
0%
0/13
N/A
1.833
 
 1  
 package org.kuali.student.lum.program.client.major.edit;
 2  
 
 3  
 import java.util.ArrayList;
 4  
 import java.util.List;
 5  
 import java.util.Set;
 6  
 import java.util.TreeSet;
 7  
 
 8  
 import org.kuali.student.common.ui.client.application.ViewContext;
 9  
 import org.kuali.student.common.ui.client.mvc.Callback;
 10  
 import org.kuali.student.common.ui.client.mvc.DataModel;
 11  
 import org.kuali.student.common.ui.client.mvc.ModelRequestCallback;
 12  
 import org.kuali.student.common.ui.client.mvc.history.HistoryManager;
 13  
 import org.kuali.student.common.ui.client.service.DataSaveResult;
 14  
 import org.kuali.student.common.ui.client.widgets.KSButton;
 15  
 import org.kuali.student.common.ui.client.widgets.KSButtonAbstract;
 16  
 import org.kuali.student.common.ui.client.widgets.notification.KSNotification;
 17  
 import org.kuali.student.common.ui.client.widgets.notification.KSNotifier;
 18  
 import org.kuali.student.common.ui.shared.IdAttributes;
 19  
 import org.kuali.student.common.ui.shared.IdAttributes.IdType;
 20  
 import org.kuali.student.core.assembly.data.Data;
 21  
 import org.kuali.student.core.assembly.data.QueryPath;
 22  
 import org.kuali.student.core.validation.dto.ValidationResultInfo;
 23  
 import org.kuali.student.lum.common.client.helpers.RecentlyViewedHelper;
 24  
 import org.kuali.student.lum.common.client.widgets.AppLocations;
 25  
 import org.kuali.student.lum.program.client.ProgramConstants;
 26  
 import org.kuali.student.lum.program.client.ProgramRegistry;
 27  
 import org.kuali.student.lum.program.client.ProgramSections;
 28  
 import org.kuali.student.lum.program.client.ProgramStatus;
 29  
 import org.kuali.student.lum.program.client.ProgramUtils;
 30  
 import org.kuali.student.lum.program.client.events.AddSpecializationEvent;
 31  
 import org.kuali.student.lum.program.client.events.AfterSaveEvent;
 32  
 import org.kuali.student.lum.program.client.events.ChangeViewEvent;
 33  
 import org.kuali.student.lum.program.client.events.MetadataLoadedEvent;
 34  
 import org.kuali.student.lum.program.client.events.ModelLoadedEvent;
 35  
 import org.kuali.student.lum.program.client.events.SpecializationCreatedEvent;
 36  
 import org.kuali.student.lum.program.client.events.SpecializationSaveEvent;
 37  
 import org.kuali.student.lum.program.client.events.SpecializationUpdateEvent;
 38  
 import org.kuali.student.lum.program.client.events.StateChangeEvent;
 39  
 import org.kuali.student.lum.program.client.events.StoreRequirementIDsEvent;
 40  
 import org.kuali.student.lum.program.client.events.UpdateEvent;
 41  
 import org.kuali.student.lum.program.client.major.MajorController;
 42  
 import org.kuali.student.lum.program.client.properties.ProgramProperties;
 43  
 import org.kuali.student.lum.program.client.rpc.AbstractCallback;
 44  
 import org.kuali.student.lum.program.client.widgets.ProgramSideBar;
 45  
 
 46  
 import com.google.gwt.core.client.GWT;
 47  
 import com.google.gwt.event.dom.client.ClickEvent;
 48  
 import com.google.gwt.event.dom.client.ClickHandler;
 49  
 import com.google.gwt.event.shared.HandlerManager;
 50  
 import com.google.gwt.user.client.Window;
 51  
 
 52  
 /**
 53  
  * @author Igor
 54  
  */
 55  0
 public class MajorEditController extends MajorController {
 56  
 
 57  0
     private final KSButton saveButton = new KSButton(ProgramProperties.get().common_save());
 58  0
     private final KSButton cancelButton = new KSButton(ProgramProperties.get().common_cancel(), KSButtonAbstract.ButtonStyle.ANCHOR_LARGE_CENTERED);
 59  0
     private final Set<String> existingVariationIds = new TreeSet<String>();
 60  
 
 61  
     private ProgramStatus previousState;
 62  
 
 63  
     /**
 64  
      * Constructor.
 65  
      *
 66  
      * @param programModel
 67  
      */
 68  
     public MajorEditController(DataModel programModel, ViewContext viewContext, HandlerManager eventBus) {
 69  0
         super(programModel, viewContext, eventBus);
 70  0
         configurer = GWT.create(MajorEditConfigurer.class);
 71  0
         sideBar.setState(ProgramSideBar.State.EDIT);
 72  0
         initHandlers();
 73  0
     }
 74  
 
 75  
     @Override
 76  
     protected void configureView() {
 77  0
         super.configureView();
 78  0
         if (!initialized) {
 79  0
             eventBus.fireEvent(new MetadataLoadedEvent(programModel.getDefinition(), this));
 80  0
             List<Enum<?>> excludedViews = new ArrayList<Enum<?>>();
 81  0
             excludedViews.add(ProgramSections.PROGRAM_REQUIREMENTS_EDIT);
 82  0
             excludedViews.add(ProgramSections.SUPPORTING_DOCUMENTS_EDIT);
 83  0
             excludedViews.add(ProgramSections.SUMMARY);
 84  0
             addCommonButton(ProgramProperties.get().program_menu_sections(), saveButton, excludedViews);
 85  0
             addCommonButton(ProgramProperties.get().program_menu_sections(), cancelButton, excludedViews);
 86  0
             initialized = true;
 87  
         }
 88  0
     }
 89  
 
 90  
     private void initHandlers() {
 91  0
         saveButton.addClickHandler(new ClickHandler() {
 92  
 
 93  
             @Override
 94  
             public void onClick(ClickEvent event) {
 95  0
                 doSave();
 96  0
             }
 97  
         });
 98  0
         cancelButton.addClickHandler(new ClickHandler() {
 99  
 
 100  
             @Override
 101  
             public void onClick(ClickEvent event) {
 102  0
                 doCancel();
 103  0
             }
 104  
         });
 105  0
         eventBus.addHandler(UpdateEvent.TYPE, new UpdateEvent.Handler() {
 106  
             @Override
 107  
             public void onEvent(UpdateEvent event) {
 108  0
                 Enum<?> view = event.getCurrentView();
 109  0
                 if (view != null) {
 110  0
                     setCurrentViewEnum(view);
 111  
                 }
 112  0
                 doSave(event.getOkCallback());
 113  
 
 114  0
             }
 115  
         });
 116  0
         eventBus.addHandler(StateChangeEvent.TYPE, new StateChangeEvent.Handler() {
 117  
             @Override
 118  
             public void onEvent(final StateChangeEvent event) {
 119  0
                 programModel.validateNextState(new Callback<List<ValidationResultInfo>>() {
 120  
                     @Override
 121  
                     public void exec(List<ValidationResultInfo> result) {
 122  0
                         boolean isSectionValid = isValid(result, true);
 123  0
                         if (isSectionValid) {
 124  0
                             Callback<Boolean> callback = new Callback<Boolean>() {
 125  
                                 @Override
 126  
                                 public void exec(Boolean result) {
 127  0
                                     if (result) {
 128  0
                                         reloadMetadata = true;
 129  0
                                         loadMetadata(new Callback<Boolean>() {
 130  
                                             @Override
 131  
                                             public void exec(Boolean result) {
 132  0
                                                 if (result) {
 133  0
                                                     ProgramUtils.syncMetadata(configurer, programModel.getDefinition());
 134  0
                                                     HistoryManager.navigate(AppLocations.Locations.VIEW_PROGRAM.getLocation(), context);
 135  
                                                 }
 136  0
                                             }
 137  
                                         });
 138  
                                     }
 139  0
                                 }
 140  
                             };
 141  0
                             previousState = ProgramStatus.of(programModel);
 142  0
                             ProgramUtils.setStatus(programModel, event.getProgramStatus().getValue());
 143  0
                             saveData(callback);
 144  0
                         } else {
 145  0
                             KSNotifier.add(new KSNotification("Unable to save, please check fields for errors.", false, true, 5000));
 146  
                         }
 147  0
                     }
 148  
                 });
 149  0
             }
 150  
         });
 151  
 
 152  0
         eventBus.addHandler(SpecializationSaveEvent.TYPE, new SpecializationSaveEvent.Handler() {
 153  
             @Override
 154  
             public void onEvent(SpecializationSaveEvent event) {
 155  
 
 156  0
                 Data currentVariations = getDataProperty(ProgramConstants.VARIATIONS);
 157  
 
 158  0
                 existingVariationIds.clear();
 159  
 
 160  0
                 for (Data.Property prop : currentVariations) {
 161  0
                     String existingId = (String) ((Data) prop.getValue()).get(ProgramConstants.ID);
 162  0
                     existingVariationIds.add(existingId);
 163  0
                 }
 164  0
                 String updatedId = event.getData().get(ProgramConstants.ID);
 165  0
                 Integer updatedKey = null;
 166  
 
 167  
                 //FIXME: This is ugly but gets us past a  blocker issue. 
 168  
                 // Theres something wrong with the way the models are
 169  
                 // handled in the major and variation controllers  so they get out of sync.
 170  
                 // This is a temporary workaround
 171  0
                 if (updatedId != null) { // this is an update of an existing variation
 172  0
                     for (Data.Property prop : currentVariations) {
 173  0
                         String id = (String) ((Data) prop.getValue()).get(ProgramConstants.ID);
 174  0
                         if (updatedId.equals(id)) {
 175  0
                             updatedKey = prop.getKey();
 176  0
                             Data currentMetaInfo = ((Data) prop.getValue()).get("metaInfo");
 177  0
                             String latestVersionInd = currentMetaInfo.get("versionInd");
 178  0
                             Data newMetaInfo = event.getData().get("metaInfo");
 179  0
                             if (newMetaInfo == null) {
 180  0
                                 newMetaInfo = new Data();
 181  0
                                 event.getData().set("metaInfo", newMetaInfo);
 182  
                             }
 183  0
                             newMetaInfo.set("versionInd", latestVersionInd);
 184  0
                             break;
 185  
                         }
 186  0
                     }
 187  
 
 188  0
                     currentVariations.set(updatedKey, event.getData());
 189  
                 } else {
 190  0
                     currentVariations.add(event.getData());
 191  
 
 192  
                 }
 193  0
                 doSave();
 194  0
             }
 195  
         });
 196  0
         eventBus.addHandler(AddSpecializationEvent.TYPE, new AddSpecializationEvent.Handler() {
 197  
             @Override
 198  
             public void onEvent(AddSpecializationEvent event) {
 199  0
                 String id = getStringProperty(ProgramConstants.ID);
 200  0
                 ProgramRegistry.setRow((getDataProperty(ProgramConstants.VARIATIONS)).size());
 201  0
                 ProgramRegistry.setData(ProgramUtils.createNewSpecializationBasedOnMajor(programModel));
 202  0
                 ViewContext viewContext = new ViewContext();
 203  0
                 viewContext.setId(id);
 204  0
                 viewContext.setIdType(IdAttributes.IdType.OBJECT_ID);
 205  0
                 HistoryManager.navigate(AppLocations.Locations.EDIT_VARIATION.getLocation(), viewContext);
 206  
 
 207  0
             }
 208  
         });
 209  
 
 210  0
         eventBus.addHandler(StoreRequirementIDsEvent.TYPE, new StoreRequirementIDsEvent.Handler() {
 211  
             @Override
 212  
             public void onEvent(StoreRequirementIDsEvent event) {
 213  0
                 List<String> ids = event.getProgramRequirementIds();
 214  
 
 215  0
                 programModel.set(QueryPath.parse(ProgramConstants.PROGRAM_REQUIREMENTS), new Data());
 216  0
                 Data programRequirements = programModel.get(ProgramConstants.PROGRAM_REQUIREMENTS);
 217  
 
 218  0
                 if (programRequirements == null) {
 219  0
                     Window.alert("Cannot find program requirements in data model.");
 220  0
                     GWT.log("Cannot find program requirements in data model", null);
 221  0
                     return;
 222  
                 }
 223  
 
 224  0
                 for (String id : ids) {
 225  0
                     programRequirements.add(id);
 226  
                 }
 227  0
                 doSave();
 228  0
             }
 229  
         });
 230  0
         eventBus.addHandler(ChangeViewEvent.TYPE, new ChangeViewEvent.Handler() {
 231  
             @Override
 232  
             public void onEvent(ChangeViewEvent event) {
 233  0
                 showView(event.getViewToken());
 234  0
             }
 235  
         });
 236  0
     }
 237  
 
 238  
     @Override
 239  
     protected void loadModel(ModelRequestCallback<DataModel> callback) {
 240  0
         ViewContext viewContext = getViewContext();
 241  0
         if (viewContext.getIdType() == IdType.COPY_OF_OBJECT_ID) {
 242  0
             createNewVersionAndLoadModel(callback, viewContext);
 243  
         } else {
 244  0
             super.loadModel(callback);
 245  
         }
 246  0
     }
 247  
 
 248  
     protected void createNewVersionAndLoadModel(final ModelRequestCallback<DataModel> callback, final ViewContext viewContext) {
 249  0
         Data data = new Data();
 250  0
         Data versionData = new Data();
 251  0
         versionData.set(new Data.StringKey("versionIndId"), getViewContext().getId());
 252  0
         versionData.set(new Data.StringKey("versionComment"), "Major Disicpline Version");
 253  0
         data.set(new Data.StringKey("versionInfo"), versionData);
 254  
 
 255  0
         programRemoteService.saveData(data, new AbstractCallback<DataSaveResult>(ProgramProperties.get().common_retrievingData()) {
 256  
             @Override
 257  
             public void onSuccess(DataSaveResult result) {
 258  0
                 super.onSuccess(result);
 259  0
                 programModel.setRoot(result.getValue());
 260  0
                 viewContext.setId(ProgramUtils.getProgramId(programModel));
 261  0
                 viewContext.setIdType(IdType.OBJECT_ID);
 262  0
                 setHeaderTitle();
 263  0
                 setStatus();
 264  0
                 callback.onModelReady(programModel);
 265  0
                 eventBus.fireEvent(new ModelLoadedEvent(programModel));
 266  0
             }
 267  
 
 268  
             @Override
 269  
             public void onFailure(Throwable caught) {
 270  0
                 super.onFailure(caught);
 271  0
                 callback.onRequestFail(caught);
 272  0
             }
 273  
         });
 274  
 
 275  0
     }
 276  
 
 277  
     private void doSave(final Callback<Boolean> okCallback) {
 278  0
         requestModel(new ModelRequestCallback<DataModel>() {
 279  
             @Override
 280  
             public void onModelReady(DataModel model) {
 281  0
                 MajorEditController.this.updateModelFromCurrentView();
 282  0
                 model.validate(new Callback<List<ValidationResultInfo>>() {
 283  
                     @Override
 284  
                     public void exec(List<ValidationResultInfo> result) {
 285  0
                         boolean isSectionValid = isValid(result, true);
 286  0
                         if (isSectionValid) {
 287  0
                             saveData(okCallback);
 288  
                         } else {
 289  0
                             okCallback.exec(false);
 290  0
                             KSNotifier.add(new KSNotification("Unable to save, please check fields for errors.", false, true, 5000));
 291  
                         }
 292  0
                     }
 293  
                 });
 294  
 
 295  0
             }
 296  
 
 297  
             @Override
 298  
             public void onRequestFail(Throwable cause) {
 299  0
                 GWT.log("Unable to retrieve model for validation and save", cause);
 300  0
             }
 301  
         });
 302  0
     }
 303  
 
 304  
     private void doCancel() {
 305  0
         showView(ProgramSections.SUMMARY);
 306  0
     }
 307  
 
 308  
     @Override
 309  
     protected void doSave() {
 310  0
         doSave(NO_OP_CALLBACK);
 311  0
     }
 312  
 
 313  
     private void saveData(final Callback<Boolean> okCallback) {
 314  0
         programRemoteService.saveData(programModel.getRoot(), new AbstractCallback<DataSaveResult>(ProgramProperties.get().common_savingData()) {
 315  
             @Override
 316  
             public void onSuccess(DataSaveResult result) {
 317  0
                 super.onSuccess(result);
 318  0
                 Data data = result.getValue();
 319  0
                 if (data != null) {
 320  0
                     programModel.setRoot(result.getValue());
 321  
                 }
 322  0
                 List<ValidationResultInfo> validationResults = result.getValidationResults();
 323  0
                 if (validationResults != null && !validationResults.isEmpty()) {
 324  0
                     if (previousState != null) {
 325  0
                         ProgramUtils.setStatus(programModel, previousState.getValue());
 326  
                     }
 327  0
                     ProgramUtils.retrofitValidationResults(validationResults);
 328  0
                     isValid(validationResults, false, true);
 329  0
                     ProgramUtils.handleValidationErrorsForSpecializations(validationResults, programModel);
 330  0
                     okCallback.exec(false);
 331  
                 } else {
 332  0
                     previousState = null;
 333  0
                     setHeaderTitle();
 334  0
                     setStatus();
 335  0
                     resetFieldInteractionFlag();
 336  0
                     configurer.applyPermissions();
 337  0
                     handleSpecializations();
 338  0
                     throwAfterSaveEvent();
 339  0
                     HistoryManager.logHistoryChange();
 340  0
                     ViewContext viewContext = getViewContext();
 341  0
                     viewContext.setId(getStringProperty(ProgramConstants.ID));
 342  0
                     viewContext.setIdType(IdType.OBJECT_ID);
 343  
 
 344  
                     // add to recently viewed now that we're sure to know the program's id
 345  0
                     ViewContext docContext = new ViewContext();
 346  0
                     docContext.setId(getStringProperty(ProgramConstants.ID));
 347  0
                     docContext.setIdType(IdType.OBJECT_ID);
 348  0
                     docContext.setAttribute(ProgramConstants.TYPE, ProgramConstants.MAJOR_LU_TYPE_ID + '/' + ProgramSections.PROGRAM_DETAILS_VIEW);
 349  0
                     RecentlyViewedHelper.addDocument(getProgramName(),
 350  
                             HistoryManager.appendContext(AppLocations.Locations.VIEW_PROGRAM.getLocation(), docContext));
 351  0
                     KSNotifier.show(ProgramProperties.get().common_successfulSave());
 352  0
                     okCallback.exec(true);
 353  0
                     processCurrentView();
 354  
                 }
 355  0
             }
 356  
         });
 357  0
     }
 358  
 
 359  
     private void processCurrentView() {
 360  0
         Enum<?> currentView = getCurrentViewEnum();
 361  0
         if (currentView.name().equals(ProgramSections.VIEW_ALL.name())) {
 362  0
             HistoryManager.navigate(AppLocations.Locations.VIEW_PROGRAM.getLocation(), getViewContext());
 363  
         } else {
 364  0
             showView(currentView);
 365  
         }
 366  0
     }
 367  
 
 368  
     /**
 369  
      * Handles after save work for specializations.
 370  
      */
 371  
     private void handleSpecializations() {
 372  0
         String newVariationId = null;
 373  0
         Data variations = programModel.get(ProgramConstants.VARIATIONS);
 374  0
         for (Data.Property prop : variations) {
 375  0
             String varId = (String) ((Data) prop.getValue()).get(ProgramConstants.ID);
 376  0
             if (!existingVariationIds.contains(varId)) {
 377  0
                 newVariationId = varId;
 378  0
                 existingVariationIds.add(newVariationId);
 379  0
                 break;
 380  
             }
 381  0
         }
 382  0
         if (newVariationId != null) {
 383  0
             eventBus.fireEvent(new SpecializationCreatedEvent(newVariationId));
 384  
         } else {
 385  0
             eventBus.fireEvent(new SpecializationUpdateEvent(variations));
 386  
         }
 387  0
     }
 388  
 
 389  
     private void throwAfterSaveEvent() {
 390  0
         eventBus.fireEvent(new AfterSaveEvent(programModel, this));
 391  0
     }
 392  
 
 393  
     @Override
 394  
     public void onModelLoadedEvent() {
 395  0
         Enum<?> changeSection = ProgramRegistry.getSection();
 396  0
         if (changeSection != null) {
 397  0
             showView(changeSection);
 398  0
             ProgramRegistry.setSection(null);
 399  
         } else {
 400  0
             String id = getStringProperty(ProgramConstants.ID);
 401  0
             if (id == null) {
 402  0
                 showView(ProgramSections.PROGRAM_DETAILS_EDIT);
 403  
             } else {
 404  0
                 showView(ProgramSections.SUMMARY);
 405  
             }
 406  
         }
 407  0
     }
 408  
 }