Imnotapotato
Imnotapotato

Reputation: 5798

PHP CodeIgniter: How to run processes in the background without getting my whole website stuck

I have a website on an Ubuntu LAMP Server - that has a form which gets variables and then they get submitted to a function that handles them. The function calls other functions in the controller that "explodes" the variables, order them in an array and run a "for" loop on each variable, gets new data from slow APIs, and inserts the new data to the relevant tables in the database.

Whenever I submit a form, the whole website gets stuck (only for my IP, on other desktops the website continue working regularly), and I get redirected until I get to the requested "redirect("new/url);".

I have been researching this issue for a while and found this post as an example: Continue PHP execution after sending HTTP response

After studding how this works in the server side, which is explained really good in this video: https://www.youtube.com/watch?v=xVSPv-9x3gk

I wanted to start learning how to write it's syntax and found out that this only work on CLI and not from APACHE, but I wasn't sure.

I opened this post a few days ago: PHP+fork(): How to run a fork in a PHP code

and after getting everything working from the server side, installing fork and figuring out the differences of the php.ini files in a server (I edited the apache2 php.ini, don't get mistaked), I stopped getting the errors I used to get for the "fork", but the processes don't run in the background, and I didn't get redirected.

This is the controller after adding fork:

<?php   

// Registers a new keyword for prod to the DB. 
public function add_keyword() {

    $keyword_p = $this->input->post('key_word');

    $prod      = $this->input->post('prod_name');
    $prod      = $this->kas_model->search_prod_name($prod);
    $prod      = $prod[0]->prod_id;

    $country   = $this->input->post('key_country');

    $keyword = explode(", ", $keyword_p);
    var_dump($keyword); 
    $keyword_count = count($keyword);
    echo "the keyword count: $keyword_count";

    for ($i=0; $i < $keyword_count ; $i++) { 
        // create your next fork
        $pid = pcntl_fork();

        if(!$pid){
            //*** get new vars from $keyword_count
            //*** run API functions to get new data_arrays
            //*** inserts new data for each $keyword_count to the DB 
            print "In child $i\n";
            exit($i);
            // end child
        }
    }

    // we are the parent (main), check child's (optional)
    while(pcntl_waitpid(0, $status) != -1){
        $status = pcntl_wexitstatus($status);
         echo "Child $status completed\n";
    }

    // your other main code: Redirect to main page. 
    redirect('banana/kas'); 

}
?>

And this is the controller without the fork:

// Registers a new keyword for prod to the DB. 
public function add_keyword() {

    $keyword_p = $this->input->post('key_word');

    $prod      = $this->input->post('prod_name');
    $prod      = $this->kas_model->search_prod_name($prod);
    $prod      = $prod[0]->prod_id;

    $country   = $this->input->post('key_country');

    $keyword = explode(", ", $keyword_p);
    var_dump($keyword); 
    $keyword_count = count($keyword);
    echo "the keyword count: $keyword_count";

    // problematic part that needs forking
    for ($i=0; $i < $keyword_count ; $i++) { 

        // get new vars from $keyword_count
        // run API functions to get new data_arrays
        // inserts new data for each $keyword_count to the DB 

    }

    // Redirect to main page. 
    redirect('banana/kas'); 

}

The for ($i=0; $i < $keyword_count ; $i++) { is the part that I want to get running in the background because it's taking too much time.

So now:

  1. How can I get this working the way I explained? Because from what I see, fork isn't what I'm looking for, or I might be doing this wrong.

  2. I will be happy to learn new techniques, so I will be happy to get suggestions about how I can do this in different ways. I am a self learner, and I found out the great advantages of Node.js for exmaple, which could have worked perfectly in this case if I would have learnt it. I will consider to learn working with Node.js in the future. sending server requests and getting back responses is awesome ;).

***** If there is a need to add more information about something, please tell me in comments and I will add more information to my post if you think it's relevant and I missed it.

Upvotes: 2

Views: 3103

Answers (1)

Farkie
Farkie

Reputation: 3337

What you're really after is a queue or a job system. There's one script running all the time, waiting for something to do. Once your original PHP script runs, it just adds a job to the list, and it can continue it's process as normal.

There's a few implementations of this - take a look at something like https://laravel.com/docs/5.1/queues

Upvotes: 1

Related Questions