productreviewcaptcha - Version 1.0.0

Version Notes

This module add captcha to "Product Reviews" form.

Download this release

Release Info

Developer Magento Core Team
Extension productreviewcaptcha
Version 1.0.0
Comparing to
See all releases


Version 1.0.0

app/code/community/OlegKoval/ProductReviewCaptcha/Block/Form.php ADDED
@@ -0,0 +1,94 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Product Review Captcha form Block
4
+ * Overrided this block to set custom review form (form with reCAPTCHA widget)
5
+ *
6
+ * @category OlegKoval
7
+ * @package OlegKoval_ProductReviewCaptcha
8
+ * @copyright Copyright (c) 2012 Oleg Koval
9
+ * @author Oleg Koval <oleh.koval@gmail.com>
10
+ */
11
+
12
+ class OlegKoval_ProductReviewCaptcha_Block_Form extends Mage_Review_Block_Form {
13
+ const XML_PATH_PRC_ENABLED = 'catalog/review/prc_enabled';
14
+ const XML_PATH_PRC_PUBLIC_KEY = 'catalog/review/prc_public_key';
15
+ const XML_PATH_PRC_PRIVATE_KEY = 'catalog/review/prc_private_key';
16
+ const XML_PATH_PRC_THEME = 'catalog/review/prc_theme';
17
+ const XML_PATH_PRC_LANG = 'catalog/review/prc_lang';
18
+
19
+ /**
20
+ * Constructor of this class which set template of review form
21
+ */
22
+ public function __construct() {
23
+ $customerSession = Mage::getSingleton('customer/session');
24
+
25
+ Mage_Core_Block_Template::__construct();
26
+
27
+ $data = Mage::getSingleton('review/session')->getFormData(true);
28
+
29
+ //maybe we do not have form data - so we try another session
30
+ if ($data == null) {
31
+ $data = Mage::getSingleton('core/session')->getFormData(true);
32
+ }
33
+
34
+ $data = new Varien_Object($data);
35
+
36
+ // add logged in customer name as nickname
37
+ if (!$data->getNickname()) {
38
+ $customer = $customerSession->getCustomer();
39
+ if ($customer && $customer->getId()) {
40
+ $data->setNickname($customer->getFirstname());
41
+ }
42
+ }
43
+
44
+ $this->setAllowWriteReviewFlag($customerSession->isLoggedIn() || Mage::helper('review')->getIsGuestAllowToWrite());
45
+ if (!$this->getAllowWriteReviewFlag) {
46
+ $this->setLoginLink(
47
+ Mage::getUrl('customer/account/login/', array(
48
+ Mage_Customer_Helper_Data::REFERER_QUERY_PARAM_NAME => Mage::helper('core')->urlEncode(
49
+ Mage::getUrl('*/*/*', array('_current' => true)) .
50
+ '#review-form')
51
+ )
52
+ )
53
+ );
54
+ }
55
+
56
+ //if "Product Review Captcha" module is enabled - then we display template with reCAPTCHA
57
+ if (Mage::getStoreConfigFlag(self::XML_PATH_PRC_ENABLED)) {
58
+ //include reCaptcha library
59
+ require_once(Mage::getBaseDir('lib') . DS .'reCaptcha'. DS .'recaptchalib.php');
60
+
61
+ //create captcha html-code
62
+ $publickey = Mage::getStoreConfig(self::XML_PATH_PRC_PUBLIC_KEY);
63
+ $captcha_code = recaptcha_get_html($publickey);
64
+
65
+ //get reCaptcha theme name
66
+ $theme = Mage::getStoreConfig(self::XML_PATH_PRC_THEME);
67
+ if (strlen($theme) == 0 || !in_array($theme, array('red', 'white', 'blackglass', 'clean'))) {
68
+ $theme = 'red';
69
+ }
70
+
71
+ //get reCaptcha lang name
72
+ $lang = Mage::getStoreConfig(self::XML_PATH_PRC_LANG);
73
+ if (strlen($lang) == 0 || !in_array($lang, array('en', 'nl', 'fr', 'de', 'pt', 'ru', 'es', 'tr'))) {
74
+ $lang = 'en';
75
+ }
76
+
77
+ //small hack for language feature - because it's not working as described in documentation
78
+ $captcha_code = str_replace('?k=', '?hl='. $lang .'&amp;k=', $captcha_code);
79
+
80
+ $this->setTemplate('productreviewcaptcha/form.phtml')
81
+ ->assign('data', $data)
82
+ ->assign('messages', Mage::getSingleton('review/session')->getMessages(true))
83
+ ->setCaptchaCode($captcha_code)
84
+ ->setCaptchaTheme($theme)
85
+ ->setCaptchaLang($lang);
86
+ }
87
+ //otherwise use standard form
88
+ else {
89
+ $this->setTemplate('review/form.phtml')
90
+ ->assign('data', $data)
91
+ ->assign('messages', Mage::getSingleton('review/session')->getMessages(true));
92
+ }
93
+ }
94
+ }
app/code/community/OlegKoval/ProductReviewCaptcha/Model/System/Config/Source/Dropdown/Lang.php ADDED
@@ -0,0 +1,47 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Custom options for "reCaptcha Language" dropdown of "Product Review Captcha" customization
4
+ *
5
+ * @category OlegKoval
6
+ * @package OlegKoval_ProductReviewCaptcha
7
+ * @copyright Copyright (c) 2012 Oleg Koval
8
+ * @author Oleg Koval <oleh.koval@gmail.com>
9
+ */
10
+ class OlegKoval_ProductReviewCaptcha_Model_System_Config_Source_Dropdown_Lang {
11
+ public function toOptionArray() {
12
+ return array(
13
+ array(
14
+ 'value' => 'en',
15
+ 'label' => 'English (default)',
16
+ ),
17
+ array(
18
+ 'value' => 'nl',
19
+ 'label' => 'Dutch',
20
+ ),
21
+ array(
22
+ 'value' => 'fr',
23
+ 'label' => 'French',
24
+ ),
25
+ array(
26
+ 'value' => 'de',
27
+ 'label' => 'German',
28
+ ),
29
+ array(
30
+ 'value' => 'pt',
31
+ 'label' => 'Portuguese',
32
+ ),
33
+ array(
34
+ 'value' => 'ru',
35
+ 'label' => 'Russian',
36
+ ),
37
+ array(
38
+ 'value' => 'es',
39
+ 'label' => 'Spanish',
40
+ ),
41
+ array(
42
+ 'value' => 'tr',
43
+ 'label' => 'Turkish',
44
+ ),
45
+ );
46
+ }
47
+ }
app/code/community/OlegKoval/ProductReviewCaptcha/Model/System/Config/Source/Dropdown/Theme.php ADDED
@@ -0,0 +1,31 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Custom options for "reCaptcha Theme" dropdown of "Product Review Captcha" customization
4
+ *
5
+ * @category OlegKoval
6
+ * @package OlegKoval_ProductReviewCaptcha
7
+ * @copyright Copyright (c) 2012 Oleg Koval
8
+ * @author Oleg Koval <oleh.koval@gmail.com>
9
+ */
10
+ class OlegKoval_ProductReviewCaptcha_Model_System_Config_Source_Dropdown_Theme {
11
+ public function toOptionArray() {
12
+ return array(
13
+ array(
14
+ 'value' => 'red',
15
+ 'label' => 'Red (default)',
16
+ ),
17
+ array(
18
+ 'value' => 'white',
19
+ 'label' => 'White',
20
+ ),
21
+ array(
22
+ 'value' => 'blackglass',
23
+ 'label' => 'Blackglass',
24
+ ),
25
+ array(
26
+ 'value' => 'clean',
27
+ 'label' => 'Clean',
28
+ ),
29
+ );
30
+ }
31
+ }
app/code/community/OlegKoval/ProductReviewCaptcha/controllers/ProductController.php ADDED
@@ -0,0 +1,71 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Product Review Captcha index controller
4
+ *
5
+ * @category OlegKoval
6
+ * @package OlegKoval_ProductReviewCaptcha
7
+ * @copyright Copyright (c) 2012 Oleg Koval
8
+ * @author Oleg Koval <oleh.koval@gmail.com>
9
+ */
10
+ //include controller to override it
11
+ require_once(Mage::getBaseDir('app') . DS .'code'. DS .'core'. DS .'Mage'. DS .'Review'. DS .'controllers'. DS .'ProductController.php');
12
+
13
+ class OlegKoval_ProductReviewCaptcha_ProductController extends Mage_Review_ProductController {
14
+ const XML_PATH_PRC_ENABLED = 'catalog/review/prc_enabled';
15
+ const XML_PATH_PRC_PRIVATE_KEY = 'catalog/review/prc_private_key';
16
+
17
+ /**
18
+ * Call parent preDispatch() method
19
+ *
20
+ */
21
+ public function preDispatch() {
22
+ parent::preDispatch();
23
+
24
+ return $this;
25
+ }
26
+
27
+ /**
28
+ * Submit new review action
29
+ *
30
+ */
31
+ public function postAction() {
32
+ if (Mage::getStoreConfigFlag(self::XML_PATH_PRC_ENABLED)) {
33
+ try {
34
+ $post = $this->getRequest()->getPost();
35
+ if ($post) {
36
+ //include reCaptcha library
37
+ require_once(Mage::getBaseDir('lib') . DS .'reCaptcha'. DS .'recaptchalib.php');
38
+
39
+ //validate captcha
40
+ $privatekey = Mage::getStoreConfig(self::XML_PATH_PRC_PRIVATE_KEY);
41
+ $remote_addr = $this->getRequest()->getServer('REMOTE_ADDR');
42
+ $captcha = recaptcha_check_answer($privatekey, $remote_addr, $post["recaptcha_challenge_field"], $post["recaptcha_response_field"]);
43
+
44
+
45
+ if (!$captcha->is_valid) {
46
+ throw new Exception("The reCAPTCHA wasn't entered correctly.", 1);
47
+ }
48
+ }
49
+ else {
50
+ throw new Exception('', 1);
51
+ }
52
+ }
53
+ catch (Exception $e) {
54
+ if (strlen($e->getMessage()) > 0) {
55
+ Mage::getSingleton('core/session')->addError($this->__($e->getMessage()));
56
+ Mage::getSingleton('core/session')->setFormData($post);
57
+ }
58
+ if ($redirectUrl = Mage::getSingleton('review/session')->getRedirectUrl(true)) {
59
+ $this->_redirectUrl($redirectUrl);
60
+ return;
61
+ }
62
+ $this->_redirectReferer();
63
+ return;
64
+ }
65
+ }
66
+
67
+ //everything is OK - call parent action
68
+ parent::postAction();
69
+ }
70
+
71
+ }
app/code/community/OlegKoval/ProductReviewCaptcha/etc/config.xml ADDED
@@ -0,0 +1,49 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <!--
3
+ /**
4
+ * Product Review Captcha
5
+ *
6
+ * @category OlegKoval
7
+ * @package OlegKoval_ProductReviewCaptcha
8
+ * @copyright Copyright (c) 2012 Oleg Koval
9
+ * @author Oleg Koval <oleh.koval@gmail.com>
10
+ */
11
+ -->
12
+ <config>
13
+ <modules>
14
+ <OlegKoval_ProductReviewCaptcha>
15
+ <version>1.0.0</version>
16
+ <depends>
17
+ <Mage_Contacts/>
18
+ </depends>
19
+ </OlegKoval_ProductReviewCaptcha>
20
+ </modules>
21
+
22
+ <global>
23
+ <blocks>
24
+ <review>
25
+ <rewrite>
26
+ <form>OlegKoval_ProductReviewCaptcha_Block_Form</form>
27
+ </rewrite>
28
+ </review>
29
+ </blocks>
30
+
31
+ <models>
32
+ <productreviewcaptcha>
33
+ <class>OlegKoval_ProductReviewCaptcha_Model</class>
34
+ </productreviewcaptcha>
35
+ </models>
36
+ </global>
37
+
38
+ <frontend>
39
+ <routers>
40
+ <review>
41
+ <args>
42
+ <modules>
43
+ <productreviewcaptcha before="Mage_Review">OlegKoval_ProductReviewCaptcha</productreviewcaptcha>
44
+ </modules>
45
+ </args>
46
+ </review>
47
+ </routers>
48
+ </frontend>
49
+ </config>
app/code/community/OlegKoval/ProductReviewCaptcha/etc/system.xml ADDED
@@ -0,0 +1,71 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <!--
3
+ /**
4
+ * Product Review Captcha
5
+ *
6
+ * @category OlegKoval
7
+ * @package OlegKoval_ProductReviewCaptcha
8
+ * @copyright Copyright (c) 2012 Oleg Koval
9
+ * @author Oleg Koval <oleh.koval@gmail.com>
10
+ */
11
+ -->
12
+ <config>
13
+ <sections>
14
+ <catalog>
15
+ <groups>
16
+ <review>
17
+ <fields>
18
+ <prc_enabled translate="label">
19
+ <label>Enable Captcha</label>
20
+ <frontend_type>select</frontend_type>
21
+ <source_model>adminhtml/system_config_source_yesno</source_model>
22
+ <backend_model>contacts/system_config_backend_links</backend_model>
23
+ <sort_order>110</sort_order>
24
+ <show_in_default>1</show_in_default>
25
+ <show_in_website>1</show_in_website>
26
+ <show_in_store>1</show_in_store>
27
+ </prc_enabled>
28
+ <prc_public_key translate="label">
29
+ <label>Public Key</label>
30
+ <comment>You got this from the signup page: https://www.google.com/recaptcha/admin/create</comment>
31
+ <frontend_type>text</frontend_type>
32
+ <sort_order>120</sort_order>
33
+ <show_in_default>1</show_in_default>
34
+ <show_in_website>1</show_in_website>
35
+ <show_in_store>1</show_in_store>
36
+ </prc_public_key>
37
+ <prc_private_key translate="label">
38
+ <label>Private Key</label>
39
+ <comment>You got this from the signup page: https://www.google.com/recaptcha/admin/create</comment>
40
+ <frontend_type>text</frontend_type>
41
+ <sort_order>130</sort_order>
42
+ <show_in_default>1</show_in_default>
43
+ <show_in_website>1</show_in_website>
44
+ <show_in_store>1</show_in_store>
45
+ </prc_private_key>
46
+ <prc_theme translate="label">
47
+ <label>reCaptcha Theme</label>
48
+ <comment>Customizing the Look of reCAPTCHA</comment>
49
+ <frontend_type>select</frontend_type>
50
+ <source_model>productreviewcaptcha/system_config_source_dropdown_theme</source_model>
51
+ <sort_order>140</sort_order>
52
+ <show_in_default>1</show_in_default>
53
+ <show_in_website>1</show_in_website>
54
+ <show_in_store>1</show_in_store>
55
+ </prc_theme>
56
+ <prc_lang translate="label">
57
+ <label>reCaptcha Language</label>
58
+ <comment>Which language is used in the reCaptcha interface</comment>
59
+ <frontend_type>select</frontend_type>
60
+ <source_model>productreviewcaptcha/system_config_source_dropdown_lang</source_model>
61
+ <sort_order>150</sort_order>
62
+ <show_in_default>1</show_in_default>
63
+ <show_in_website>1</show_in_website>
64
+ <show_in_store>1</show_in_store>
65
+ </prc_lang>
66
+ </fields>
67
+ </review>
68
+ </groups>
69
+ </catalog>
70
+ </sections>
71
+ </config>
app/design/frontend/base/default/template/productreviewcaptcha/form.phtml ADDED
@@ -0,0 +1,145 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Magento
4
+ *
5
+ * NOTICE OF LICENSE
6
+ *
7
+ * This source file is subject to the Academic Free License (AFL 3.0)
8
+ * that is bundled with this package in the file LICENSE_AFL.txt.
9
+ * It is also available through the world-wide-web at this URL:
10
+ * http://opensource.org/licenses/afl-3.0.php
11
+ * If you did not receive a copy of the license and are unable to
12
+ * obtain it through the world-wide-web, please send an email
13
+ * to license@magentocommerce.com so we can send you a copy immediately.
14
+ *
15
+ * DISCLAIMER
16
+ *
17
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
18
+ * versions in the future. If you wish to customize Magento for your
19
+ * needs please refer to http://www.magentocommerce.com for more information.
20
+ *
21
+ * @category design
22
+ * @package base_default
23
+ * @copyright Copyright (c) 2012 Magento Inc. (http://www.magentocommerce.com)
24
+ * @license http://opensource.org/licenses/afl-3.0.php Academic Free License (AFL 3.0)
25
+ */
26
+ ?>
27
+ <div class="form-add">
28
+ <h2><?php echo $this->__('Write Your Own Review') ?></h2>
29
+ <?php if ($this->getAllowWriteReviewFlag()): ?>
30
+ <script type="text/javascript">
31
+ //<![CDATA[
32
+ var RecaptchaOptions = {
33
+ theme : '<?php echo $this->getCaptchaTheme(); ?>',
34
+ lang : '<?php echo $this->getCaptchaLang(); ?>',
35
+ };
36
+ //]]>
37
+ </script>
38
+ <form action="<?php echo $this->getAction() ?>" method="post" id="review-form">
39
+ <fieldset>
40
+ <?php echo $this->getChildHtml('form_fields_before')?>
41
+ <h3><?php echo $this->__("You're reviewing:"); ?> <span><?php echo $this->htmlEscape($this->getProductInfo()->getName()) ?></span></h3>
42
+ <?php if( $this->getRatings() && $this->getRatings()->getSize()): ?>
43
+ <h4><?php echo $this->__('How do you rate this product?') ?> <em class="required">*</em></h4>
44
+ <span id="input-message-box"></span>
45
+ <table class="data-table" id="product-review-table">
46
+ <col />
47
+ <col width="1" />
48
+ <col width="1" />
49
+ <col width="1" />
50
+ <col width="1" />
51
+ <col width="1" />
52
+ <thead>
53
+ <tr>
54
+ <th>&nbsp;</th>
55
+ <th><span class="nobr"><?php echo $this->__('1 star') ?></span></th>
56
+ <th><span class="nobr"><?php echo $this->__('2 stars') ?></span></th>
57
+ <th><span class="nobr"><?php echo $this->__('3 stars') ?></span></th>
58
+ <th><span class="nobr"><?php echo $this->__('4 stars') ?></span></th>
59
+ <th><span class="nobr"><?php echo $this->__('5 stars') ?></span></th>
60
+ </tr>
61
+ </thead>
62
+ <tbody>
63
+ <?php foreach ($this->getRatings() as $_rating): ?>
64
+ <tr>
65
+ <th><?php echo $this->escapeHtml($_rating->getRatingCode()) ?></th>
66
+ <?php foreach ($_rating->getOptions() as $_option): ?>
67
+ <td class="value"><input type="radio" name="ratings[<?php echo $_rating->getId() ?>]" id="<?php echo $this->escapeHtml($_rating->getRatingCode()) ?>_<?php echo $_option->getValue() ?>" value="<?php echo $_option->getId() ?>" class="radio" /></td>
68
+ <?php endforeach; ?>
69
+ </tr>
70
+ <?php endforeach; ?>
71
+ </tbody>
72
+ </table>
73
+ <input type="hidden" name="validate_rating" class="validate-rating" value="" />
74
+ <script type="text/javascript">decorateTable('product-review-table')</script>
75
+ <?php endif; ?>
76
+ <ul class="form-list">
77
+ <li>
78
+ <label for="nickname_field" class="required"><em>*</em><?php echo $this->__('Nickname') ?></label>
79
+ <div class="input-box">
80
+ <input type="text" name="nickname" id="nickname_field" class="input-text required-entry" value="<?php echo $this->htmlEscape($data->getNickname()) ?>" />
81
+ </div>
82
+ </li>
83
+ <li>
84
+ <label for="summary_field" class="required"><em>*</em><?php echo $this->__('Summary of Your Review') ?></label>
85
+ <div class="input-box">
86
+ <input type="text" name="title" id="summary_field" class="input-text required-entry" value="<?php echo $this->htmlEscape($data->getTitle()) ?>" />
87
+ </div>
88
+ </li>
89
+ <li>
90
+ <label for="review_field" class="required"><em>*</em><?php echo $this->__('Review') ?></label>
91
+ <div class="input-box">
92
+ <textarea name="detail" id="review_field" cols="5" rows="3" class="required-entry"><?php echo $this->htmlEscape($data->getDetail()) ?></textarea>
93
+ </div>
94
+ </li>
95
+ <li class="wide">
96
+ <div class="input-box">
97
+ <?php echo $this->getCaptchaCode(); ?>
98
+ </div>
99
+ </li>
100
+ </ul>
101
+ </fieldset>
102
+ <div class="buttons-set">
103
+ <button type="submit" title="<?php echo $this->__('Submit Review') ?>" class="button"><span><span><?php echo $this->__('Submit Review') ?></span></span></button>
104
+ </div>
105
+ </form>
106
+ <script type="text/javascript">
107
+ //<![CDATA[
108
+ var dataForm = new VarienForm('review-form');
109
+ Validation.addAllThese(
110
+ [
111
+ ['validate-rating', '<?php echo $this->__('Please select one of each of the ratings above') ?>', function(v) {
112
+ var trs = $('product-review-table').select('tr');
113
+ var inputs;
114
+ var error = 1;
115
+
116
+ for( var j=0; j < trs.length; j++ ) {
117
+ var tr = trs[j];
118
+ if( j > 0 ) {
119
+ inputs = tr.select('input');
120
+
121
+ for( i in inputs ) {
122
+ if( inputs[i].checked == true ) {
123
+ error = 0;
124
+ }
125
+ }
126
+
127
+ if( error == 1 ) {
128
+ return false;
129
+ } else {
130
+ error = 1;
131
+ }
132
+ }
133
+ }
134
+ return true;
135
+ }]
136
+ ]
137
+ );
138
+ //]]>
139
+ </script>
140
+ <?php else: ?>
141
+ <p class="review-nologged" id="review-form">
142
+ <?php echo $this->__('Only registered users can write reviews. Please, <a href="%s">log in</a> or <a href="%s">register</a>', $this->getLoginLink(), Mage::helper('customer')->getRegisterUrl()) ?>
143
+ </p>
144
+ <?php endif ?>
145
+ </div>
app/etc/modules/OlegKoval_ProductReviewCaptcha.xml ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <!--
3
+ /**
4
+ * Product Review Captcha
5
+ *
6
+ * @category OlegKoval
7
+ * @package OlegKoval_ProductReviewCaptcha
8
+ * @copyright Copyright (c) 2012 Oleg Koval
9
+ * @author Oleg Koval <oleh.koval@gmail.com>
10
+ */
11
+ -->
12
+ <config>
13
+ <modules>
14
+ <OlegKoval_ProductReviewCaptcha>
15
+ <active>true</active>
16
+ <codePool>community</codePool>
17
+ </OlegKoval_ProductReviewCaptcha>
18
+ </modules>
19
+ </config>
app/locale/en_US/OlegKoval_ProductReviewCaptcha.csv ADDED
@@ -0,0 +1,6 @@
 
 
 
 
 
 
1
+ "Product Review Captcha","Product Review Captcha"
2
+ "Enable Captcha","Enable Captcha"
3
+ "Public Key","Public Key"
4
+ "Private Key","Private Key"
5
+ "You got this from the signup page: https://www.google.com/recaptcha/admin/create","You got this from the signup page: https://www.google.com/recaptcha/admin/create"
6
+ "The reCAPTCHA wasn't entered correctly.","The reCAPTCHA wasn't entered correctly."
lib/reCaptcha/recaptchalib.php ADDED
@@ -0,0 +1,277 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /*
3
+ * This is a PHP library that handles calling reCAPTCHA.
4
+ * - Documentation and latest version
5
+ * http://recaptcha.net/plugins/php/
6
+ * - Get a reCAPTCHA API Key
7
+ * https://www.google.com/recaptcha/admin/create
8
+ * - Discussion group
9
+ * http://groups.google.com/group/recaptcha
10
+ *
11
+ * Copyright (c) 2007 reCAPTCHA -- http://recaptcha.net
12
+ * AUTHORS:
13
+ * Mike Crawford
14
+ * Ben Maurer
15
+ *
16
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
17
+ * of this software and associated documentation files (the "Software"), to deal
18
+ * in the Software without restriction, including without limitation the rights
19
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
20
+ * copies of the Software, and to permit persons to whom the Software is
21
+ * furnished to do so, subject to the following conditions:
22
+ *
23
+ * The above copyright notice and this permission notice shall be included in
24
+ * all copies or substantial portions of the Software.
25
+ *
26
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
27
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
28
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
29
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
30
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
31
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
32
+ * THE SOFTWARE.
33
+ */
34
+
35
+ /**
36
+ * The reCAPTCHA server URL's
37
+ */
38
+ define("RECAPTCHA_API_SERVER", "http://www.google.com/recaptcha/api");
39
+ define("RECAPTCHA_API_SECURE_SERVER", "https://www.google.com/recaptcha/api");
40
+ define("RECAPTCHA_VERIFY_SERVER", "www.google.com");
41
+
42
+ /**
43
+ * Encodes the given data into a query string format
44
+ * @param $data - array of string elements to be encoded
45
+ * @return string - encoded request
46
+ */
47
+ function _recaptcha_qsencode ($data) {
48
+ $req = "";
49
+ foreach ( $data as $key => $value )
50
+ $req .= $key . '=' . urlencode( stripslashes($value) ) . '&';
51
+
52
+ // Cut the last '&'
53
+ $req=substr($req,0,strlen($req)-1);
54
+ return $req;
55
+ }
56
+
57
+
58
+
59
+ /**
60
+ * Submits an HTTP POST to a reCAPTCHA server
61
+ * @param string $host
62
+ * @param string $path
63
+ * @param array $data
64
+ * @param int port
65
+ * @return array response
66
+ */
67
+ function _recaptcha_http_post($host, $path, $data, $port = 80) {
68
+
69
+ $req = _recaptcha_qsencode ($data);
70
+
71
+ $http_request = "POST $path HTTP/1.0\r\n";
72
+ $http_request .= "Host: $host\r\n";
73
+ $http_request .= "Content-Type: application/x-www-form-urlencoded;\r\n";
74
+ $http_request .= "Content-Length: " . strlen($req) . "\r\n";
75
+ $http_request .= "User-Agent: reCAPTCHA/PHP\r\n";
76
+ $http_request .= "\r\n";
77
+ $http_request .= $req;
78
+
79
+ $response = '';
80
+ if( false == ( $fs = @fsockopen($host, $port, $errno, $errstr, 10) ) ) {
81
+ die ('Could not open socket');
82
+ }
83
+
84
+ fwrite($fs, $http_request);
85
+
86
+ while ( !feof($fs) )
87
+ $response .= fgets($fs, 1160); // One TCP-IP packet
88
+ fclose($fs);
89
+ $response = explode("\r\n\r\n", $response, 2);
90
+
91
+ return $response;
92
+ }
93
+
94
+
95
+
96
+ /**
97
+ * Gets the challenge HTML (javascript and non-javascript version).
98
+ * This is called from the browser, and the resulting reCAPTCHA HTML widget
99
+ * is embedded within the HTML form it was called from.
100
+ * @param string $pubkey A public key for reCAPTCHA
101
+ * @param string $error The error given by reCAPTCHA (optional, default is null)
102
+ * @param boolean $use_ssl Should the request be made over ssl? (optional, default is false)
103
+
104
+ * @return string - The HTML to be embedded in the user's form.
105
+ */
106
+ function recaptcha_get_html ($pubkey, $error = null, $use_ssl = false)
107
+ {
108
+ if ($pubkey == null || $pubkey == '') {
109
+ die ("To use reCAPTCHA you must get an API key from <a href='https://www.google.com/recaptcha/admin/create'>https://www.google.com/recaptcha/admin/create</a>");
110
+ }
111
+
112
+ if ($use_ssl) {
113
+ $server = RECAPTCHA_API_SECURE_SERVER;
114
+ } else {
115
+ $server = RECAPTCHA_API_SERVER;
116
+ }
117
+
118
+ $errorpart = "";
119
+ if ($error) {
120
+ $errorpart = "&amp;error=" . $error;
121
+ }
122
+ return '<script type="text/javascript" src="'. $server . '/challenge?k=' . $pubkey . $errorpart . '"></script>
123
+
124
+ <noscript>
125
+ <iframe src="'. $server . '/noscript?k=' . $pubkey . $errorpart . '" height="300" width="500" frameborder="0"></iframe><br/>
126
+ <textarea name="recaptcha_challenge_field" rows="3" cols="40"></textarea>
127
+ <input type="hidden" name="recaptcha_response_field" value="manual_challenge"/>
128
+ </noscript>';
129
+ }
130
+
131
+
132
+
133
+
134
+ /**
135
+ * A ReCaptchaResponse is returned from recaptcha_check_answer()
136
+ */
137
+ class ReCaptchaResponse {
138
+ var $is_valid;
139
+ var $error;
140
+ }
141
+
142
+
143
+ /**
144
+ * Calls an HTTP POST function to verify if the user's guess was correct
145
+ * @param string $privkey
146
+ * @param string $remoteip
147
+ * @param string $challenge
148
+ * @param string $response
149
+ * @param array $extra_params an array of extra variables to post to the server
150
+ * @return ReCaptchaResponse
151
+ */
152
+ function recaptcha_check_answer ($privkey, $remoteip, $challenge, $response, $extra_params = array())
153
+ {
154
+ if ($privkey == null || $privkey == '') {
155
+ die ("To use reCAPTCHA you must get an API key from <a href='https://www.google.com/recaptcha/admin/create'>https://www.google.com/recaptcha/admin/create</a>");
156
+ }
157
+
158
+ if ($remoteip == null || $remoteip == '') {
159
+ die ("For security reasons, you must pass the remote ip to reCAPTCHA");
160
+ }
161
+
162
+
163
+
164
+ //discard spam submissions
165
+ if ($challenge == null || strlen($challenge) == 0 || $response == null || strlen($response) == 0) {
166
+ $recaptcha_response = new ReCaptchaResponse();
167
+ $recaptcha_response->is_valid = false;
168
+ $recaptcha_response->error = 'incorrect-captcha-sol';
169
+ return $recaptcha_response;
170
+ }
171
+
172
+ $response = _recaptcha_http_post (RECAPTCHA_VERIFY_SERVER, "/recaptcha/api/verify",
173
+ array (
174
+ 'privatekey' => $privkey,
175
+ 'remoteip' => $remoteip,
176
+ 'challenge' => $challenge,
177
+ 'response' => $response
178
+ ) + $extra_params
179
+ );
180
+
181
+ $answers = explode ("\n", $response [1]);
182
+ $recaptcha_response = new ReCaptchaResponse();
183
+
184
+ if (trim ($answers [0]) == 'true') {
185
+ $recaptcha_response->is_valid = true;
186
+ }
187
+ else {
188
+ $recaptcha_response->is_valid = false;
189
+ $recaptcha_response->error = $answers [1];
190
+ }
191
+ return $recaptcha_response;
192
+
193
+ }
194
+
195
+ /**
196
+ * gets a URL where the user can sign up for reCAPTCHA. If your application
197
+ * has a configuration page where you enter a key, you should provide a link
198
+ * using this function.
199
+ * @param string $domain The domain where the page is hosted
200
+ * @param string $appname The name of your application
201
+ */
202
+ function recaptcha_get_signup_url ($domain = null, $appname = null) {
203
+ return "https://www.google.com/recaptcha/admin/create?" . _recaptcha_qsencode (array ('domains' => $domain, 'app' => $appname));
204
+ }
205
+
206
+ function _recaptcha_aes_pad($val) {
207
+ $block_size = 16;
208
+ $numpad = $block_size - (strlen ($val) % $block_size);
209
+ return str_pad($val, strlen ($val) + $numpad, chr($numpad));
210
+ }
211
+
212
+ /* Mailhide related code */
213
+
214
+ function _recaptcha_aes_encrypt($val,$ky) {
215
+ if (! function_exists ("mcrypt_encrypt")) {
216
+ die ("To use reCAPTCHA Mailhide, you need to have the mcrypt php module installed.");
217
+ }
218
+ $mode=MCRYPT_MODE_CBC;
219
+ $enc=MCRYPT_RIJNDAEL_128;
220
+ $val=_recaptcha_aes_pad($val);
221
+ return mcrypt_encrypt($enc, $ky, $val, $mode, "\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0");
222
+ }
223
+
224
+
225
+ function _recaptcha_mailhide_urlbase64 ($x) {
226
+ return strtr(base64_encode ($x), '+/', '-_');
227
+ }
228
+
229
+ /* gets the reCAPTCHA Mailhide url for a given email, public key and private key */
230
+ function recaptcha_mailhide_url($pubkey, $privkey, $email) {
231
+ if ($pubkey == '' || $pubkey == null || $privkey == "" || $privkey == null) {
232
+ die ("To use reCAPTCHA Mailhide, you have to sign up for a public and private key, " .
233
+ "you can do so at <a href='http://www.google.com/recaptcha/mailhide/apikey'>http://www.google.com/recaptcha/mailhide/apikey</a>");
234
+ }
235
+
236
+
237
+ $ky = pack('H*', $privkey);
238
+ $cryptmail = _recaptcha_aes_encrypt ($email, $ky);
239
+
240
+ return "http://www.google.com/recaptcha/mailhide/d?k=" . $pubkey . "&c=" . _recaptcha_mailhide_urlbase64 ($cryptmail);
241
+ }
242
+
243
+ /**
244
+ * gets the parts of the email to expose to the user.
245
+ * eg, given johndoe@example,com return ["john", "example.com"].
246
+ * the email is then displayed as john...@example.com
247
+ */
248
+ function _recaptcha_mailhide_email_parts ($email) {
249
+ $arr = preg_split("/@/", $email );
250
+
251
+ if (strlen ($arr[0]) <= 4) {
252
+ $arr[0] = substr ($arr[0], 0, 1);
253
+ } else if (strlen ($arr[0]) <= 6) {
254
+ $arr[0] = substr ($arr[0], 0, 3);
255
+ } else {
256
+ $arr[0] = substr ($arr[0], 0, 4);
257
+ }
258
+ return $arr;
259
+ }
260
+
261
+ /**
262
+ * Gets html to display an email address given a public an private key.
263
+ * to get a key, go to:
264
+ *
265
+ * http://www.google.com/recaptcha/mailhide/apikey
266
+ */
267
+ function recaptcha_mailhide_html($pubkey, $privkey, $email) {
268
+ $emailparts = _recaptcha_mailhide_email_parts ($email);
269
+ $url = recaptcha_mailhide_url ($pubkey, $privkey, $email);
270
+
271
+ return htmlentities($emailparts[0]) . "<a href='" . htmlentities ($url) .
272
+ "' onclick=\"window.open('" . htmlentities ($url) . "', '', 'toolbar=0,scrollbars=0,location=0,statusbar=0,menubar=0,resizable=0,width=500,height=300'); return false;\" title=\"Reveal this e-mail address\">...</a>@" . htmlentities ($emailparts [1]);
273
+
274
+ }
275
+
276
+
277
+ ?>
package.xml ADDED
@@ -0,0 +1,20 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?xml version="1.0"?>
2
+ <package>
3
+ <name>productreviewcaptcha</name>
4
+ <version>1.0.0</version>
5
+ <stability>stable</stability>
6
+ <license uri="http://opensource.org/licenses/OSL-3.0">OSL v3.0</license>
7
+ <channel>community</channel>
8
+ <extends/>
9
+ <summary>This module add captcha to "Product Reviews" form.</summary>
10
+ <description>"Product Review Captcha" extension add in easy way the captcha to "Product Reviews" form and will protect this form from unwanted spambots.&#xD;
11
+ &#xD;
12
+ This extension uses reCaptcha library (http://www.google.com/recaptcha).&lt;/p&gt;</description>
13
+ <notes>This module add captcha to "Product Reviews" form.</notes>
14
+ <authors><author><name>Oleg Koval</name><user>auto-converted</user><email>oleh.koval@gmail.com</email></author></authors>
15
+ <date>2012-11-28</date>
16
+ <time>10:26:51</time>
17
+ <contents><target name="magecommunity"><dir name="OlegKoval"><dir name="ProductReviewCaptcha"><dir name="Block"><file name="Form.php" hash="70454bf86759df1b27c28c06db04ee20"/></dir><dir name="Model"><dir name="System"><dir name="Config"><dir name="Source"><dir name="Dropdown"><file name="Lang.php" hash="2378589b507b2c57c04831cf6ac544b0"/><file name="Theme.php" hash="be96ab4e09cd14b48a033c467ae74901"/></dir></dir></dir></dir></dir><dir name="controllers"><file name="ProductController.php" hash="bdfb3a9f5f7caa4fb7bf470c43fbbbb1"/></dir><dir name="etc"><file name="config.xml" hash="574af54ec3b8ce8e67b3264cfc97bf49"/><file name="system.xml" hash="df300a3aa36c9e80c7c13a46892e517d"/></dir></dir></dir></target><target name="mageetc"><dir name="modules"><file name="OlegKoval_ProductReviewCaptcha.xml" hash="f83ed30bb9b3b3fbecd4099cf23fa162"/></dir></target><target name="magelib"><dir name="reCaptcha"><file name="recaptchalib.php" hash="b206569ed973563107c29902ca7ab35b"/></dir></target><target name="magedesign"><dir name="frontend"><dir name="base"><dir name="default"><dir name="template"><dir name="productreviewcaptcha"><file name="form.phtml" hash="fa0f697bd7efe03446385e78de9f7ca9"/></dir></dir></dir></dir></dir></target><target name="magelocale"><dir name="en_US"><file name="OlegKoval_ProductReviewCaptcha.csv" hash="3e503ab7756be41684d848deaea746b4"/></dir></target></contents>
18
+ <compatible/>
19
+ <dependencies/>
20
+ </package>