From 30087b87e8f64f0572cc2a4c27b7c6c3d28a918b Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 14 Dec 2015 00:00:00 +0100 Subject: [PATCH 01/46] Removed assignements from conditions. --- ContributionPlugin.php | 11 ++++++----- controllers/ContributionController.php | 11 +++++++---- libraries/ContributionImportUsers.php | 3 ++- models/Api/ContributionType.php | 6 +++--- 4 files changed, 18 insertions(+), 13 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..61511478 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -181,7 +181,8 @@ public function hookUpgrade($args) } $pagePath = get_option('contribution_page_path'); - if ($pagePath = 'contribution/') { + $pagePath = 'contribution/'; + if ($pagePath) { delete_option('contribution_page_path'); } else { set_option('contribution_page_path', trim($pagePath, '/')); @@ -524,11 +525,11 @@ public function hookAdminItemsBrowseDetailedEach($args) */ public function hookItemsBrowseSql($args) { + $select = $args['select']; + $params = $args['params']; - $select = $args['select']; - $params = $args['params']; - - if (($request = Zend_Controller_Front::getInstance()->getRequest())) { + $request = Zend_Controller_Front::getInstance()->getRequest(); + if ($request) { $db = get_db(); $contributed = $request->get('contributed'); diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 96e931c1..1f99f671 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -61,12 +61,13 @@ public function contributeAction() $csrf = new Omeka_Form_SessionCsrf; $this->view->csrf = $csrf; if(!empty($_POST)) { + $defaultType = get_option('contribution_default_type'); if (!$csrf->isValid($_POST)) { $this->_helper->_flashMessenger(__('There was an error on the form. Please try again.'), 'error'); $typeId = null; if (isset($_POST['contribution_type']) && ($postedType = $_POST['contribution_type'])) { $typeId = $postedType; - } else if ($defaultType = get_option('contribution_default_type')) { + } elseif ($defaultType) { $typeId = $defaultType; } $this->_setupContributeSubmit($typeId); @@ -79,7 +80,7 @@ public function contributeAction() $typeId = null; if (isset($_POST['contribution_type']) && ($postedType = $_POST['contribution_type'])) { $typeId = $postedType; - } else if ($defaultType = get_option('contribution_default_type')) { + } elseif ($defaultType) { $typeId = $defaultType; } if ($this->_captcha) { @@ -146,7 +147,8 @@ public function _setupContributeSubmit($typeId) $profileType = $this->_helper->db->getTable('UserProfilesType')->find($profileTypeId); $this->view->profileType = $profileType; - if($user = current_user()) { + $user = current_user(); + if($user) { $profile = $this->_helper->db->getTable('UserProfilesProfile')->findByUserIdAndTypeId($user->id, $profileTypeId); } if(empty($profile)) { @@ -248,7 +250,8 @@ protected function _processForm($post) // This is a hack to allow the file upload job to succeed // even with the synchronous job dispatcher. - if ($acl = get_acl()) { + $acl = get_acl(); + if ($acl) { $acl->allow(null, 'Items', 'showNotPublic'); $acl->allow(null, 'Collections', 'showNotPublic'); } diff --git a/libraries/ContributionImportUsers.php b/libraries/ContributionImportUsers.php index 1f147e69..40ec9241 100644 --- a/libraries/ContributionImportUsers.php +++ b/libraries/ContributionImportUsers.php @@ -19,7 +19,8 @@ public function perform() //create username from email and set up for some validation checks $username = $contributor['email']; $email = $contributor['email']; - if($user = $db->getTable('User')->findByEmail($contributor['email'])) { + $user = $db->getTable('User')->findByEmail($contributor['email']); + if ($user) { $userContributorMap[$user->id][] = $contributor['id']; } else { if(!$emailValidator->isValid($email)) { diff --git a/models/Api/ContributionType.php b/models/Api/ContributionType.php index 37ec9cea..7690f8fd 100644 --- a/models/Api/ContributionType.php +++ b/models/Api/ContributionType.php @@ -6,14 +6,14 @@ public function getRepresentation(Omeka_Record_AbstractRecord $type) { $representation = array( 'id' => $type->id, - 'url' => self::getResourceUrl("/contribution_types/{$ype->id}"), + 'url' => self::getResourceUrl('/contribution_types/' . $type->id), 'display_name' => $type->display_name, 'file_permissions' => $type->file_permissions ); $representation['item_type'] = array( 'id' => $type->item_type_id, - 'url' => self::getResourceUrl("/item_types/{$type->item_type_id}") - ); + 'url' => self::getResourceUrl('/item_types/' . $type->item_type_id) + ); return $representation; } From 61d6af15120d566a29f772b79964cec6ddd2d7d3 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 14 Dec 2015 00:00:00 +0100 Subject: [PATCH 02/46] Fixed various typos. --- controllers/ContributionController.php | 4 ++-- .../ResponseAdapter/OmekaNet/ContributorFieldsAdapter.php | 2 +- models/Mixin/ContributionOrder.php | 2 +- views/admin/items/browse.php | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 1f99f671..43e18c37 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -261,7 +261,7 @@ protected function _processForm($post) $item->setOwner($user); $item->save(); $item = update_item($item, $itemMetadata, array(), $fileMetadata); - } catch(Omeka_Validator_Exception $e) { + } catch(Omeka_Validate_Exception $e) { $this->flashValidatonErrors($e); return false; } catch (Omeka_File_Ingest_InvalidException $e) { @@ -282,7 +282,7 @@ protected function _processForm($post) $item->save(); //if not simple and the profile doesn't process, send back false for the error $this->_processUserProfile($post, $user); - $this->_linkItemToContributedItem($item, $contributor, $post); + $this->_linkItemToContributedItem($item, null, $post); $this->_sendEmailNotifications($user, $item); return true; } diff --git a/libraries/ApiImport/ResponseAdapter/OmekaNet/ContributorFieldsAdapter.php b/libraries/ApiImport/ResponseAdapter/OmekaNet/ContributorFieldsAdapter.php index 2303f4b4..6873bf6f 100644 --- a/libraries/ApiImport/ResponseAdapter/OmekaNet/ContributorFieldsAdapter.php +++ b/libraries/ApiImport/ResponseAdapter/OmekaNet/ContributorFieldsAdapter.php @@ -39,7 +39,7 @@ protected function getElementSet() $userProfilesType->public = 0; $userProfilesType->required = 0; $userProfilesType->element_set_id = $this->elementSet->id; - $userProfileType->save(); + $userProfilesType->save(); return $this->elementSet; } } \ No newline at end of file diff --git a/models/Mixin/ContributionOrder.php b/models/Mixin/ContributionOrder.php index 807b29e0..ed8a1b0a 100644 --- a/models/Mixin/ContributionOrder.php +++ b/models/Mixin/ContributionOrder.php @@ -95,7 +95,7 @@ public function reorderChildren() array($parentId)); } - public function addChild(Omeka_Record $child) + public function addChild(Omeka_Record_AbstractRecord $child) { if (!$this->_record->exists()) { throw new Omeka_Record_Exception(__('Cannot add a child to a record that does not exist yet!')); diff --git a/views/admin/items/browse.php b/views/admin/items/browse.php index 02eddb2f..09fc4cf0 100644 --- a/views/admin/items/browse.php +++ b/views/admin/items/browse.php @@ -45,7 +45,7 @@ - +
From 1d69836a23f7d5b0c59d2b03d367d89feb52bbb6 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 5 Dec 2016 00:00:00 +0100 Subject: [PATCH 03/46] Fixed mysql install. --- ContributionPlugin.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 61511478..81a73e09 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -111,7 +111,7 @@ public function hookInstall() `id` INT UNSIGNED NOT NULL AUTO_INCREMENT, `item_type_id` INT UNSIGNED NOT NULL, `display_name` VARCHAR(255) NOT NULL, - `file_permissions` ENUM('Disallowed', 'Allowed', 'Required') NOT NULL DEFAULT 'Disallowed', + `file_permissions` ENUM('Disallowed', 'Allowed', 'Required') NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `item_type_id` (`item_type_id`) ) ENGINE=MyISAM;"; From 00038c4a3f711c74f662a19ccd29c5d1d8a49e28 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 2 Jun 2014 02:47:02 +0200 Subject: [PATCH 04/46] Added readme. --- README.md | 87 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 87 insertions(+) create mode 100644 README.md diff --git a/README.md b/README.md new file mode 100644 index 00000000..7677ea03 --- /dev/null +++ b/README.md @@ -0,0 +1,87 @@ +Contribution (plugin for Omeka) +=============================== + + +Summary +------- + +This plugin for [Omeka] provides a way to collect stories, images, or other +files from the public and manage those contributions in your Omeka archive as +items. The form can also automatically add a reCAPTCHA box at the bottom of each +form to prevent spam-bots from spamming your website. + +For more information, see the [Contribution presentation] on [Omeka] and the +[update] done for Omeka 2. + + +Installation +------------ + +Contribution depends on the [Guest User] plugin. You will need to install it +before you can install [Contribution]. + +Uncompress files and rename plugin folder "Contribution". + +Then install it like any other Omeka plugin. + +Settings are not on the plugin page, but at https://www.example.com/admin/contribution/index. + + +Warning +------- + +Use it at your own risk. + +It's always recommended to backup your files and database so you can roll back +if needed. + + +Troubleshooting +--------------- + +See online issues on [Contribution issues] page on GitHub. + + +License +------- + +This plugin is published under [GNU/GPL]. + +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, write to the Free Software Foundation, Inc., +51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + + +Contact +------- + +Current maintainers: + +* Roy Rosenzweig Center for History and New Media + + +Copyright +--------- + +* Copyright Roy Rosenzweig Center for History and New Media, 2010-2013 +* Copyright Daniel Berthereau, 2014 (improvements, see [Daniel-KM]) + + +[Omeka]: https://omeka.org +[Contribution presentation]: http://omeka.org/codex/Plugins/Contribution +[update]: http://omeka.org/codex/Plugins/Contribution_2.0 +[Contribution]: https://github.com/Omeka/plugin-Contribution +[Contribution issues]: https://github.com/Omeka/plugin-Contribution/issues +[Guest User]: https://github.com/Omeka/plugin-GuestUser +[GNU/GPL]: https://www.gnu.org/licenses/gpl-3.0.html "GNU/GPL v3" +[Daniel-KM]: https://github.com/Daniel-KM "Daniel Berthereau" From 3c1bf72b04c73791846ff89467a855dd918d4735 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 05/46] Added a

title to my contributions. --- views/public/contribution/my-contributions.php | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/views/public/contribution/my-contributions.php b/views/public/contribution/my-contributions.php index fab13a28..a48d1a51 100644 --- a/views/public/contribution/my-contributions.php +++ b/views/public/contribution/my-contributions.php @@ -1,6 +1,14 @@ - + $title, + 'bodyclass' => $bodyClass, +)); ?>
+

@@ -30,4 +38,4 @@ - + Date: Mon, 15 Sep 2014 02:47:02 +0200 Subject: [PATCH 06/46] Simplified custom route. --- ContributionPlugin.php | 48 +++++++++++++----------- controllers/SettingsController.php | 5 ++- helpers/ThemeHelpers.php | 36 +++++++----------- plugin.ini | 2 +- views/public/contribution/contribute.php | 3 -- 5 files changed, 45 insertions(+), 49 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..ab2356ed 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -142,6 +142,7 @@ public function hookInstall() $this->_createDefaultContributionTypes(); set_option('contribution_email_recipients', get_option('administrator_email')); + set_option('contribution_page_path', 'contribution'); } /** @@ -259,6 +260,13 @@ public function hookUpgrade($args) set_option('contribution_open', get_option('contribution_simple')); delete_option('contribution_simple'); } + + if (version_compare($oldVersion, '3.1.4', '<')) { + $pagePath = get_option('contribution_page_path'); + if (empty($pagePath)) { + set_option('contribution_page_path', 'contribution'); + } + } } public function hookUninstallMessage() @@ -305,40 +313,38 @@ public function hookDefineAcl($args) /** * Contribution define_routes hook + * * Defines public-only routes that set the contribution controller as the * only accessible one. */ public function hookDefineRoutes($args) { $router = $args['router']; + // Only apply custom routes on public theme. // The wildcards on both routes make these routes always apply for the // contribution controller. - // get the base path - $bp = get_option('contribution_page_path'); - if ($bp) { - $router->addRoute('contributionCustom', - new Zend_Controller_Router_Route("$bp/:action/*", - array('module' => 'contribution', - 'controller' => 'contribution', - 'action' => 'contribute'))); - } else { - - $router->addRoute('contributionDefault', - new Zend_Controller_Router_Route('contribution/:action/*', - array('module' => 'contribution', - 'controller' => 'contribution', - 'action' => 'contribute'))); - - } + // Get the base path. + $basePath = get_option('contribution_page_path'); + $router->addRoute('contribution', + new Zend_Controller_Router_Route( + "$basePath/:action/*", + array( + 'module' => 'contribution', + 'controller' => 'contribution', + 'action' => 'contribute', + ))); if (is_admin_theme()) { $router->addRoute('contributionAdmin', - new Zend_Controller_Router_Route('contribution/:controller/:action/*', - array('module' => 'contribution', - 'controller' => 'index', - 'action' => 'index'))); + new Zend_Controller_Router_Route( + 'contribution/:controller/:action/*', + array( + 'module' => 'contribution', + 'controller' => 'index', + 'action' => 'index', + ))); } } diff --git a/controllers/SettingsController.php b/controllers/SettingsController.php index 958aeccc..6f014dde 100644 --- a/controllers/SettingsController.php +++ b/controllers/SettingsController.php @@ -78,8 +78,9 @@ private function _getForm() $form->addElementToEditGroup('text', 'contribution_page_path', array( 'label' => __('Contribution Slug'), - 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. If left blank, the default path will be named “contribution.”'), - 'filters' => array(array('StringTrim', '/\\\s')) + 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. Default path is “contribution.”'), + 'required' => true, + 'filters' => array(array('StringTrim', '/\\\s')), )); $form->addElementToEditGroup('text', 'contribution_email_sender', array( diff --git a/helpers/ThemeHelpers.php b/helpers/ThemeHelpers.php index 962d4b96..0edd187f 100644 --- a/helpers/ThemeHelpers.php +++ b/helpers/ThemeHelpers.php @@ -15,7 +15,6 @@ * @return string */ - function contribution_admin_header($subsections = array()) { $mainTitle = __('Contribution'); @@ -40,24 +39,17 @@ function contribution_link_to_contribute($linkText = 'Contribute', $actionName = return "$linkText"; } -/** - * Get a URL to the public contribution page. - * - * @param string $action Action to link to, main index if none. - * @return string URL - */ -function contribution_contribute_url($actionName = null) -{ - $path = get_option('contribution_page_path'); - if (empty($path)) { - $route = 'contributionDefault'; - } else { - $route = 'contributionCustom'; - } - $options = array(); - if (!empty($actionName)) { - $options['action'] = $actionName; - } - return get_view()->url($options, $route, array(), true); -} - +/** + * Get a URL to the public contribution page. + * + * @param string $action Action to link to, main index if none. + * @return string URL + */ +function contribution_contribute_url($actionName = null) +{ + $options = array(); + if (!empty($actionName)) { + $options['action'] = $actionName; + } + return get_view()->url($options, 'contribution', array(), true); +} diff --git a/plugin.ini b/plugin.ini index b9dfbc78..30d4ec3a 100644 --- a/plugin.ini +++ b/plugin.ini @@ -6,7 +6,7 @@ link="http://omeka.org/codex/Plugins/Contribution_2.0" support_link="http://omeka.org/forums/forum/plugins" omeka_minimum_version="2.3" omeka_target_version="2.3" -version="3.1.0" +version="3.1.4" tags="social, items" license="GPLv3" required_plugins="GuestUser" diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index 30bc025d..2b1f40c0 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -8,9 +8,6 @@ queue_js_file('contribution-public-form'); $contributionPath = get_option('contribution_page_path'); -if(!$contributionPath) { - $contributionPath = 'contribution'; -} queue_css_file('form'); //load user profiles js and css if needed From c91b420be516de8b8b94e02fee6d5bdceff6ac02 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 07/46] Protected the page "My Contributions". --- controllers/ContributionController.php | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 43e18c37..9c8deb06 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -24,6 +24,10 @@ public function indexAction() public function myContributionsAction() { $user = current_user(); + if (empty($user)) { + $this->_helper->redirector('login', 'users', 'default'); + } + $contribItemTable = $this->_helper->db->getTable('ContributionContributedItem'); $contribItems = array(); From e1b924a6f88cd9f66ec01e58a54192a218e7d73f Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 08/46] Fixed custom route for upgrade. --- ContributionPlugin.php | 1 + 1 file changed, 1 insertion(+) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index ab2356ed..99b3e87a 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -327,6 +327,7 @@ public function hookDefineRoutes($args) // Get the base path. $basePath = get_option('contribution_page_path'); + $basePath = $basePath ?: 'contribution'; $router->addRoute('contribution', new Zend_Controller_Router_Route( "$basePath/:action/*", From abe1dc14e4ca1f130bd59e72fa2bc0d0c00745ee Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 09/46] Internationalized some strings. --- ContributionPlugin.php | 2 +- languages/template.pot | 4 ++-- views/public/contribution/contribute.php | 7 +++++-- views/public/contribution/thankyou.php | 4 ++-- 4 files changed, 10 insertions(+), 7 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 81a73e09..474d80a9 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -674,7 +674,7 @@ public function filterItemCitation($cite,$args) public function filterGuestUserLinks($nav) { $nav['Contribution'] = array( - 'label' => 'My Contributions', + 'label' => __('My Contributions'), 'uri' => contribution_contribute_url('my-contributions'), ); return $nav; diff --git a/languages/template.pot b/languages/template.pot index 099a704c..2e633f12 100644 --- a/languages/template.pot +++ b/languages/template.pot @@ -607,7 +607,7 @@ msgstr "" #, php-format msgid "" "Your contribution will show up in the archive once an administrator approves " -"it. Meanwhile, feel free to %s or %s ." +"it. Meanwhile, feel free to %s or %s." msgstr "" #: views/public/contribution/thankyou.php:7 @@ -619,7 +619,7 @@ msgstr "" msgid "" "If you would like to interact with the site further, you can use an account " "that is ready for you. Visit %s, and request a new password for the email " -"you used" +"you used." msgstr "" #: views/public/contribution/type-form.php:3 diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index 30bc025d..d12498df 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -16,7 +16,7 @@ //load user profiles js and css if needed if(get_option('contribution_user_profile_type') && plugin_is_active('UserProfiles') ) { queue_js_file('admin-globals'); - queue_js_file('tiny_mce', 'javascripts/vendor/tiny_mce'); + queue_js_file('tiny_mce', 'javascripts/vendor/tiny_mce'); queue_js_file('elements'); queue_css_string("input.add-element {display: block}"); } @@ -42,7 +42,10 @@ redirect = absolute_url(); ?> -

You must '>create an account or '>log in before contributing. You can still leave your identity to site visitors anonymous.

+

+ ', '', '', ''); ?> + +

diff --git a/views/public/contribution/thankyou.php b/views/public/contribution/thankyou.php index a2bc1d32..1a805e68 100644 --- a/views/public/contribution/thankyou.php +++ b/views/public/contribution/thankyou.php @@ -1,10 +1,10 @@

-

" . __('browse the archive') . ""); ?> +

" . __('browse the archive') . ""); ?>

-

" . __('this page') . ""); ?> +

" . __('this page') . ""); ?>

From 71d36148220420e1c6b129180fa1dd07b5a21631 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 2 Jun 2014 02:47:02 +0200 Subject: [PATCH 10/46] Allowed to upload multiple files. --- ContributionPlugin.php | 7 +++ controllers/ContributionController.php | 16 +++-- models/ContributionType.php | 17 ++--- plugin.ini | 2 +- views/admin/types/form.php | 28 ++++++--- views/public/contribution/contribute.php | 19 ++++-- views/public/contribution/type-form.php | 59 +++++++++++++++--- views/public/css/form.css | 7 ++- .../javascripts/contribution-public-form.js | 62 ++++++++++++++++++- 9 files changed, 179 insertions(+), 38 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..8437dde4 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -112,6 +112,7 @@ public function hookInstall() `item_type_id` INT UNSIGNED NOT NULL, `display_name` VARCHAR(255) NOT NULL, `file_permissions` ENUM('Disallowed', 'Allowed', 'Required') NOT NULL DEFAULT 'Disallowed', + `multiple_files` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', PRIMARY KEY (`id`), UNIQUE KEY `item_type_id` (`item_type_id`) ) ENGINE=MyISAM;"; @@ -259,6 +260,12 @@ public function hookUpgrade($args) set_option('contribution_open', get_option('contribution_simple')); delete_option('contribution_simple'); } + + if (version_compare($oldVersion, '3.1.1', '<')) { + $db = $this->_db; + $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `multiple_files` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; + $db->query($sql); + } } public function hookUninstallMessage() diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 96e931c1..662bbbf3 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -159,7 +159,7 @@ public function _setupContributeSubmit($typeId) /** * Creates the reCAPTCHA object and returns it. - * + * * @return Zend_Captcha_Recaptcha|null */ protected function _setupCaptcha() @@ -244,7 +244,7 @@ protected function _processForm($post) $itemMetadata['collection_id'] = (int) $collectionId; } - $fileMetadata = $this->_processFileUpload($contributionType); + $fileMetadata = $this->_processFilesUpload($contributionType); // This is a hack to allow the file upload job to succeed // even with the synchronous job dispatcher. @@ -310,10 +310,14 @@ protected function _processUserProfile($post, $user) /** * Deals with files specified on the contribution form. * + * @todo Check if multiple files are allowed. + * @todo Error when option is required and when multiple files are allowed: an empty contributed_file input generate an error. + * * @param ContributionType $contributionType Type of contribution. - * @return array File upload array. + * @return array Files upload array. */ - protected function _processFileUpload($contributionType) { + protected function _processFilesUpload($contributionType) + { if ($contributionType->isFileAllowed()) { $options = array(); if ($contributionType->isFileRequired()) { @@ -385,13 +389,13 @@ protected function _addElementTextsToItem($item, $elements) */ protected function _validateContribution($post) { - + // ReCaptcha ignores the first argument. if ($this->_captcha and !$this->_captcha->isValid(null, $_POST)) { $this->_helper->flashMessenger(__('Your CAPTCHA submission was invalid, please try again.'), 'error'); return false; } - + if ($post['terms-agree'] == 0) { $this->_helper->flashMessenger(__('You must agree to the Terms and Conditions.'), 'error'); return false; diff --git a/models/ContributionType.php b/models/ContributionType.php index adfbaafb..b532534e 100644 --- a/models/ContributionType.php +++ b/models/ContributionType.php @@ -22,9 +22,12 @@ class ContributionType extends Omeka_Record_AbstractRecord public $item_type_id; public $display_name; public $file_permissions = 'Disallowed'; - - protected $_related = array('ContributionTypeElements' => 'getTypeElements', - 'ItemType' => 'getItemType'); + public $multiple_files = 0; + + protected $_related = array( + 'ContributionTypeElements' => 'getTypeElements', + 'ItemType' => 'getItemType', + ); protected function filterPostData($post) { @@ -34,7 +37,7 @@ protected function filterPostData($post) } return $post; } - + protected function _validate() { if(empty($this->item_type_id)) { @@ -47,7 +50,7 @@ protected function _initializeMixins() $this->_mixins[] = new Mixin_ContributionOrder($this, 'ContributionTypeElement', 'type_id', 'Elements'); } - + /** * Get the type elements associated with this type. * @@ -57,7 +60,7 @@ public function getTypeElements() { return $this->_db->getTable('ContributionTypeElement')->findByType($this); } - + /** * Get the item type associated with this type. * @@ -173,7 +176,7 @@ public function getPossibleTypeElements() } return $options; } - + public function getRecordUrl($action = 'show') { return url("contribution/types/$action/id/{$this->id}"); diff --git a/plugin.ini b/plugin.ini index b9dfbc78..6b839bfc 100644 --- a/plugin.ini +++ b/plugin.ini @@ -6,7 +6,7 @@ link="http://omeka.org/codex/Plugins/Contribution_2.0" support_link="http://omeka.org/forums/forum/plugins" omeka_minimum_version="2.3" omeka_target_version="2.3" -version="3.1.0" +version="3.1.1" tags="social, items" license="GPLv3" required_plugins="GuestUser" diff --git a/views/admin/types/form.php b/views/admin/types/form.php index 3cdd85b0..40e1e79b 100644 --- a/views/admin/types/form.php +++ b/views/admin/types/form.php @@ -1,8 +1,8 @@ -getTable('ContributionType')->getPossibleItemTypes(); $itemTypeOptions = array('' => 'Select an Item Type') + $itemTypeOptions; ?> - +
@@ -42,17 +42,27 @@ formSelect('file_permissions', $contribution_type->file_permissions, array(), ContributionType::getPossibleFilePermissions()); ?>
- - + + +
+
+ +
+
+

+
+ formCheckbox("multiple_files", null, array('checked' => $contribution_type->multiple_files)); ?> +
+
+
-
    - +
  • Element->name); ?> @@ -65,7 +75,7 @@
    - +
    Element->description); ?>
    @@ -96,7 +106,7 @@ ?> - +
  • @@ -112,7 +122,7 @@
    - + exists()): ?> 'big red button delete-confirm')); ?> diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index 30bc025d..fe442b93 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -6,13 +6,13 @@ * @package Contribution */ -queue_js_file('contribution-public-form'); $contributionPath = get_option('contribution_page_path'); if(!$contributionPath) { $contributionPath = 'contribution'; } queue_css_file('form'); +queue_js_file('contribution-public-form'); //load user profiles js and css if needed if(get_option('contribution_user_profile_type') && plugin_is_active('UserProfiles') ) { queue_js_file('admin-globals'); @@ -32,7 +32,7 @@
    - +

    redirect = absolute_url(); ?> -

    You must '>create an account or '>log in before contributing. You can still leave your identity to site visitors anonymous.

    +

    You must '>create an account or '>log in before contributing. You can still leave your identity to site visitors anonymous.

    @@ -54,7 +54,18 @@
    - + partial('contribution/type-form.php', $partialOptions); + }?>
diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 9512c838..f4513653 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -5,18 +5,40 @@

display_name); ?>

multiple_files; + if ($type->isFileRequired()): $required = true; ?> + + +
+ formLabel('contributed_file', __('Upload a file'), array( + 'id' => 'file-inputs', + )); ?> +
+
+ formFile('contributed_file[0]', array('class' => 'fileinput button')); ?> +

+
+
+
+
formLabel('contributed_file', __('Upload a file')); ?>
- formFile('contributed_file', array('class' => 'fileinput')); ?> + formFile('contributed_file', array('class' => 'fileinput button')); ?> +

+ @@ -29,14 +51,35 @@ isFileAllowed()): ?> -
-
- formLabel('contributed_file', __('Upload a file (Optional)')); ?> -
-
- formFile('contributed_file', array('class' => 'fileinput')); ?> + + +
+ formLabel('contributed_file', __('Upload a file (Optional)'), array( + 'id' => 'file-inputs', + )); ?> +
+
+ formFile('contributed_file[0]', array('class' => 'fileinput button')); ?> +

+
+ +
+
+ formLabel('contributed_file', __('Upload a file (Optional)')); ?> +
+
+ formFile('contributed_file', array('class' => 'fileinput button')); ?> +

+
+
+ + @@ -90,7 +133,7 @@

description; ?>

- Elements as $element) { echo $this->profileElementForm($element, $profile); } diff --git a/views/public/css/form.css b/views/public/css/form.css index 1cd40f8a..2a87f42c 100644 --- a/views/public/css/form.css +++ b/views/public/css/form.css @@ -1,7 +1,7 @@ div#contribution-type-form div.inputs { width: 60%; - + } div#location_form { @@ -24,4 +24,7 @@ p#contribution-userprofile-visibility { div.contribution-userprofile.exists { display: none; -} \ No newline at end of file +} +#upload-files input { + display: block; +} diff --git a/views/public/javascripts/contribution-public-form.js b/views/public/javascripts/contribution-public-form.js index 5c28871a..9e7d6c36 100644 --- a/views/public/javascripts/contribution-public-form.js +++ b/views/public/javascripts/contribution-public-form.js @@ -1,3 +1,63 @@ +if (!Omeka) { + var Omeka = {}; +} + +// From admin/themes/default/javascripts/items.js. +if (typeof Omeka === 'undefined') { + Omeka = {}; +} + +Omeka.Items = {}; + +(function ($) { + /** + * Enable drag and drop sorting for files. + */ + Omeka.Items.enableSorting = function () { + $('.sortable').sortable({ + items: 'li.file', + forcePlaceholderSize: true, + forceHelperSize: true, + revert: 200, + placeholder: "ui-sortable-highlight", + containment: 'document', + update: function (event, ui) { + $(this).find('.file-order').each(function (index) { + $(this).val(index + 1); + }); + } + }); + $( ".sortable" ).disableSelection(); + + $( ".sortable input[type=checkbox]" ).each(function () { + $(this).css("display", "none"); + }); + }; + + /** + * Allow adding an arbitrary number of file input elements to the items form so that + * more than one file can be uploaded at once. + * + * @param {string} label + */ + Omeka.Items.enableAddFiles = function (label) { + var filesDiv = $('#files-metadata .files'); + + var link = $('' + label + ''); + link.click(function (event) { + event.preventDefault(); + var inputs = filesDiv.find('input'); + var inputCount = inputs.length; + var fileHtml = '
'; + $(fileHtml).insertAfter(inputs.last()).hide().slideDown(200, function () { + // Extra show fixes IE bug. + $(this).show(); + }); + }); + + $('#upload-files').after(link); + }; +})(jQuery); function toggleProfileEdit() { jQuery('div.contribution-userprofile').toggle(); @@ -26,7 +86,7 @@ function enableContributionAjaxForm(url) { form.empty(); if (value != "") { jQuery.post(url, {contribution_type: value}, function(data) { - form.append(data); + form.append(data); form.show(duration, function() { form.trigger('contribution-form-shown'); form.trigger('omeka:tabselected'); From 29aebffbabeb48d032f38debd413c6ac031ec476 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 15 Sep 2014 02:47:02 +0200 Subject: [PATCH 11/46] Set InnoDB as default engine. --- ContributionPlugin.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 99b3e87a..113356fc 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -114,7 +114,7 @@ public function hookInstall() `file_permissions` ENUM('Disallowed', 'Allowed', 'Required') NOT NULL DEFAULT 'Disallowed', PRIMARY KEY (`id`), UNIQUE KEY `item_type_id` (`item_type_id`) - ) ENGINE=MyISAM;"; + ) ENGINE=InnoDB;"; $this->_db->query($sql); $sql = "CREATE TABLE IF NOT EXISTS `$db->ContributionTypeElement` ( @@ -127,7 +127,7 @@ public function hookInstall() PRIMARY KEY (`id`), UNIQUE KEY `type_id_element_id` (`type_id`, `element_id`), KEY `order` (`order`) - ) ENGINE=MyISAM;"; + ) ENGINE=InnoDB;"; $this->_db->query($sql); $sql = "CREATE TABLE IF NOT EXISTS `$db->ContributionContributedItem` ( @@ -137,7 +137,7 @@ public function hookInstall() `anonymous` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', PRIMARY KEY (`id`), UNIQUE KEY `item_id` (`item_id`) - ) ENGINE=MyISAM;"; + ) ENGINE=InnoDB;"; $this->_db->query($sql); $this->_createDefaultContributionTypes(); From 78a2ede1a0ae54c899c7b9adf160215f9d671984 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 12/46] Updated tests. --- tests/cases/ContributionTypeTest.php | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/tests/cases/ContributionTypeTest.php b/tests/cases/ContributionTypeTest.php index d245f847..c6140026 100644 --- a/tests/cases/ContributionTypeTest.php +++ b/tests/cases/ContributionTypeTest.php @@ -25,13 +25,13 @@ public function testIsFileAllowed() $type = new ContributionType; $this->assertFalse($type->isFileAllowed()); - $type->file_permissions = ContributionType::FILE_PERMISSION_ALLOWED; + $type->file_permissions = 'Allowed'; $this->assertTrue($type->isFileAllowed()); - $type->file_permissions = ContributionType::FILE_PERMISSION_REQUIRED; + $type->file_permissions = 'Required'; $this->assertTrue($type->isFileAllowed()); - $type->file_permissions = ContributionType::FILE_PERMISSION_DISALLOWED; + $type->file_permissions = 'Disallowed'; $this->assertFalse($type->isFileAllowed()); } @@ -41,22 +41,22 @@ public function testIsFileRequired() $type = new ContributionType; $this->assertFalse($type->isFileRequired()); - $type->file_permissions = ContributionType::FILE_PERMISSION_ALLOWED; + $type->file_permissions = 'Allowed'; $this->assertFalse($type->isFileRequired()); - $type->file_permissions = ContributionType::FILE_PERMISSION_REQUIRED; + $type->file_permissions = 'Required'; $this->assertTrue($type->isFileRequired()); - $type->file_permissions = ContributionType::FILE_PERMISSION_DISALLOWED; + $type->file_permissions = 'Disallowed'; $this->assertFalse($type->isFileRequired()); } public function testFilePermissionsCoverage() { $permissions = ContributionType::getPossibleFilePermissions(); - $this->assertAndRemoveArrayKey(ContributionType::FILE_PERMISSION_ALLOWED, $permissions); - $this->assertAndRemoveArrayKey(ContributionType::FILE_PERMISSION_REQUIRED, $permissions); - $this->assertAndRemoveArrayKey(ContributionType::FILE_PERMISSION_DISALLOWED, $permissions); + $this->assertAndRemoveArrayKey('Allowed', $permissions); + $this->assertAndRemoveArrayKey('Required', $permissions); + $this->assertAndRemoveArrayKey('Disallowed', $permissions); $this->assertEquals(0, count($permissions), 'Not all file permission levels are covered by testing.'); } From aaceda9ac7b2444182b28976e2eb528887c78ed1 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 18 Aug 2014 02:47:02 +0200 Subject: [PATCH 13/46] Fixed error message when multiple files are downloaded. --- controllers/ContributionController.php | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 662bbbf3..b7107dc2 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -244,6 +244,7 @@ protected function _processForm($post) $itemMetadata['collection_id'] = (int) $collectionId; } + // TODO Check if there is at least one file if one file or more is required and remove the catch below. $fileMetadata = $this->_processFilesUpload($contributionType); // This is a hack to allow the file upload job to succeed @@ -265,6 +266,11 @@ protected function _processForm($post) // Copying this cruddy hack if (strstr($e->getMessage(), "'contributed_file'")) { $this->_helper->flashMessenger("You must upload a file when making a {$contributionType->display_name} contribution.", 'error'); + } + // Check multiple files. + elseif (strstr($e->getMessage(), "contributed_file_")) { + $this->_helper->flashMessenger(__('One or more files have not been uploaded.') + . ' ' . __('You must upload a file when making a %s contribution.', $contributionType->display_name), 'error'); } else { $this->_helper->flashMessenger($e->getMessage()); } @@ -273,6 +279,7 @@ protected function _processForm($post) $this->_helper->flashMessenger($e->getMessage()); return false; } + $this->_addElementTextsToItem($item, $post['Elements']); // Allow plugins to deal with the inputs they may have added to the form. fire_plugin_hook('contribution_save_form', array('contributionType'=>$contributionType,'record'=>$item, 'post'=>$post)); @@ -320,11 +327,7 @@ protected function _processFilesUpload($contributionType) { if ($contributionType->isFileAllowed()) { $options = array(); - if ($contributionType->isFileRequired()) { - $options['ignoreNoFile'] = false; - } else { - $options['ignoreNoFile'] = true; - } + $options['ignoreNoFile'] = !$contributionType->isFileRequired(); $fileMetadata = array( 'file_transfer_type' => 'Upload', From 3cadb5393e674fe85888716c6cd0c862b80f8375 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 15 Sep 2014 02:47:02 +0200 Subject: [PATCH 14/46] Made standard the config form. --- ContributionPlugin.php | 102 +++++++++++++----- libraries/Contribution/Form/Settings.php | 87 +++++++++++++++ views/admin/contribution-navigation.php | 29 +++-- views/admin/index/index.php | 2 +- .../plugins/contribution-config-form.php | 16 +++ 5 files changed, 191 insertions(+), 45 deletions(-) create mode 100644 libraries/Contribution/Form/Settings.php create mode 100644 views/admin/plugins/contribution-config-form.php diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 113356fc..af2b3ad3 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -27,11 +27,13 @@ class ContributionPlugin extends Omeka_Plugin_AbstractPlugin protected $_hooks = array( 'initialize', 'install', - 'uninstall', 'upgrade', + 'uninstall', + 'uninstall_message', + 'config_form', + 'config', 'define_acl', 'define_routes', - 'uninstall_message', 'admin_items_search', 'admin_items_show_sidebar', 'admin_items_browse_detailed_each', @@ -59,7 +61,7 @@ class ContributionPlugin extends Omeka_Plugin_AbstractPlugin * @var array Options and their default values. */ protected $_options = array( - 'contribution_page_path', + 'contribution_page_path' => 'contribution', 'contribution_email_sender', 'contribution_email_recipients', 'contribution_consent_text', @@ -140,30 +142,10 @@ public function hookInstall() ) ENGINE=InnoDB;"; $this->_db->query($sql); - $this->_createDefaultContributionTypes(); - set_option('contribution_email_recipients', get_option('administrator_email')); - set_option('contribution_page_path', 'contribution'); - } + $this->_options['contribution_email_recipients'] = get_option('administrator_email'); + $this->_installOptions(); - /** - * Contribution uninstall hook - */ - public function hookUninstall() - { - // Delete all the Contribution options - foreach ($this->_options as $option) { - delete_option($option); - } - $db = $this->_db; - // Drop all the Contribution tables - $sql = "DROP TABLE IF EXISTS - `$db->ContributionType`, - `$db->ContributionTypeElement`, - `$db->ContributionContributor`, - `$db->ContributionContributedItem`, - `$db->ContributionContributorField`, - `$db->ContributionContributorValue`;"; - $this->_db->query($sql); + $this->_createDefaultContributionTypes(); } public function hookUpgrade($args) @@ -264,11 +246,30 @@ public function hookUpgrade($args) if (version_compare($oldVersion, '3.1.4', '<')) { $pagePath = get_option('contribution_page_path'); if (empty($pagePath)) { - set_option('contribution_page_path', 'contribution'); + set_option('contribution_page_path', $this->_options['contribution_page_path']); } } } + /** + * Contribution uninstall hook + */ + public function hookUninstall() + { + $db = $this->_db; + // Drop all the Contribution tables + $sql = "DROP TABLE IF EXISTS + `$db->ContributionType`, + `$db->ContributionTypeElement`, + `$db->ContributionContributor`, + `$db->ContributionContributedItem`, + `$db->ContributionContributorField`, + `$db->ContributionContributorValue`;"; + $this->_db->query($sql); + + $this->_uninstallOptions(); + } + public function hookUninstallMessage() { echo '

Warning: Uninstalling the Contribution plugin @@ -277,6 +278,52 @@ public function hookUninstallMessage()

The contributed items themselves will remain.

'; } + /** + * Shows plugin configuration page. + */ + public function hookConfigForm($args) + { + $view = $args['view']; + + require_once dirname(__FILE__) . DIRECTORY_SEPARATOR . 'forms' . DIRECTORY_SEPARATOR . 'Settings.php'; + $form = new Contribution_Form_Settings; + $defaults = array(); + foreach ($this->_options as $key => $value) { + if (is_string($key)) { + $defaults[$key] = get_option($key); + } + else { + $defaults[$value] = get_option($value); + } + } + $form->setDefaults($defaults); + + echo $view->partial( + 'plugins/contribution-config-form.php', + array( + 'form' => $form, + )); + } + + /** + * Saves plugin configuration page. + * + * @param array Options set in the config form. + */ + public function hookConfig($args) + { + $post = $args['post']; + + // Manage an exception. + if (empty($post['contribution_page_path'])) { + $post['contribution_page_path'] = $this->_options['contribution_page_path']; + } + + foreach ($post as $key => $value) { + set_option($key, $value); + } + } + /** * Contribution define_acl hook * Restricts access to admin-only controllers and actions. @@ -327,7 +374,6 @@ public function hookDefineRoutes($args) // Get the base path. $basePath = get_option('contribution_page_path'); - $basePath = $basePath ?: 'contribution'; $router->addRoute('contribution', new Zend_Controller_Router_Route( "$basePath/:action/*", diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php new file mode 100644 index 00000000..4ce72e45 --- /dev/null +++ b/libraries/Contribution/Form/Settings.php @@ -0,0 +1,87 @@ +setOptions(array('type' => 'contribution_settings')); + $this->setAttrib('id', 'settings-form'); + + $db = get_db(); + + $this->addElement('text', 'contribution_page_path', array( + 'label' => __('Contribution Slug'), + 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. Default path is “contribution.”'), + 'required' => true, + 'filters' => array(array('StringTrim', '/\\\s')), + )); + + $this->addElement('text', 'contribution_email_sender', array( + 'label' => __('Contribution Confirmation Email'), + 'description' => __('An email message will be sent to each contributor from this address confirming that they submitted a contribution to this website. Leave blank if you do not want an email sent.'), + 'validators' => array('EmailAddress'), + )); + + $this->addElement('textarea', 'contribution_email_recipients', array( + 'label' => __('New Contribution Notification Emails'), + 'description' => __('An email message will be sent to each address here whenever a new item is contributed. Leave blank if you do not want anyone to be alerted of contributions by email.'), + 'attribs' => array('rows' => '5'), + )); + + $this->addElement('textarea', 'contribution_consent_text', array( + 'label' => __('Text of Terms of Service'), + 'description' => __('The text of the legal disclaimer to which contributors will agree.'), + 'attribs' => array('class' => 'html-editor', 'rows' => '15'), + )); + + $this->addElement('checkbox', 'contribution_simple', array( + 'label' => __("Use 'Simple' Options"), + 'description' => __("This will require an email address from contributors, and create a guest user from that information. If those users want to use the account, they will have to request a new password for the account. If you want to collect additional information about contributors, you cannot use the simple option. See documentation for details. "), + ), + array('checked' => (bool) get_option('contribution_simple') ? 'checked' : '') + ); + + $this->addElement('textarea', 'contribution_email', array( + 'label' => __("Email text to send to contributors"), + 'description' => __("Email text to send to contributors when they submit an item. A link to their contribution will be appended. If using the 'Simple' option, we recommend that you notify contributors that a guest user account has been created for them, and what they gain by confirming their account."), + 'attribs' => array('class' => 'html-editor', 'rows' => '15'), + )); + + $collections = $db->getTable('Collection')->findPairsForSelectForm(); + $collections = array('' => __('Do not put contributions in any collection')) + $collections; + + $this->addElement('select', 'contribution_collection_id', array( + 'label' => __('Contribution Collection'), + 'description' => __('The collection to which contributions will be added. Changes here will only affect new contributions.'), + 'multiOptions' => $collections, + )); + + $types = $db->getTable('ContributionType')->findPairsForSelectForm(); + $types = array('' => __('No default type')) + $types; + + $this->addElement('select', 'contribution_default_type', array( + 'label' => __('Default Contribution Type'), + 'description' => __('The type that will be chosen for contributors by default.'), + 'multiOptions' => $types, + )); + + if (plugin_is_active('UserProfiles')) { + $profileTypes = $db->getTable('UserProfilesType')->findPairsForSelectForm(); + $this->addElement('select', 'contribution_user_profile_type', array( + 'label' => __('Choose a profile type for contributors'), + 'description' => __('Configure the profile type under User Profiles'), + 'multiOptions' => array('' => __("None")) + $profileTypes, + )); + } + } +} diff --git a/views/admin/contribution-navigation.php b/views/admin/contribution-navigation.php index 995777a9..3182afc8 100644 --- a/views/admin/contribution-navigation.php +++ b/views/admin/contribution-navigation.php @@ -1,20 +1,17 @@ \ No newline at end of file + diff --git a/views/admin/index/index.php b/views/admin/index/index.php index e3bd2217..bbd11a45 100644 --- a/views/admin/index/index.php +++ b/views/admin/index/index.php @@ -42,7 +42,7 @@ -
" . __('submission settings') . ""); ?>
+
'Contribution')) . '">', ''); ?>
  • diff --git a/views/admin/plugins/contribution-config-form.php b/views/admin/plugins/contribution-config-form.php new file mode 100644 index 00000000..b88bf3ae --- /dev/null +++ b/views/admin/plugins/contribution-config-form.php @@ -0,0 +1,16 @@ + + +getElements(); +foreach( $elements as $element) { + echo $element; +} +?> From b3702099f6cccdc5eff686f27bd0a5d0b2cf0ab0 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 15/46] Fixed color of the message when the settings are saved. --- controllers/SettingsController.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/controllers/SettingsController.php b/controllers/SettingsController.php index 958aeccc..fe16846a 100644 --- a/controllers/SettingsController.php +++ b/controllers/SettingsController.php @@ -31,7 +31,7 @@ public function editAction() if (isset($_POST['submit'])) { if ($form->isValid($_POST)) { $this->_setOptions($form->getValues()); - $this->_helper->flashMessenger(__('Settings have been saved.')); + $this->_helper->flashMessenger(__('Settings have been saved.'), 'success'); } else { $this->_helper->flashMessenger(__('There were errors found in your form. Please edit and resubmit.', 'error')); } From 294813880175512ce5ab15f861c7ab64365583dd Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 16/46] Renamed 'contributed_file' to 'file' in order to use default upload method. --- controllers/ContributionController.php | 6 +++--- views/public/contribution/type-form.php | 16 ++++++++-------- .../javascripts/contribution-public-form.js | 2 +- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index b7107dc2..fe6e5e16 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -264,11 +264,11 @@ protected function _processForm($post) return false; } catch (Omeka_File_Ingest_InvalidException $e) { // Copying this cruddy hack - if (strstr($e->getMessage(), "'contributed_file'")) { + if (strstr($e->getMessage(), "'file'")) { $this->_helper->flashMessenger("You must upload a file when making a {$contributionType->display_name} contribution.", 'error'); } // Check multiple files. - elseif (strstr($e->getMessage(), "contributed_file_")) { + elseif (strstr($e->getMessage(), "file_")) { $this->_helper->flashMessenger(__('One or more files have not been uploaded.') . ' ' . __('You must upload a file when making a %s contribution.', $contributionType->display_name), 'error'); } else { @@ -331,7 +331,7 @@ protected function _processFilesUpload($contributionType) $fileMetadata = array( 'file_transfer_type' => 'Upload', - 'files' => 'contributed_file', + 'files' => 'file', 'file_ingest_options' => $options ); diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index f4513653..1b59f60a 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -18,12 +18,12 @@ });
    - formLabel('contributed_file', __('Upload a file'), array( + formLabel('file', __('Upload a file'), array( 'id' => 'file-inputs', )); ?>
    - formFile('contributed_file[0]', array('class' => 'fileinput button')); ?> + formFile('file[0]', array('class' => 'fileinput button')); ?>

    @@ -31,10 +31,10 @@
    - formLabel('contributed_file', __('Upload a file')); ?> + formLabel('file', __('Upload a file')); ?>
    - formFile('contributed_file', array('class' => 'fileinput button')); ?> + formFile('file', array('class' => 'fileinput button')); ?>

    @@ -58,12 +58,12 @@ });
    - formLabel('contributed_file', __('Upload a file (Optional)'), array( + formLabel('file', __('Upload a file (Optional)'), array( 'id' => 'file-inputs', )); ?>
    - formFile('contributed_file[0]', array('class' => 'fileinput button')); ?> + formFile('file[0]', array('class' => 'fileinput button')); ?>

    @@ -71,10 +71,10 @@
    - formLabel('contributed_file', __('Upload a file (Optional)')); ?> + formLabel('file', __('Upload a file (Optional)')); ?>
    - formFile('contributed_file', array('class' => 'fileinput button')); ?> + formFile('file', array('class' => 'fileinput button')); ?>

    diff --git a/views/public/javascripts/contribution-public-form.js b/views/public/javascripts/contribution-public-form.js index 9e7d6c36..263209ce 100644 --- a/views/public/javascripts/contribution-public-form.js +++ b/views/public/javascripts/contribution-public-form.js @@ -48,7 +48,7 @@ Omeka.Items = {}; event.preventDefault(); var inputs = filesDiv.find('input'); var inputCount = inputs.length; - var fileHtml = '
    '; + var fileHtml = '
    '; $(fileHtml).insertAfter(inputs.last()).hide().slideDown(200, function () { // Extra show fixes IE bug. $(this).show(); From 7dc14ea029e72e3bfde034541880c9a76858110d Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 15 Sep 2014 02:47:02 +0200 Subject: [PATCH 17/46] Allowed admins to change the config of the plugin (same as old UI). --- ContributionPlugin.php | 15 +-- controllers/SettingsController.php | 124 ++--------------------- libraries/Contribution/Form/Settings.php | 13 ++- views/admin/contribution-navigation.php | 5 +- views/admin/index/index.php | 2 +- views/admin/settings/edit.php | 25 ++++- 6 files changed, 46 insertions(+), 138 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index af2b3ad3..0871c34f 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -287,15 +287,7 @@ public function hookConfigForm($args) require_once dirname(__FILE__) . DIRECTORY_SEPARATOR . 'forms' . DIRECTORY_SEPARATOR . 'Settings.php'; $form = new Contribution_Form_Settings; - $defaults = array(); - foreach ($this->_options as $key => $value) { - if (is_string($key)) { - $defaults[$key] = get_option($key); - } - else { - $defaults[$value] = get_option($value); - } - } + $defaults = $form->getCurrentOptions(); $form->setDefaults($defaults); echo $view->partial( @@ -815,11 +807,6 @@ public function _mapOwners($contribItemData, $map) } } - public function getOptions() - { - return $this->_options; - } - /** * Remove the form controls * diff --git a/controllers/SettingsController.php b/controllers/SettingsController.php index 6f014dde..1099c258 100644 --- a/controllers/SettingsController.php +++ b/controllers/SettingsController.php @@ -24,13 +24,18 @@ public function indexAction() */ public function editAction() { - $form = $this->_getForm(); - $defaults = $this->_getOptions(); + $form = new Contribution_Form_Settings; + $defaults = $form->getCurrentOptions(); $form->setDefaults($defaults); if (isset($_POST['submit'])) { if ($form->isValid($_POST)) { - $this->_setOptions($form->getValues()); + $options = array_keys($defaults); + foreach ($form->getValues() as $optionName => $optionValue) { + if (in_array($optionName, $options)) { + set_option($optionName, $optionValue); + } + } $this->_helper->flashMessenger(__('Settings have been saved.')); } else { $this->_helper->flashMessenger(__('There were errors found in your form. Please edit and resubmit.', 'error')); @@ -39,117 +44,4 @@ public function editAction() $this->view->form = $form; } - - /** - * Returns the options that are specified in the $_options property. - * - * @return array Array of option names. - */ - private function _getOptions() - { - $options = array(); - $cnt = new ContributionPlugin(); - $pluginOptions = $cnt->getOptions(); - foreach ($pluginOptions as $option) { - $options[$option] = get_option($option); - } - return $options; - } - - /** - * Sets options that appear in both the form and $_options. - * - * @param array $newOptions array of $optionName => $optionValue. - */ - private function _setOptions($newOptions) - { - $cnt = new ContributionPlugin(); - $options = $cnt->getOptions(); - foreach ($newOptions as $optionName => $optionValue) { - if (in_array($optionName, $options)) { - set_option($optionName, $optionValue); - } - } - } - - private function _getForm() - { - $form = new Omeka_Form_Admin(array('type'=>'contribution_settings')); - - $form->addElementToEditGroup('text', 'contribution_page_path', array( - 'label' => __('Contribution Slug'), - 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. Default path is “contribution.”'), - 'required' => true, - 'filters' => array(array('StringTrim', '/\\\s')), - )); - - $form->addElementToEditGroup('text', 'contribution_email_sender', array( - 'label' => __('Contribution Confirmation Email'), - 'description' => __('An email message will be sent to each contributor from this address confirming that they submitted a contribution to this website. Leave blank if you do not want an email sent.'), - 'validators' => array('EmailAddress') - )); - - $form->addElementToEditGroup('textarea', 'contribution_email_recipients', array( - 'label' => __('New Contribution Notification Emails'), - 'description' => __('An email message will be sent to each address here whenever a new item is contributed. Leave blank if you do not want anyone to be alerted of contributions by email.'), - 'attribs' => array('rows' => '5') - )); - - $form->addElementToEditGroup('textarea', 'contribution_consent_text', array( - 'label' => __('Text of Terms of Service'), - 'description' => __('The text of the legal disclaimer to which contributors will agree.'), - 'attribs' => array('class' => 'html-editor', 'rows' => '15') - )); - - - $form->addElementToEditGroup('checkbox', 'contribution_open', array( - 'label' => __("Allow Non-registered Contributions"), - 'description' => __("This will require an email address from contributors, and create a guest user from that information. If those users want to use the account, they will have to request a new password for the account. If you want to collect additional information about contributors, they must create an account. See documentation for details. "), - ), - array('checked'=> (bool) get_option('contribution_open') ? 'checked' : '') - ); - - - $form->addElementToEditGroup('checkbox', 'contribution_strict_anonymous', array( - 'label' => __("Allow Anonymous Contributions"), - 'description' => __("If non-registered contributions are allowed above, this option allows contributors to remain completely anonymous, even to administrators. A dummy user account will be created that stores no identifing information. See documentation for details. "), - ), - array('checked'=> (bool) get_option('contribution_strict_anonymous') ? 'checked' : '') - ); - - $form->addElementToEditGroup('textarea', 'contribution_email', array( - 'label' => __("Email text to send to contributors"), - 'description' => __("Email text to send to contributors when they submit an item. A link to their contribution will be appended. If using the 'Non-registered', but not 'Anonymous', options, we recommend that you notify contributors that a guest user account has been created for them, and what they gain by confirming their account."), - 'attribs' => array('class' => 'html-editor', 'rows' => '15') - )); - - $collections = get_db()->getTable('Collection')->findPairsForSelectForm(); - $collections = array('' => __('Do not put contributions in any collection')) + $collections; - - $form->addElementToEditGroup('select', 'contribution_collection_id', array( - 'label' => __('Contribution Collection'), - 'description' => __('The collection to which contributions will be added. Changes here will only affect new contributions.'), - 'multiOptions' => $collections - )); - - $types = get_db()->getTable('ContributionType')->findPairsForSelectForm(); - $types = array('' => __('No default type')) + $types; - - $form->addElementToEditGroup('select', 'contribution_default_type', array( - 'label' => __('Default Contribution Type'), - 'description' => __('The type that will be chosen for contributors by default.'), - 'multiOptions' => $types - )); - - if(plugin_is_active('UserProfiles')) { - $profileTypes = $this->_helper->db->getTable('UserProfilesType')->findPairsForSelectForm(); - $form->addElementToEditGroup('select', 'contribution_user_profile_type', array( - 'label' => __('Choose a profile type for contributors'), - 'description' => __('Configure the profile type under User Profiles'), - 'multiOptions' => array('' => __("None")) + $profileTypes - )); - } - - return $form; - } } diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php index 4ce72e45..8e9071ea 100644 --- a/libraries/Contribution/Form/Settings.php +++ b/libraries/Contribution/Form/Settings.php @@ -13,9 +13,9 @@ class Contribution_Form_Settings extends Omeka_Form { public function init() { - parent::init(); $this->setOptions(array('type' => 'contribution_settings')); $this->setAttrib('id', 'settings-form'); + parent::init(); $db = get_db(); @@ -84,4 +84,15 @@ public function init() )); } } + + public function getCurrentOptions() + { + $currents = array(); + $elements = $this->getElements(); + foreach ($elements as $element) { + $option = $element->getName(); + $currents[$option] = get_option($option); + } + return $currents; + } } diff --git a/views/admin/contribution-navigation.php b/views/admin/contribution-navigation.php index 3182afc8..9a08c50d 100644 --- a/views/admin/contribution-navigation.php +++ b/views/admin/contribution-navigation.php @@ -3,8 +3,9 @@ $navArray = array(); if (is_allowed('Contribution_Types', 'edit')) { - $navArray['Getting Started'] = array('label'=>__('Getting Started'), 'uri'=>url('contribution/index')); - $navArray['Contribution Types'] = array('label'=>__('Contribution Types'), 'uri'=>url('contribution/types')); + $navArray['Getting Started'] = array('label' => __('Getting Started'), 'uri' => url('contribution/index')); + $navArray['Contribution Types'] = array('label' => __('Contribution Types'), 'uri' => url('contribution/types')); + $navArray['Submission Settings'] = array('label' => __('Submission Settings'), 'uri' => url('contribution/settings')); } $navArray['Contributors'] = array( diff --git a/views/admin/index/index.php b/views/admin/index/index.php index bbd11a45..e3bd2217 100644 --- a/views/admin/index/index.php +++ b/views/admin/index/index.php @@ -42,7 +42,7 @@
-
'Contribution')) . '">', ''); ?>
+
" . __('submission settings') . ""); ?>
  • diff --git a/views/admin/settings/edit.php b/views/admin/settings/edit.php index ed85b765..b1d13199 100644 --- a/views/admin/settings/edit.php +++ b/views/admin/settings/edit.php @@ -6,21 +6,38 @@ * @package Contribution */ - queue_js_file('contribution'); queue_js_file('tiny_mce', 'javascripts/vendor/tiny_mce'); queue_js_string('setUpSettingsWysiwyg();'); contribution_admin_header(array(__('Submission Settings'))); - ?> -partial('contribution-navigation.php'); ?>
    - + +
    + getElements(); + foreach( $elements as $element) { + echo $element; + } + ?> +
    +
    +
    + formSubmit( + 'submit', __('Save Changes'), + array('class' => 'submit big green button')); + ?> +
    +
    +
    From d645d393843f2c8f0d06333872434551922d2bdf Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 18/46] Fixed tag when there is no captcha. --- views/public/contribution/contribute.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index d12498df..6da463ba 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -61,8 +61,8 @@
-
> - +
> +
From aed239807154ae3bfb4389737016f30d0fb5192e Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 19/46] Allowed to upload multiple files when type is not preset. --- views/public/contribution/contribute.php | 1 + views/public/contribution/type-form.php | 11 ++++++++++- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index fe442b93..7065e6f3 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -56,6 +56,7 @@
display_name); ?> multiple_files; if ($type->isFileRequired()): @@ -13,9 +14,13 @@
formLabel('file', __('Upload a file'), array( @@ -53,9 +58,13 @@ ?>
formLabel('file', __('Upload a file (Optional)'), array( @@ -88,7 +97,7 @@
formLabel('contribution_email', __('Email (Optional)')); + echo $this->formLabel('contribution_email', __('Email (Optional)')); } else { echo $this->formLabel('contribution_email', __('Email (Required)')); } From 6fd55e57390a9aee7b7ddb1476518b0c09c7f933 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 20/46] Fixed form settings after rebase on v3.1.0. --- ContributionPlugin.php | 29 ++++++++++++------------ libraries/Contribution/Form/Settings.php | 17 ++++++++++---- 2 files changed, 27 insertions(+), 19 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 0871c34f..fd1901b2 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -62,15 +62,15 @@ class ContributionPlugin extends Omeka_Plugin_AbstractPlugin */ protected $_options = array( 'contribution_page_path' => 'contribution', - 'contribution_email_sender', - 'contribution_email_recipients', - 'contribution_consent_text', - 'contribution_collection_id', - 'contribution_default_type', - 'contribution_user_profile_type', - 'contribution_open', - 'contribution_email', - 'contribution_strict_anonymous' + 'contribution_email_sender' => '', + 'contribution_email_recipients' => '', + 'contribution_consent_text' => '', + 'contribution_collection_id' => null, + 'contribution_default_type' => null, + 'contribution_user_profile_type' => null, + 'contribution_open' => false, + 'contribution_email' => '', + 'contribution_strict_anonymous' => false, ); public function setUp() @@ -285,7 +285,6 @@ public function hookConfigForm($args) { $view = $args['view']; - require_once dirname(__FILE__) . DIRECTORY_SEPARATOR . 'forms' . DIRECTORY_SEPARATOR . 'Settings.php'; $form = new Contribution_Form_Settings; $defaults = $form->getCurrentOptions(); $form->setDefaults($defaults); @@ -311,8 +310,10 @@ public function hookConfig($args) $post['contribution_page_path'] = $this->_options['contribution_page_path']; } - foreach ($post as $key => $value) { - set_option($key, $value); + foreach ($this->_options as $optionKey => $optionValue) { + if (isset($post[$optionKey])) { + set_option($optionKey, $post[$optionKey]); + } } } @@ -364,8 +365,8 @@ public function hookDefineRoutes($args) // The wildcards on both routes make these routes always apply for the // contribution controller. - // Get the base path. - $basePath = get_option('contribution_page_path'); + // Get the base path. The check is kept in case of error. + $basePath = get_option('contribution_page_path') ?: $this->_options['contribution_page_path']; $router->addRoute('contribution', new Zend_Controller_Router_Route( "$basePath/:action/*", diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php index 8e9071ea..a44e58f5 100644 --- a/libraries/Contribution/Form/Settings.php +++ b/libraries/Contribution/Form/Settings.php @@ -44,16 +44,23 @@ public function init() 'attribs' => array('class' => 'html-editor', 'rows' => '15'), )); - $this->addElement('checkbox', 'contribution_simple', array( - 'label' => __("Use 'Simple' Options"), - 'description' => __("This will require an email address from contributors, and create a guest user from that information. If those users want to use the account, they will have to request a new password for the account. If you want to collect additional information about contributors, you cannot use the simple option. See documentation for details. "), + $this->addElement('checkbox', 'contribution_open', array( + 'label' => __("Allow Non-registered Contributions"), + 'description' => __("This will require an email address from contributors, and create a guest user from that information. If those users want to use the account, they will have to request a new password for the account. If you want to collect additional information about contributors, they must create an account. See documentation for details. "), ), - array('checked' => (bool) get_option('contribution_simple') ? 'checked' : '') + array('checked' => (bool) get_option('contribution_open') ? 'checked' : '') + ); + + $this->addElement('checkbox', 'contribution_strict_anonymous', array( + 'label' => __("Allow Anonymous Contributions"), + 'description' => __("If non-registered contributions are allowed above, this option allows contributors to remain completely anonymous, even to administrators. A dummy user account will be created that stores no identifing information. See documentation for details. "), + ), + array('checked'=> (bool) get_option('contribution_strict_anonymous') ? 'checked' : '') ); $this->addElement('textarea', 'contribution_email', array( 'label' => __("Email text to send to contributors"), - 'description' => __("Email text to send to contributors when they submit an item. A link to their contribution will be appended. If using the 'Simple' option, we recommend that you notify contributors that a guest user account has been created for them, and what they gain by confirming their account."), + 'description' => __("Email text to send to contributors when they submit an item. A link to their contribution will be appended. If using the 'Non-registered', but not 'Anonymous', options, we recommend that you notify contributors that a guest user account has been created for them, and what they gain by confirming their account."), 'attribs' => array('class' => 'html-editor', 'rows' => '15'), )); From 11f3c2f02e02730596763e2e7488740a916322f6 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 21/46] Made the element form label themable. --- ContributionPlugin.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 474d80a9..086a0645 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -801,7 +801,7 @@ public function elementFormFilter($components, $args) $type = $view->type; $contributionElement = $this->_db->getTable('ContributionTypeElement')->findByElementAndType($element, $type); $prompt = $contributionElement->prompt; - $components['label'] = ''; + $components['label'] = $view->formLabel(null, $prompt, array('disableFor' => true)); $components['add_input'] = null; return $components; } From 7aff034e616ba88b9c4c24ecbc23e57d64963720 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 18 Aug 2014 02:47:02 +0200 Subject: [PATCH 22/46] Removed new item if an error appears when processing contribution. --- controllers/ContributionController.php | 3 +++ 1 file changed, 3 insertions(+) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 96e931c1..33020302 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -260,6 +260,7 @@ protected function _processForm($post) $item = update_item($item, $itemMetadata, array(), $fileMetadata); } catch(Omeka_Validator_Exception $e) { $this->flashValidatonErrors($e); + $item->delete(); return false; } catch (Omeka_File_Ingest_InvalidException $e) { // Copying this cruddy hack @@ -268,9 +269,11 @@ protected function _processForm($post) } else { $this->_helper->flashMessenger($e->getMessage()); } + $item->delete(); return false; } catch (Exception $e) { $this->_helper->flashMessenger($e->getMessage()); + $item->delete(); return false; } $this->_addElementTextsToItem($item, $post['Elements']); From 86318be6949ea105bf8189440baccff79e94f579 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 2 Jun 2014 02:47:02 +0200 Subject: [PATCH 23/46] Allowed to add tags. --- ContributionPlugin.php | 13 ++++++++++--- controllers/ContributionController.php | 4 +++- models/ContributionType.php | 1 + plugin.ini | 2 +- views/admin/types/form.php | 14 ++++++++++++-- views/public/contribution/type-form.php | 12 ++++++++++++ 6 files changed, 39 insertions(+), 7 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..52ded17b 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -78,7 +78,7 @@ public function setUp() $this->_hooks[] = 'user_profiles_user_page'; } - if (! is_admin_theme()) { + if (!is_admin_theme()) { //dig up all the elements being used, and add their ElementForm hook $elementsTable = $this->_db->getTable('Element'); $select = $elementsTable->getSelect(); @@ -112,6 +112,7 @@ public function hookInstall() `item_type_id` INT UNSIGNED NOT NULL, `display_name` VARCHAR(255) NOT NULL, `file_permissions` ENUM('Disallowed', 'Allowed', 'Required') NOT NULL DEFAULT 'Disallowed', + `add_tags` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', PRIMARY KEY (`id`), UNIQUE KEY `item_type_id` (`item_type_id`) ) ENGINE=MyISAM;"; @@ -259,6 +260,12 @@ public function hookUpgrade($args) set_option('contribution_open', get_option('contribution_simple')); delete_option('contribution_simple'); } + + if (version_compare($oldVersion, '3.1.2', '<')) { + $db = $this->_db; + $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `add_tags` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; + $db->query($sql); + } } public function hookUninstallMessage() @@ -634,8 +641,8 @@ public function hookUserProfilesUserPage($args) { $user = $args['user']; $contributionCount = $this->_db->getTable('ContributionContributedItem')->count(array('contributor' => $user->id)); - if ($contributionCount !=0) { - echo "id) . "'>Contributed Items ($contributionCount)"; + if ($contributionCount != 0) { + echo "id) . "'>" . __('Contributed Items (%d)', $contributionCount) . ''; } } diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 96e931c1..192899e2 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -185,7 +185,6 @@ protected function _setupCaptcha() protected function _processForm($post) { if (!empty($post)) { - //for the "Simple" configuration, look for the user if exists by email. Log them in. //If not, create the user and log them in. $user = current_user(); @@ -274,6 +273,9 @@ protected function _processForm($post) return false; } $this->_addElementTextsToItem($item, $post['Elements']); + if ($contributionType->add_tags && isset($post['tags'])) { + $item->addTags($post['tags']); + } // Allow plugins to deal with the inputs they may have added to the form. fire_plugin_hook('contribution_save_form', array('contributionType'=>$contributionType,'record'=>$item, 'post'=>$post)); $item->save(); diff --git a/models/ContributionType.php b/models/ContributionType.php index adfbaafb..6785d978 100644 --- a/models/ContributionType.php +++ b/models/ContributionType.php @@ -22,6 +22,7 @@ class ContributionType extends Omeka_Record_AbstractRecord public $item_type_id; public $display_name; public $file_permissions = 'Disallowed'; + public $add_tags = 0; protected $_related = array('ContributionTypeElements' => 'getTypeElements', 'ItemType' => 'getItemType'); diff --git a/plugin.ini b/plugin.ini index b9dfbc78..d31c8d97 100644 --- a/plugin.ini +++ b/plugin.ini @@ -6,7 +6,7 @@ link="http://omeka.org/codex/Plugins/Contribution_2.0" support_link="http://omeka.org/forums/forum/plugins" omeka_minimum_version="2.3" omeka_target_version="2.3" -version="3.1.0" +version="3.1.2" tags="social, items" license="GPLv3" required_plugins="GuestUser" diff --git a/views/admin/types/form.php b/views/admin/types/form.php index 3cdd85b0..d73ec36c 100644 --- a/views/admin/types/form.php +++ b/views/admin/types/form.php @@ -43,9 +43,19 @@
- - +
+
+ +
+
+

+
+ formCheckbox('add_tags', null, array('checked' => $contribution_type->add_tags)); ?> +
+
+
+
    +add_tags) : ?> +
    +
    + formLabel('tags', __('Add Tags')); ?> +
    +
    +

    + formText('tags'); ?> +
    +
    + + isFileAllowed()): ?> From c498290237bb03066aedc1ee8ad82ec479edcbeb Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 24/46] Simplified upload of multiple files. --- views/public/contribution/type-form.php | 92 ++++++++----------------- 1 file changed, 28 insertions(+), 64 deletions(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 98d2ebd2..547030eb 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -1,94 +1,58 @@ -

    - +isFileRequired(); +$isAllowed = $type->isFileAllowed(); +$allowMultipleFiles = $isAllowed && $type->multiple_files; +?>

    display_name); ?>

    multiple_files; - -if ($type->isFileRequired()): - $required = true; -?> - - - +if ($isRequired): ?>
    - formLabel('file', __('Upload a file'), array( - 'id' => 'file-inputs', - )); ?> -
    -
    - formFile('file[0]', array('class' => 'fileinput button')); ?> -

    -
    -
    -
    - -
    formLabel('file', __('Upload a file')); ?>
    -
    - formFile('file', array('class' => 'fileinput button')); ?> -

    +
    +
    + formFile($allowMultipleFiles ? 'file[0]' : 'file', array('class' => 'fileinput button')); ?> +

    +
    - - getTypeElements() as $contributionTypeElement) { echo $this->elementForm($contributionTypeElement->Element, $item, array('contributionTypeElement'=>$contributionTypeElement)); } ?> -isFileAllowed()): -?> - - +
    - formLabel('file', __('Upload a file (Optional)'), array( - 'id' => 'file-inputs', - )); ?> -
    -
    - formFile('file[0]', array('class' => 'fileinput button')); ?> -

    -
    -
    -
    - -
    formLabel('file', __('Upload a file (Optional)')); ?>
    -
    - formFile('file', array('class' => 'fileinput button')); ?> -

    +
    +
    + formFile($allowMultipleFiles ? 'file[0]' : 'file', array('class' => 'fileinput button')); ?> +

    +
    + + @@ -156,4 +120,4 @@ // on a type-by-type basis). fire_plugin_hook('contribution_type_form', array('type'=>$type, 'view'=>$this)); ?> - + Date: Tue, 9 Sep 2014 02:47:02 +0200 Subject: [PATCH 25/46] Added possibility for user to delete a contribution. --- ContributionPlugin.php | 11 ++++++++++- controllers/ContributionController.php | 13 +++++++++++-- helpers/ThemeHelpers.php | 14 ++++++++++++++ models/ContributionContributedItem.php | 15 +++++++++++++-- views/admin/common/contribution-quick-filters.php | 2 ++ views/admin/contributors/show.php | 14 ++++++++------ views/admin/items/browse.php | 4 +++- views/public/contribution/my-contributions.php | 13 +++++++------ 8 files changed, 68 insertions(+), 18 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..10dabc83 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -135,6 +135,7 @@ public function hookInstall() `item_id` INT UNSIGNED NOT NULL, `public` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', `anonymous` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', + `deleted` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0', PRIMARY KEY (`id`), UNIQUE KEY `item_id` (`item_id`) ) ENGINE=MyISAM;"; @@ -259,6 +260,12 @@ public function hookUpgrade($args) set_option('contribution_open', get_option('contribution_simple')); delete_option('contribution_simple'); } + + if (version_compare($oldVersion, '3.1.3', '<')) { + $db = $this->_db; + $sql = "ALTER TABLE `$db->ContributionContributedItem` ADD COLUMN `deleted` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0' AFTER `anonymous`"; + $db->query($sql); + } } public function hookUninstallMessage() @@ -714,7 +721,9 @@ private function _adminBaseInfo($args) $publicMessage = ''; if (is_allowed($item, 'edit')) { - if ($contributedItem->public) { + if ($contributedItem->deleted) { + $publicMessage = __('This item has been deleted by user. It cannot be made public.'); + } elseif ($contributedItem->public) { $publicMessage = __("This item can be made public."); } else { $publicMessage = __("This item cannot be made public."); diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 33020302..5bb1acb8 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -38,16 +38,25 @@ public function myContributionsAction() $contribItem->public = $value; $contribItem->anonymous = $_POST['contribution_anonymous'][$id]; + if ($post['contribution_deleted'][$id]) { + $contribItem->makeDeletedByUser(); + } + if($contribItem->save()) { $this->_helper->flashMessenger( __('Your contributions have been updated.'), 'success'); } else { $this->_helper->flashMessenger($contribItem->getErrors()); } - $contribItems[] = $contribItem; + if (!$contribItem->deleted) { + $contribItems[] = $contribItem; + } } } else { - $contribItems = $contribItemTable->findBy(array('contributor'=>$user->id)); + $contribItems = $contribItemTable->findBy(array( + 'contributor' => $user->id, + 'deleted' => false, + )); } $this->view->contrib_items = $contribItems; } diff --git a/helpers/ThemeHelpers.php b/helpers/ThemeHelpers.php index 962d4b96..324eac87 100644 --- a/helpers/ThemeHelpers.php +++ b/helpers/ThemeHelpers.php @@ -61,3 +61,17 @@ function contribution_contribute_url($actionName = null) return get_view()->url($options, $route, array(), true); } +/** + * Get a URL to the public contribution remove page. + * + * @param Record|integer $contributedItem. + * @return string URL + */ +function contribution_remove_url($contributedItem) +{ + $basePath = get_option('contribution_page_path'); + $string = $basePath ? $basePath : 'contribution'; + $string .= '/remove/'; + $string .= is_object($contributedItem) ? $contributedItem->id : (integer) $contributedItem; + return url($string); +} diff --git a/models/ContributionContributedItem.php b/models/ContributionContributedItem.php index c98276a3..68aebf7a 100644 --- a/models/ContributionContributedItem.php +++ b/models/ContributionContributedItem.php @@ -17,7 +17,8 @@ class ContributionContributedItem extends Omeka_Record_AbstractRecord public $item_id; public $public; public $anonymous; - + public $deleted = 0; + protected $_related = array( 'Item' => 'getItem', 'Contributor' => 'getContributor' @@ -36,7 +37,17 @@ public function makeNotPublic() $item->save(); release_object($item); } - + + /** + * Delete a contributed item. In fact, for security reason, make it private + * and invisible to contributor. + */ + public function makeDeletedByUser() + { + $this->deleted = true; + $this->makeNotPublic(); + } + public function getContributor() { $owner = $this->Item->getOwner(); diff --git a/views/admin/common/contribution-quick-filters.php b/views/admin/common/contribution-quick-filters.php index f8d5c7c4..0abe00e3 100644 --- a/views/admin/common/contribution-quick-filters.php +++ b/views/admin/common/contribution-quick-filters.php @@ -6,6 +6,8 @@
  • +
  • +
diff --git a/views/admin/contributors/show.php b/views/admin/contributors/show.php index 0dfaf006..1d75aea2 100644 --- a/views/admin/contributors/show.php +++ b/views/admin/contributors/show.php @@ -29,14 +29,16 @@
- - Item); ?> + + Item); ?>
- Item->public) { + deleted) { + $status = __('User Deleted'); + } elseif ($contributedItem->Item->public) { $status = __('Public'); } else { - if($item->public) { + if($contributedItem->public) { $status = __('Needs review'); } else { $status = __('Private contribution'); @@ -45,7 +47,7 @@ ?>

-

anonymous ? " | " . __('Anonymous') : ""; ?>

+

anonymous ? " | " . __('Anonymous') : ""; ?>

array('class' => 'admin-thumb panel')), diff --git a/views/admin/items/browse.php b/views/admin/items/browse.php index 02eddb2f..c0580785 100644 --- a/views/admin/items/browse.php +++ b/views/admin/items/browse.php @@ -120,7 +120,9 @@
+ @@ -15,15 +16,15 @@ Item; ?> - - + + + - -
- + deleted): ?> + + diff --git a/views/public/contribution/my-contributions.php b/views/public/contribution/my-contributions.php index fab13a28..4ba7b75f 100644 --- a/views/public/contribution/my-contributions.php +++ b/views/public/contribution/my-contributions.php @@ -8,6 +8,7 @@
formCheckbox("contribution_public[{$contribItem->id}]", null, array('checked'=>$contribItem->public) ); ?> - formCheckbox("contribution_anonymous[{$contribItem->id}]", null, array('checked'=>$contribItem->anonymous) ); ?> - formCheckbox("contribution_public[{$contribItem->id}]", + null, array('checked' => $contribItem->public)); ?>formCheckbox("contribution_anonymous[{$contribItem->id}]", + null, array('checked' => $contribItem->anonymous)); ?> formCheckbox("contribution_deleted[{$contribItem->id}]", + null, array('checked' => false)); ?>
From dd44b473c3f2873b397a02f23f5fd47c42ab400f Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 26/46] Fixed element "add tag" in form after rebase on v3.1.0. --- views/public/contribution/type-form.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 2d3a7cbc..257df4ff 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -28,10 +28,10 @@ add_tags) : ?>
-
+
formLabel('tags', __('Add Tags')); ?>
-
+

formText('tags'); ?>
From 030e17eb8bd9ca4a215c71bea22ee1766c3f5512 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 27/46] Replaced the makeNotPublic() method by the afterSave() hook. --- controllers/ContributionController.php | 15 +++----- models/ContributionContributedItem.php | 50 ++++++++++++++++---------- 2 files changed, 35 insertions(+), 30 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 5bb1acb8..324b7659 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -30,17 +30,9 @@ public function myContributionsAction() if(!empty($_POST)) { foreach($_POST['contribution_public'] as $id=>$value) { $contribItem = $contribItemTable->find($id); - if($value) { - $contribItem->public = true; - } else { - $contribItem->makeNotPublic(); - } - $contribItem->public = $value; - $contribItem->anonymous = $_POST['contribution_anonymous'][$id]; - - if ($post['contribution_deleted'][$id]) { - $contribItem->makeDeletedByUser(); - } + $contribItem->public = (integer) $value; + $contribItem->anonymous = (integer) $_POST['contribution_anonymous'][$id]; + $contribItem->deleted = (integer) $_POST['contribution_deleted'][$id]; if($contribItem->save()) { $this->_helper->flashMessenger( __('Your contributions have been updated.'), 'success'); @@ -48,6 +40,7 @@ public function myContributionsAction() $this->_helper->flashMessenger($contribItem->getErrors()); } + // Clean list for next view. if (!$contribItem->deleted) { $contribItems[] = $contribItem; } diff --git a/models/ContributionContributedItem.php b/models/ContributionContributedItem.php index 68aebf7a..f96fd5f1 100644 --- a/models/ContributionContributedItem.php +++ b/models/ContributionContributedItem.php @@ -29,25 +29,6 @@ public function getItem() return $this->getDb()->getTable('Item')->find($this->item_id); } - public function makeNotPublic() - { - $this->public = false; - $item = $this->Item; - $item->public = false; - $item->save(); - release_object($item); - } - - /** - * Delete a contributed item. In fact, for security reason, make it private - * and invisible to contributor. - */ - public function makeDeletedByUser() - { - $this->deleted = true; - $this->makeNotPublic(); - } - public function getContributor() { $owner = $this->Item->getOwner(); @@ -68,4 +49,35 @@ public function getContributor() } return $owner; } + + /** + * Before-save hook. + * + * @param array $args + */ + protected function beforeSave($args) + { + // Delete a contributed item. In fact, for security reason, make it + // private and invisible to contributor. + if ($this->deleted) { + $this->public = false; + } + } + + /** + * After-save hook. + * + * @param array $args + */ + protected function afterSave($args) + { + if (!$this->public) { + $item = $this->Item; + if ($item->public) { + $item->public = false; + $item->save(false); + } + release_object($item); + } + } } From f24eabeb3ad32b686d40490bedc870ffc06c598d Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 28/46] Allowed contributors to edit their contributions. --- ContributionPlugin.php | 55 ++- controllers/ContributionController.php | 340 +++++++++++++++--- helpers/ThemeHelpers.php | 28 +- libraries/Contribution/Form/Settings.php | 7 + models/ContributionContributedItem.php | 12 +- models/Table/ContributionType.php | 13 + views/public/contribution/contribute.php | 47 +-- .../contribution/contribution-submit-form.php | 22 ++ views/public/contribution/edit.php | 86 +++++ .../public/contribution/my-contributions.php | 6 + views/public/contribution/type-form.php | 6 +- 11 files changed, 543 insertions(+), 79 deletions(-) create mode 100644 views/public/contribution/contribution-submit-form.php create mode 100644 views/public/contribution/edit.php diff --git a/ContributionPlugin.php b/ContributionPlugin.php index d9bd57a9..393e542d 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -37,6 +37,7 @@ class ContributionPlugin extends Omeka_Plugin_AbstractPlugin 'admin_items_search', 'admin_items_show_sidebar', 'admin_items_browse_detailed_each', + 'public_items_show', 'items_browse_sql', 'before_save_item', 'after_delete_item', @@ -71,6 +72,7 @@ class ContributionPlugin extends Omeka_Plugin_AbstractPlugin 'contribution_open' => false, 'contribution_email' => '', 'contribution_strict_anonymous' => false, + 'contribution_allow_edit' => false, ); public function setUp() @@ -351,10 +353,14 @@ public function hookDefineAcl($args) $acl->addResource('Contribution_Contribution'); $acl->allow(array('super', 'admin', 'researcher', 'contributor'), 'Contribution_Contribution'); + $privileges = array('show', 'contribute', 'thankyou', 'my-contributions', 'type-form'); + if (get_option('contribution_allow_edit')) { + $privileges[] = 'edit'; + } if (get_option('contribution_open')) { - $acl->allow(null, 'Contribution_Contribution', array('show', 'contribute', 'thankyou', 'my-contributions', 'type-form')); + $acl->allow(null, 'Contribution_Contribution', $privileges); } else { - $acl->allow('guest', 'Contribution_Contribution', array('show', 'contribute', 'thankyou', 'my-contributions', 'type-form')); + $acl->allow('guest', 'Contribution_Contribution', $privileges); } $acl->allow(null, 'Contribution_Contribution', array('contribute', 'terms', 'thankyou')); @@ -398,6 +404,19 @@ public function hookDefineRoutes($args) 'action' => 'contribute', ))); + $router->addRoute('contributionId', + new Zend_Controller_Router_Route( + "$basePath/:action/:id/*", + array( + 'module' => 'contribution', + 'controller' => 'contribution', + 'action' => 'contribute', + ), + array( + 'action' => 'edit', + 'id' => '\d+', + ))); + if (is_admin_theme()) { $router->addRoute('contributionAdmin', new Zend_Controller_Router_Route( @@ -584,6 +603,38 @@ public function hookAdminItemsBrowseDetailedEach($args) echo $this->_adminBaseInfo($args); } + public function hookPublicItemsShow($args) + { + if (!is_allowed('Contribution_Contribution', 'edit')) { + return; + } + + if (!plugin_is_active('UserProfiles')) { + return; + } + + $user = current_user(); + $item = $args['item']; + if (!$user || $user->id != $item->owner_id) { + return; + } + + $contributedItem = get_db()->getTable('ContributionContributedItem')->findByItem($item); + if (!$contributedItem) { + return; + } + + $html = ''; + $html .= '
'; + $html .= '

' . __('Edit My Contribution') . '

'; + $html .= '
    '; + $html .= '
  • ' . contribution_link_to($contributedItem, 'edit', __('Edit')) . '
  • '; + $html .= '
  • ' . contribution_link_to($contributedItem, 'delete', __('Delete')) . '
  • '; + $html .= '
'; + $html .= '
'; + echo $html; + } + /** * Deal with Contribution-specific search terms. * diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 5c678bb7..8afbc221 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -11,8 +11,17 @@ */ class Contribution_ContributionController extends Omeka_Controller_AbstractActionController { + protected $_autoCsrfProtection = true; + protected $_captcha; + protected $_profile; + + public function init() + { + $this->_helper->db->setDefaultModelName('ContributionContributedItem'); + } + /** * Index action; simply forwards to contributeAction. */ @@ -108,6 +117,105 @@ public function contributeAction() } } + /** + * Action for main contribution edit form. + * + * Current differences with "add contribution": The type cannot be changed; + * no captcha; old images are displayed and not removable. + */ + public function editAction() + { + // Check contribution (else keep error 404?). + $contributedItem = $this->_helper->db->findById(); + if (empty($contributedItem) || $contributedItem->deleted) { + $this->_helper->_flashMessenger(__("This contribution doesn't exist."), 'error'); + return current_user() + ? $this->_helper->redirector('my-contributions') + : $this->_helper->redirector('index', 'index', 'default'); + } + + // Check rights of the user on this contribution (owner of the item). + $contributor = $contributedItem->getContributor(); + $user = $this->getCurrentUser(); + $item = $contributedItem->Item; + if (!$user || $user->id !== $contributor->id || $item->owner_id !== $user->id) { + $this->_helper->_flashMessenger(__('You are not the contributor of this item.'), 'error'); + return $item->public + ? $this->_helper->redirector('show', 'items', 'default', array('id' => $item->id)) + : $this->_helper->redirector('index', 'index', 'default'); + } + + // Prepare next view (TODO Set it in another method to avoid preparation if not needed?) + $csrf = new Omeka_Form_SessionCsrf; + $this->view->csrf = $csrf; + $this->view->contribution_contributed_item = $contributedItem; + $this->view->item = $item; + $contributionType = $this->_helper->db->getTable('ContributionType')->getByItemType($item->item_type_id); + $this->_setupContributionSubmit($contributionType); + + if (!$this->getRequest()->isPost()) { + return; + } + + if (!$csrf->isValid($_POST)) { + $this->_helper->_flashMessenger(__('There was an error on the form. Please try again.'), 'error'); + return; + } + + if (!$this->_validateContribution($_POST)) { + return; + } + + // Because there is already one attached file when item is created, + // no new check is done on required file. + + // If not simple and the profile doesn't process, send back false for the + // error. This should be done before processing item in order to set + // profile type and to avoid settings profile elements to item. + $this->_processUserProfile($user, $_POST); + + // Use a specific setPostData() for item, because some post fields are + // not set in the post. Metadata are not changed via contribution + // form. + $this->_setPostData($item, $_POST); + + // Tags are added separately. + if ($contributionType->add_tags && isset($_POST['tags'])) { + $item->addTags($_POST['tags']); + } + + // Allow plugins to deal with the inputs they may have added to the form + // and that are not managed via hooks before or after save item. + fire_plugin_hook( + 'contribution_save_form', + array( + 'contributionType' => $contributionType, + 'record' => $item, + 'post' => $_POST, + )); + + // Everything has been checked, so save item. + if ($item->save(false)) { + $successMessage = $this->_getEditSuccessMessage($contributedItem); + $this->_helper->flashMessenger($successMessage, 'success'); + + // Update contribution before redirect. + $contributedItem->public = (integer) $_POST['contribution-public']; + if (!$contributedItem->public) { + $contributedItem->makeNotPublic(); + } + $contributedItem->anonymous = (integer) $_POST['contribution-anonymous']; + $contributedItem->deleted = 0; + $contributedItem->save(); + + $this->_redirectAfterEdit($contributedItem); + } + // Error during saving. + else { + $this->_helper->flashMessenger($item->getErrors()); + } + } + /** * Action for AJAX request from contribute form. */ @@ -134,19 +242,30 @@ public function thankyouAction() /** * Common tasks whenever displaying submit form for contribution. * - * @param int $typeId ContributionType id + * @param ContributionType|int $contributionType ContributionType id + */ + protected function _setupContributeSubmit($contributionType) + { + $this->view->item = new Item; + $this->_setupContributionSubmit($contributionType); + } + + /** + * Common tasks whenever displaying submit form for contribution or edition. + * + * @param ContributionType|int $contributionType ContributionType or id. */ - public function _setupContributeSubmit($typeId) + protected function _setupContributionSubmit($contributionType) { // Override default element form display $this->view->addHelperPath(CONTRIBUTION_HELPERS_DIR, 'Contribution_View_Helper'); - $item = new Item; - $this->view->item = $item; - $type = get_db()->getTable('ContributionType')->find($typeId); - $this->view->type = $type; + if (!is_object($contributionType)) { + $contributionType = get_db()->getTable('ContributionType')->find($contributionType); + } + $this->view->type = $contributionType; - //setup profile stuff, if needed + // Setup profile stuff, if needed. $profileTypeId = get_option('contribution_user_profile_type'); if(plugin_is_active('UserProfiles') && $profileTypeId) { $this->view->addHelperPath(USER_PROFILES_DIR . '/helpers', 'UserProfiles_View_Helper_'); @@ -226,33 +345,30 @@ protected function _processForm($post) } } - // The final form submit was not pressed. - if (!isset($post['form-submit'])) { - return false; - } if (!$this->_validateContribution($post)) { return false; } - $contributionTypeId = trim($post['contribution_type']); - if ($contributionTypeId !== "" && is_numeric($contributionTypeId)) { + $contributionTypeId = (integer) $post['contribution_type']; + if (!empty($contributionTypeId)) { $contributionType = get_db()->getTable('ContributionType')->find($contributionTypeId); $itemTypeId = $contributionType->getItemType()->id; } else { $this->_helper->flashMessenger(__('You must select a type for your contribution.'), 'error'); return false; } + // Public is updated with the contributed item. $itemMetadata = array('public' => false, 'featured' => false, 'item_type_id' => $itemTypeId); - $collectionId = get_option('contribution_collection_id'); - if (!empty($collectionId) && is_numeric($collectionId)) { - $itemMetadata['collection_id'] = (int) $collectionId; + $collectionId = (integer) get_option('contribution_collection_id'); + if (!empty($collectionId)) { + $itemMetadata['collection_id'] = $collectionId; } // TODO Check if there is at least one file if one file or more is required and remove the catch below. - $fileMetadata = $this->_processFilesUpload($contributionType); + $fileMetadata = $this->_prepareFilesUpload($contributionType); // This is a hack to allow the file upload job to succeed // even with the synchronous job dispatcher. @@ -292,40 +408,67 @@ protected function _processForm($post) } $this->_addElementTextsToItem($item, $post['Elements']); + + // Tags are added separately. if ($contributionType->add_tags && isset($post['tags'])) { $item->addTags($post['tags']); } - // Allow plugins to deal with the inputs they may have added to the form. + // Allow plugins to deal with the inputs they may have added to the form + // and that are not managed via hooks before or after save item. fire_plugin_hook('contribution_save_form', array('contributionType'=>$contributionType,'record'=>$item, 'post'=>$post)); + $item->save(); //if not simple and the profile doesn't process, send back false for the error - $this->_processUserProfile($post, $user); - $this->_linkItemToContributedItem($item, null, $post); + $this->_processUserProfile($user, $post); + $this->_linkItemToContributedItem($item, $post); $this->_sendEmailNotifications($user, $item); return true; } return false; } - protected function _processUserProfile($post, $user) + protected function _processUserProfile($user, $post) { - $profileTypeId = get_option('contribution_user_profile_type'); - if($profileTypeId && plugin_is_active('UserProfiles')) { - $profile = $this->_helper->db->getTable('UserProfilesProfile')->findByUserIdAndTypeId($user->id, $profileTypeId); - if(!$profile) { - $profile = new UserProfilesProfile(); - $profile->setOwner($user); - $profile->type_id = $profileTypeId; - $profile->public = 0; - $profile->setRelationData(array('subject_id'=>$user->id, 'user_id'=>$user->id)); + $profile = $this->_getProfileForUser($user); + // Check if there is a profile. + if (!$profile) { + return true; + } + $profile->setPostData($post); + return $profile->save(false); + } + + /** + * Get the user profile if the plugin User Profile is used and active. The + * profile is a new one, for the current user, if it is not set. + * + * @param User $user Current user if null. + * @return UserProfilesProfile|false. False if the plugin is not used. + */ + protected function _getProfileForUser($user = null) + { + if (is_null($this->_profile)) { + $profileTypeId = get_option('contribution_user_profile_type'); + if ($profileTypeId && plugin_is_active('UserProfiles')) { + if (is_null($user)) { + $user = current_user(); + } + $profile = $this->_helper->db->getTable('UserProfilesProfile')->findByUserIdAndTypeId($user->id, $profileTypeId); + if (!$profile) { + $profile = new UserProfilesProfile; + $profile->setOwner($user); + $profile->type_id = $profileTypeId; + $profile->public = 0; + $profile->setRelationData(array('subject_id' => $user->id, 'user_id' => $user->id)); + } + $this->_profile = $profile; } - $profile->setPostData($post); - $this->_profile = $profile; - if(!$profile->save(false)) { - return false; + // The plugin is not used. + else { + $this->_profile = false; } } - return true; + return $this->_profile; } /** @@ -337,7 +480,7 @@ protected function _processUserProfile($post, $user) * @param ContributionType $contributionType Type of contribution. * @return array Files upload array. */ - protected function _processFilesUpload($contributionType) + protected function _prepareFilesUpload($contributionType) { if ($contributionType->isFileAllowed()) { $options = array(); @@ -358,12 +501,13 @@ protected function _processFilesUpload($contributionType) return array(); } - protected function _linkItemToContributedItem($item, $contributor, $post) + protected function _linkItemToContributedItem($item, $post) { $linkage = new ContributionContributedItem; $linkage->item_id = $item->id; - $linkage->public = $post['contribution-public']; - $linkage->anonymous = $post['contribution-anonymous']; + $linkage->public = (integer) $post['contribution-public']; + $linkage->anonymous = (integer) $post['contribution-anonymous']; + $linkage->deleted = 0; $linkage->save(); } @@ -394,6 +538,74 @@ protected function _addElementTextsToItem($item, $elements) } } + /** + * Set post data to an item. + * + * All data in the post are set: elements, basic metadata (item_type_id, + * collection_id, featured, public, owner_id), and other data attached to an + * item, like geolocation. + * + * @todo Use builder? + * + * @param Item $item Item to add texts to. + * @param array $post Array of element inputs from form. + * @param array $itemMetadata Array of basic data of item (public...). + * @return boolean True if success, false else. + */ + protected function _setPostData($item, $post, $itemMetadata = array()) + { + // Check if there is a profile in order to remove elements data used for + // profile because they are related to profile, not to item. + $profile = $this->_getProfileForUser(); + if ($profile) { + $profileElements = $profile->getAllElements(); + foreach ($profileElements as $key => $value) { + foreach ($value as $element) { + unset($post['Elements'][$element->id]); + } + } + } + + if (!isset($post['Elements'])) { + $post['Elements'] = array(); + } + + // Overwrite post data with internal itemMetadata. + if ($itemMetadata) { + $post += $itemMetadata; + } + // Else reset metadata to keep clean current ones (avoid checking post). + else { + unset($post['item_type_id']); + unset($post['collection_id']); + unset($post['featured']); + unset($post['public']); + unset($post['owner_id']); + } + + // If ReplaceElementTexts() is true, all element texts are removed. + // If an element is set, it replaces all fields of the element. + // If an element is not set, it is removed. + // If a non element is not set, it is not changed. + // So, to get all element texts is needed to update a record. + + // Get and format current metadata. + $currentElements = array(); + foreach ($item->getAllElementTexts() as $elementText) { + $currentElements[$elementText->element_id] = array( + array( + 'text' => $elementText->text, + 'html' => $elementText->html, + ), + ); + } + + // This is not a merge, but an update. + $post['Elements'] += $currentElements; + + $item->setPostData($post); + } + /** * Validate the contribution form submission. * @@ -406,10 +618,13 @@ protected function _addElementTextsToItem($item, $elements) */ protected function _validateContribution($post) { + if (empty($post)) { + return false; + } - // ReCaptcha ignores the first argument. - if ($this->_captcha and !$this->_captcha->isValid(null, $_POST)) { - $this->_helper->flashMessenger(__('Your CAPTCHA submission was invalid, please try again.'), 'error'); + // The final form submit was not pressed. + if (!isset($post['form-submit'])) { + $this->_helper->flashMessenger(__('You should press submit button.'), 'error'); return false; } @@ -417,6 +632,13 @@ protected function _validateContribution($post) $this->_helper->flashMessenger(__('You must agree to the Terms and Conditions.'), 'error'); return false; } + + // ReCaptcha ignores the first argument. + if ($this->_captcha and !$this->_captcha->isValid(null, $post)) { + $this->_helper->flashMessenger(__('Your CAPTCHA submission was invalid, please try again.'), 'error'); + return false; + } + return true; } @@ -548,4 +770,38 @@ protected function _createNewAnonymousUser() $user->save(); return $user; } + + /** + * Return the success message for editing a record. + * + * @param Omeka_Record_AbstractRecord $record + * @return string + */ + protected function _getEditSuccessMessage($record) + { + $itemTitle = $this->_getElementMetadata($record->Item, 'Dublin Core', 'Title'); + if ($itemTitle != '') { + return __('The contributed item "%s" was successfully updated!', $itemTitle); + } else { + return __('The contributed item #%s was successfully updated!', strval($item->id)); + } + } + + protected function _getElementMetadata($record, $elementSetName, $elementName) + { + $m = new Omeka_View_Helper_Metadata; + return strip_formatting($m->metadata($record, array($elementSetName, $elementName))); + } + + /** + * Redirect to items/show after a contribution is successfully edited. + * + * The default is to redirect to this record's show page. + * + * @param Omeka_Record_AbstractRecord $record + */ + protected function _redirectAfterEdit($record) + { + $this->_helper->redirector('show', 'items', 'default', array('id' => $record->item_id)); + } } diff --git a/helpers/ThemeHelpers.php b/helpers/ThemeHelpers.php index b9120b23..474e8679 100644 --- a/helpers/ThemeHelpers.php +++ b/helpers/ThemeHelpers.php @@ -55,15 +55,35 @@ function contribution_contribute_url($actionName = null) } /** - * Get a URL to the public contribution remove page. + * Get a link to the public contribution action page. * * @param Record|integer $contributedItem. + * @param string $action Action to link to, main index if none. + * @param string $linkText + * @return string HTML + */ +function contribution_link_to($contributedItem = null, $action = null, $linkText = 'Contribute') +{ + $url = contribution_url($action, $contributedItem); + return sprintf('%s', $url, $linkText); +} + +/** + * Get a URL to the public contribution action page. + * + * @param string $action Action to link to, main index if none. + * @param Record|integer $contributedItem. * @return string URL */ -function contribution_remove_url($contributedItem) +function contribution_url($action = null, $contributedItem = null) { $string = get_option('contribution_page_path'); - $string .= '/remove/'; - $string .= is_object($contributedItem) ? $contributedItem->id : (integer) $contributedItem; + if (!empty($action)) { + $string .= '/' . $action; + if (!empty($contributedItem)) { + $string .= '/'; + $string .= is_object($contributedItem) ? $contributedItem->id : (integer) $contributedItem; + } + } return url($string); } diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php index a44e58f5..4a5323cd 100644 --- a/libraries/Contribution/Form/Settings.php +++ b/libraries/Contribution/Form/Settings.php @@ -90,6 +90,13 @@ public function init() 'multiOptions' => array('' => __("None")) + $profileTypes, )); } + + $this->addElement('checkbox', 'contribution_allow_edit', array( + 'label' => __("Allow to Edit Contribution"), + 'description' => __('If checked, contributors will be able to edit and to delete their contributions.'), + ), + array('checked' => (bool) get_option('contribution_allow_edit') ? 'checked' : '') + ); } public function getCurrentOptions() diff --git a/models/ContributionContributedItem.php b/models/ContributionContributedItem.php index f96fd5f1..04d8a8be 100644 --- a/models/ContributionContributedItem.php +++ b/models/ContributionContributedItem.php @@ -23,7 +23,7 @@ class ContributionContributedItem extends Omeka_Record_AbstractRecord 'Item' => 'getItem', 'Contributor' => 'getContributor' ); - + public function getItem() { return $this->getDb()->getTable('Item')->find($this->item_id); @@ -31,7 +31,15 @@ public function getItem() public function getContributor() { - $owner = $this->Item->getOwner(); + $item = $this->Item; + // If there is no item, make a fake user called "No User". + if (empty($item)) { + $owner = new User(); + $owner->name = __('No User'); + return $owner; + } + + $owner = $item->getOwner(); //if the user has been deleted, make a fake user called "Deleted User" if(!$owner) { $owner = new User(); diff --git a/models/Table/ContributionType.php b/models/Table/ContributionType.php index 643ca940..0d5b7f4a 100644 --- a/models/Table/ContributionType.php +++ b/models/Table/ContributionType.php @@ -15,6 +15,19 @@ */ class Table_ContributionType extends Omeka_Db_Table { + /** + * Get a contribution type by item type. + * + * @param ItemType|integer $itemType Item type record or id. + * @return ContributionType|null + */ + public function getByItemType($itemType) + { + $params = array(); + $params['item_type_id'] = is_object($itemType) ? $itemType->id : (integer) $itemType; + $result = $this->findBy($params, 1); + return $result ? reset($result) : null; + } /** * Used to create options for HTML select form elements. diff --git a/views/public/contribution/contribute.php b/views/public/contribution/contribute.php index c4a810a2..5743576e 100644 --- a/views/public/contribution/contribute.php +++ b/views/public/contribution/contribute.php @@ -18,19 +18,23 @@ queue_css_string("input.add-element {display: block}"); } -$head = array('title' => 'Contribute', - 'bodyclass' => 'contribution'); -echo head($head); ?> +$title = __('Contribute'); +$bodyClass = 'contribution add'; + +echo head(array( + 'title' => $title, + 'bodyclass' => $bodyClass, +)); ?>
-

+

-
> - -
- -
- - formCheckbox('contribution-public', $public, null, array('1', '0')); ?> - formLabel('contribution-public', __('Publish my contribution on the web.')); ?> -
-
- - formCheckbox('contribution-anonymous', $anonymous, null, array(1, 0)); ?> - formLabel('contribution-anonymous', __("Keep identity private.")); ?> -
-

" . __('Terms and Conditions') . "."); ?>

-
- - formCheckbox('terms-agree', $agree, null, array('1', '0')); ?> - formLabel('terms-agree', __('I agree to the Terms and Conditions.')); ?> -
- formSubmit('form-submit', __('Contribute'), array('class' => 'submitinput')); ?> -
- + partial('contribution/contribution-submit-form.php', $submitOptions); + echo $csrf; ?>
diff --git a/views/public/contribution/contribution-submit-form.php b/views/public/contribution/contribution-submit-form.php new file mode 100644 index 00000000..1ba3408c --- /dev/null +++ b/views/public/contribution/contribution-submit-form.php @@ -0,0 +1,22 @@ +
> + +
+ +
+ public); ?> + formCheckbox('contribution-public', $public, null, array('1', '0')); ?> + formLabel('contribution-public', __('Publish my contribution on the web.')); ?> +
+
+ anonymous); ?> + formCheckbox('contribution-anonymous', $anonymous, null, array(1, 0)); ?> + formLabel('contribution-anonymous', __("Keep identity private.")); ?> +
+

" . __('Terms and Conditions') . "."); ?>

+
+ + formCheckbox('terms-agree', $agree, null, array('1', '0')); ?> + formLabel('terms-agree', __('I agree to the Terms and Conditions.')); ?> +
+ formSubmit('form-submit', __('Contribute'), array('class' => 'submitinput')); ?> +
diff --git a/views/public/contribution/edit.php b/views/public/contribution/edit.php new file mode 100644 index 00000000..7f281927 --- /dev/null +++ b/views/public/contribution/edit.php @@ -0,0 +1,86 @@ + $title, + 'bodyclass' => $bodyClass, +)); ?> + +
+ + +

+ +
+
+ + display_name; ?> + +
+
    + Files as $key => $file): ?> +
  • +
    + +
    +
  • + +
+
+ +
+ partial('contribution/type-form.php', $partialOptions); + }?> +
+
+ + partial('contribution/contribution-submit-form.php', $submitOptions); + echo $csrf; ?> +
+
+ + + + @@ -29,8 +32,11 @@ formCheckbox("contribution_anonymous[{$contribItem->id}]", null, array('checked' => $contribItem->anonymous)); ?> + + formCheckbox("contribution_deleted[{$contribItem->id}]", null, array('checked' => false)); ?> + diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 240cb5c5..695c33df 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -5,7 +5,11 @@ $isAllowed = $type->isFileAllowed(); $allowMultipleFiles = $isAllowed && $type->multiple_files; ?> -

display_name); ?>

+

display_name); + } ?> +

Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 29/46] Simplified contribution controller for contribution. --- controllers/ContributionController.php | 258 +++++++++++-------------- 1 file changed, 113 insertions(+), 145 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 8afbc221..c7e96804 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -88,28 +88,32 @@ public function contributeAction() $this->_setupContributeSubmit($typeId); return; } + if ($this->_processForm($_POST)) { - $route = $this->getFrontController()->getRouter()->getCurrentRouteName(); - $this->_helper->_redirector->gotoRoute(array('action' => 'thankyou'), $route); - } else { - $typeId = null; - if (isset($_POST['contribution_type']) && ($postedType = $_POST['contribution_type'])) { - $typeId = $postedType; - } elseif ($defaultType) { - $typeId = $defaultType; - } - if ($this->_captcha) { - $this->view->captchaScript = $this->_captcha->render(new Zend_View); - } - $this->_setupContributeSubmit($typeId); + return $this->_helper->_redirector->gotoRoute(array('action' => 'thankyou'), 'contribution'); + } - if(isset($this->_profile) && !$this->_profile->exists()) { - $this->_helper->flashMessenger($this->_profile->getErrors(), 'error'); - return; - } + // Error in contribution, so refresh view. + $typeId = null; + if (isset($_POST['contribution_type']) && ($postedType = $_POST['contribution_type'])) { + $typeId = $postedType; + } elseif ($defaultType) { + $typeId = $defaultType; } - } else { - if($this->_captcha) { + if ($this->_captcha) { + $this->view->captchaScript = $this->_captcha->render(new Zend_View); + } + $this->_setupContributeSubmit($typeId); + + if (!empty($this->_profile) && !$this->_profile->exists()) { + $this->_helper->flashMessenger($this->_profile->getErrors(), 'error'); + return; + } + } + + // No post, so prepare base view. + else { + if ($this->_captcha) { $this->view->captchaScript = $this->_captcha->render(new Zend_View); } $defaultType = get_option('contribution_default_type'); @@ -311,119 +315,110 @@ protected function _setupCaptcha() */ protected function _processForm($post) { - if (!empty($post)) { - //for the "Simple" configuration, look for the user if exists by email. Log them in. - //If not, create the user and log them in. - $user = current_user(); - $open = get_option('contribution_open'); - if ( get_option('contribution_strict_anonymous') ) { - $strictAnonymous = empty($post['contribution_email']); - } else { - $strictAnonymous = false; - } - + if (!$this->_validateContribution($post)) { + return false; + } - if(!$user && $open && !$strictAnonymous) { - $user = $this->_helper->db->getTable('User')->findByEmail($post['contribution_email']); - } + // For the "Simple" configuration, look for the user if exists by email. + // Log them in. If not, create the user and log them in. + $user = current_user(); + $open = get_option('contribution_open'); + if ( get_option('contribution_strict_anonymous') ) { + $strictAnonymous = empty($post['contribution_email']); + } else { + $strictAnonymous = false; + } - if (!$user && $strictAnonymous) { - $user = $this->_createNewAnonymousUser(); - } - // if still not a user, need to create one based on the email address - if(!$user) { - $user = $this->_createNewGuestUser($post); - if($user->hasErrors()) { - $errors = $user->getErrors()->get(); - //since we're creating the user behind the scenes, skip username and name errors - unset($errors['name']); - unset($errors['username']); - foreach($errors as $error) { - $this->_helper->flashMessenger($error, 'error'); - } - return false; - } - } + if(!$user && $open && !$strictAnonymous) { + $user = $this->_helper->db->getTable('User')->findByEmail($post['contribution_email']); + } - if (!$this->_validateContribution($post)) { + if (!$user && $strictAnonymous) { + $user = $this->_createNewAnonymousUser(); + } + // If still not a user, need to create one based on the email address. + if (!$user) { + $user = $this->_createNewGuestUser($post); + if ($user->hasErrors()) { + $errors = $user->getErrors()->get(); + // Since we're creating the user behind the scenes, skip + // username and name errors. + unset($errors['name']); + unset($errors['username']); + foreach ($errors as $error) { + $this->_helper->flashMessenger($error, 'error'); + } return false; } + } - $contributionTypeId = (integer) $post['contribution_type']; - if (!empty($contributionTypeId)) { - $contributionType = get_db()->getTable('ContributionType')->find($contributionTypeId); - $itemTypeId = $contributionType->getItemType()->id; - } else { - $this->_helper->flashMessenger(__('You must select a type for your contribution.'), 'error'); - return false; - } - // Public is updated with the contributed item. - $itemMetadata = array('public' => false, - 'featured' => false, - 'item_type_id' => $itemTypeId); - - $collectionId = (integer) get_option('contribution_collection_id'); - if (!empty($collectionId)) { - $itemMetadata['collection_id'] = $collectionId; - } + $contributionTypeId = (integer) $post['contribution_type']; + if (!empty($contributionTypeId)) { + $contributionType = get_db()->getTable('ContributionType')->find($contributionTypeId); + $itemTypeId = $contributionType->getItemType()->id; + } else { + $this->_helper->flashMessenger(__('You must select a type for your contribution.'), 'error'); + return false; + } + // Public is updated with the contributed item. + $itemMetadata = array('public' => false, + 'featured' => false, + 'item_type_id' => $itemTypeId); - // TODO Check if there is at least one file if one file or more is required and remove the catch below. - $fileMetadata = $this->_prepareFilesUpload($contributionType); + $collectionId = (integer) get_option('contribution_collection_id'); + if (!empty($collectionId)) { + $itemMetadata['collection_id'] = $collectionId; + } - // This is a hack to allow the file upload job to succeed - // even with the synchronous job dispatcher. - $acl = get_acl(); - if ($acl) { - $acl->allow(null, 'Items', 'showNotPublic'); - $acl->allow(null, 'Collections', 'showNotPublic'); - } - try { - //in case we're doing Simple, create and save the Item so the owner is set, then update with the data - $item = new Item(); - $item->setOwner($user); - $item->save(); - $item = update_item($item, $itemMetadata, array(), $fileMetadata); - } catch(Omeka_Validate_Exception $e) { - $this->flashValidatonErrors($e); - $item->delete(); - return false; - } catch (Omeka_File_Ingest_InvalidException $e) { - // Copying this cruddy hack - if (strstr($e->getMessage(), "'file'")) { - $this->_helper->flashMessenger("You must upload a file when making a {$contributionType->display_name} contribution.", 'error'); - } - // Check multiple files. - elseif (strstr($e->getMessage(), "file_")) { - $this->_helper->flashMessenger(__('One or more files have not been uploaded.') - . ' ' . __('You must upload a file when making a %s contribution.', $contributionType->display_name), 'error'); - } else { - $this->_helper->flashMessenger($e->getMessage()); - } - $item->delete(); - return false; - } catch (Exception $e) { - $this->_helper->flashMessenger($e->getMessage()); - $item->delete(); - return false; - } + // In case we're doing Simple, create and save the Item so the owner + // is set, then update with the data. + $item = new Item(); + $item->setOwner($user); + + $fileMetadata = $this->_prepareFilesUpload($contributionType); - $this->_addElementTextsToItem($item, $post['Elements']); + // If not simple and the profile doesn't process, send back false for the + // error. This should be done before processing item in order to set + // profile type and to avoid settings profile elements to item. + $this->_processUserProfile($user, $post); + + // Use a specific setPostData() for item, because some post fields are + // not set in the post. + $this->_setPostData($item, $post, $itemMetadata); + + // Tags are added separately. + if ($contributionType->add_tags && isset($post['tags'])) { + $item->addTags($post['tags']); + } + + // Allow plugins to deal with the inputs they may have added to the form + // and that are not managed via hooks before or after save item. + fire_plugin_hook( + 'contribution_save_form', + array( + 'contributionType' => $contributionType, + 'record' => $item, + 'post' => $post, + )); - // Tags are added separately. - if ($contributionType->add_tags && isset($post['tags'])) { - $item->addTags($post['tags']); + // Everything has been checked, so save item. + if ($item->save(false)) { + // Check if a required file has been uploaded. + if ($contributionType->isFileRequired() && empty($item->fileCount())) { + $this->_helper->flashMessenger($item->getErrors()); + $this->_helper->flashMessenger(__('You must upload a file when making a %s contribution.', $contributionType->display_name), 'error'); + $item->delete(); + return; } - // Allow plugins to deal with the inputs they may have added to the form - // and that are not managed via hooks before or after save item. - fire_plugin_hook('contribution_save_form', array('contributionType'=>$contributionType,'record'=>$item, 'post'=>$post)); - - $item->save(); - //if not simple and the profile doesn't process, send back false for the error - $this->_processUserProfile($user, $post); - $this->_linkItemToContributedItem($item, $post); + $this->_linkItemToContributedItem($item, $contributor, $post); $this->_sendEmailNotifications($user, $item); return true; } + // Error during saving. + else { + $this->_helper->flashMessenger($item->getErrors()); + $item->delete(); + } return false; } @@ -511,33 +506,6 @@ protected function _linkItemToContributedItem($item, $post) $linkage->save(); } - /** - * Adds ElementTexts to item. - * - * @param Item $item Item to add texts to. - * @param array $elements Array of element inputs from form - */ - protected function _addElementTextsToItem($item, $elements) - { - $db = get_db(); - $elementTable = $db->getTable('Element'); - $sql = "SELECT DISTINCT `id` from `$db->ElementSet` WHERE `record_type` = 'UserProfilesType' "; - $userProfilesElementSets = $db->fetchCol($sql); - foreach($elements as $elementId => $elementTexts) { - $element = $elementTable->find($elementId); - $elSet = $element->getElementSet(); - //need to skip over elements that are intended for a User Profile, not the item - if (in_array($elSet->id, $userProfilesElementSets)) { - continue; - } - foreach($elementTexts as $elementText) { - if (!empty($elementText['text'])) { - $item->addTextForElement($element, $elementText['text']); - } - } - } - } - /** * Set post data to an item. * From f1bd5de4cc014855520e2defe154a81dd4c2febb Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Sep 2014 02:47:02 +0200 Subject: [PATCH 30/46] Fixed link to contribution delete. --- ContributionPlugin.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 393e542d..878a338a 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -629,7 +629,7 @@ public function hookPublicItemsShow($args) $html .= '

' . __('Edit My Contribution') . '

'; $html .= '
    '; $html .= '
  • ' . contribution_link_to($contributedItem, 'edit', __('Edit')) . '
  • '; - $html .= '
  • ' . contribution_link_to($contributedItem, 'delete', __('Delete')) . '
  • '; + // $html .= '
  • ' . contribution_link_to($contributedItem, 'delete', __('Delete')) . '
  • '; $html .= '
'; $html .= '
'; echo $html; From 900c4dd3322de1d641edf23af358af28bf883a2f Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 6 Oct 2014 02:47:02 +0200 Subject: [PATCH 31/46] Fixed new contribution. --- controllers/ContributionController.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index c7e96804..9317f197 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -351,6 +351,7 @@ protected function _processForm($post) return false; } } + $contributor = $user; $contributionTypeId = (integer) $post['contribution_type']; if (!empty($contributionTypeId)) { @@ -410,7 +411,7 @@ protected function _processForm($post) $item->delete(); return; } - $this->_linkItemToContributedItem($item, $contributor, $post); + $this->_linkItemToContributedItem($item, $post); $this->_sendEmailNotifications($user, $item); return true; } From 04ed0adab8524aa0b1afeb9798bbbcb6574b448a Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 10 Oct 2014 02:47:02 +0200 Subject: [PATCH 32/46] Fixed use of empty() with an old php version. --- controllers/ContributionController.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 9317f197..f158a09b 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -405,7 +405,8 @@ protected function _processForm($post) // Everything has been checked, so save item. if ($item->save(false)) { // Check if a required file has been uploaded. - if ($contributionType->isFileRequired() && empty($item->fileCount())) { + $fileCount = $item->fileCount(); + if ($contributionType->isFileRequired() && empty($fileCount)) { $this->_helper->flashMessenger($item->getErrors()); $this->_helper->flashMessenger(__('You must upload a file when making a %s contribution.', $contributionType->display_name), 'error'); $item->delete(); From 1da6236df9ebb97dad12a02225b96df9bba65485 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Thu, 23 Oct 2014 02:47:02 +0200 Subject: [PATCH 33/46] Trim post element texts. --- controllers/ContributionController.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index f158a09b..784e68ff 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -564,7 +564,7 @@ protected function _setPostData($item, $post, $itemMetadata = array()) foreach ($item->getAllElementTexts() as $elementText) { $currentElements[$elementText->element_id] = array( array( - 'text' => $elementText->text, + 'text' => trim($elementText->text), 'html' => $elementText->html, ), ); From cc27630e5f9310e3e14f29a9c09c4eff0152043f Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Fri, 19 Dec 2014 02:47:02 +0100 Subject: [PATCH 34/46] Fixed upgrade. --- controllers/AjaxController.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/controllers/AjaxController.php b/controllers/AjaxController.php index 28e91924..63ca6efe 100644 --- a/controllers/AjaxController.php +++ b/controllers/AjaxController.php @@ -40,7 +40,7 @@ public function updateAction() } $id = (integer) $this->_getParam('id'); - $contributedItem = get_record_by_id('ContributionContributedItem', $id); + $contributedItem = $this->_helper->db->find($id); if (!$contributedItem) { $this->getResponse()->setHttpResponseCode(400); return; @@ -74,7 +74,7 @@ public function deleteAction() // Handle action. try { $id = (integer) $this->_getParam('id'); - $contributedItem = get_record_by_id('ContributionContributedItem', $id); + $contributedItem = $this->_helper->db->find($id); if (!$contributedItem) { $this->getResponse()->setHttpResponseCode(400); return; From 9392e7696fd940bdb201c26f808c58f4da279fd9 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 35/46] Fixed add tags. --- views/public/contribution/type-form.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 695c33df..f049011b 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -66,7 +66,7 @@

- formText('tags'); ?> + formText('tags', isset($tags) ? $tags : ''); ?>
From 7f5a07c0f44778715414a0bc7c32115f3291e609 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 36/46] Fixed contribute second title. --- views/public/contribution/type-form.php | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index f049011b..311088ed 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -5,11 +5,9 @@ $isAllowed = $type->isFileAllowed(); $allowMultipleFiles = $isAllowed && $type->multiple_files; ?> -

display_name); - } ?> -

+ +

display_name); ?>

+ Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 37/46] Fixed tag for user. --- views/public/contribution/type-form.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 311088ed..4098e8bb 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -94,7 +94,7 @@ -

+

' . metadata($user, 'name') . ''); ?>

Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 38/46] Added a title for files in edit form. --- views/public/contribution/edit.php | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/views/public/contribution/edit.php b/views/public/contribution/edit.php index 7f281927..ef0ed167 100644 --- a/views/public/contribution/edit.php +++ b/views/public/contribution/edit.php @@ -43,6 +43,10 @@ display_name; ?>
+
+ +
+
    Files as $key => $file): ?>
  • @@ -52,6 +56,7 @@
+
From d4431f8af2eac6418a2a55926b46bff30f3775da Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 39/46] Cleaned some public pages. --- views/public/contribution/terms.php | 15 +++++++++------ views/public/contribution/thankyou.php | 11 +++++++++-- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/views/public/contribution/terms.php b/views/public/contribution/terms.php index 92e6666f..a215227f 100644 --- a/views/public/contribution/terms.php +++ b/views/public/contribution/terms.php @@ -1,10 +1,13 @@ - __('Contribution Terms of Service')); -echo head($head); -?> + $title, + 'bodyclass' => $bodyClass, +)); ?>
-

+

- \ No newline at end of file + + $title, + 'bodyclass' => $bodyClass, +)); ?>

" . __('browse the archive') . ""); ?> @@ -7,4 +14,4 @@

" . __('this page') . ""); ?>

- + Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 40/46] Fixed previous upgrade of the base in some version. --- ContributionPlugin.php | 63 +++++++++++++++++++++++++++--------------- 1 file changed, 40 insertions(+), 23 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 878a338a..8a007b18 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -155,6 +155,8 @@ public function hookInstall() public function hookUpgrade($args) { + $db = $this->_db; + $oldVersion = $args['old_version']; $newVersion = $args['new_version']; // Catch-all for pre-2.0 versions @@ -181,7 +183,7 @@ public function hookUpgrade($args) $this->hookInstall(); } - + if (version_compare($oldVersion, '3.0', '<')) { if(!is_writable(CONTRIBUTION_PLUGIN_DIR . "/upgrade_files")) { throw new Omeka_Plugin_Installer_Exception("'upgrade_files' directory must be writable by the web server"); @@ -216,7 +218,7 @@ public function hookUpgrade($args) $this->_db->query($sql); } - + if (version_compare($oldVersion, '3.0.2', '<')) { //fix some previous bad upgrades //need to check if contributor_posting was properly changed to anonymous @@ -243,28 +245,43 @@ public function hookUpgrade($args) $this->_db->query($sql); } } - + if (version_compare($oldVersion, 3.1, '<')) { set_option('contribution_open', get_option('contribution_simple')); delete_option('contribution_simple'); } if (version_compare($oldVersion, '3.1.1', '<')) { - $db = $this->_db; - $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `multiple_files` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; - $db->query($sql); + // Need to check columns with old versions. + $sql = "SHOW COLUMNS IN `{$db->ContributionType}`"; + $result = $db->query($sql); + $cols = $result->fetchAll(Zend_Db::FETCH_COLUMN); + if (!in_array('multiple_files', $cols)) { + $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `multiple_files` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; + $db->query($sql); + } } if (version_compare($oldVersion, '3.1.2', '<')) { - $db = $this->_db; - $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `add_tags` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; - $db->query($sql); + // Need to check columns with old versions. + $sql = "SHOW COLUMNS IN `{$db->ContributionType}`"; + $result = $db->query($sql); + $cols = $result->fetchAll(Zend_Db::FETCH_COLUMN); + if (!in_array('add_tags', $cols)) { + $sql = "ALTER TABLE `$db->ContributionType` ADD COLUMN `add_tags` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0'"; + $db->query($sql); + } } if (version_compare($oldVersion, '3.1.3', '<')) { - $db = $this->_db; - $sql = "ALTER TABLE `$db->ContributionContributedItem` ADD COLUMN `deleted` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0' AFTER `anonymous`"; - $db->query($sql); + // Need to check columns with old versions. + $sql = "SHOW COLUMNS IN `{$db->ContributionContributedItem}`"; + $result = $db->query($sql); + $cols = $result->fetchAll(Zend_Db::FETCH_COLUMN); + if (!in_array('deleted', $cols)) { + $sql = "ALTER TABLE `$db->ContributionContributedItem` ADD COLUMN `deleted` TINYINT(1) UNSIGNED NOT NULL DEFAULT '0' AFTER `anonymous`"; + $db->query($sql); + } } if (version_compare($oldVersion, '3.1.4', '<')) { @@ -348,9 +365,9 @@ public function hookConfig($args) public function hookDefineAcl($args) { $acl = $args['acl']; - + $acl->addRole(new Zend_Acl_Role('contribution-anonymous'), null); - + $acl->addResource('Contribution_Contribution'); $acl->allow(array('super', 'admin', 'researcher', 'contributor'), 'Contribution_Contribution'); $privileges = array('show', 'contribute', 'thankyou', 'my-contributions', 'type-form'); @@ -448,20 +465,20 @@ public function filterApiResources($apiResources) ); return $apiResources; } - + public function filterApiImportOmekaAdapters($adapters, $args) { if (strpos($args['endpointUri'], 'omeka.net') !== false) { - $contributedItemAdapter = + $contributedItemAdapter = new ApiImport_ResponseAdapter_Omeka_GenericAdapter(null, $args['endpointUri'], 'ContributionContributedItem'); $contributedItemAdapter->setResourceProperties(array('item' => 'Item')); $adapters['contributions'] = $contributedItemAdapter; - - $contributionTypeAdapter = + + $contributionTypeAdapter = new ApiImport_ResponseAdapter_Omeka_GenericAdapter(null, $args['endpointUri'], 'ContributionType'); $contributionTypeAdapter->setResourceProperties(array('item_type' => 'ItemType')); $adapters['contribution_types'] = $contributionTypeAdapter; - + $contributionTypeElementsAdapter = new ApiImport_ResponseAdapter_Omeka_GenericAdapter(null, $args['endpointUri'], 'ContributionTypeElement'); $contributionTypeElementsAdapter->setResourceProperties( @@ -472,22 +489,22 @@ public function filterApiImportOmekaAdapters($adapters, $args) ); $adapters['contribution_type_elements'] = $contributionTypeElementsAdapter; } else { - $contributionContributorsAdapter = + $contributionContributorsAdapter = new ApiImport_ResponseAdapter_OmekaNet_ContributorsAdapter( null, $args['endpointUri'], 'User' ); $adapters['contribution_contributors'] = $contributionContributorsAdapter; - $contributedItemAdapter = + $contributedItemAdapter = new ApiImport_ResponseAdapter_OmekaNet_ContributedItemsAdapter( null, $args['endpointUri'], 'ContributionContributedItem' ); $adapters['contribution_contributed_items'] = $contributedItemAdapter; - $typesAdapter = + $typesAdapter = new ApiImport_ResponseAdapter_Omeka_GenericAdapter(null, $args['endpointUri'], 'ContributionType'); $typesAdapter->setResourceProperties(array('item_type' => 'ItemType')); $adapters['contribution_types'] = $typesAdapter; - $typeElementsAdapter = + $typeElementsAdapter = new ApiImport_ResponseAdapter_Omeka_GenericAdapter(null, $args['endpointUri'], 'ContributionTypeElement'); $typeElementsAdapter->setResourceProperties( array('type' => 'ContributionType', From 4cd692b85538a9e5e65872a62ae5f652bdb88f83 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 41/46] Fixed message after the update of a contribution. --- controllers/ContributionController.php | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 784e68ff..e36ef426 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -749,11 +749,12 @@ protected function _createNewAnonymousUser() */ protected function _getEditSuccessMessage($record) { - $itemTitle = $this->_getElementMetadata($record->Item, 'Dublin Core', 'Title'); + $item = $record->Item; + $itemTitle = $this->_getElementMetadata($item, 'Dublin Core', 'Title'); if ($itemTitle != '') { return __('The contributed item "%s" was successfully updated!', $itemTitle); } else { - return __('The contributed item #%s was successfully updated!', strval($item->id)); + return __('The contributed item #%d was successfully updated!', $item->id); } } From d560c62757b07969c26b85a7d1fa932747da2085 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 42/46] Improved the description to allow edition of contributions. --- libraries/Contribution/Form/Settings.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php index 4a5323cd..1ae7ffe3 100644 --- a/libraries/Contribution/Form/Settings.php +++ b/libraries/Contribution/Form/Settings.php @@ -93,7 +93,8 @@ public function init() $this->addElement('checkbox', 'contribution_allow_edit', array( 'label' => __("Allow to Edit Contribution"), - 'description' => __('If checked, contributors will be able to edit and to delete their contributions.'), + 'description' => __('If checked, contributors will be able to edit and to delete their contributions.') + . ' ' . __('Deleted contributions are only hidden for public and guest users.'), ), array('checked' => (bool) get_option('contribution_allow_edit') ? 'checked' : '') ); From 3dfc2af6fe83b15908a0ce43dedbbe4e5060c2a6 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 43/46] Improved placement of the hook in type form. --- views/public/contribution/type-form.php | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/views/public/contribution/type-form.php b/views/public/contribution/type-form.php index 4098e8bb..2a8b23f5 100644 --- a/views/public/contribution/type-form.php +++ b/views/public/contribution/type-form.php @@ -69,6 +69,14 @@
+
+$type, 'view'=>$this)); +?> +
+
@@ -94,8 +102,11 @@
+

' . metadata($user, 'name') . ''); ?>

+
+ @@ -128,10 +139,4 @@ - -$type, 'view'=>$this)); -?> Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 44/46] Added the total of contributions as title of the page "my-contributions". --- ContributionPlugin.php | 2 +- controllers/ContributionController.php | 1 + .../public/contribution/my-contributions.php | 21 +++++++++++++++++-- 3 files changed, 21 insertions(+), 3 deletions(-) diff --git a/ContributionPlugin.php b/ContributionPlugin.php index 4afff01e..efa51d9c 100644 --- a/ContributionPlugin.php +++ b/ContributionPlugin.php @@ -696,7 +696,7 @@ public function filterGuestUserWidgets($widgets) __('See all my contributions')); } else { - $html = '

' . __('No contribution yet.') . '

'; + $html = '

' . __('No contribution yet, or removed contributions.') . '

'; } $widget['content'] = $html; $widgets[] = $widget; diff --git a/controllers/ContributionController.php b/controllers/ContributionController.php index 96e931c1..199f8053 100644 --- a/controllers/ContributionController.php +++ b/controllers/ContributionController.php @@ -50,6 +50,7 @@ public function myContributionsAction() $contribItems = $contribItemTable->findBy(array('contributor'=>$user->id)); } $this->view->contrib_items = $contribItems; + $this->view->total_results = count($contribItems); } /** diff --git a/views/public/contribution/my-contributions.php b/views/public/contribution/my-contributions.php index fab13a28..2e3852f1 100644 --- a/views/public/contribution/my-contributions.php +++ b/views/public/contribution/my-contributions.php @@ -1,6 +1,13 @@ - + $pageTitle, + 'bodyclass' => 'contributions browse', +)); ?>
+

+
@@ -29,5 +36,15 @@
+ +

+ +

+

+ ', '', + '', ''); ?> +

+
- + Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 45/46] Fixed string in setting form. --- libraries/Contribution/Form/Settings.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/Contribution/Form/Settings.php b/libraries/Contribution/Form/Settings.php index 1ae7ffe3..535df808 100644 --- a/libraries/Contribution/Form/Settings.php +++ b/libraries/Contribution/Form/Settings.php @@ -21,7 +21,7 @@ public function init() $this->addElement('text', 'contribution_page_path', array( 'label' => __('Contribution Slug'), - 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. Default path is “contribution.”'), + 'description' => __('Relative path from the Omeka root to the desired location for the contribution form. Default path is “contribution“.'), 'required' => true, 'filters' => array(array('StringTrim', '/\\\s')), )); From 8dd6c28d84d4aefbf547e28637428279f1ff9277 Mon Sep 17 00:00:00 2001 From: Daniel Berthereau Date: Mon, 19 Dec 2016 00:00:00 +0100 Subject: [PATCH 46/46] Updated readme. --- README.md | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 7677ea03..9df0f5d6 100644 --- a/README.md +++ b/README.md @@ -2,9 +2,6 @@ Contribution (plugin for Omeka) =============================== -Summary -------- - This plugin for [Omeka] provides a way to collect stories, images, or other files from the public and manage those contributions in your Omeka archive as items. The form can also automatically add a reCAPTCHA box at the bottom of each @@ -13,6 +10,14 @@ form to prevent spam-bots from spamming your website. For more information, see the [Contribution presentation] on [Omeka] and the [update] done for Omeka 2. +This fork contains some improvements: + +* Possibility to upload multiple files, if wanted +* Possibility to add tags, if wanted +* Possibility for a contributor to edit and delete his/her contributions +* Simplification of some parts of code +* various strict standards fixes + Installation ------------ @@ -32,14 +37,14 @@ Warning Use it at your own risk. -It's always recommended to backup your files and database so you can roll back -if needed. +It's always recommended to backup your files and database regularly so you can +roll back if needed. Troubleshooting --------------- -See online issues on [Contribution issues] page on GitHub. +See online issues on the [plugin issues] page on GitHub. License @@ -73,15 +78,15 @@ Current maintainers: Copyright --------- -* Copyright Roy Rosenzweig Center for History and New Media, 2010-2013 -* Copyright Daniel Berthereau, 2014 (improvements, see [Daniel-KM]) +* Copyright Roy Rosenzweig Center for History and New Media, 2010-2016 +* Copyright Daniel Berthereau, 2014-2016 (improvements, see [Daniel-KM]) [Omeka]: https://omeka.org [Contribution presentation]: http://omeka.org/codex/Plugins/Contribution [update]: http://omeka.org/codex/Plugins/Contribution_2.0 [Contribution]: https://github.com/Omeka/plugin-Contribution -[Contribution issues]: https://github.com/Omeka/plugin-Contribution/issues +[plugin issues]: https://github.com/Omeka/plugin-Contribution/issues [Guest User]: https://github.com/Omeka/plugin-GuestUser [GNU/GPL]: https://www.gnu.org/licenses/gpl-3.0.html "GNU/GPL v3" [Daniel-KM]: https://github.com/Daniel-KM "Daniel Berthereau"