1

I am creating a cron job that will run every few minutes and it will read from database data to see which function needs to be called and act accordingly to the data but half the crons are written in codeigniter and the other half in native php.

Is there any way to do this? I have been googling but the anwser. I came up with is that it is impossible. I tried changing directory and than including or requiring index.php from the codeigniter, in which the function is that i need to call.

while doing this if my class is written in native php, It returns some errors that don't make sense and if I correct those errors, I would say that half the system function from codeigniter would be gone. It would still be a question if it will work even then.

If my class is written in codeigniter, when I include index.php, it just breaks. No errors no response or it says that the "ENVIRONMENT" variables are already defined. Thus I have been looking for a way to undefine those variables from config file or overwrite them to null or empty string but nothing works.

If you have any ideas it would be much appreciated.

I saw a question question link about some cron jobs in php where the user @michal kralik gave an answer about what i am doing in general with database and one cron class that will call other crons (coould use help for that too).

btw forgot to mention that using curl and exec will not work, because on our servers they sometimes just stop working for no reason.

UPDATE 1:

this is my class currently after so many tries:

 class Unicron extends MY_Controller {       

        public $config;

        function __construct() {
            parent::__construct();
        }

        public function init(){
            $config['base_url'] = "http://localhost/test";
            define('EXT_CALL', true); // Added EXT_CALL constant to mark external calls
            $_GET['controller/method'] = ''; // add pair to $_GET with call route as key

            $current = getcwd(); // Save current directory path
            chdir('C:/inetpub/wwwroot/test/'); // change directory to CI_INSTALLATION

            include_once 'index.php'; // Add index.php (CI) to script
            define('BASEPATH', 'C:/inetpub/wwwroot/test/system/');

            $this->load->library("../../application/controllers/controller.php");
            $job = new $this->controller->Class();
            $isDone = $job->exportExcel(somekey);
            echo $isDone;

            $CI =& get_instance(); // Get instance of CI

            $CI->exportExcel('baseparts', 'exportExcel');
            // FOR STATIC CALLING!!
            //$CI->method('controller','method'); 
            //replace controller and method with call route
            // eg: $CI->list('welcome','list'); If calling welcome/list route.

            //$OUT->_display(); // to display output. (quick one)

            // Or if you need output in variable,
            //$output = $CI->load->view('VIEW_NAME',array(),TRUE); 
            //To call any specific view file (bit slow)
            // You can pass variables in array. View file will pick those as it works in CI

           chdir($current); // Change back to current directory
           echo $current;
    }

where i try to define BASEPATH it does not define it nor override the previous value. In the index.php of other codeigniter i put:

  if(!defined('ENVIRONMENT')) 
     define('ENVIRONMENT', 'development');

this way i resolved my issue with ENVIRONMENT already being set error.

this is a few things i found and combined together, hoping it could work but still when i call it via command line it shows nothing (even tried echo anything everywhere and nothing).

Community
  • 1
  • 1
grimy88
  • 11
  • 4
  • 2
    Things don't stop for no reason. That's Newton's first law. – Anthony May 13 '14 at 07:13
  • define BASEPATH in the file you're running from the cron job and just include the file in the codeigniter directory? – Bryan May 13 '14 at 07:41
  • ok, could you explain a bit more? BASEPATH to what exactly should that path point to the file of cron or the path to the other Codeigniter? – grimy88 May 13 '14 at 07:54
  • according to 'google', there are quite a lot of articles about running codeigniter from the command line, which, i assume, is what you want to do. What do you want to do that is different? – Ryan Vincent May 13 '14 at 10:21
  • It is different, i can run my script from command line that part is ok and works but my script needs to be able to instantiate some other codeigniter which is on the same server and load a controller and one of his functions. Multiple codeigniters on same server. – grimy88 May 13 '14 at 10:43
  • Would the php 'system' command help you to run a separate instance of codeigniter from inside your class? they would be completely separate from each other. – Ryan Vincent May 13 '14 at 14:38
  • Interesting idea but i don't quite understand, could you elaborate a bit more and maybe give an example? – grimy88 May 13 '14 at 19:20

1 Answers1

1

This may be a long comment rather than a answer as the code supplied requires a lot of work to make it useful.

Running multiple instances of 'codeigniter' - executed from codeigniter.

Using the 'execute programs via the shell' from PHP. Each instance runs in its own environment.

There are some excellent answers already available:

By default the PHP commands 'shell' wait for the command to complete...

732832/php-exec-vs-system-vs-passthru.

However, we want to 'fire and forget' quite often so this answer is quite useful...

1019867/is-there-a-way-to-use-shell-exec-without-waiting-for-the-command-to-complete

All i did was use this show an example of how to use 'codeigniter' to do this. The example was the 'Hello World' cli example from user manual. The version of ci is 2.1.14. I haven't used 'ci' before.

It is tested and works on 'PHP 5.3.18' on windows xp.

As well as the usual 'Hello World' example, i used an example of a a command that uses 'sleep' for a total of 20 seconds so that we can easily see that the 'ci' instances are separate from each other while executing.

Examples:

<?php
class Tools extends CI_Controller {

    // the usual 'hello world' program
    public function message($to = 'World')
    {
       echo "Hello {$to}!".PHP_EOL;
    }

    // so you can see that the processes are independant and 'standalone'
    // run for 20 seconds and show progress every second.
    public function waitMessage($to = 'World')
    {
        $countDown = 20;
        while ($countDown >= 0) {
            echo "Hello {$to}! - ending in {$countDown} seconds".PHP_EOL;
            sleep(1);
            $countDown--;
        }
    }
}

'ci' code to run 'ci' code...

<?php
class Runtools extends CI_Controller {
    /*
     * Executing background processes from PHP on Windows
     * http://www.somacon.com/p395.php
     */

    // spawn a process and do not wait for it to complete
    public function runci_nowait($controller, $method, $param)
    {
       $runit  = "php index.php {$controller} {$method} {$param}" ;
       pclose(popen("start \"{$controller} {$method}\" {$runit}", "r"));
       return;
    }

    // spawn a process and wait for the output.
    public function runci_wait($controller, $method, $param)
    {
       $runit  = "php index.php {$controller} {$method} {$param}";
       $output = exec("{$runit}");
       echo $output;
    }

}

How to run them from the cli...

To run the 'ci' 'nowait' routine then do:

php index.php runtools runci_nowait <controller> <method> <param>

where the parameters are the ci controller you want to run. Chnge to 'runci_wait' for the other one.

'Hello World: 'wait for output' - (ci: tools message )

codeigniter>php index.php runtools runci_wait tools message ryan3
Hello ryan3!

The waitMessage - 'do not wait for output' - (ci : tools waitMessage )

codeigniter>php index.php runtools runci_nowait tools waitMessage ryan1

codeigniter>php index.php runtools runci_nowait tools waitMessage ryan2

These will start and run two separate 'ci' processes.

Community
  • 1
  • 1
Ryan Vincent
  • 4,310
  • 7
  • 19
  • 29
  • 1
    Nice answer and very good explanation thank you, but still what i need is to switch between codeigniters without using exec commands that's the limitation and the main problem. – grimy88 May 14 '14 at 17:31
  • @grimy88, hmm, what do you mean by 'switch between codeignighters'? Do you mean once you have finished processing the current 'controller/method' you do another one in the same instance i.e. instead of one ci instance processing one route, it processes a list of routes? that may be possibe. Or do you have some other meaning? And why the limitation? – Ryan Vincent May 14 '14 at 19:08
  • What i meant was that my class is alone in a codeigniter and is called as a cron job the only one and i need this cron job to call and use controllers/methods from other codeigniter projects there are three i think. Example project1 is where my class will be and called as a cron job and based on the database i need to call project2->controller/method after that call project3->controller/method than project3->controller/method without cli/exec because those functions for some reason sometimes work and sometimes don't on the server, where each project is a separate codeigniter project. – grimy88 May 15 '14 at 06:31
  • calling other projects and controllers/methods is something that will depend on data from database but still when i call other project controller/method it either gives errors about ENVIRONMENT and other variables already being set so somehow i managed to work something about that and when i include index.php from another project it just breaks and exits no warnings no errors. As you could see the code i used in my question even when changing directories still not working. – grimy88 May 15 '14 at 06:35