Joomla, Sp Page Builder and ReCaptcha

时间:2017-04-06 16:53:38

标签: joomla captcha contact-form recaptcha

It's the First time that I use SP Page Builder component with Joomla. I want to use their contact form, but it doesn't support Google ReCaptcha. I'm good enough with coding to thought that I could manually add it into : /com_sppagebuilder/addons/ajax_contact/site.php and get it to work. I did add : <div class="g-recaptcha" data-sitekey="My_Key"></div>; And the Joomla ReCaptcha plugin is activated. I didn't know if I had to, but I added <script src='https://www.google.com/recaptcha/api.js'></script> into the head tag. With this the ReCaptcha is showing fine.

My problem is with the validation. I did try to add some validation code in the site.php but I believe SP Page Builder uses JFactory::getMailer(); to get the email ready and send it, and I don't know anything about that.

Thus, I do not know where I can add my ReCaptcha validation code, and as I did find few versions of that code online, I really don't know which one to use. I've been searching everywhere for some answers to how to do this verification... and I tried many things, but it's still not working.

Can anyone help me through this one ?

Thank you very much !

EDIT

I think my question is not clear enough :

I want to add Recaptcha, that is already working fine in other forms on my website (so it's not a configuration with Joomla problem). I want to use the following SP Page Builder contact form and not a RSFormPro as on the rest of the Website. The validation process should be done around this section, but I tried to add the Google validation code, and I tried a few versions of it I found around the Internet, and it's not working at all :

public static function getAjax() {
    $input = JFactory::getApplication()->input;
    $mail = JFactory::getMailer();

    //inputs
    $inputs             = $input->get('data', array(), 'ARRAY');

    foreach ($inputs as $input) {

        if( $input['name'] == 'recipient' ) {
            $recipient          = base64_decode($input['value']);
        }

        if( $input['name'] == 'email' ) {
            $email          = $input['value'];
        }

        if( $input['name'] == 'name' ) {
            $name           = $input['value'];
        }

        if( $input['name'] == 'subject' ) {
            $subject            = $input['value'];
        }

        if( $input['name'] == 'message' ) {
            $message            = nl2br( $input['value'] );
        }
    }

    /*Try at the validation*/
    $captcha_plugin = JFactory::getConfig()->get('captcha');
    if ($captcha_plugin != '0') {
    $captcha = JCaptcha::getInstance($captcha_plugin);
    $field_id = 'google-recaptcha';
     print $captcha->display($field_id, $field_id, 'g-recaptcha');
    }


    $sender = array($email, $name);
    $mail->setSender($sender);
    $mail->addRecipient($recipient);
    $mail->setSubject($subject);
    $mail->isHTML(true);
    $mail->Encoding = 'base64';
    $mail->setBody($message);

    if ($mail->Send()) {
        return '<span class="sppb-text-success">'. JText::_('COM_SPPAGEBUILDER_ADDON_AJAX_CONTACT_SUCCESS') .'</span>';
    } else {
        return '<span class="sppb-text-danger">'. JText::_('COM_SPPAGEBUILDER_ADDON_AJAX_CONTACT_FAILED') .'</span>';
    }
}

Any suggestions ?

Thank you !

3 个答案:

答案 0 :(得分:0)

我已成功将验证码添加到Ajax联系表单中。虽然代码仍然需要一些改进,但这就是我所做的:

看到我正在使用n3tseznamcaptcha captcha插件,我仍然需要实现其他验证码的更改才能工作(recaptcha等),但你可以根据自己的需要进行调整。

SP Pagebuilder插件包含两个文件:admin和site。在管理站点中,我删除了默认的验证码,缺少许多安全措施。然后在网站部分我添加了以下内容:

function ajax_contact_addon($atts)
{
    global $formcaptcha;
    (...)
    if($formcaptcha) 
    {
            // TODO: Add Joomla's captcha:
            JPluginHelper::importPlugin('captcha');
            $dispatcher = JDispatcher::getInstance();

            // This will put the code to load CAPTCHA's JavaScript file into your <head>
            $dispatcher->trigger('onInit', 'dynamic_captcha_1');

            // This will return the array of HTML code.
            $captcha = $dispatcher->trigger('onDisplay', array(null, 'dynamic_captcha_1', 'class=""'));
            // I have only 1 recaptcha plugin enabled so the HTML is at 0 index, this will be improved in next version, following the contact component
            $output .= (isset($captcha[0])) ? $captcha[0] : '';
            $output .= '<div class="clearfix"></div><p></p>';
    }
    (...)
}

function ajax_contact_get_ajax() 
{
    global $formcaptcha;

    $jinput         = JFactory::getApplication()->input;
    $mail           = JFactory::getMailer();
    $config         = JFactory::getConfig();

    // TODO: CHECK CAPTCHA and add a Helper Class to get the captchas fields
    $captchaset = 'n3tseznamcaptcha';
    if ($captchaset === 'n3tseznamcaptcha')
    {   
        $captcha_field_hash = 'n3t_seznam_captcha_hash';
        $captcha_field_answer = 'n3t_seznam_captcha';
    }

    //inputs
    $inputs             = $jinput->get('data', array(), 'ARRAY');
    foreach ($inputs as $input) 
    {
            if( $input['name'] == 'title' ) 
            {
                $title                  = $input['value'];
            }
            if( $input['name'] == 'recipient' ) 
            {
                    $recipient      = base64_decode($input['value']);
            }

            if( $input['name'] == 'email' ) 
            {
                    $email          = $input['value'];
            }

            (...)

            if( $input['name'] == $captcha_field_hash ) 
            {
                    $captcha_hash   = $input['value'];
            }

            if( $input['name'] == $captcha_field_answer ) 
            {
                    $captcha_answer     = $input['value'];
            }
    }

    if($formcaptcha)
    {
            // get the plugin
            JPluginHelper::importPlugin('captcha');
            $dispatcher = JEventDispatcher::getInstance();

            // In order the plugin can check the code, we have to insert it into the request data:
            $jinput->set('n3t_seznam_captcha_hash', $captcha_hash);
            $jinput->set('n3t_seznam_captcha', $captcha_answer);

            // Here we check for the code:
            $res = $dispatcher->trigger('onCheckAnswer', $captcha_answer);

            if(!$res[0])
            {
                    // There is a problem with pagebuilder cache and captchas, so we need to clean the cache, to renew the captcha code:
                    $cache = JFactory::getCache('page');
                    $cache->clean();
                    return '<span class="pb-text-danger">'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_FORM_WRONG_CAPTCHA') .'</span>';
            }
}

}

我认为就是这样。希望它可以帮助你找到答案。

答案 1 :(得分:0)

所以在这里你有完整的解决方案。请注意,我也改变了管理员方面的一些事情。此版本将显示并验证在Joomla配置中选择的默认验证码,但它仅适用于recaptcha和n3tsezam ..其他应手动添加。原因是这个插件没有在请求中添加挑战和响应字段,验证码用于验证,因此我们需要检索它并写入我们的ajax函数(ajax_contact_get_ajax)中的jinput,以及整个复杂化的原因事实是每个验证码插件都使用不同的字段。无论如何..如果你需要任何其他验证码插件只是可以将它添加到交换机,你应该完成。

function ajax_contact_addon($ atts)     {

        extract(AddonAtts(array(
                "title"             => '',
                "show_title"                    => '',
                "heading_selector"      => 'h3',
                "title_fontsize"        => '',
                "title_fontweight"      => '',
                "title_text_color"      => '',
                "title_margin_top"      => '',
                "title_margin_bottom"           => '',  
                "recipient_email"       => '',
                "formcaptcha"           => '',
                "class"             => '',
                ), $atts));

        JHtml::script('media/com_pagebuilder/js/ajax-contact.js');        

//      There is a problem with pagebuilder cache and captchas
        $cache = JFactory::getCache('page');
        $cache->clean();

        $output  = '<div class="pb-addon pb-addon-ajax-contact ' . $class . '">';

        if(boolval($show_title) && $title) 
        {

                $title_style = '';
                if($title_margin_top !='') $title_style .= 'margin-top:' . (int) $title_margin_top . 'px;';
                if($title_margin_bottom !='') $title_style .= 'margin-bottom:' . (int) $title_margin_bottom . 'px;';
                if($title_text_color) $title_style .= 'color:' . $title_text_color  . ';';
                if($title_fontsize) $title_style .= 'font-size:'.$title_fontsize.'px;line-height:'.$title_fontsize.'px;';
                if($title_fontweight) $title_style .= 'font-weight:'.$title_fontweight.';';

                $output .= '<'.$heading_selector.' class="pb-addon-title" style="' . $title_style . '">' . $title . '</'.$heading_selector.'>';
        }

        $output .= '<div class="pb-addon-content">';
        $output .= '<form class="pb-ajax-contact-form">';

        $output .= '<div class="pb-form-group">';
        $output .= '<input type="text" name="name" class="pb-form-control" placeholder="'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_NAME') .'" required="required">';
        $output .= '</div>';

        $output .= '<div class="pb-form-group">';
        $output .= '<input type="email" name="email" class="pb-form-control" placeholder="'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_EMAIL') .'" required="required">';
        $output .= '</div>';

        $output .= '<div class="pb-form-group">';
        $output .= '<input type="text" name="subject" class="pb-form-control" placeholder="'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_SUBJECT') .'" required="required">';
        $output .= '</div>';

        $output .= '<div class="pb-form-group">';
        $output .= '<textarea type="text" name="message" rows="5" class="pb-form-control" placeholder="'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_MESSAGE') .'" required="required"></textarea>';
        $output .= '</div>';

        if($formcaptcha) 
        {
                JPluginHelper::importPlugin('captcha');
                $dispatcher = JDispatcher::getInstance();
                $dispatcher->trigger('onInit', 'dynamic_captcha_1');

                $captchas = $dispatcher->trigger('onDisplay', array(null, 'dynamic_captcha_1', 'class=""'));
                $index = 0;

                foreach (JPluginHelper::getPlugin('captcha') as $plugin)
                {
                        if (JFactory::getApplication()->get('captcha', '0') === $plugin->name)
                        {
                                $captcha = $captchas[$index];
                                break;
                        }
                        $index++;
                }
                $output .= (isset($captcha)) ? $captcha : '';
                $output .= '<div class="clearfix"></div><p></p>';
        }

        $output .= '<input type="hidden" name="recipient" value="'. base64_encode($recipient_email) .'">';
        $output .= '<input type="hidden" name="title" value="'. $title .'">';

        $output .= '<button type="submit" class="btn btn-default"><i class="fa"></i> '. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_SEND') .'</button>';

        $output .= '</form>';

        $output .= '<div style="display:none;margin-top:10px;" class="pb-ajax-contact-status"></div>';

        $output .= '</div>';

        $output .= '</div>';

        return $output;

}

function ajax_contact_get_ajax() 
{
        $config                         = JFactory::getConfig();
        $jinput             = JFactory::getApplication()->input;
        //inputs
        $inputs             = $jinput->get('data', array(), 'ARRAY');

        $mail               = JFactory::getMailer();

        // TODO: Find the way to check if captcha is enabled in the addon
        $formcaptcha = true;
        $message = "";

        // TODO: CHECK CAPTCHA and add a Helper Class to get the captchas
        switch (JFactory::getApplication()->get('captcha', '0'))
        {
            case 'recaptcha':
                // v.1:
                //$captcha_challenge_field = 'recaptcha_challenge_field';
                //$captcha_answer_field = 'recaptcha_response_field';
                // v.2:
                $captcha_challenge_field = '';
                $captcha_answer_field = 'g-recaptcha-response';
                break;
            case 'n3tseznamcaptcha':
                $captcha_challenge_field = 'n3t_seznam_captcha_hash';
                $captcha_answer_field = 'n3t_seznam_captcha';
                break;
            default:
                // disable captcha as we could not find the right fields
                $formcaptcha = false;
        }

        foreach ($inputs as $input) 
        {

                if( $input['name'] == 'title' ) 
                {
                        $title                  = $input['value'];
                }
                if( $input['name'] == 'recipient' ) 
                {
                        $recipient      = base64_decode($input['value']);
                }

                if( $input['name'] == 'email' ) 
                {
                        $email          = $input['value'];
                }

                if( $input['name'] == 'name' ) 
                {
                        $name           = $input['value'];
                }

                if( $input['name'] == 'subject' ) 
                {
                        $subject            = $input['value'];
                }

                if( $input['name'] == 'message' ) 
                {
                        $message            = nl2br( $input['value'] );
                }

                if( $input['name'] == $captcha_challenge_field ) 
                {
                        $captcha_challenge  = $input['value'];
                }

                if( $input['name'] == $captcha_answer_field ) 
                {
                        $captcha_answer     = $input['value'];
                }

        }

        $valid_captcha = true;
        if($formcaptcha)
        {
                // get the plugin
                JPluginHelper::importPlugin('captcha');
                $dispatcher = JEventDispatcher::getInstance();

                $jinput->set($captcha_challenge_field,  $captcha_challenge);
                $jinput->set($captcha_answer_field,     $captcha_answer);

                $res = $dispatcher->trigger('onCheckAnswer', $captcha_answer);

                $index = 0;
                foreach (JPluginHelper::getPlugin('captcha') as $plugin)
                {
                        if (JFactory::getApplication()->get('captcha', '0') === $plugin->name)
                        {
                                $valid_captcha = $res[$index];
                                break;
                        }
                        $index++;
                }
                if(!$valid_captcha)
                {
                    $msg = '<span class="pb-text-danger">'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_FORM_WRONG_CAPTCHA') .'</span>';                        
                }
        }

        if ($valid_captcha)
        {
                // We do not want to send the email as a fake user, it may cause spam problems
                $sender = array( 
                        $config->get( 'mailfrom' ),
                        $config->get( 'fromname' ) 
                );

                $subject = (($title)? '['.$title.'] ' : '') . $subject;
                $message .= JText::sprintf('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_EMAIL_SIGNATURE', JUri::getInstance()->toString(),  JUri::getInstance());

                $mail->setSender($sender);
                $mail->addRecipient($recipient);
                $mail->setSubject($subject);
                $mail->AddReplyTo($email);
                $mail->isHTML(true);
                $mail->Encoding = 'base64'; 
                $mail->setBody($message);

                if ($mail->Send()) 
                {
                        $msg = '<span class="pb-text-success">'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_SUCCESS') .'</span>';
                } else {
                        $msg = '<span class="pb-text-danger">'. JText::_('COM_PAGEBUILDER_ADDON_AJAX_CONTACT_FAILED') .'</span>';
                }
        }

//      There is a problem with pagebuilder cache and captchas
        $cache = JFactory::getCache('page');
        $cache->clean();

        return $msg;

}

答案 2 :(得分:0)

该功能现已集成到SP Page Builder联系人表格插件中。

1)从控制台中获取reCaptcha API密钥:https://www.google.com/recaptcha/admin get recaptcha keys

2)在Joomla的后端中启用reCaptcha插件: Joomla控制面板并导航到扩展>插件>验证码-reCaptcha enable recaptcha plugin

3)在您的Joomla配置中启用reCaptcha: 转到系统>全局配置>站点设置>默认验证码 set joomla configutarion for recaptcha

4)转到您的联系表单(或创建一个新表单)并启用验证码。然后在验证码类型选择器中选择“ CAPTCHA-reCAPTCHA”。 set recaptcha on form

完成上述步骤后,如果您在联系表单前端看不到reCAPTCHA框,则表明您的模板使用了旧的联系人插件代码。在大多数情况下,您可以安全地进行备份,然后删除以下文件夹(粗体):templates \ YOUR-TEMPLATE-NAME \ sppagebuilder \ addons \ ajax_contact

您需要的所有信息都可以在本文中找到:https://www.joomshaper.com/blog/google-recaptcha-joomla-contact-forms-integration