PHP: Экономим на входящем трафике

Некоторые провайдеры предоставляют скидки на локальный трафик (в зоне провайдера), которые могут достигать 80%. В эту зону может включаться входящая почта с сервера провайдера. Как этим можно воспользоваться? Посмотрим.

Имеем:

  • хостинг с поддержкой PHP (желательно без ограниченного трафика)
  • провайдер, предоставляющий скидки
  • почтовый ящик, расположенный на сервере провайдера

    Принцип работы будет заключаться в закачке необходимого файла на свой WEB-сервер и отправке его на почтовый ящик, расположенный у провайдера.

    Необходимо учесть увеличение размера посылки в связи с использованием base64. И чем меньше будет нужный файл, тем меньше будет и выигрыш в трафике. Остается только уложиться в максимальный размер письма для Вашего почтового ящика.

    Отправляем на сервер скрипт downmail.php и вызываем его через браузер. При своей работе скрипт также использует класс для отправки почты с аттачментом mailer. Основная форма содержится в самом скрипте и исключена из примера для компактности.

    <?php
    
      // выводим ошибку
      function PrintError($str)
      {
        echo "<FONT COLOR=\"#ff0000\">$str</FONT><BR />\n";
      }
    
      // передаваемые через форму значения
      $url = $HTTP_POST_VARS['url'];
      $email = $HTTP_POST_VARS['email'];
      if(!strlen($url) || !strlen($email))
      {
        PrintError('Необходимо заполнить все поля!');
        exit();
      }
    
      // отключаем тайм-аут
      if( !get_cfg_var('safe_mode') )
        set_time_limit(0);
    
      // отправим 256 пробелов для Explorer'a и Opera
      echo str_repeat(' ', 256);
    
      echo 'Open remote file ' . $url . "...\n";
      flush();
    
      $name = parse_url($url);
      // создаем заголовок HTTP-запроса
      $opts = array(
        'http' => array(
          'method' => "GET",
          // представимся Explorer'ом
          'user_agent' => "User-Agent: Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)\r\n",
          'header' => 
            'Host: ' . $name['host'] . "\r\n" .
            "Accept: */*\r\n" .
            "Pragma: no-cache\r\n" .
            "Connection: close\r\n" .
            "Cache-control: no-cache\r\n"
        )
      );
      $context = stream_context_create($opts);
    
      $fl = @fopen ($url, 'rb', false, $context);
      if(!$fl)
        PrintError('Error open remote file');
      else
      {
        echo "OK<BR />Create local file...\n";
        flush();
    
        $file = basename($name['path']);
        $fname = './' . $file;
        $fo = @fopen($fname, 'wb'); // $fo - file out
        if(!$fo)
          PrintError('Error');
        else
        {
          echo "OK<BR />Get file info...\n";
          flush();
    
          $len = 0; // размер удаленного файла
    
          // получим заголовок ответа сервера
          $data = stream_get_meta_data($fl);
          $head = $data['wrapper_data'];
    
          // из полученного ответа находим длину файла
          while( list(, $val) = each($head) )
            if( substr(strtoupper($val), 0, 16) == 'CONTENT-LENGTH: ' )
            {
              $len = intval( substr($val, 16) );
              break;
            }
    
          echo ' length = ' . $len . "\n";
          echo '<BR />Get content...<BR />' . "\n";
          if($len)
            echo '0%' . "\n";
          flush();
    
          // переменные для вывода процентной шкалы
          $wrlen = 0; // записанные данные
          $delta = 10; // выводим каждые $delta процентов
          $next = $delta; // следующее выводимое значение
    
          // получаем содержимое файла
          while(true)
          {
            $data = fread($fl, 4096);
            if(strlen($data) == 0)
              break;
            $wrlen += fwrite($fo, $data);
    
            // выводим процентную шкалу, если получили Content-Length
            if($len)
              if( ($wrlen*100)/$len >= $next)
              {
                // кол-во записанных данных превысило $next
                // выводим процент закачки и увеличиваем $next
                echo ' === ' . $next . '%' ."\n";
                flush();
                $next += $delta;
              }
          }
          fclose($fo);
    
          $valid = true;
          if($len && filesize($fname) != $len )
          {
            // если получили Content-Length и длина закаченного файла
            // не равна длине удаленного файла - ошибка
            $valid = false;
            PrintError('Error: length');
          }
          else
            echo '<BR />OK<BR />';
    
          if($valid)
          {
            // отправляем по почте только валидный файл
            echo "Post...\n";
            flush();
    
            // подключаем класс mailer для отправки почты
            include('./mailer.php');
    
            $mail = new mailer();
            $mail->add_body( $HTTP_POST_VARS['body'] );
            $mail->add_attachment('.', $file);
            $mail->build_message('win');
    
            // отправка письма через SMTP-сервер smtp.myserver.ru
            // на почтовый ящик $email, от <postmaster@myserver.ru>
            // тема письма - $file
            if( $mail->send('smtp.myserver.ru', $email, "<postmaster@myserver.ru>", $file) )
              echo 'OK';
            else
              PrintError('Error');
          }
          // удаляем закаченный файл со своего сервера
          unlink('./' . $file);
        }
        fclose ($fl);
      }
      echo '<BR />End';
    
    ?>
    
    Данный скрипт можно использовать и для других целей. Вместо простого файла выбираем картинку, пишем сопроводительное письмо, отправляем на нужный адрес и получаем поздравительное послание. В таком виде можно организовать центр рассылки поздравлений.

    В файле, предложенном для скачивания, находятся два скрипта (downmail.php и mailer.php). В связи со вносимыми изменениями, версия в файле может немного отличаться от предложенной в этой статье.
    Скачать >> (rar-архив 4k)

    Замечания и пожелания принимаются.

    Взято с arkasoft.narod.ru, автор Алимов Рустем



  • Опубликовал admin
    11 Июн, Пятница 2004г.



    Программирование для чайников.