Package org.olat.course.nodes.ta

Source Code of org.olat.course.nodes.ta.DropboxController

/**
* OLAT - Online Learning and Training<br>
* http://www.olat.org
* <p>
* Licensed under the Apache License, Version 2.0 (the "License"); <br>
* you may not use this file except in compliance with the License.<br>
* You may obtain a copy of the License at
* <p>
* http://www.apache.org/licenses/LICENSE-2.0
* <p>
* Unless required by applicable law or agreed to in writing,<br>
* software distributed under the License is distributed on an "AS IS" BASIS, <br>
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
* See the License for the specific language governing permissions and <br>
* limitations under the License.
* <p>
* Copyright (c) since 2004 at Multimedia- & E-Learning Services (MELS),<br>
* University of Zurich, Switzerland.
* <p>
*/

package org.olat.course.nodes.ta;

import java.io.File;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import org.apache.velocity.VelocityContext;
import org.apache.velocity.context.Context;
import org.olat.admin.quota.QuotaConstants;
import org.olat.commons.file.filechooser.FileChooserController;
import org.olat.core.commons.modules.bc.FolderConfig;
import org.olat.core.commons.modules.bc.vfs.OlatNamedContainerImpl;
import org.olat.core.commons.modules.bc.vfs.OlatRootFolderImpl;
import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.Component;
import org.olat.core.gui.components.link.Link;
import org.olat.core.gui.components.link.LinkFactory;
import org.olat.core.gui.components.velocity.VelocityContainer;
import org.olat.core.gui.control.Controller;
import org.olat.core.gui.control.Event;
import org.olat.core.gui.control.WindowControl;
import org.olat.core.gui.control.controller.BasicController;
import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController;
import org.olat.core.gui.control.generic.modal.DialogBoxController;
import org.olat.core.gui.render.velocity.VelocityHelper;
import org.olat.core.id.Identity;
import org.olat.core.id.UserConstants;
import org.olat.core.logging.AssertException;
import org.olat.core.util.FileUtils;
import org.olat.core.util.Formatter;
import org.olat.core.util.mail.MailHelper;
import org.olat.core.util.mail.MailTemplate;
import org.olat.core.util.mail.MailerResult;
import org.olat.core.util.mail.MailerWithTemplate;
import org.olat.core.util.notifications.ContextualSubscriptionController;
import org.olat.core.util.notifications.NotificationsManager;
import org.olat.core.util.notifications.SubscriptionContext;
import org.olat.core.util.vfs.LocalFileImpl;
import org.olat.core.util.vfs.Quota;
import org.olat.core.util.vfs.QuotaManager;
import org.olat.core.util.vfs.VFSContainer;
import org.olat.core.util.vfs.VFSLeaf;
import org.olat.core.util.vfs.callbacks.FullAccessWithQuotaCallback;
import org.olat.course.auditing.UserNodeAuditManager;
import org.olat.course.nodes.AssessableCourseNode;
import org.olat.course.nodes.CourseNode;
import org.olat.course.nodes.TACourseNode;
import org.olat.course.run.environment.CourseEnvironment;
import org.olat.course.run.userview.UserCourseEnvironment;
import org.olat.modules.ModuleConfiguration;

/**
* Initial Date:  02.09.2004
* @author Mike Stock
*/

public class DropboxController extends BasicController {
 
  public static String DROPBOX_DIR_NAME = "dropboxes";
  // config
 
  protected ModuleConfiguration config;
  protected CourseNode node;
  protected UserCourseEnvironment userCourseEnv;
  private VelocityContainer myContent;
  private FileChooserController fileChooserController;
  private SubscriptionContext subsContext;
  private ContextualSubscriptionController contextualSubscriptionCtr;
  private Link ulButton;
  private DialogBoxController confirmationDialogController;
  private CloseableModalController cmc;

 
  // Constructor for ProjectBrokerDropboxController
  protected DropboxController(UserRequest ureq, WindowControl wControl) {
    super(ureq, wControl);
    this.setBasePackage(DropboxController.class);
  }
 
  /**
   * Implements a dropbox.
   * @param ureq
   * @param wControl
   * @param config
   * @param node
   * @param userCourseEnv
   * @param previewMode
   */
  public DropboxController(UserRequest ureq, WindowControl wControl, ModuleConfiguration config, CourseNode node, UserCourseEnvironment userCourseEnv, boolean previewMode) {
    super(ureq, wControl);
    this.setBasePackage(DropboxController.class);
    this.config = config;
    this.node = node;
    this.userCourseEnv = userCourseEnv;
    boolean isCourseAdmin = userCourseEnv.getCourseEnvironment().getCourseGroupManager().isIdentityCourseAdministrator(ureq.getIdentity());
    boolean isCourseCoach = userCourseEnv.getCourseEnvironment().getCourseGroupManager().isIdentityCourseCoach(ureq.getIdentity());
    boolean hasNotification = (isCourseAdmin || isCourseCoach);
    init(ureq, wControl, previewMode, hasNotification);
  }
 
  protected void init(UserRequest ureq, WindowControl wControl, boolean previewMode, boolean hasNotification) {
    myContent = createVelocityContainer("dropbox");
   
    ulButton = LinkFactory.createButton("dropbox.upload", myContent, this);
   
    if (!previewMode) {
      File fDropbox = getDropBox(ureq.getIdentity());
      int numFiles = fDropbox.list().length;
      if (numFiles > 0) myContent.contextPut("numfiles", new String[] {Integer.toString(numFiles)});
     
    } else {
      myContent.contextPut("numfiles", "0");
    }
    myContent.contextPut("previewMode", previewMode ? Boolean.TRUE : Boolean.FALSE);

    // notification
    if ( hasNotification && !previewMode) {
      // offer subscription, but not to guests
      subsContext = DropboxFileUploadNotificationHandler.getSubscriptionContext(userCourseEnv, node);
      if (subsContext != null) {
        contextualSubscriptionCtr = AbstractTaskNotificationHandler.createContextualSubscriptionController(ureq, wControl, getDropboxPathRelToFolderRoot(
            userCourseEnv.getCourseEnvironment(), node), subsContext, DropboxController.class);
        myContent.put("subscription", contextualSubscriptionCtr.getInitialComponent());
        myContent.contextPut("hasNotification", Boolean.TRUE);
      }
    } else {
      myContent.contextPut("hasNotification", Boolean.FALSE);
    }

    putInitialPanel(myContent);
  }
 
  /**
   * Dropbox path relative to folder root.
   * @param courseEnv
   * @param cNode
   * @return Dropbox path relative to folder root.
   */
  public static String getDropboxPathRelToFolderRoot(CourseEnvironment courseEnv, CourseNode cNode) {
    return courseEnv.getCourseBaseContainer().getRelPath() + File.separator + DROPBOX_DIR_NAME + File.separator + cNode.getIdent();
  }
 
 
  /**
   * Get the dropbox of an identity.
   * @param identity
   * @return Dropbox of an identity
   */
  protected File getDropBox(Identity identity) {
    File f = new File( getAbsolutDropBoxFilePath(identity)  );
    if (!f.exists()) f.mkdirs();
    return f;
  }
 
  protected String getAbsolutDropBoxFilePath(Identity identity) {
    return FolderConfig.getCanonicalRoot() + getRelativeDropBoxFilePath(identity);
  }
 
  protected String getRelativeDropBoxFilePath(Identity identity) {
    return getDropboxPathRelToFolderRoot(userCourseEnv.getCourseEnvironment(), node) + File.separator + identity.getName();
  }
 
  /**
   * @see org.olat.core.gui.control.DefaultController#event(org.olat.core.gui.UserRequest, org.olat.core.gui.components.Component, org.olat.core.gui.control.Event)
   */
  public void event(UserRequest ureq, Component source, Event event) {
    if (source == ulButton) {
      fileChooserController = new FileChooserController(ureq, getWindowControl(), this, getUploadLimit(ureq) , true);
      cmc = new CloseableModalController(getWindowControl(), translate("close"), fileChooserController.getInitialComponent(), true, "Upload");
      cmc.activate();
    }
  }

  /**
   * Get upload limit for dropbox of a certain user. The upload can be limited
   * by available-folder space, max folder size or configurated upload-limit.
   * @param ureq
   * @return max upload limit in KB
   */
  private int getUploadLimit(UserRequest ureq) {
    String dropboxPath = getRelativeDropBoxFilePath(ureq.getIdentity());
    Quota dropboxQuota = QuotaManager.getInstance().getCustomQuota(dropboxPath);
    if (dropboxQuota == null) {
      dropboxQuota = QuotaManager.getInstance().getDefaultQuota(QuotaConstants.IDENTIFIER_DEFAULT_NODES);
    }
    OlatRootFolderImpl rootFolder = new OlatRootFolderImpl( getRelativeDropBoxFilePath(ureq.getIdentity()), null);
    VFSContainer dropboxContainer = new OlatNamedContainerImpl(ureq.getIdentity().getName(), rootFolder);
    FullAccessWithQuotaCallback secCallback = new FullAccessWithQuotaCallback(dropboxQuota);
    rootFolder.setLocalSecurityCallback(secCallback);
    int ulLimit = QuotaManager.getInstance().getUploadLimitKB(dropboxQuota.getQuotaKB(),dropboxQuota.getUlLimitKB(),dropboxContainer);
    return ulLimit;
  }

  /**
   * @see org.olat.core.gui.control.DefaultController#event(org.olat.core.gui.UserRequest, org.olat.core.gui.control.Controller, org.olat.core.gui.control.Event)
   */
  public void event(UserRequest ureq, Controller source, Event event) {
    if (source == fileChooserController) {
      cmc.deactivate();
      if (event.equals(Event.DONE_EVENT)) {
        File fIn;
        File fDropbox = getDropBox(ureq.getIdentity());
        boolean success = false;
        if (fileChooserController.isFileFromFolder()) {
          VFSLeaf fileSelection = fileChooserController.getFileSelection();
          if (!(fileSelection instanceof LocalFileImpl))
            throw new AssertException("Only local files supported for dropboc so far.");
          fIn = ((LocalFileImpl)fileSelection).getBasefile();
          String fileName = fIn.getName();
          if (new File(fDropbox, fileName).exists()) {
            //FIXME ms: check if dropbox quota is exceeded -> mit customers abkl�ren
            // temporarily rename
            File fInNew = new File(fIn.getParent(), getNewUniqueName(fileName));
            fIn.renameTo(fInNew);
            // copy
            success = FileUtils.copyFileToDir(fInNew, fDropbox);
            // rename to old name
            fInNew.renameTo(fIn);
            fIn = fInNew;
          } else {
            success = FileUtils.copyFileToDir(fIn, fDropbox);
          }
        } else {
          fIn = fileChooserController.getUploadedFile();
          if (new File(fDropbox, fIn.getName()).exists()) {
            File fInNew = new File(fIn.getParent(), getNewUniqueName(fIn.getName()));
            fIn.renameTo(fInNew);
            fIn = fInNew;
          }
          success = FileUtils.moveFileToDir(fIn, fDropbox);
        }
        if (success) {
          int numFiles = fDropbox.list().length;
          myContent.contextPut("numfiles", new String[] {Integer.toString(numFiles)});
          // assemble confirmation
          String confirmation = getConfirmation(ureq, fIn.getName());
          // send email if necessary
          Boolean sendEmail = (Boolean)config.get(TACourseNode.CONF_DROPBOX_ENABLEMAIL);
          if (sendEmail == null) sendEmail = Boolean.FALSE;
          boolean sendMailError = false;
          if (sendEmail.booleanValue()) {
            MailTemplate mailTempl = new MailTemplate(translate("conf.mail.subject"), confirmation, null) {

              @Override
              public void putVariablesInMailContext(VelocityContext context, Identity recipient) {
                // nothing to do
              }
            };
             
            MailerResult result = MailerWithTemplate.getInstance().sendMail(ureq.getIdentity(), null, null, mailTempl, null);
            if(result.getFailedIdentites().size() > 0) {
              List<Identity> disabledIdentities = new ArrayList<Identity>();
              disabledIdentities = result.getFailedIdentites();
              //show error that message can not be sent
              ArrayList<String> myButtons = new ArrayList<String>();
              myButtons.add(translate("back"));
              String title = MailHelper.getTitleForFailedUsersError(ureq.getLocale());
              String message = MailHelper.getMessageForFailedUsersError(ureq.getLocale(), disabledIdentities);
              // add dropbox specific error message
              message += "\n<br />"+translate("conf.mail.error");
              //FIXME:FG:6.2: fix problem in info message, not here
              message += "\n<br />\n<br />"+confirmation.replace("\n", "&#10;").replace("\r", "&#10;").replace("\u2028", "&#10;");
              DialogBoxController noUsersErrorCtr = null;
              noUsersErrorCtr = activateGenericDialog(ureq, title, message, myButtons, noUsersErrorCtr);
              sendMailError = true;
            } else if(result.getReturnCode() > 0) {
              //show error that message can not be sent
              ArrayList<String> myButtons = new ArrayList<String>();
              myButtons.add(translate("back"));
              DialogBoxController noUsersErrorCtr = null;
              String message = translate("conf.mail.error");
              //FIXME:FG:6.2: fix problem in info message, not here
              message += "\n<br />\n<br />"+confirmation.replace("\n", "&#10;").replace("\r", "&#10;").replace("\u2028", "&#10;");
              noUsersErrorCtr = activateGenericDialog(ureq, translate("error.header"), message, myButtons, noUsersErrorCtr);
              sendMailError = true;
            }
          }

          subsContext = DropboxFileUploadNotificationHandler.getSubscriptionContext(userCourseEnv, node);
          // inform subscription manager about new element
          if (subsContext != null) {
            NotificationsManager.getInstance().markPublisherNews(subsContext, ureq.getIdentity());
          }                         
          // configuration is already translated, don't use showInfo(i18nKey)!
          //FIXME:FG:6.2: fix problem in info message, not here
          if(!sendMailError) {
            getWindowControl().setInfo(confirmation.replace("\n", "&#10;").replace("\r", "&#10;").replace("\u2028", "&#10;"));
          }
          return;
        } else {
          getWindowControl().setInfo("File upload failed.");
        }
      }
    }
  }
 
  private String getNewUniqueName(String name) {
    String body = null;
    String ext = null;
    int dot = name.lastIndexOf(".");
    if (dot != -1) {
      body = name.substring(0, dot);
      ext = name.substring(dot);
    } else {
      body = name;
      ext = "";
    }
    String tStamp = new SimpleDateFormat("yyMMdd-HHmmss").format(new Date());
    return body + "." + tStamp + ext;
  }
 
  private String getConfirmation(UserRequest ureq, String filename) {
    // grab standard text
    String confirmation = translate("conf.stdtext");
    config.set(TACourseNode.CONF_DROPBOX_CONFIRMATION, confirmation);
   
    Context c = new VelocityContext();
    Identity identity = ureq.getIdentity();
    c.put("login", identity.getName());
    c.put("first", identity.getUser().getProperty(UserConstants.FIRSTNAME, getLocale()));
    c.put("last", identity.getUser().getProperty(UserConstants.LASTNAME, getLocale()));
    c.put("email", identity.getUser().getProperty(UserConstants.EMAIL, getLocale()));
    c.put("filename", filename);
    Date now = new Date();
    Formatter f = Formatter.getInstance(ureq.getLocale());
    c.put("date", f.formatDate(now));
    c.put("time", f.formatTime(now));
   
    // update attempts counter for this user: one file - one attempts
    AssessableCourseNode acn = (AssessableCourseNode) node;
    acn.incrementUserAttempts(userCourseEnv);
       
    // log entry for this file
    UserNodeAuditManager am = userCourseEnv.getCourseEnvironment().getAuditManager();
    am.appendToUserNodeLog(node, identity, identity, "FILE UPLOADED: " + filename);

    return VelocityHelper.getInstance().evaluateVTL(confirmation, c);
  }
 
  /**
   *
   * @see org.olat.core.gui.control.DefaultController#doDispose(boolean)
   */
  protected void doDispose() {
    // DialogBoxController gets disposed by BasicController
    if (fileChooserController != null) {
      fileChooserController.dispose();
      fileChooserController = null;
    }
    if (contextualSubscriptionCtr != null) {
      contextualSubscriptionCtr.dispose();
      contextualSubscriptionCtr = null;
    }
  } 
}
TOP

Related Classes of org.olat.course.nodes.ta.DropboxController

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.