Узкие места, замедляющие часть моего сценария - PullRequest
0 голосов
/ 19 апреля 2011

У меня есть скрипт, который выполняет следующие шаги

  1. Пользователь входит в систему, добавляет SMS-сообщение и указывает получателей.Эта информация добавляется в «таблицу сообщений в очереди»;
  2. Некоторые процессы отправляют сообщения с помощью API, и сообщения перемещаются в «таблицу отправленных сообщений»;
  3. Приходит отчет о доставке и сообщения удаляются.из "таблицы отправленных сообщений" и запись в журнале, ссылающаяся на отправленные сообщения, добавляется в "таблицу журналов отправленных сообщений".

, когда большое количество сообщений помещается в очередь в «таблице сообщений в очереди», шаги (2) и (3) занимают много времени,

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

Ниже приведен пример сценария

<?php
class Message {

    /*
    * random unique id for mobile number
    */
    protected $mobile_ids = array();

    public function add_unique_id($id, $mobile) 
    {
        $this->mobile_ids[] = array($id, $mobile);
    }

    public function get_unique_id()
    {
        return $this->mobile_ids;
    }

    // The method that generated the xml for API
     public function makeXML($param,$multi_part=false) 
     {
            $xmlString =
            "<SMS>
            <authentification>
            <username>sss</username>
            <password>sss</password>
            </authentification>
            <message>
            <sender>sender</sender>";
            if($multi_part == "longSMS") $xmlString .= "<type>longSMS</type>";

            $xmlString .= "<text>{$param['text']}</text></message><recipients>";

            // Array of mobile numbers came from $param
            $phone_numbers = $param['numbers'];

            // Loop through the array and generate <gsm messageId='0001'>mobile</gsm>
            foreach($phone_numbers as $mobile) {

                // Generate id for mobile
                $msg_id = $this->make_random_int();

                /**
                 * This is the slow part of the script,
                 * IDs are added to the array for logging into the database
                 * When message is sent, i looped through the id and created a log for this message
                 **/
                $this->add_unique_id($msg_id, $mobile);


                $xmlString .= "<gsm messageId=\"{$msg_id}\">{$mobile}</gsm>";
            }
            $xmlString .= "</recipients></SMS>";
            return $xmlString;
        }

         /**
          * This is the method that created the log
         * Log the sms
         * You will need to call $msgid = $this->update_db('the sms')
         * return value of $msgid is last_insert_id
         */
        public function log_sms($msgid) {
            // Log the currently sent message
            $userData = array();
            $now = date('Y-m-d H:i:s');
            foreach ($this->mobile_ids as $data) {
                $userData[] = "('{$msgid}', '{$data[0]}', '{$data[1]}', 'QUEUED', '0000-00-00', '0000-00-00', '{$now}')";
             }

             $query = 'INSERT INTO sent_sms_log (txtId,msgID,mobile,status,sentdate_time,deliver_date_time,sysdate_time) VALUES' . implode(',', $userData);
             $this->ci->db->query($query);

             $this->mobile_ids = array(); // reset the array
        }       
     // Make random int
      protected function make_random_int() {
            $this->ci->load->helper('string');
            $int =  random_string('numeric', 12);
            return $int;
        }

         /**
         * Update database after sms sent
         * @return int
         */
        public function update_db($msg, $owner, $qid=0) {
            $data = array('qid'=> $qid, 'sms' => $msg, 'date_time' => date('Y-m-d H:i:s'), 'owner' => $owner);
            $this->ci->db->insert('f_sent_sms', $data);
            return $this->ci->db->insert_id();
        }
}

Ответы [ 2 ]

0 голосов
/ 19 апреля 2011

Полагаю, это сейчас работает на каком-то цикле?Вместо того, чтобы вставлять неизвестное количество записей по одной за раз, проверьте метод insert_batch () для Active Record в Руководстве пользователя http://codeigniter.com/user_guide/database/active_record.html Вы можете использовать один вызов базы данных, чтобы вставить все свои записи.Вместо цикла вставки данных в базу данных все, что нужно сделать циклу, - это построить массив всех данных, которые будут вставлены.После завершения цикла запустите insert_batch ('f_sent_sms', $ my_data) для только что созданного массива.

Было бы хорошей идеей также сравнить все (до и после), как уже сказал @Matthew.

0 голосов
/ 19 апреля 2011

Полагаю, это может быть API, с которым вы работаете.Мне приходилось работать с apis для разных сервисов, которые были крайне медленными.Возможно, попробуйте профилировать различные части кода с помощью класса теста:

http://codeigniter.com/user_guide/libraries/benchmark.html

Это будет быстрый и простой способ найти самые медленные части кода.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...