enable user to inform recipients about a shared file by mail

This commit is contained in:
Bjoern Schiessle 2013-08-30 13:53:49 +02:00
parent 0a23ac18bc
commit 77adaee645
12 changed files with 292 additions and 31 deletions

View File

@ -131,7 +131,7 @@ if ($needUpgrade) {
if ($trashEnabled) { if ($trashEnabled) {
$trashEmpty = \OCA\Files_Trashbin\Trashbin::isEmpty($user); $trashEmpty = \OCA\Files_Trashbin\Trashbin::isEmpty($user);
} }
OCP\Util::addscript('files', 'fileactions'); OCP\Util::addscript('files', 'fileactions');
OCP\Util::addscript('files', 'files'); OCP\Util::addscript('files', 'files');
OCP\Util::addscript('files', 'keyboardshortcuts'); OCP\Util::addscript('files', 'keyboardshortcuts');
@ -151,5 +151,6 @@ if ($needUpgrade) {
$tmpl->assign('isPublic', false); $tmpl->assign('isPublic', false);
$tmpl->assign('publicUploadEnabled', $publicUploadEnabled); $tmpl->assign('publicUploadEnabled', $publicUploadEnabled);
$tmpl->assign("encryptedFiles", \OCP\Util::encryptedFiles()); $tmpl->assign("encryptedFiles", \OCP\Util::encryptedFiles());
$tmpl->assign("mailNotificationEnabled", \OC_Appconfig::getValue('core', 'shareapi_allow_mail_notification', 'yes'));
$tmpl->printPage(); $tmpl->printPage();
} }

View File

@ -120,3 +120,4 @@
<input type="hidden" name="allowZipDownload" id="allowZipDownload" value="<?php p($_['allowZipDownload']); ?>" /> <input type="hidden" name="allowZipDownload" id="allowZipDownload" value="<?php p($_['allowZipDownload']); ?>" />
<input type="hidden" name="usedSpacePercent" id="usedSpacePercent" value="<?php p($_['usedSpacePercent']); ?>" /> <input type="hidden" name="usedSpacePercent" id="usedSpacePercent" value="<?php p($_['usedSpacePercent']); ?>" />
<input type="hidden" name="encryptedFiles" id="encryptedFiles" value="<?php $_['encryptedFiles'] ? p('1') : p('0'); ?>" /> <input type="hidden" name="encryptedFiles" id="encryptedFiles" value="<?php $_['encryptedFiles'] ? p('1') : p('0'); ?>" />
<input type="hidden" name="mailNotificationEnabled" id="mailNotificationEnabled" value="<?php p($_['mailNotificationEnabled']) ?>" />

View File

@ -23,6 +23,8 @@ OC_JSON::checkLoggedIn();
OCP\JSON::callCheck(); OCP\JSON::callCheck();
OC_App::loadApps(); OC_App::loadApps();
$defaults = new \OCP\Defaults();
if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSource'])) { if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSource'])) {
switch ($_POST['action']) { switch ($_POST['action']) {
case 'share': case 'share':
@ -33,7 +35,7 @@ if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSo
if ($shareType === OCP\Share::SHARE_TYPE_LINK && $shareWith == '') { if ($shareType === OCP\Share::SHARE_TYPE_LINK && $shareWith == '') {
$shareWith = null; $shareWith = null;
} }
$token = OCP\Share::shareItem( $token = OCP\Share::shareItem(
$_POST['itemType'], $_POST['itemType'],
$_POST['itemSource'], $_POST['itemSource'],
@ -41,7 +43,7 @@ if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSo
$shareWith, $shareWith,
$_POST['permissions'] $_POST['permissions']
); );
if (is_string($token)) { if (is_string($token)) {
OC_JSON::success(array('data' => array('token' => $token))); OC_JSON::success(array('data' => array('token' => $token)));
} else { } else {
@ -81,6 +83,102 @@ if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSo
($return) ? OC_JSON::success() : OC_JSON::error(); ($return) ? OC_JSON::success() : OC_JSON::error();
} }
break; break;
case 'informRecipients':
$l = OC_L10N::get('core');
$shareType = (int) $_POST['shareType'];
$itemType = $_POST['itemType'];
$itemSource = $_POST['itemSource'];
$recipient = $_POST['recipient'];
$from = \OCP\Util::getDefaultEmailAddress('sharing-noreply');
$subject = $defaults->getShareNotificationSubject($itemType);
$noMail = array();
$recipientList = array();
if ($shareType === \OCP\Share::SHARE_TYPE_GROUP) {
$users = \OC_Group::usersInGroup($recipient);
foreach ($users as $user) {
$email = OC_Preferences::getValue($user, 'settings', 'email', '');
if ($email !== '' || $recipient === \OCP\User::getUser()) {
$recipientList[] = array(
'email' => $email,
'displayName' => \OCP\User::getDisplayName($user),
'uid' => $user,
);
} else {
$noMail[] = \OCP\User::getDisplayName($user);
}
}
} else { // shared to a single user
$email = OC_Preferences::getValue($recipient, 'settings', 'email', '');
if ($email !== '') {
$recipientList[] = array(
'email' => $email,
'displayName' => \OCP\User::getDisplayName($recipient),
'uid' => $recipient,
);
} else {
$noMail[] = \OCP\User::getDisplayName($recipient);
}
}
// send mail to all recipients with an email address
foreach ($recipientList as $recipient) {
//get correct target folder name
$users = \OCP\Share::getItemSharedWithUser($itemType, $itemSource, $recipient['uid']);
$targetName = $users[0]['file_target'];
//$share = $shareManager->getShares($itemType, array('shareWith' => $recipient['uid'], 'isShareWithUser' => true, 'itemSource' => $itemSource));
//$targetName = $share[0]->getItemTarget();
if ($itemType === 'folder') {
$foldername = "/Shared/" . $targetName;
$filename = $targetName;
} else {
// if it is a file we can just link to the Shared folder,
// that's the place where the user will find the file
$foldername = "/Shared";
$filename = $targetName;
}
$url = \OCP\Util::linkToAbsolute('files', 'index.php', array("dir" => $foldername));
$text = $defaults->getShareNotificationText(\OCP\User::getDisplayName(), $filename, $itemType, $url);
try {
OCP\Util::sendMail(
$recipient['email'],
$recipient['displayName'],
$subject,
$text,
$from,
\OCP\User::getDisplayName()
);
} catch (Exception $exception) {
$noMail[] = \OCP\User::getDisplayName($recipient['displayName']);
}
}
\OCP\Share::setSendMailStatus($itemType, $itemSource, $shareType, true);
if (empty($noMail)) {
OCP\JSON::success();
} else {
OCP\JSON::error(array('data' => array('message' => $l->t("Couldn't send mail to following users: %s ", implode(', ', $noMail)))));
}
break;
case 'informRecipientsDisabled':
$itemSource = $_POST['itemSource'];
$itemType = $_POST['itemType'];
$recipient = $_POST['recipient'];
//$share = $shareManager->getShares($itemType, array('shareWith' => $recipient, 'isShareWithUser' => true, 'itemSource' => $itemSource));
//$share[0]->setMailSend(false);
//$shareManager->update($share[0]);
//write status to db
OCP\JSON::success();
break;
case 'email': case 'email':
// read post variables // read post variables
$user = OCP\USER::getUser(); $user = OCP\USER::getUser();
@ -213,10 +311,10 @@ if (isset($_POST['action']) && isset($_POST['itemType']) && isset($_POST['itemSo
} }
} }
$count = 0; $count = 0;
// enable l10n support // enable l10n support
$l = OC_L10N::get('core'); $l = OC_L10N::get('core');
foreach ($groups as $group) { foreach ($groups as $group) {
if ($count < 15) { if ($count < 15) {
if (stripos($group, $_GET['search']) !== false if (stripos($group, $_GET['search']) !== false

View File

@ -11,7 +11,7 @@
margin-right:7em; margin-right:7em;
position:absolute; position:absolute;
right:0; right:0;
width:19em; width:25em;
z-index:500; z-index:500;
padding:1em; padding:1em;
} }
@ -24,7 +24,7 @@
#shareWithList li { #shareWithList li {
padding-top:.1em; padding-top:.1em;
} }
#shareWithList li:first-child { #shareWithList li:first-child {
white-space:normal; white-space:normal;
} }

View File

@ -217,9 +217,9 @@ OC.Share={
OC.Share.showLink(share.token, share.share_with, itemSource); OC.Share.showLink(share.token, share.share_with, itemSource);
} else { } else {
if (share.collection) { if (share.collection) {
OC.Share.addShareWith(share.share_type, share.share_with, share.share_with_displayname, share.permissions, possiblePermissions, share.collection); OC.Share.addShareWith(share.share_type, share.share_with, share.share_with_displayname, share.permissions, possiblePermissions, share.mail_send, share.collection);
} else { } else {
OC.Share.addShareWith(share.share_type, share.share_with, share.share_with_displayname, share.permissions, possiblePermissions, false); OC.Share.addShareWith(share.share_type, share.share_with, share.share_with_displayname, share.mail_send, share.permissions, possiblePermissions, share.mail_send, false);
} }
} }
if (share.expiration != null) { if (share.expiration != null) {
@ -299,7 +299,7 @@ OC.Share={
} }
}); });
}, },
addShareWith:function(shareType, shareWith, shareWithDisplayName, permissions, possiblePermissions, collection) { addShareWith:function(shareType, shareWith, shareWithDisplayName, permissions, possiblePermissions, mailSend, collection) {
if (!OC.Share.itemShares[shareType]) { if (!OC.Share.itemShares[shareType]) {
OC.Share.itemShares[shareType] = []; OC.Share.itemShares[shareType] = [];
} }
@ -341,6 +341,14 @@ OC.Share={
}else{ }else{
html += escapeHTML(shareWithDisplayName); html += escapeHTML(shareWithDisplayName);
} }
mailNotificationEnabled = $('input:hidden[name=mailNotificationEnabled]').val();
if (mailNotificationEnabled === 'yes') {
checked = '';
if (mailSend === true) {
checked = 'checked';
}
html += '<input type="checkbox" name="mailNotification" class="mailNotification" ' + checked + ' />'+t('core', 'notify user by email')+'</label>';
}
if (possiblePermissions & OC.PERMISSION_CREATE || possiblePermissions & OC.PERMISSION_UPDATE || possiblePermissions & OC.PERMISSION_DELETE) { if (possiblePermissions & OC.PERMISSION_CREATE || possiblePermissions & OC.PERMISSION_UPDATE || possiblePermissions & OC.PERMISSION_DELETE) {
if (editChecked == '') { if (editChecked == '') {
html += '<label style="display:none;">'; html += '<label style="display:none;">';
@ -484,7 +492,7 @@ $(document).ready(function() {
$('input:[type=checkbox]', this).hide(); $('input:[type=checkbox]', this).hide();
$('label', this).hide(); $('label', this).hide();
} }
} else { } else {
$('a.unshare', this).hide(); $('a.unshare', this).hide();
} }
}); });
@ -686,5 +694,28 @@ $(document).ready(function() {
} }
}); });
$(document).on('click', '#dropdown input[name=mailNotification]', function(event) {
event.preventDefault();
event.stopPropagation();
var li = $(this).parent();
var itemType = $('#dropdown').data('item-type');
var itemSource = $('#dropdown').data('item-source');
if (this.checked) {
action = 'informRecipients';
} else {
action = 'informRecipientsDisabled';
}
shareType = $(li).data('share-type');
shareWith = $(li).data('share-with');
$.post(OC.filePath('core', 'ajax', 'share.php'), {action: action, recipient: shareWith, shareType: shareType, itemSource: itemSource, itemType: itemType}, function(result) {
if (result.status !== 'success') {
OC.dialogs.alert(t('core', result.data.message), t('core', 'Warning'));
}
});
});
}); });

View File

@ -846,6 +846,14 @@
<length>32</length> <length>32</length>
</field> </field>
<field>
<name>mail_send</name>
<type>integer</type>
<default>0</default>
<notnull>true</notnull>
<length>1</length>
</field>
<index> <index>
<name>token_index</name> <name>token_index</name>
<field> <field>

View File

@ -13,6 +13,7 @@ if (file_exists(OC::$SERVERROOT . '/themes/' . OC_Util::getTheme() . '/defaults.
class OC_Defaults { class OC_Defaults {
private $theme; private $theme;
private $l;
private $defaultEntity; private $defaultEntity;
private $defaultName; private $defaultName;
@ -24,7 +25,7 @@ class OC_Defaults {
private $defaultLogoClaim; private $defaultLogoClaim;
function __construct() { function __construct() {
$l = OC_L10N::get('core'); $this->l = OC_L10N::get('core');
$this->defaultEntity = "ownCloud"; /* e.g. company name, used for footers and copyright notices */ $this->defaultEntity = "ownCloud"; /* e.g. company name, used for footers and copyright notices */
$this->defaultName = "ownCloud"; /* short name, used when referring to the software */ $this->defaultName = "ownCloud"; /* short name, used when referring to the software */
@ -32,7 +33,7 @@ class OC_Defaults {
$this->defaultBaseUrl = "http://owncloud.org"; $this->defaultBaseUrl = "http://owncloud.org";
$this->defaultSyncClientUrl = " http://owncloud.org/sync-clients/"; $this->defaultSyncClientUrl = " http://owncloud.org/sync-clients/";
$this->defaultDocBaseUrl = "http://doc.owncloud.org"; $this->defaultDocBaseUrl = "http://doc.owncloud.org";
$this->defaultSlogan = $l->t("web services under your control"); $this->defaultSlogan = $this->l->t("web services under your control");
$this->defaultLogoClaim = ""; $this->defaultLogoClaim = "";
if (class_exists("OC_Theme")) { if (class_exists("OC_Theme")) {
@ -47,6 +48,32 @@ class OC_Defaults {
return false; return false;
} }
/**
*
* @param string $itemType typically "file" or "folder"
*/
public function getShareNotificationSubject($itemType) {
if ($this->themeExist('getShareNotificationSubject')) {
return $this->theme->getShareNotificationSubject($itemType);
} else {
return $this->l->t("A %s was shared with you", array($itemType));
}
}
/**
* @param string $sender owner of the file/folder
* @param string $itemName name of the file/folder
* @param string $itemType typically "file" or "folder"
* @param string $link link directly to the file/folder in your ownCloud
*/
public function getShareNotificationText($sender, $itemName, $itemType, $link) {
if ($this->themeExist('getShareNotificationText')) {
return $this->theme->getShareNotificationText($sender, $itemName, $itemType, $link);
} else {
return $this->l->t("%s shared a %s called %s with you. You can find the %s here: %s", array($sender, $itemType, $itemName, $itemType, $link));
}
}
public function getBaseUrl() { public function getBaseUrl() {
if ($this->themeExist('getBaseUrl')) { if ($this->themeExist('getBaseUrl')) {
return $this->theme->getBaseUrl(); return $this->theme->getBaseUrl();

View File

@ -34,6 +34,25 @@ class Defaults {
$this->defaults = new \OC_Defaults(); $this->defaults = new \OC_Defaults();
} }
/**
* @brief subject for notification mails if a new file was shared
* @param string $itemType typically "file" or "folder"
*/
public function getShareNotificationSubject($itemType = "file") {
return $this->defaults->getShareNotificationSubject($itemType);
}
/**
* @brief mail body for notification mails if a new file was shared
* @param string $sender owner of the file/folder
* @param string $itemName name of the file/folder
* @param string $itemType typically "file" or "folder"
* @param string $link link directly to the file/folder in your ownCloud
*/
public function getShareNotificationText($sender, $itemName, $itemType, $link) {
return $this->defaults->getShareNotificationText($sender, $itemName, $itemType, $link);
}
/** /**
* @breif get base URL for the organisation behind your ownCloud instance * @breif get base URL for the organisation behind your ownCloud instance
* @return string * @return string

View File

@ -106,22 +106,22 @@ class Share {
} }
return false; return false;
} }
/** /**
* @brief Prepare a path to be passed to DB as file_target * @brief Prepare a path to be passed to DB as file_target
* @return string Prepared path * @return string Prepared path
*/ */
public static function prepFileTarget( $path ) { public static function prepFileTarget( $path ) {
// Paths in DB are stored with leading slashes, so add one if necessary // Paths in DB are stored with leading slashes, so add one if necessary
if ( substr( $path, 0, 1 ) !== '/' ) { if ( substr( $path, 0, 1 ) !== '/' ) {
$path = '/' . $path; $path = '/' . $path;
} }
return $path; return $path;
} }
/** /**
@ -251,7 +251,57 @@ class Share {
return self::getItems($itemType, $itemTarget, self::$shareTypeUserAndGroups, \OC_User::getUser(), null, $format, return self::getItems($itemType, $itemTarget, self::$shareTypeUserAndGroups, \OC_User::getUser(), null, $format,
$parameters, 1, $includeCollections); $parameters, 1, $includeCollections);
} }
/**
* @brief Get the item of item type shared with a given user by source
* @param string Item type
* @param string Item source
* @param string User user to whom the item was shared
* @return Return list of items with file_target, permissions and expiration
*/
public static function getItemSharedWithUser($itemType, $itemSource, $user) {
$shares = array();
// first check if there is a db entry for the specific user
$query = \OC_DB::prepare(
'SELECT `file_target`, `permissions`, `expiration`
FROM
`*PREFIX*share`
WHERE
`item_source` = ? AND `item_type` = ? AND `share_with` = ?'
);
$result = $query->execute(array($itemSource, $itemType, $user));
while ($row = $result->fetchRow()) {
$shares[] = $row;
}
//if didn't found a result than let's look for a group share.
if(empty($shares)) {
$groups = \OC_Group::getUserGroups($user);
$query = \OC_DB::prepare(
'SELECT `file_target`, `permissions`, `expiration`
FROM
`*PREFIX*share`
WHERE
`item_source` = ? AND `item_type` = ? AND `share_with` in (?)'
);
$result = $query->execute(array($itemSource, $itemType, implode(',', $groups)));
while ($row = $result->fetchRow()) {
$shares[] = $row;
}
}
return $shares;
}
/** /**
* @brief Get the item of item type shared with the current user by source * @brief Get the item of item type shared with the current user by source
* @param string Item type * @param string Item type
@ -633,6 +683,23 @@ class Share {
} }
return false; return false;
} }
/**
* @brief sent status if users got informed by mail about share
* @param string $itemType
* @param string $itemSource
* @param int $shareType SHARE_TYPE_USER, SHARE_TYPE_GROUP, or SHARE_TYPE_LINK
* @param bool $status
*/
public static function setSendMailStatus($itemType, $itemSource, $shareType, $status) {
$status = $status ? 1 : 0;
$query = \OC_DB::prepare(
'UPDATE `*PREFIX*share`
SET `mail_send` = ?
WHERE `item_type` = ? AND `item_source` = ? AND `share_type` = ?');
$query->execute(array($status, $itemType, $itemSource, $shareType));
}
/** /**
* @brief Set the permissions of an item for a specific user or group * @brief Set the permissions of an item for a specific user or group

View File

@ -98,7 +98,7 @@ class OC_Util {
public static function getVersion() { public static function getVersion() {
// hint: We only can count up. Reset minor/patchlevel when // hint: We only can count up. Reset minor/patchlevel when
// updating major/minor version number. // updating major/minor version number.
return array(5, 80, 05); return array(5, 80, 06);
} }
/** /**
@ -352,10 +352,10 @@ class OC_Util {
$encryptedFiles = true; $encryptedFiles = true;
} }
} }
return $encryptedFiles; return $encryptedFiles;
} }
/** /**
* Check for correct file permissions of data directory * Check for correct file permissions of data directory
* @return array arrays with error messages and hints * @return array arrays with error messages and hints
@ -581,16 +581,16 @@ class OC_Util {
} }
return $value; return $value;
} }
/** /**
* @brief Public function to encode url parameters * @brief Public function to encode url parameters
* *
* This function is used to encode path to file before output. * This function is used to encode path to file before output.
* Encoding is done according to RFC 3986 with one exception: * Encoding is done according to RFC 3986 with one exception:
* Character '/' is preserved as is. * Character '/' is preserved as is.
* *
* @param string $component part of URI to encode * @param string $component part of URI to encode
* @return string * @return string
*/ */
public static function encodePath($component) { public static function encodePath($component) {
$encoded = rawurlencode($component); $encoded = rawurlencode($component);
@ -734,7 +734,7 @@ class OC_Util {
} }
} }
/** /**
* Check if the connection to the internet is disabled on purpose * Check if the connection to the internet is disabled on purpose
*/ */
@ -887,7 +887,7 @@ class OC_Util {
$theme = OC_Config::getValue("theme", ''); $theme = OC_Config::getValue("theme", '');
if($theme === '') { if($theme === '') {
if(is_dir(OC::$SERVERROOT . '/themes/default')) { if(is_dir(OC::$SERVERROOT . '/themes/default')) {
$theme = 'default'; $theme = 'default';
} }

View File

@ -33,16 +33,17 @@ $tmpl->assign('shareAPIEnabled', OC_Appconfig::getValue('core', 'shareapi_enable
// Check if connected using HTTPS // Check if connected using HTTPS
if (OC_Request::serverProtocol() === 'https') { if (OC_Request::serverProtocol() === 'https') {
$connectedHTTPS = true; $connectedHTTPS = true;
} else { } else {
$connectedHTTPS = false; $connectedHTTPS = false;
} }
$tmpl->assign('isConnectedViaHTTPS', $connectedHTTPS); $tmpl->assign('isConnectedViaHTTPS', $connectedHTTPS);
$tmpl->assign('enforceHTTPSEnabled', OC_Config::getValue( "forcessl", false)); $tmpl->assign('enforceHTTPSEnabled', OC_Config::getValue( "forcessl", false));
$tmpl->assign('allowLinks', OC_Appconfig::getValue('core', 'shareapi_allow_links', 'yes')); $tmpl->assign('allowLinks', OC_Appconfig::getValue('core', 'shareapi_allow_links', 'yes'));
$tmpl->assign('allowPublicUpload', OC_Appconfig::getValue('core', 'shareapi_allow_public_upload', 'yes')); $tmpl->assign('allowPublicUpload', OC_Appconfig::getValue('core', 'shareapi_allow_public_upload', 'yes'));
$tmpl->assign('allowResharing', OC_Appconfig::getValue('core', 'shareapi_allow_resharing', 'yes')); $tmpl->assign('allowResharing', OC_Appconfig::getValue('core', 'shareapi_allow_resharing', 'yes'));
$tmpl->assign('allowMailNotification', OC_Appconfig::getValue('core', 'shareapi_allow_mail_notification', 'yes'));
$tmpl->assign('sharePolicy', OC_Appconfig::getValue('core', 'shareapi_share_policy', 'global')); $tmpl->assign('sharePolicy', OC_Appconfig::getValue('core', 'shareapi_share_policy', 'global'));
$tmpl->assign('forms', array()); $tmpl->assign('forms', array());
foreach($forms as $form) { foreach($forms as $form) {

View File

@ -163,6 +163,14 @@ if (!$_['internetconnectionworking']) {
<label for="sharePolicyGroupsOnly"><?php p($l->t('Allow users to only share with users in their groups'));?></label><br/> <label for="sharePolicyGroupsOnly"><?php p($l->t('Allow users to only share with users in their groups'));?></label><br/>
</td> </td>
</tr> </tr>
<tr>
<td <?php if ($_['shareAPIEnabled'] === 'no') print_unescaped('style="display:none"');?>>
<input type="checkbox" name="shareapi_allow_mail_notification" id="allowMailNotification"
value="1" <?php if ($_['allowMailNotification'] === 'yes') print_unescaped('checked="checked"'); ?> />
<label for="allowMailNotification"><?php p($l->t('Allow mail notification'));?></label><br/>
<em><?php p($l->t('Allow user to send mail notification for shared files')); ?></em>
</td>
</tr>
</table> </table>
</fieldset> </fieldset>
@ -223,7 +231,7 @@ endfor;?>
</td> </td>
<td> <td>
<?php if(is_int($entry->time)){ <?php if(is_int($entry->time)){
p(OC_Util::formatDate($entry->time)); p(OC_Util::formatDate($entry->time));
} else { } else {
p($entry->time); p($entry->time);
}?> }?>