0

I have a script that checks a website ($host) for an string of characters ($find). If the string exists the nothing happens, if the string is not found then an email is sent to a pre-set email address.

The problem I have is that I need to have an array of URL's and I believe a second array of text. The text in the array needs to match up to the URL's in the array.

Perhaps storing the URL's and text in a text file(s) might be a better solution.

Here is the script as it is right now, working on the single domain.

<?php
    $host = 'www.my-domain.com';
    $find = 'content on my page';

    function check($host, $find) {
        $fp = fsockopen($host, 80, $errno, $errstr, 10);
        if (!$fp) {
            echo "$errstr ($errno)\n";
        } else {
           $header = "GET / HTTP/1.1\r\n";
           $header .= "Host: $host\r\n";
           $header .= "Connection: close\r\n\r\n";
           fputs($fp, $header);
           while (!feof($fp)) {
               $str.= fgets($fp, 1024);
           }
           fclose($fp);
           return (strpos($str, $find) !== false);
        }
    }


    function alert($host) {
        mail('[email protected]', 'Monitoring', $host.' down');
    }

    if (!check($host, $find)) alert($host);

    ?>

New code with array in place:

$hostMap = array(
    'www.my-domain.com' => 'content on site',
    'www.my-domain2.ca' => 'content on second site',
 );

foreach ($hostMap as $host => $find)
{
        function check($host, $find)
        {
                $fp = fsockopen($host, 80, $errno, $errstr, 10);
                if (!$fp)
                {
                        echo "$errstr ($errno)\n";
                } else {
                        $header = "GET / HTTP/1.1\r\n";
                        $header .= "Host: $host\r\n";
                        $header .= "Connection: close\r\n\r\n";
                        fputs($fp, $header);
                        while (!feof($fp)) {
                                $str.= fgets($fp, 1024);
                        }
                        fclose($fp);
                        return (strpos($str, $find) !== false);
                }
        }

        function alert($host)
        {
                mail('[email protected]', 'Website Monitoring', $host.' is down');
        }

        print $host;
        print $find;

//if (!check($host, $find)) alert($host);

        if( !check( $host, $find ) )
        {
                alert($host);
        }
}

?>

Moved the functions outside of the foreach(

ini_set( 'display_errors', true );
        $hostMap = array(
        'www.my-domain.com' => 'content on site',
        'www.my-domain2.ca' => 'content on second site',
     );

          function check($host, $find)
            {
                    $fp = fsockopen($host, 80, $errno, $errstr, 10);
                    if (!$fp)
                    {
                            echo "$errstr ($errno)\n";
                    } else {
                            $header = "GET / HTTP/1.1\r\n";
                            $header .= "Host: $host\r\n";
                            $header .= "Connection: close\r\n\r\n";
                            fputs($fp, $header);
                            while (!feof($fp)) {
                                    $str.= fgets($fp, 1024);
                            }
                            fclose($fp);
                            return (strpos($str, $find) !== false);
                    }
            }

            function alert($host)
            {
                    mail('[email protected]', 'Website Monitoring', $host.' is down');
            }

            print $host;
            print $find;

    //if (!check($host, $find)) alert($host);
    foreach ($hostMap as $host => $find)
    {

            if( !check( $host, $find ) )
            {
                    alert($host);
            }
    }

    ?>

Here is the final code with a working Array in case anyone else wants a solution like this.

    function check($host, $find)
    {
        $fp = fsockopen($host, 80, $errno, $errstr, 10);
        if (!$fp)
            {
                            echo "$errstr ($errno)\n";
                        } else {
                            $header = "GET / HTTP/1.1\r\n";
                            $header .= "Host: $host\r\n";
                            $header .= "Connection: close\r\n\r\n";
                            fputs($fp, $header);
                            while (!feof($fp)) {
                                    $str.= fgets($fp, 1024);
                            }
                            fclose($fp);
                            return (strpos($str, $find) !== false);
                        }
    }

function alert($host)
    {
        $headers = 'From: Set your from address here';
        mail('[email protected]', 'Website Monitoring', $host.' is down' $headers);
    }

$hostMap = array(
'www.my-domain.com' => 'content on site',
'www.my-domain2.com' => 'content on second site',
);

    //if (!check($host, $find)) alert($host);
    foreach ($hostMap as $host => $find)
    {

            if( !check( $host, $find ) )
            {
                    alert($host);
            }
    }
unset($host);
unset($find);

?>
1
  • The 3rd iteration of the code has a foreach that does not seem to run through the array. The first site in the array is the only one checked. The only message I get is "Undefined variable: str in /srv/www/php/php_testing/monitor.php on line 25". I'm not sure where my mistake is. Commented Oct 21, 2011 at 17:56

2 Answers 2

2
$hostMap = array(
    'www.my-domain.com' => 'content on my page',
    /* etc. */
);

foreach( $hostMap as $host => $find )
{
    if( !check( $host, $find ) )
    {
         alert($host);
    }
}

However, be aware that -- depending on the amount of domains you are checking -- sequentially mailing large amounts of mails with PHP's native mail() is not very efficient. You may wanna look in to more specialized mail libraries for that, such as SwiftMailer.

On the other hand -- seeing you are mailing one and the same e-mail address -- you could also simply save the failing domains in an array, and mail them all in one e-mail after you're done checking of course.

Sign up to request clarification or add additional context in comments.

3 Comments

I've been trying to get this to work but what I've come up with doesn't seem to step beyond the 1st site in the array. I've added the new code to the question above.
@user973661: You should define the functions outside of the foreach loop once (not on every iteration in the foreach loop). As a matter of fact; it's not even allowed to redefine functions. This will cause a fatal error. I presume you are not displaying errors on screen (by putting ini_set( 'display_errors', true ) at the beginning of your script), otherwise you must have been notified of this error. Make sure you only use error displaying on development machine, not on a production machine.
I added the display_errors and moved the functions outside of the foreach (I added the code above). I am getting a undefined variable and I still only get one site checked.
1

You can just store everything in a multidimensional array and put an iterator around the entire working section of code.

$list_of_sites[0]["url"] = blah;
$list_of_sites[0]["text"] = blah;
$list_of_sites[1]["url"] = blah;
$list_of_sites[1]["text"] = blah;

foreach($list_of_sites as $site){  
    $url = $site["url"];
    $text = $site["text"];

    check($url, $text);
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.