Index: /trunk/expressoMail1_2/inc/class.imap_functions.inc.php =================================================================== --- /trunk/expressoMail1_2/inc/class.imap_functions.inc.php (revision 990) +++ /trunk/expressoMail1_2/inc/class.imap_functions.inc.php (revision 1000) @@ -209,7 +209,21 @@ * com .emls gerados pelo expresso, e o arquivo pode ser um zip contendo vários emls ou um .eml. */ +/** + * Função que importa arquivos .eml exportados pelo expresso para a caixa do usuário. Testado apenas + * com .emls gerados pelo expresso, e o arquivo pode ser um zip contendo vários emls ou um .eml. + */ function import_msgs($params) { - if(!$this->mbox) + if(!$this->mbox) $this->mbox = $this->open_mbox(); + + if( preg_match('/local_/',$params["folder"]) ) + { + + $tmp_box = mb_convert_encoding('INBOX/Lixeira/tmpMoveToLocal', "UTF7-IMAP", "UTF-8"); + if ( ! imap_createmailbox( $this -> mbox,"{".$this -> imap_server."}$tmp_box" ) ) + return $this->functions->getLang( 'Import to Local : fail...' ); + imap_reopen($this->mbox, "{".$this->imap_server.":".$this->imap_port.$this->imap_options."}".$tmp_box); + $params["folder"] = $tmp_box; + } $errors = array(); $invalid_format = false; @@ -218,5 +232,5 @@ if((($quota['limit'] - $quota['usage'])*1024) <= $params['FILES'][0]['size']){ return array( 'error' => $this->functions->getLang("fail in import:"). - " ".$this->functions->getLang("Over quota")); + " ".$this->functions->getLang("Over quota")); } if(substr($filename,strlen($filename)-4)==".zip") { @@ -225,5 +239,5 @@ if ($zip) { while ($zip_entry = zip_read($zip)) { - + if (zip_entry_open($zip, $zip_entry, "r")) { $email = zip_entry_read($zip_entry, zip_entry_filesize($zip_entry)); @@ -239,4 +253,18 @@ zip_close($zip); } + + if ( isset( $tmp_box ) && ! sizeof( $errors ) ) + { + + $mc = imap_check($this->mbox); + + $result = imap_fetch_overview( $this -> mbox, "1:{$mc -> Nmsgs}", 0 ); + + $ids = array( ); + foreach ($result as $overview) + $ids[ ] = $overview -> uid; + + return implode( ',', $ids ); + } } else if(substr($filename,strlen($filename)-4)==".eml") { @@ -251,10 +279,13 @@ } } - else - { + else + { + if ( isset( $tmp_box ) ) + imap_deletemailbox( $this->mbox,"{".$this -> imap_server."}$tmp_box" ); + return array("error" => $this->functions->getLang("wrong file format")); $invalid_format = true; } - + if(!$invalid_format) { if(count($errors)>0) { @@ -266,8 +297,8 @@ } else - return $this->functions->getLang("The import was executed successfully."); - } - } - /* + return $this->functions->getLang("The import was executed successfully."); + } + } + /* Remove os anexos de uma mensagem. A estratégia para isso é criar uma mensagem nova sem os anexos, mantendo apenas a primeira parte do e-mail, que é o texto, sem anexos. @@ -2851,4 +2882,92 @@ return $header; } + +//Por Bruno Costa(bruno.vieira-costa@serpro.gov.br - Insere emails no imap a partir do fonte do mesmo. Se o argumento timestamp for passado ele utiliza do script python +///expressoMail1_2/imap.py para inserir uma msg com o horário correto pois isso não é porssível com a função imap_append do php. + + function insert_email($source,$folder,$timestamp){ + $username = $_SESSION['phpgw_info']['expressomail']['user']['userid']; + $password = $_SESSION['phpgw_info']['expressomail']['user']['passwd']; + $imap_server = $_SESSION['phpgw_info']['expressomail']['email_server']['imapServer']; + $imap_port = $_SESSION['phpgw_info']['expressomail']['email_server']['imapPort']; + $imap_options = '/notls/novalidate-cert'; + $mbox_stream = imap_open("{".$imap_server.":".$imap_port.$imap_options."}".$folder, $username, $password); + if(imap_last_error()) + { + imap_createmailbox($mbox_stream,imap_utf7_encode("{".$imap_server."}".$folder)); + } + if($timestamp){ + $tempDir = ini_get("session.save_path"); + $file = $tempDir."imap_".md5(microtime()); + $f = fopen($file,"w"); + fputs($f,base64_encode($source)); + fclose($f); + $command = "python ".$_SERVER['DOCUMENT_ROOT']."expressoMail1_2/imap.py ".$imap_server." ".$imap_port." ".$username." ".$password." ".$timestamp." ".$folder." ".$file; + $return['command']=exec($command); + }else{ + $return['append'] = imap_append($mbox_stream, "{".$imap_server.":".$imap_port."}".$folder, $source, "\\Seen"); + } + $status = imap_status($mbox_stream, "{".$this->imap_server.":".$this->imap_port."}".$folder, SA_UIDNEXT); + $return['msg_no'] = $status->uidnext - 1; + $return['error'] = imap_last_error(); + if($mbox_stream) + imap_close($mbox_stream); + return $return; + + } + +//Por Bruno Costa(bruno.vieira-costa@serpro.gov.br - Trata fontes de emails enviados via POST para o servidor por um xmlhttprequest, as partes codificados com +//Base64 os "+" são substituidos por " " no envio e essa função arruma esse efeito. + + function treat_base64_from_post($source){ + $offset = 0; + do + { + if($inicio = strpos($source, 'Content-Transfer-Encoding: base64', $offset)) + { + $inicio = strpos($source, "\n\r", $inicio); + $fim = strpos($source, '--', $inicio); + if(!$fim) + $fim = strpos($source,"\n\r", $inicio); + $length = $fim-$inicio; + $parte = substr( $source,$inicio,$length-1); + $parte = str_replace(" ", "+", $parte); + $source = substr_replace($source, $parte, $inicio, $length-1); + } + if($offset > $inicio) + $offset=FALSE; + else + $offset = $inicio; + } + while($offset); + return $source; + } + +//Por Bruno Costa(bruno.vieira-costa@serpro.gov.br - Recebe os fontes dos emails a serem desarquivados, separa e envia cada um para função insert_mail. + + function unarchive_mail($params) + { + $dest_folder = $params['folder']; + $sources = explode("#@#@#@",$params['source']); + $timestamps = explode("#@#@#@",$params['timestamp']); + foreach($sources as $index=>$src) { + if($src!=""){ + $source = $this->treat_base64_from_post($src); + $insert = $this->insert_email($source,$dest_folder,$timestamps[$index]); + } + } + return $insert; + } + + function download_all_local_attachments($params) + { + $source = $params['source']; + $source = $this->treat_base64_from_post($source); + $insert = $this->insert_email($source,'INBOX'.$this->imap_delimiter.'decifradas'); + $exporteml = new ExportEml(); + $params['num_msg']=$insert['msg_no']; + $params['folder']='INBOX'.$this->imap_delimiter.'decifradas'; + return $exporteml->download_all_attachments($params); + } } ?> Index: /trunk/expressoMail1_2/inc/class.exporteml.inc.php =================================================================== --- /trunk/expressoMail1_2/inc/class.exporteml.inc.php (revision 711) +++ /trunk/expressoMail1_2/inc/class.exporteml.inc.php (revision 1000) @@ -44,5 +44,9 @@ // create EML File. - function createFileEml($sEMLData, $tempDir, $id) + // Funcao alterada para tratar a exportacao + // de mensagens arquivadas localmente. + // Rommel Cysne (rommel.cysne@serpro.gov.br) + // em 17/12/2008. + function createFileEml($sEMLData, $tempDir, $id, $subject=false, $i) { if($id) @@ -54,9 +58,23 @@ $subject = substr($subject, 0, 59); - $subject = ereg_replace('/', '\'', $subject); + //$subject = ereg_replace('/', '\'', $subject); + $from = "áàâãäéèêëíìîïóòôõöúùûüç?\"!@#$%š&*()-=+Ž`[]{}~^,<>;:/?\\|¹²³£¢¬§ªº°ÁÀÂÃÄÉÈÊËÍÌÎÏÓÒÔÕÖÚÙÛÜÇ"; + $to = "aaaaaeeeeiiiiooooouuuuc__________________________________________AAAAAEEEEIIIIOOOOOUUUUC"; + $subject = strtr($subject,$from,$to); $file = $subject."_".$id.".eml"; + } else{ + // Se mensagem for arquivada localmente, $subject (assunto da mensagem) + // sera passado para compor o nome do arquivo .eml; + + if($subject){ + $from = "áàâãäéèêëíìîïóòôõöúùûüç?\"!@#$%š&*()-=+Ž`[]{}~^,<>;:/?\\|¹²³£¢¬§ªº°ÁÀÂÃÄÉÈÊËÍÌÎÏÓÒÔÕÖÚÙÛÜÇ"; + $to = "aaaaaeeeeiiiiooooouuuuc__________________________________________AAAAAEEEEIIIIOOOOOUUUUC"; + $subject = strtr($subject,$from,$to); + //$subject = ereg_replace(':', '_', $subject); + //$subject = ereg_replace('/', '_', $subject); + $file = $subject."_".$i.".eml"; + } else{ + $file = "email_".md5(microtime()).".eml"; } - else{ - $file = "email_".md5(microtime()).".eml"; } @@ -124,16 +142,55 @@ } + // Funcao alterada para tratar a exportacao + // de mensagens arquivadas localmente. + // Rommel Cysne (rommel.cysne@serpro.gov.br) + // em 17/12/2008. function makeAll($params) { - - $this-> folder = $params['folder']; - $this->folder = mb_convert_encoding($this->folder, "UTF7-IMAP","UTF-8"); - $array_ids = explode(',', $params['msgs_to_export']); - $error = False; - $fileNames = ""; - $tempDir = ini_get("session.save_path"); - $this->connectImap(); - - for($i = 0; $i < count($array_ids); $i++) { - + // Exportacao de mensagens arquivadas localmente + if($params['l_msg'] == "t"){ + // Recebe todos os subjects e bodies das mensagens locais selecionadas para exportacao + // e gera arrays com os conteudos separados; + $array_mesgs = explode('@@',$params['mesgs']); + $array_subjects = explode('@@',$params['subjects']); + $array_ids = explode(',', $params['msgs_to_export']); + $tempDir = ini_get("session.save_path"); + // Para cada mensagem selecionada sera gerado um arquivo .eml cujo titulo sera o assunto (subject) da mesma; + include_once("class.imap_functions.inc.php"); + $imapf = new imap_functions(); + foreach($array_ids as $i=>$id) { + $sEMLData=$imapf->treat_base64_from_post($array_mesgs[$i]); + $fileName=$this->CreateFileEml($sEMLData, $tempDir,'',$array_subjects[$i],$i); + if(!$fileName){ + $error = True; + break; + } else{ + $fileNames .= "\"".$fileName."\" "; + } + } + $nameFileZip = 'False'; + if($fileNames && !$error) { + $nameFileZip = $this -> createFileZip($fileNames, $tempDir); + if($nameFileZip){ + $file = $tempDir.'/'.$nameFileZip; + } else{ + $file = false; + } + + } else{ + $file = false; + } + + return $file; + + // Exportacao de mensagens da caixa de entrada (imap) - processo original do Expresso + } else{ + $this-> folder = $params['folder']; + $this->folder = mb_convert_encoding($this->folder, "UTF7-IMAP","UTF-8"); + $array_ids = explode(',', $params['msgs_to_export']); + $error = False; + $fileNames = ""; + $tempDir = ini_get("session.save_path"); + $this->connectImap(); + for($i = 0; $i < count($array_ids); $i++) { $header = $this-> getHeader($array_ids[$i]); $body = $this-> getBody($array_ids[$i]); @@ -165,5 +222,6 @@ return $file; - } + } + } function export_msg($params) { @@ -209,5 +267,5 @@ imap_close($this->mbox_stream); return $urlPath; - } + } function remove_accents($string) { @@ -241,7 +299,4 @@ $imap_attachment = new imap_attachment(); $attachments = $imap_attachment->download_attachment($this->mbox_stream, $id_number); - - - foreach($attachments as $i => $attachment){ if($i && $i == 'names') @@ -280,5 +335,5 @@ imap_close($this->mbox_stream); return $return_attachments; - } + } private function getFileType($nameFile) { Index: /trunk/expressoMail1_2/js/search.js =================================================================== --- /trunk/expressoMail1_2/js/search.js (revision 976) +++ /trunk/expressoMail1_2/js/search.js (revision 1000) @@ -351,7 +351,6 @@ add_className(tr,'tr_msg_unread'); add_className(tr, i%2 != 0 ? 'tr_msg_read2' : 'tr_msg_read'); - - var _onclick = function () { cExecute("$this.imap_functions.get_info_msg&msg_number="+this.parentNode.id+"&msg_folder="+url_encode(this.parentNode.getAttribute('name')),show_msg); }; - for(var j=0 ; j < 10 ; j++) + var _onclick = function () { proxy_mensagens.get_msg(this.parentNode.id,url_encode(this.parentNode.getAttribute('name')),false,show_msg);}; + for(var j=0 ; j < 10 ; j++) { var td = document.createElement("TD"); Index: /trunk/expressoMail1_2/js/messages_proxy.js =================================================================== --- /trunk/expressoMail1_2/js/messages_proxy.js (revision 670) +++ /trunk/expressoMail1_2/js/messages_proxy.js (revision 1000) @@ -183,5 +183,8 @@ } else { - write_msg(get_lang("you can't move mails from local to server folders")); + //Por Bruno Costa (bruno.vieira-costa@serpro.gov.br) permite o desarquivamento de menssagens chamando a função unarchive_msgs quando uma msg é movida de uma pasta local para uma pasta remota. + + expresso_local_messages.unarchive_msgs(folder,new_folder,msgs_number); + //write_msg(get_lang("you can't move mails from local to server folders")); } @@ -250,4 +253,44 @@ } + messages_proxy.prototype.msg_img = function(msgs_number,folder_name,call_back) { + if(this.is_local_folder(folder_name)){ + var msg = expresso_local_messages.get_local_mail(msgs_number); + eval('call_back(msg)'); + } + else + cExecute('$this.imap_functions.get_info_msg&msg_number='+msgs_number+'&msg_folder='+folder_name,call_back); + } + + messages_proxy.prototype.export_all_messages = function(folder){ + + if (!folder){ + folder = get_current_folder(); + } + + if(!this.is_local_folder(folder)){ + export_all_selected_msgs(); + }else{ + local_messages.prototype.local_messages_to_export(); + } + } + + messages_proxy.prototype.proxy_export_all_msg=function(){ + + var er=/^local/; + + + if(ttree.FOLDER == "local_root"){return false;} //Usuario não selecionou uma pasta local e esta no começo dos nós + var nm_bx = ttree.FOLDER.split(cyrus_delimiter); + + var name_f = nm_bx[nm_bx.length -1].replace("local_",""); + + if (!er.test(nm_bx)){ + //Se a pasta nao for local, ou seja a string nao contem a string "local" + ttreeBox.export_all_msg(); + } else{ + expresso_local_messages.get_all_local_folder_messages(name_f); + } + } + var proxy_mensagens; proxy_mensagens = new messages_proxy(); Index: /trunk/expressoMail1_2/js/common_functions.js =================================================================== --- /trunk/expressoMail1_2/js/common_functions.js (revision 994) +++ /trunk/expressoMail1_2/js/common_functions.js (revision 1000) @@ -119,5 +119,5 @@ function set_msg_as_unread(msg_number){ tr_message = Element(msg_number); - if (exist_className(tr_message, 'tr_msg_read') || exist_className(tr_message, 'tr_msg_read2')) + if (exist_className(tr_message, 'tr_msg_read') || exist_className(tr_message, 'tr_msg_read2')) increment_folder_unseen(); remove_className(tr_message, 'selected_msg'); @@ -693,5 +693,5 @@ Element('new_m').innerHTML = '' + abas_unseen + ''; } - if ( current_folder.indexOf( 'INBOX' ) !== 0 ) + if ( current_folder.indexOf( 'INBOX' ) !== 0 && current_folder.indexOf( 'local_' ) !== 0 ) { var display_unseen_in_shared_folders = Element('dftree_user_unseen'); Index: /trunk/expressoMail1_2/js/local_messages.js =================================================================== --- /trunk/expressoMail1_2/js/local_messages.js (revision 670) +++ /trunk/expressoMail1_2/js/local_messages.js (revision 1000) @@ -59,5 +59,4 @@ local_messages.prototype.insert_mail = function(msg_info,msg_header,anexos,folder) { - try { this.init_local_messages(); @@ -82,5 +81,4 @@ msg_info.cc = null; msg_header.Size=null; - //If the mail was archieved in the same date the user received it, the date cames with the time. //here I solved it @@ -109,6 +107,5 @@ var rs = this.dbGears.execute("select rowid from folder where folder=? and uid_usuario=?",[folder,account_id]); - - if(rs.isValidRow()) + if(rs.isValidRow()) id_folder=rs.field(0); else { @@ -119,5 +116,5 @@ if(msg_info.Unseen=="U") unseen = 1; - this.dbGears.execute("insert into mail (mail,original_id,original_folder,header,timestamp,uid_usuario,unseen,id_folder,ffrom,subject,fto,cc,body,size) values (?,?,?,?,?,?,?,?,?,?,?,?,?,?)",[mail,original_id,original_folder,header,timestamp,login,unseen,id_folder,from,subject,to,cc,body,size]); + this.dbGears.execute("insert into mail (mail,original_id,original_folder,header,timestamp,uid_usuario,unseen,id_folder,ffrom,subject,fto,cc,body,size) values (?,?,?,?,?,?,?,?,?,?,?,?,?,?)",[mail,original_id,original_folder,header,timestamp,login,unseen,id_folder,from,subject,to,cc,body,size]); var call_back = function() { } @@ -148,4 +145,30 @@ retorno['subject'] = rs.field(3); retorno['body'] = rs.field(4); + //Codigo que as imagens embutidas em emails (com multipart/related ou multipart/mixed) sejam corretamente mostradas em emails arquivados. Os links do + //tipo "./inc/show_embedded_attach.php?msg_folder=[folder]&msg_num=[msg_num]&msg_part=[part]" + //são substituidos pelos links dos anexos capturados pelo gears. + + var thumbs= retorno.thumbs; + var anexos= retorno.array_attach; + for (i in anexos) + { + nomeArquivo = anexos[i]['name'].substring(0,anexos[i]['name'].length - 4); + if(nomeArquivo.match('jpg')||anexos[i]['name'].match('gif')||anexos[i]['name'].match('png')) + { + var er_imagens = new RegExp("\\.\\/inc\\/show_embedded_attach.php\\?msg_folder=[\\w/]+\\&msg_num=[0-9]+\\&msg_part="+anexos[i]['pid']); + var Result_imagens = er_imagens.exec(retorno['body']); + retorno['body'] = retorno['body'].replace(Result_imagens,anexos[i]['url']); + if(thumbs && thumbs[i]){ + er_imagens = new RegExp("\\.\\/inc\\/show_thumbs.php\\?file_type=image\\/[\\w]+\\&msg_num=[0-9]+\\&msg_folder=[\\w/%]+\\&msg_part="+anexos[i]['pid']); + Result_imagens = er_imagens.exec(thumbs[i]); + thumbs[i] = thumbs[i].replace(Result_imagens,"'"+anexos[i]['url']+"'"); + er_imagens = new RegExp("\\.\\/inc\\/show_img.php\\?msg_num=[0-9]+\\&msg_folder=[\\w/%]+\\&msg_part="+anexos[i]['pid']); + Result_imagens = er_imagens.exec(thumbs[i]); + thumbs[i] = thumbs[i].replace(Result_imagens,"'"+anexos[i]['url']+"'"); + thumbs[i] = thumbs[i].replace(/ 1){ + var msgs_to_export_id = currentTab.substring(0,currentTab.length-2,currentTab); + }else{ + var msgs_to_export_id = get_selected_messages(); + } + var handler_local_mesgs_to_export = function(data){ + download_attachments(null, null, data, null,null,'mensagens.zip'); + } + if(msgs_to_export_id){ + this.init_local_messages(); + var l_msg = "t"; + var mesgs =""; + var subjects =""; + var rs = this.dbGears.execute("select mail,subject from mail where rowid in ("+msgs_to_export_id+")"); + while(rs.isValidRow()){ + mail = connector.unserialize(rs.field(0)); + src = this.get_src(mail.url_export_file); + subject = rs.field(1); + mesgs += src; + mesgs += "@@"; + subjects += subject; + subjects += "@@"; + rs.next(); + } + rs.close(); + this.finalize(); + mesgs = escape(mesgs); + subjects = escape(subjects); + params = "subjects="+subjects+"&mesgs="+mesgs+"&l_msg="+l_msg+"&msgs_to_export="+msgs_to_export_id; + cExecute ("$this.exporteml.makeAll&", handler_local_mesgs_to_export, params); + } + return true; + } + + local_messages.prototype.get_all_local_folder_messages= function(folder_name){ + + + var mesgs = new Array(); + var subjects = new Array(); + var hoje = new Date(); + var msgs_to_export = new Array(); + var l_msg="t"; + + this.init_local_messages(); + var query = "select mail,subject,mail.rowid from mail inner join folder on (mail.id_folder=folder.rowid) where folder.folder='" + folder_name + "'"; + + var rs = this.dbGears.execute(" "+query) + + var handler_local_mesgs_to_export = function(data){ + //alert("data - " + data + " - tipo - " + typeof(data)); + download_attachments(null, null, data, null,null,'mensagens.zip'); + } + var j=0; + while (rs.isValidRow()){ + msgs_to_export[j]=rs.field(2) + mail = connector.unserialize(rs.field(0)); + msg=this.get_src(mail.url_export_file); + subject = rs.field(1); + mesgs += msg; + mesgs += "@@"; + subjects += subject; + subjects += "@@"; + rs.next(); + j++; + + } + rs.close(); + this.finalize(); + source = escape(mesgs); + subjects = escape(subjects); + params = "folder="+folder_name+"&subjects="+subjects+"&mesgs="+source+"&l_msg="+l_msg+"&msgs_to_export="+msgs_to_export; + cExecute ("$this.exporteml.makeAll&", handler_local_mesgs_to_export, params); + + + } + + + /*************************************************************************/ + var expresso_local_messages; Index: /trunk/expressoMail1_2/js/TreeS.js =================================================================== --- /trunk/expressoMail1_2/js/TreeS.js (revision 689) +++ /trunk/expressoMail1_2/js/TreeS.js (revision 1000) @@ -45,5 +45,6 @@ ""+ "