<?php
require_once LIBRARY_PATH.'/Zend/Controller/Action.php';
/**
 * Goweb Sitemanager 5 Framework
 *
 * Action
 *
 * @version    5.0.25
 * @category   Goweb
 * @package    Goweb_Controller_Action
 * @author     I&D <dev@goweb.pt>, Pedro Pinto <ppinto@goweb.pt>
 * @copyright  2010 (c) Goweb (http://www.goweb.pt)
 *
 *
 */

Goweb::loadClass('Zend_Auth');
class Goweb_Controller_Action extends Zend_Controller_Action {
    /**
     * Flag de teste se o output do controller vai ser incluido dentro de uma pagina de sistema do CMS.
     * E efectuada uma pesquisa se existe no CMS uma pegina com um slug baseado no controller e action:
     *
     * /controller/action/ e transformado no slug: 'controller-action'
     *
     * Caso nao exista a pagina de sistema com este slug e criado dinamicamente.
     * Caso esta flag esteja a TRUE e porque ha um pedido directo ao modulo.
     *
     * @var  bool
     */
    protected $_directRequest = true;
    
    /**
     * Canal a ser usado no controller
     *
     * @var String
     */
    protected $_canal = 'base';

    /**
     * Flag de controlo de tipo de controller
     *
     * @var bool
     */
    protected $_isAdmin = false;
    
    /**
     * String com o nome do servidor
     *
     * @var String
     */
    protected $_serverName = null;

    /**
     * @var Goweb_Session
     */
    protected $_session = null;

    /**
     * Goweb_Request object wrapping the request environment
     * @var Goweb_Request
     */
    protected $_request = null;

    /**
     * Zend_Auth
     *
     * @var Zend_Auth
     */
    protected $_auth;
    
    /**
     * Contrurctor
     *
     * @param Goweb_Request $request
     * @param Zend_Controller_Response_Http $response
     * @param mixed $invokeArgs
     */
    public function __construct(Zend_Controller_Request_Abstract $request,
                                Zend_Controller_Response_Abstract $response,
                                array $invokeArgs = array()){
        if(!$request) $request = new Goweb_Request();
        if(!$response) $response = new Zend_Controller_Response_Http();
        if(!$invokeArgs) $invokeArgs = array();
        $this->_auth = Zend_Auth::getInstance();
        $response->setHeader('Content-Type', 'text/html; charset=' . CHARSET);
        parent::__construct($request, $response, $invokeArgs);
        $this->view->assign('baseUrl', str_replace('/admin', '', str_replace('/index.php', '', $this->_request->getBaseUrl())));
        $this->_helper->viewRenderer->setNoController(true);
        $this->_session = Goweb::registry('session');
        $this->view->session = $this->_session; 
        if($this->_getParam('lang') && $this->_getParam('lang') != $this->_session->lang && is_array($this->_session->langs) && in_array($this->_getParam('lang'), $this->_session->langs)){
            $this->_session->lang = $this->_getParam('lang'); // actualizar a variável de sessão
            if (!$this->_request->isPost())
                return $this->_redirect(str_replace($this->_request->getBaseUrl(), '', $this->_request->getRequestUri()), array('code' => 301));
        }
        if ($this->_getParam('lang') && !in_array($this->_getParam('lang'), $this->_session->langs)){
            $this->_setParam('lang', $this->_session->lang);
            $this->_request->setParam('lang', $this->_session->lang);
        }
        
        if (!is_null($this->_getparam('directRequest'))) $this->setDirectRequest($this->_getparam('directRequest'));
        if (is_null($this->view->baseUrl)) $this->view->baseUrl = str_replace('/admin', '',  str_replace('/index.php', '', $this->_request->getBaseUrl()));
        if ($this->isAdmin()){
            $this->_helper->acl->deny(null);
            $this->_helper->acl->allow('Super Utilizador');
        }else{
            $this->_helper->acl->allow(null);
        }
        $this->_helper->acl->allow(null, 'auth');
        $this->_updateAcl();
        if ($this->isAdmin()){
            $this->view->hasPainel = false;
            if ($this->_auth->hasIdentity()){
                $user = Zend_Auth::getInstance()->getIdentity();
                if(is_object($user)) {
                    $role = $this->_auth->getIdentity()->role;
                }elseif (is_array($user)){
                    $auth = $this->_auth->getIdentity();
                    $role = $auth['role'];
                }
                if ($this->_helper->acl->isAllowed($role, 'Painel') || $this->_helper->acl->isAllowed($role, 'painel')){
                    $this->view->hasPainel = true;
                }
                $this->_helper->acl->allow(null, 'filemanager');
                $this->_helper->acl->allow(null, 'dashboard');

            }
        }
        $this->_serverName = $this->_request->getScheme() .'://' . $this->_request->getHttpHost();
        $this->view->serverName = $this->_serverName;
        if ($this->_request->isAjax()) $this->setDirectRequest(false);
        if ($this->_request->getParam('isLightwindow')){
            $this->_canal = 'simples';
        }
        $this->view->isAjax = $this->_request->isAjax();
    }
    
    protected function _updateAcl(){
        if ($this->_request->getControllerName() == 'setup') return;
        if ($this->isAdmin()){
            $aclModel = Goweb::getModelInstance('Acl_Model_Backoffice', 'db');
        }else{
            $aclModel = Goweb::getModelInstance('Acl_Model_Frontoffice', 'db');
        }
        $cache = Zend_Registry::get('cache');
        if (!$tables = $cache->load('listTables')){
            $tables = $aclModel->getAdapter()->listTables();
            $cache->save($tables, 'listTables');
        }
        if (!in_array($aclModel->getTableName(), $tables)){
            return;
        }
        if (($username = $this->_auth->getIdentity()) && isset($username['utilizador']['perfil_id'])){
            $aclModel->where('perfil_id = ?', $username['utilizador']['perfil_id']);
            $aclModel->order('controller');
            $aclResult = $aclModel->fetchAll();
            $perfil = $username['role'];
            $this->_helper->acl->addRole($perfil);
            if ($aclResult){
                $controllers = array();
                foreach ($aclResult as $item){
                    if (!isset($controllers[strtolower($item->controller)])){
                        $controllers[strtolower($item->controller)] = array();
                        $this->_helper->acl->allow($perfil, $item->controller);
			$this->_helper->acl->allow($perfil, strtolower($item->controller));
                    }
                    $controllers[strtolower($item->controller)][] = $item->action;
                }
                foreach ($controllers as $controller => $actions){
                    if (!in_array($controller, array('index', 'auth')))
                        $this->_helper->acl->allow($perfil, $controller, $actions);
                }
            }
            if ($this->isAdmin() && $this->_session->logged) {
                $moduloModel = Goweb::getModelInstance('Sistema_Model_Modulo', 'db', false);
                $cache = Zend_Registry::get('cache');
                if (!$tables = $cache->load('listTables')){
                    $tables = $moduloModel->getAdapter()->listTables();
                    $cache->save($tables, 'listTables');
                }
                $modulos = array();
                $modulosMenu = array();
                if (in_array($moduloModel->getTableName(), $tables)){
                    $moduloModel->where('permissao = ?', '1');
                    $moduloModel->order('titulo');
                    $moduloRowset = $moduloModel->fetchAll();

                    if ($moduloRowset) {
                        foreach ($moduloRowset as $row) {
                            if ($this->_session->utilizador['perfil']['superuser'] > 0 || $this->_helper->acl->isAllowed($this->_session->utilizador['perfil']['nome'], strtolower($row->nome))) {
                                $modulos[$row->nome] = $row->titulo;
                                if ($row->menu == '1') {
                                    $modulosMenu[strtolower($row->nome)] = $row->titulo;
                                }
                            }
                        }
                    }
                }
                $this->_session->modulos = $modulos;
                $this->_session->modulos_menu = $modulosMenu;
            }
        }
        
    }
    
    /**
     * Identifica se o controller pertence � administra��o
     *
     * @return bool
     */
    public function isAdmin(){
        return $this->_isAdmin;
    }
    
    /**
     * Diferenciar se um pedido foi feito directamente ou por componente
     *
     * @param bool $flag
     */
    public function setDirectRequest($flag = true){
        $this->_directRequest = $flag;
    }

    /**
     * Valida um id do tipo inteiro
     *
     * @param   string  $id  Variavel contendo o Id
     * @return  bool         TRUE se for um Id valido
     */
    protected function _validateId($id) {
        if ($id > 0 && preg_match('/^[0-9]+$/', $id)) {
            return true;
        }
        return false;
    }
    
    /**
     * Obter o nome do servidor http[s]://www.goweb.pt
     *
     * @return string com o nome do servidor, ex: http[s]://www.goweb.pt
     */
    protected function _getServerName(){
        return $this->_serverName;
    }
    
    /**
     * Dispatch the requested action
     *
     * @param string $action Method name of action
     * @return void
     */
    public function dispatch($action)
    {
        if (!is_null($this->_getparam('directRequest'))){
            $this->setDirectRequest($this->_getparam('directRequest'));  
        }
        // Notify helpers of action preDispatch state
        $this->_helper->notifyPreDispatch();
        if ($this->getRequest()->getControllerName() == 'painel_goweb' && $this->getRequest()->getActionName() == 'update') {
            $front = Zend_Controller_Front::getInstance();
            $front->getDispatcher()->setParam('disableOutputBuffering', true);
        }
        $this->preDispatch();
        if ($this->getRequest()->isDispatched()) {
            if (null === $this->_classMethods) {
                $this->_classMethods = get_class_methods($this);
            }
            // preDispatch() didn't change the action, so we can continue
            if ($this->getInvokeArg('useCaseSensitiveActions') || in_array($action, $this->_classMethods)) {
                /**
                 * Retirar warning ............
                 */
                /*if ($this->getInvokeArg('useCaseSensitiveActions')) {
                    trigger_error('Using case sensitive actions without word separators is deprecated; please do not rely on this "feature"');
                }*/
                $this->$action();
            } else {
                $this->__call($action, array());
            }
            $this->postDispatch();
        }

        // whats actually important here is that this action controller is
        // shutting down, regardless of dispatching; notify the helpers of this
        // state
        $this->_helper->notifyPostDispatch();
    }    

    /**
     * Obter Caracteres especiais usados em windows
     *
     * @return array
     */
    protected function _get_html_translation_table_CP1252() {
        $trans = get_html_translation_table(HTML_ENTITIES);
        $trans[chr(130)] = '&sbquo;';    // Single Low-9 Quotation Mark
        $trans[chr(131)] = '&fnof;';    // Latin Small Letter F With Hook
        $trans[chr(132)] = '&bdquo;';    // Double Low-9 Quotation Mark
        $trans[chr(133)] = '&hellip;';    // Horizontal Ellipsis
        $trans[chr(134)] = '&dagger;';    // Dagger
        $trans[chr(135)] = '&Dagger;';    // Double Dagger
        $trans[chr(136)] = '&circ;';    // Modifier Letter Circumflex Accent
        $trans[chr(137)] = '&permil;';    // Per Mille Sign
        $trans[chr(138)] = '&Scaron;';    // Latin Capital Letter S With Caron
        $trans[chr(139)] = '&lsaquo;';    // Single Left-Pointing Angle Quotation Mark
        $trans[chr(140)] = '&OElig;    ';    // Latin Capital Ligature OE
        $trans[chr(145)] = '&lsquo;';    // Left Single Quotation Mark
        $trans[chr(146)] = '&rsquo;';    // Right Single Quotation Mark
        $trans[chr(147)] = '&ldquo;';    // Left Double Quotation Mark
        $trans[chr(148)] = '&rdquo;';    // Right Double Quotation Mark
        $trans[chr(149)] = '&bull;';    // Bullet
        $trans[chr(150)] = '&ndash;';    // En Dash
        $trans[chr(151)] = '&mdash;';    // Em Dash
        $trans[chr(152)] = '&tilde;';    // Small Tilde
        $trans[chr(153)] = '&trade;';    // Trade Mark Sign
        $trans[chr(154)] = '&scaron;';    // Latin Small Letter S With Caron
        $trans[chr(155)] = '&rsaquo;';    // Single Right-Pointing Angle Quotation Mark
        $trans[chr(156)] = '&oelig;';    // Latin Small Ligature OE
        $trans[chr(159)] = '&Yuml;';    // Latin Capital Letter Y With Diaeresis
        ksort($trans);
        return $trans;
    }

    /**
     * Limpar a string de caracteres estranhos, especialmente em ficheiros 
     *
     * @param String $sString
     * @return String
     */
    protected function _clearString($sString) {
        // utf8_decode por causa dos caracteres manhosos do windows...
        $string = strtr(utf8_decode($sString), $this->_get_html_translation_table_CP1252());
        $string =  preg_replace('/\&(.)[^;]*;/', '\\1', $string);
        $string = preg_replace('/[ ]/', '_', $string);
        return $string;
    }

    /**
     * Metodo para criar caminho completo para upload.
     *
     * @param string
     * @param string
     */    
    function _makeUploadPath($basePath, $uploadPath) {
        $basePath = DIRECTORY_SEPARATOR . trim($basePath, '/');
        $uploadPath = trim($uploadPath, '/');
        $path = '';
        foreach (explode('/', $uploadPath) as $dir) {
            $path .= DIRECTORY_SEPARATOR . $dir;
            if (!file_exists($basePath . $path)) {
                try {
                    //// Goweb::dump($basePath . $path);
                    mkdir($basePath . $path);
                    chmod($basePath . $path, 0777);
                } catch (Exception $e) {
                    throw new Goweb_Exception('N&atilde;o &eacute; poss&iacute;vel criar a directoria: "' . $basePath . $path . '".');
                }
            }
        }
    }

    /**
     * Carregar o model com os valores do formulario, fazer o upload, etc
     * se for para actualizar dados, fazer o find ao model antes de chamar esta função
     *
     * @param Goweb_Form $form
     * @param Goweb_Db_Model $model
     * @return Goweb_Db_Model
     */
    protected function _formModelValues($form = null, $model = null){
        if (is_null($form) || 
            is_null($model) || 
            ! $form instanceof Goweb_Form || 
            ! $model instanceof Goweb_Db_Model){
                throw new Goweb_Exception('este form ou este model nao sao válidos');   
        }
        foreach ($form->getElementsNames() as $element) {
            if (!$model->colExists($element)) continue;
            if ($form->{$element}->type != 'submit' &&  $form->{$element}->type != 'button' && !$model->getCol($element)->getParam('on_insert')) {
                if ($model->getCol($element)->getParam('readonly') && $model->isLoaded()) {
                    continue;
                }
                if ($form->{$element}->type == 'rte') {
                    $model->{$element} = $form->{$element}->value;
                } else if ($form->{$element}->type == 'file') {
                    if ($form->{$element}->isUploaded()) {
                        if ($model->getCol($element)->getParam('prefix')) {
                            $ext = pathinfo($form->{$element}->getFileName(), PATHINFO_EXTENSION);
                            $filename = $model->getCol($element)->getParam('prefix') . '_' . time() . '_' . rand(1000, 9999) . '.' . $ext;
                        } else {
                            $filename = time() . '_' . rand(1000, 9999) . '_' . $this->_clearString($form->{$element}->getFileName(null, false));
                        }
                        if (strpos($model->getCol($element)->getParam('target'), '/', 0) === 0) {
                            $uploadPath = WWW_PATH . DIRECTORY_SEPARATOR  . trim($model->getCol($element)->getParam('target'), '/') . DIRECTORY_SEPARATOR;
                            $baseUploadPath = $uploadPath;
                            if (!file_exists($uploadPath) || !is_dir($uploadPath)) {
                                $this->_makeUploadPath(WWW_PATH, $model->getCol($element)->getParam('target'));
                            }
                        } else {
                            $uploadPath = WWW_PATH . DIRECTORY_SEPARATOR  . 'uploads' . DIRECTORY_SEPARATOR . trim($model->getCol($element)->getParam('target'), '/') . DIRECTORY_SEPARATOR;
                            $baseUploadPath = WWW_PATH . DIRECTORY_SEPARATOR  . 'uploads' . DIRECTORY_SEPARATOR;
                            if (!file_exists($uploadPath) || !is_dir($uploadPath)) {
                                $this->_makeUploadPath($baseUploadPath, $model->getCol($element)->getParam('target'));
                            }
                        }

                        try {
                            if (!$form->{$element}->isReceived() && !$form->{$element}->receive()) {
                                throw new Goweb_Exception('Ocorreu um erro a gravar o ficheiro');
                            }
                            
                            if (!is_writable($uploadPath)){
                                throw new Goweb_Exception('N&atilde;o &eacute; escrever na directoria: "' . $uploadPath . '".');
                            }
                            rename($form->{$element}->getFileName(), $uploadPath . $filename);
                            chmod($uploadPath . $filename, 0777);

                            if ($model->getCol($element)->getType() == 'Image') {
                                Goweb::loadClass('Goweb_Image_Resize');

                                $imageResize = new Goweb_Image_Resize();


                                $sizes = $model->getCol($element)->getParam('sizes');
                                foreach ($sizes as $size){
                                    if (($model->getCol($element)->getParam($size . '_max_width')) &&
                                    ($model->getCol($element)->getParam($size . '_max_height'))) {
                                        
                                        $imageResize->resizeMaintainRatio($uploadPath . $filename, $uploadPath . $size . '_' . $filename,
                                        $model->getCol($element)->getParam($size . '_max_width'),
                                        $model->getCol($element)->getParam($size . '_max_height'), 100);

                                        chmod($uploadPath . $size . '_' . $filename, 0777);
                                        /*
                                         if ($model->getCol($element)->getParam($size . '_watermark')) {
                                         // Goweb::dump('a corrigir bugs...', 'break point 4');
                                         $this->_applyWatermark($uploadPath . $size . '_' . $filename, $model->getCol($element)->getParam($size . '_watermark'));
                                         }
                                         */
                                    }
                                }

                                if ($model->getCol($element)->getParam('original') == 0) {
                                    // Goweb::dump('a corrigir bugs...', 'break point 7');
                                    unlink($uploadPath . $filename);
                                }

                            }

                        } catch (Exception $e) {
                            throw new Goweb_Exception('Ocorreu um erro a gravar o ficheiro: ' . $e->getMessage() . ' (linha '. $e->getLine() . ')');
                        }


                        if ($model->{$element} != '' && (!$model->getLang() || in_array($element, $model->getSyncCols()))) {
                            if (file_exists($uploadPath . $model->{$element})) {
                                unlink($uploadPath . $model->{$element});
                            }
                            if ($model->getCol($element)->getType() == 'Image') {
                                $sizes = $model->getCol($element)->getParam('sizes');
                                foreach ($sizes as $size){
                                    if (file_exists($uploadPath . $size . '_' . $model->{$element})) {
                                        unlink($uploadPath . $size . '_' . $model->{$element});
                                    }
                                }
                            }
                        }
                        $model->{$element} = $filename;
                    } elseif ($this->_request->{$element . '_del'}) {
                        if (!$model->getLang() || in_array($element, $model->getSyncCols())){
                            if (strpos($model->getCol($element)->getParam('target'), '/', 0) === 0) {
                                $uploadPath = WWW_PATH . DIRECTORY_SEPARATOR . trim($model->getCol($element)->getParam('target'), '/') . DIRECTORY_SEPARATOR;
                            } else {
                                $uploadPath = WWW_PATH . DIRECTORY_SEPARATOR . 'uploads' . DIRECTORY_SEPARATOR . trim($model->getCol($element)->getParam('target'), '/') . DIRECTORY_SEPARATOR;
                            }
                            if ($model->getCol($element)->getType() == 'Image') {
                                $sizes = $model->getCol($element)->getParam('sizes');
                                foreach ($sizes as $size){
                                    if (file_exists($uploadPath . $size . '_' . $model->{$element})) {
                                        unlink($uploadPath . $size . '_' . $model->{$element});
                                    }
                                }
                            }
                            if ($model->{$element} && file_exists($uploadPath . $model->{$element})) {
                                unlink($uploadPath . $model->{$element});
                            }
                        }
                        $model->{$element} = null;
                    }
                } else {
                    if ($form->elementExists($element) && $model->colExists($element)) {
                        if ($element == 'privado' && $model->colExists('perfis')){
                            $tmparray=$this->_request->perfis;
                            $tmpperfis='';
                            if (is_array($tmparray)){
                                foreach ($tmparray as $node){
                                    $tmpperfis.=$node . '|';
                                }
                                if (substr($tmpperfis,-1)=='|')
                                $tmpperfis=substr($tmpperfis,0,-1);
                                $model->perfis=$tmpperfis;
                            }
                        }
                        if ($form->{$element}->type != 'password'){
                            $saveValue = $form->{$element}->value;
                            $model->{$element} = is_array($saveValue) ? serialize($saveValue) : $saveValue;
                        }
                        else if ($form->{$element}->type == 'password' && $form->{$element}->value != '') {
                            $model->{$element} = sha1($form->{$element}->value);
                        }
                    }
                }
            }
        }
        return $model;
    }
    
    /**
     * Formata uma string para se mostrada como label.
     *
     * Substitui palavras separadas por '-', '_', ou '.' por maiusculas e
     * remove todos caracteres que n&atilde;o sejam alfanemericos.
     * 
     * @param   string
     * @return  string
     */
    protected static function _formatNameForLabel($unformatted) {
        $unformatted = str_replace(array('-', '_', '.'), ' ', strtolower($unformatted));
        $unformatted = preg_replace('[^a-z0-9 ]', '', $unformatted);
        return ucwords($unformatted);
    }
    
    /**
     * Corrigir os labels
     *
     * @param array $cols
     * @param array $labels
     * @return array
     */
    protected function _fixLabels($cols, $labels){
        $newCols = array();
        foreach ($cols as $colName => $label) {
            if (array_key_exists($colName, $labels) && strlen($labels[$colName])) {
                $label = $labels[$colName];
            } else {
                $label = $this->_formatNameForLabel($colName);
            }
            $newCols[$colName]=$label;
        }
        return $newCols;
    }

    /**
     * Metodo para o tratamento das informacoes - helper para exportacao.
     *
     * @param array $fieldsType
     * @param mixed $result
     * @return array
     */
    public static function resultArray($fieldsType, $result) {
        $fields = array();
        for ($i=0; $i<count($fieldsType); $i++) {
            foreach ($fieldsType[$i] as $campo => $object) {
                $fields[] = $campo;
            }
        }
        // Quantidade de linhas devolvidas pelo select
        $linReg  = count($result);
        // quantidade de colunas da tabela
        $qtdColunas = count($fields);
        $i = 0;
        $linha = array();
        foreach ($result as $row) {
            $colunas = $row->getCols();
            for($excelCol = 0; $excelCol < $qtdColunas; $excelCol++) {
                $objCol = $fieldsType[$excelCol][$fields[$excelCol]];
                if ($row->{$fields[$excelCol]} instanceof Goweb_Db_Model_Row) {
                    $linha[$i][$fields[$excelCol]] = trim($row->{$fields[$excelCol]}->__toString());
                } else {
                    $linha[$i][$fields[$excelCol]] = trim($row->{$fields[$excelCol]});
                }
                if ($objCol->getType() == 'ForeignKey'){
                    $alias = $objCol->getParam('alias');
                    if ($row->colExists($alias)){
                        $linha[$i][$fields[$excelCol]] = trim($row->{$alias});
                    }
                }
            }
            $i++;
        }

        return $linha;
    }

    
    /**
     * Função Genérica de exportação. Deve ser passado na view a variavel model (do model a exportar) e a variavel result (com o resultado a exportar)
     *
     * @param Goweb_View $view
     */
    public static function export($view){

        $label     = array();
        $labels    = $view->labels ? $view->labels : $view->cols;
        $model     = null;
        $modelCols = array();
        $list      = null;

        $modelColsNames            = $view->cols;
        if ($modelColsNames != array_values($modelColsNames)){
            $modelColsNames = array_keys($modelColsNames); 
        }
        
        $modelForeignColsWithAlias = $view->model->getForeignColsWithAliases();
        
        foreach ($modelColsNames as $campo) {
            $type = null;
            if (array_key_exists($campo, $modelForeignColsWithAlias)) {
                $campo = $modelForeignColsWithAlias[$campo];
            }
            $type = $view->model->getCol($campo);
            $label[][$campo] = $type;
            if (array_key_exists($campo, $modelForeignColsWithAlias)) {
                $label[][$modelForeignColsWithAlias[$campo]] = $type;
            }
            if (!array_key_exists($campo, $labels) || !strlen($labels[$campo])) {
                $labels[$campo] = self::_formatNameForLabel($campo);
            }
        }
        $result = $view->result;
        if ($view->model instanceof Form_Model_Barebone){
            $elementModel = Goweb::getModelInstance('Form_Model_Element', 'db', false);
            foreach ($result as $row){
                if(preg_match_all('/element_(\d*)/i', join(',', $row->getCols()), $matches) ){
                    foreach ($matches[1] as $element){
                        if ($elementModel->find($element) && $elementModel->element == 'combo'){
                            Goweb::loadClass('Goweb_Form_Element_Combo');
                            $elementCombo = new Goweb_Form_Element_Combo(array(
                                        'name' => 'element_' . $element,
                                        'db_type' => $elementModel->db_type,
                                        'db_host' => $elementModel->db_host,
                                        'db_user' => $elementModel->db_user,
                                        'db_pass' => $elementModel->db_pass,
                                        'db_name' => $elementModel->db_name,
                                        'db_table' => $elementModel->db_table,
                                        'db_table_value' => $elementModel->db_table_value,
                                        'db_table_desc' => $elementModel->db_table_desc,
                                        'clausulas_extras' => $elementModel->clausulas_extras));
                            $row->{'element_' . $element} = $elementCombo->getDescFromValue($row->{'element_' . $element});
                        }
                    }
                }
                
            }
            
        }
        
        
        if ($result) {
            $request = Goweb::registry('request');
            $export = $request->getParam('export');
            $resultArray = Goweb_Controller_Action::resultArray($label, $result);
            if ($export == 1) {
                $export = 'csv';
            }
            if (in_array(strtolower($export), array('xls', 'csv', 'xlsx'))){
                Goweb::loadClass('Goweb_Excel_Maker_Xls');
                $excel = new Goweb_Excel_Maker_Xls();
            } else if (in_array(strtolower($export), array('ods'))){
                Goweb::loadClass('Goweb_Excel_Maker_Ods');
                $excel = new Goweb_Excel_Maker_Ods();
            } else {
                throw new Goweb_Exception('Formato '.$export.' não implementado');
            }
            $excel->sqlToExcel($resultArray, $view->model->getTableName(), $labels);
        }
    }
    
    /**
     * Corrigir valor Float
     *
     * @param string $valor
     * @return string
     */
    protected function _fixValor($valor){
        return $this->view->fixValor($valor);
    }

    /**
     * Obter todos os pais para o id seleccionado
     *
     * @param String|Goweb_Db_Model $model
     * @param int $pid
     * @param String $parent
     * @return array
     */
    protected function _getBreadcrumb($model, $pid = 0, $parent = null){
        $parents = array();
        if (is_null($pid)) return $parents;
        if ($pid === 0) return $parents;
        if (is_null($parent)) $parent = 'pai_id';
        $categoriaModel = is_string($model) ? Goweb::getModelInstance($model, 'db', false) : $model;
	    if (!$categoriaModel instanceof Goweb_Db_Model){
            throw new Goweb_Exception('Vari&aacute;vel '.get_class($categoriaModel) .' n&atilde;o &eacute; do tipo Goweb_Db_Model.');   
	    }
        
        $key = $categoriaModel->getPrimary();
        $label = $categoriaModel->getToString();
        if ($categoriaModel->find($pid)){
            $parents[$categoriaModel->{$key}] = $categoriaModel->{$label};
            while ($categoriaModel->{$parent} > 0 && $categoriaModel->find($categoriaModel->{$parent})){
                $parents[$categoriaModel->{$key}] = $categoriaModel->{$label};
            }
        }
        $parents = array_reverse($parents, true);
        return $parents;
    }

    /**
     * Obter todos os pais para o id seleccionado
     *
     * @param String|Goweb_Db_Model $model
     * @param int $pid
     * @param String $parent
     * @return array
     */
    protected function _getBreadcrump($model, $pid = 0, $parent = null){
        trigger_error('_getBreadcrump is incorrect. please use _getBreadcrumb. This is deprecated"', E_USER_WARNING);
        return $this->_getBreadcrumb($model, $pid, $parent);
    }
    
    /**
     * Funcao rescursiva para obter todas as subcategorias de uma categoria
     *
     * @param string|Goweb_Db_Model $model
     * @param array &$subcats
     * @param int $catId
     * @param string $cat
     */
	protected function _getSubCategorias($model, &$subcats, $catId, $cat = null){
	    $model = is_string($model) ? Goweb::getModelInstance($model, 'db', false) : $model;
	    if (!$model instanceof Goweb_Db_Model){
            throw new Goweb_Exception('Vari&aacute;vel '.get_class($model) .' n&atilde;o &eacute; do tipo Goweb_Db_Model.');   
	    }
	    if (is_null($cat) || !$model->colExists($cat)) $cat = 'pai_id';
		$model->where($cat .'=?', $catId);
        $key = $model->getPrimary();
        $label = $model->getToString();
		$result = $model->fetchAll(array($key, $label));
		if($result){
			foreach($result as $sub){
				$subcats[$sub->{$key}] = $sub->{$label};
				$this->_getSubCategorias($model, $subcats, $sub->{$key});
			}
		}
	}
	
    /**
     * Redirect to another URL
     *
     * Proxies to {@link Zend_Controller_Action::_redirect()}.
     *
     * @param string $url
     * @param array $options Options to be used when redirecting
     * @return void
     */
	protected function _redirect($url, array $options = array()){
	    /**
	     * force disable page cache on redirects
	     */
	    if (Zend_Registry::isRegistered('page_cache')){
            $pageCache = Zend_Registry::get('page_cache');
            $pageCache->cancel();
	    }
        parent::_redirect($url, $options);
    }

    /**
     * Verifica se o utilizador esta logado.
     *
     * @return bool
     */
    protected function _verifyIsLogged() {
        if (is_null($this->_session)) $this->_session = Goweb::registry('session');
        if ($this->_session->logged && substr($this->_session->getNamespace(), -6) == '_FRONT'){
            return true;
        }
        //return $this->_redirect('/');
        $this->view->setViewsPath(VIEWS_PATH);
        $this->getResponse()->setRawHeader('HTTP/1.1 403 Forbidden');
        $this->_helper->viewRenderer->setRender('403');
        return false;
    }
}
