2014-11-18

Sending email via mail function in base64

$messsage = base64_encode($message);
$send = mail($address, "=?utf-8?B?".base64_encode($subject)."?=", $message, "Content-type:text/plain; charset=UTF-8\r\nContent-Transfer-Encoding: base64");

How to set subject with "ru" locale in mail function (for utf-8)

$subject = "Тема сообщения";
$subject = "=?utf-8?B?".base64_encode($subject)."?=";

2014-11-09

Access control list (ACL) in zend framework 1

For implementing ACL you have to create class, in which will be created roles, resources and settings permissions. For this reason add to application/configs/application.ini:
autoloadernamespaces.app = "App_"
And create file library/App/Acl.php:
/**
 * Class App_Acl
 */
class App_Acl extends Zend_Acl
{
    function __construct()
    {
        $defaultResource = new Zend_Acl_Resource('default');
        $adminResource = new Zend_Acl_Resource('admin');

        $this->addResource($adminResource);
        $this->addResource($defaultResource);

        // guest/client resources
        $this->addResource(new Zend_Acl_Resource('index'), $defaultResource);
        $this->addResource(new Zend_Acl_Resource('payment'), $defaultResource);
        $this->addResource(new Zend_Acl_Resource('panel'), $defaultResource);
        $this->addResource(new Zend_Acl_Resource('user'), $defaultResource);

        // admin resources
        $this->addResource(new Zend_Acl_Resource('admin_user'), $adminResource);
        $this->addResource(new Zend_Acl_Resource('admin_exchange'), $adminResource);
        $this->addResource(new Zend_Acl_Resource('admin_rate'), $adminResource);
        $this->addResource(new Zend_Acl_Resource('admin_eps'), $adminResource);
        $this->addResource(new Zend_Acl_Resource('admin_page'), $adminResource);

        $this->addRole(new Zend_Acl_Role(App_Acl_Roles::GUEST));
        $this->addRole(new Zend_Acl_Role(App_Acl_Roles::CLIENT), App_Acl_Roles::GUEST);
        $this->addRole(new Zend_Acl_Role(App_Acl_Roles::ADMIN), App_Acl_Roles::CLIENT);

        $this->deny();

        $this->allow(App_Acl_Roles::GUEST, 'index');
        $this->allow(App_Acl_Roles::GUEST, 'payment');
        $this->allow(App_Acl_Roles::CLIENT, 'user');
        $this->allow(App_Acl_Roles::CLIENT, 'panel');

        // Allow all to administrator
        $this->allow(App_Acl_Roles::ADMIN);
    }

    /**
     * Check if user has permission to the requested resource
     *
     * @param null $resource
     * @param null $privilege
     *
     * @return bool Return true if user has permission
     */
    public static function checkPermissions($resource = null, $privilege = null)
    {
        $acl = new App_Acl();

        $auth = Zend_Auth::getInstance()->getIdentity();

        $role = App_Acl_Roles::GUEST;

        if (isset($auth->role) && $auth->role) {
            $role = $auth->role;
        }

        return $acl->isAllowed($role, $resource, $privilege);
    }
}
Note: your auth instance must contains 'role' property.
Then create file library/App/Acl/Roles.php:
/**
 * Class App_Acl_Roles
 */
class App_Acl_Roles
{
    const ADMIN = 'admin';
    const CLIENT = 'client';
    const GUEST = 'guest';
}
From this moment you can add to your controller:
public function preDispatch()
{
  parent::preDispatch();

  if (!App_Acl::checkPermissions($this->getRequest()->getModuleName())) {
      $this->redirect('/login');
  }
}
And if user doesn't have permissions to the controller - it will be redirected to the login page or whatever you want.

2014-11-08

Writing errors/exceptions to a log file in zend framework 1

Add to application.ini
resources.log.stream.writerName = "Stream"
resources.log.stream.writerParams.stream = APPLICATION_PATH "/data/logs/application.log"
resources.log.stream.writerParams.mode = "a"
resources.log.stream.filterName = "Priority"
resources.log.stream.filterParams.priority = 5
Add method to application/Bootstrap.php:
/**
* Error handler
*
* @param $errno
* @param $errstr
* @param $errfile
* @param $errline
*
* @throws ErrorException
*/
public function exceptionErrorHandler($errno, $errstr, $errfile, $errline)
{
  throw new ErrorException($errstr, $errno, 0, $errfile, $errline);
}
and to constructor in the same file:
set_error_handler([$this, 'exceptionErrorHandler']);
Then in application/controllers/ErrorController.php. Find method "errorAction" and replace:
$log->log($this->view->message, $priority, $errors->exception);
$log->log('Request Parameters', $priority, $errors->request->getParams());
with
$logMessage = $errors->exception->getMessage() . PHP_EOL .
    $errors->exception->getTraceAsString() . PHP_EOL .
    'Request Parameters:' . PHP_EOL .
    var_export($errors->request->getParams(), true) . PHP_EOL .
    str_repeat('-', 50) . PHP_EOL;
$log->log($logMessage, $priority, $errors->exception);
And in the same file change $priority = Zend_Log::CRIT; to $priority = Zend_Log::NOTICE;
Don't forget to create application/data/logs/application.log and set writing permissions to it. Exceptions will be written to this file.

2014-11-06

How to enable ssl/https in zend framework 1

Add this to application/Bootstrap.php:
protected function _initForceSSL() {
    if($_SERVER['SERVER_PORT'] != '443') {
        header('Location: https://' . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI']);
        exit();
    }
}

2014-11-04

Localization in zend framework 1

In zf1 you can localize text, date, numbers and many other.
First of all you have to create folders for each locale. E.g. for russian locale: application/languages/ru_RU/, where ru - locale, RU - country.
Then you can create files with translations. As example create FormLabel.csv in your ru_RU folder:
"Login:";"Логин:"
"Password:";"Пароль:"
"Password confirmation:";"Подтверждение пароля:"
"First name:";"Имя:"
"Last name:";"Фамилия:"
Also you need to add locale initialization to your bootstrap file (application/Bootstrap.php):
protected function _initTranslate()
{
  $locale = new Zend_Locale('ru_RU');
  $registry = Zend_Registry::getInstance();
  $registry->set('Zend_Locale', $locale);

  $translate = new Zend_Translate(Zend_Translate::AN_CSV, APPLICATION_PATH . '/languages', null,
      ['scan' => Zend_Translate::LOCALE_DIRECTORY]);

  $registry->set('Zend_Translate', $translate);
}
From this moment localization will be enabled and if you create form with label "Login:" it'll be displayed as "Логин:".
But if you want to handy translate text in your templates add this function
function __()
{
    return Zend_Registry::get('Zend_Translate')->translate(func_get_args());
}
after
require_once 'Zend/Application.php';
to public/index.php.
And then in your phtml you can translate text:
<?= __('Password:') ?>