JetJagger Posted February 12, 2008 Share Posted February 12, 2008 Here's my general problem: I'm trying to replace a short string in files sitting on my Web server. The strings contain the ' / ' forward-slash character. My PHP script doesn't like that. It is throwing back error messages for every instance of the string it finds with the ' / ' character in it. Here's the instructional file: <?php require_once('TextSearch.class.php'); $path = "/home/hsmhost/public_html/"; //setting path to search $logFile = "log_result.txt"; //setting log file $obj = new TextSearch(); $obj->setExtensions(array('php')); $obj->addExtension('txt'); $obj->setSearchKey('[color=red][b]/__HS0108/images/head'[/b][/color]); //what to search for <<< HERE $obj->setReplacementKey('[color=red][b]/images/head[/b][/color]'); //replacement text <<< HERE $obj->startSearching($path); $obj->showLog(); $obj->writeLogToFile($logFile); ?> The lines '//what to search for' and '//replacement text' contain the trouble-making character that needs to be replaced. Now, here is the processing script that does the work: <?php class TextSearch { var $extensions = array(); var $searchKey = ''; var $replacementKey = ''; var $caseSensitive = 0; //by default case sensitivity is OFF var $findAllExts = 1; //by default all extensions var $isReplacingEnabled = 0; var $logString = ''; var $errorText = ''; var $totalFound = 0; //total matches /** * Sets extensions to look * @param Array extensions * @return none */ function setExtensions($extensions = array()) { $this->extensions = $extensions; if(sizeof($this->extensions)) { $this->findAllExts = 0; //not all extensions } }//End of Method /** * Adds a search extension * @param file extension * @return none */ function addExtension($extension) { array_push($this->extensions, $extension); $this->findAllExts = 0; //not all extensions }//End of function /** * Sets search key and case sensitivity * @param search key, case sensitivity * @return none */ function setSearchKey($searchKey, $caseSensitive = 0) { $this->searchKey = $searchKey; if($caseSensitivity) { $this->caseSensitive = 1; //yeah, case sensitive } }//End of function /** * Sets key to replace searchKey with * @param : replacement key * @return none */ function setReplacementKey($replacementKey) { $this->replacementKey = $replacementKey; $this->isReplacingEnabled = 1; }//End of function /** * Wrapper function around function findDirFiles() * @param $path to search * @return none */ function startSearching($path) { $this->findDirFiles($path); }//EO Method /** * Recursively traverses files of a specified path * @param path to execute * @return none */ function findDirFiles($path) { $dir = opendir ($path); while ($file = readdir ($dir)) { if (($file == ".") or ($file == "..")) { continue; } if (filetype ("$path/$file") == "dir") { $this->findDirFiles("$path/$file"); //recursive traversing here } elseif($this->matchedExtension($file)) //checks extension if we need to search this file { if(filesize("$path/$file")) { $this->searchFileData("$path/$file"); //search file data } } } //End of while closedir($dir); }//EO Method /** * Finds extension of a file * @param filename * @return file extension */ function findExtension($file) { return array_pop(explode(".",$file)); }//End of function /** * Checks if a file extension is one the extensions we are going to search * @param filename * @return true in success, false otherwise */ function matchedExtension($file) { if($this->findAllExts) //checks if all extensions are to be searched { return true; } elseif(sizeof(array_keys($this->extensions, $this->findExtension($file)))==1) { return true; } return false; }//EO Method /** * Searches data, replaces (if enabled) with given key, prepares log * @param $file * @return none */ function searchFileData($file) { $searchKey = preg_quote($this->searchKey); if($this->caseSensitive) { $pattern = "/$searchKey/U"; } else { $pattern = "/$searchKey/Ui"; } $subject = file_get_contents($file); $found = 0; $found = preg_match_all($pattern, $subject, $matches, PREG_PATTERN_ORDER); $this->totalFound +=$found; if($found) { $foundStr = "Found in $found places"; $this->appendToLog($file, $foundStr); } if($this->isReplacingEnabled && $this->replacementKey && $found) { $outputStr = preg_replace($pattern, $this->replacementKey, $subject); $foundStr = "Found in $found places"; $this->writeToFile($file, $outputStr); $this->appendToLog($file, $foundStr, $this->replacementKey); } elseif($this->isReplacingEnabled && $this->replacementKey == '') { $this->errorText .= "Replacement Text is not defined\n"; $this->appendToLog($file, "Replacement Text is not defined", $this->replacementKey); } elseif(!found) { $this->appendToLog($file, "No matching Found", $this->replacementKey); } }//EO Method /** * Writes new data (after the replacement) to file * @param $file, $data * @return none */ function writeToFile($file, $data) { if(is_writable($file)) { $fp = fopen($file, "w"); fwrite($fp, $data); fclose($fp); } else { $this->errorText .= "Can not replace text. File $file is not writable. \nPlease make it writable\n"; } }//EO Method /** * Appends log data to previous log data * @param filename, match string, replacement key if any * @return none */ function appendToLog($file, $matchStr, $replacementKey = null) { if($this->logString == '') { $this->logString = " --- Searching for '".$this->searchKey."' --- \n"; } if($replacementKey == null) { $this->logString .= "Searching File $file : " . $matchStr."\n"; } else { $this->logString .= "Searching File $file : " . $matchStr.". Replaced by '$replacementKey'\n"; } }//EO Method /** * Shows Log * @param none * @return none */ function showLog() { $this->dBug("------ Total ".$this->totalFound." Matches Found -----"); $this->dBug(nl2br($this->logString)); if($this->errorText!='') { $this->dBug("------Error-----"); $this->dBug(nl2br($this->errorText)); } }//EO Method /** * Writes log to file * @param log filename * @return none */ function writeLogToFile($file) { $fp = fopen($file, "wb") OR die("Can not open file <b>$file</b>"); fwrite($fp, $this->logString); fwrite($fp, "\n------ Total ".$this->totalFound." Matches Found -----\n"); if($this->errorText!='') { fwrite($fp, "\n------Error-----\n"); fwrite($fp, $this->errorText); } fclose($fp); }//EO Method /** * Dumps data * @param data to be dumped * @return none */ function dBug($dump) { echo "<pre>"; print_r($dump); echo "</pre>"; }//EO Method } //End of class ?> Keep in mind that this all working server-side (both files sit on the server and are executed by 'type URL'>'Press Enter Key'). If no ' / ' character is used in the search or replace string, then no problem. This script works just fine and it spits out a txt log file. MY QUESTION IS THIS. How does this script need to be written to find and replace strings with ' / ' (forward-slash) in them? Two weeks of searching the Web for answers, and nobody has a clue, yet. Maybe today is my luck day ;-) Thanks all! -Jet- Quote Link to comment Share on other sites More sharing options...
KrisNz Posted February 12, 2008 Share Posted February 12, 2008 Try changing this $searchKey = preg_quote($this->searchKey); to $searchKey = preg_quote($this->searchKey,'/'); If this works, I can't really take credit for it, it was on the manual page for preg_quote, but it worked for me. Quote Link to comment Share on other sites More sharing options...
aschk Posted February 12, 2008 Share Posted February 12, 2008 Are you getting an error from PHP? As in , is the preg_quote failing? Or another part failing? 1) It seems to me that the paths you are specifying are absolute (i.e. got from the base directory of your system) 2) You are not escaping the / character in your preg_match_all, so it will HALT when it encounters the first / because this terminates the regular expression. Thusly, change: $pattern = "/$searchKey/U"; to $pattern = "@$searchKey@U"; or $pattern = "/".addslashes($searchKey)."/U"; Quote Link to comment Share on other sites More sharing options...
JetJagger Posted February 12, 2008 Author Share Posted February 12, 2008 Try changing this $searchKey = preg_quote($this->searchKey); to $searchKey = preg_quote($this->searchKey,'/'); If this works, I can't really take credit for it, it was on the manual page for preg_quote, but it worked for me. WORKED LIKE A CHARM - Thanks! Quote Link to comment Share on other sites More sharing options...
Lukeup Posted March 18, 2009 Share Posted March 18, 2009 Hi freaks, can someone help me remove the "Replacement Text is not defined" check in this class. I need to replace "\r\n " with "" in several files and I receive the 'not defined' error when $obj->setReplacementKey(""); is empty. I'm not really sure what to modify with out messing it up (noob). Appreciate any help. Thanks, Luke. ps... This is really a great tool. Script: <?php require_once('TextSearch.class.php'); $path = "c:\secu"; //setting search path $logFile = "c:\secu\searchResult.txt"; //setting log file $obj = new TextSearch(); $obj->setExtensions(array('txt')); //setting extensions to search files within $obj->addExtension('php');//adding an extension to search within $obj->setSearchKey("\r\n "); $obj->setReplacementKey("");//setting replacement text if you want to replace matches with that $obj->startSearching($path);//starting search $obj->showLog();//showing log $obj->writeLogToFile($logFile); //writting result to log file ?> Class: TextSearch I did not post the class because of the rules but it is the same one posted in this thread. Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.