Due to reasons that are have nothing to do with the actual question, I need to call and use an external script via PHP to perform a string replacement on a complete html document. The replacement strings and the source code need to be passded to this script via php exec(). For this example, I have used a simple python script to take over the replacement.
PHP script looks like this:
$source = file_get_contents("somehtmlfile.html");
$replaceString = "Some text in the HTML doc";
$replaceTo = "Some other text";
$parsedString = system("python replace.py $replaceString $replaceTo $source", $retval);
print ("Done:" .$mystring);
Then the Python script will do the following:
import sys
import string
dataFrom = sys.argv[1];
dataTo = sys.argv[2];
dataSourceCode = sys.argv[3];
rep = dataSourceCode.replace(dataFrom, dataTo);
print rep;
The problem is that I can't pass the complete html source as an argument to the shell, at least not in the way shown above. From what I understood, while the html code gets passed to the shell it interpretes some sections as commands (multiline could be an issue here I suppose).
The output I receive from the script :
sh: cannot open !DOCTYPE: No such file
sh: cannot open html: No such file
sh: cannot open head: No such file
sh: cannot open title: No such file
... (this goes on)
Any suggestions?
It is not working because there are spaces and quotes in the html text that you pass as an argument, so it is seen as multiple arguments. To solve this, you have to put quotes around the arguments.
The correct code is $parsedString = system("python replace.py '$replaceString' '$replaceTo' '$source'", $retval);
Related
I am looking for a way to obtain a Python list and display it on my website using PHP.
I've checked out and tried many online help-requests so I was hoping someone would be able to explain to me what it is I am doing wrong.
My Python script scrapes a website and puts the result in a Python list.
What I am trying to achieve is the following:
I want to display (a part) of the list on my website.
I've tried to accomplish this with the following code:
PHP
<?php
$outputArray = [];
$returnStatus;
exec('python ./scrapeWebsite.py', $outputArray, $returnStatus);
var_dump($outputArray);
echo $returnStatus;
?>
Python:
print(newsHeadlines) -> returning a list like this: ['item 1','item 2','item 3','item 4']
However, the array comes back as array(0) { } and the $returnStatus value is 1.
Encoding the list with JSON and writing it to a file on the disk, and then reading the file in PHP and decoding JSON did the trick. To ensure the web-data is up-to-date I'm using exec(); to execute the python file.
If going full Python this is an option you could use.
To help others with a similar problem, this is the code I used:
Python:
myListJson = json.dumps(myList) #Encode our Python list into a JSON string
f = open("./fileName.txt", "w") #Open the file that we want to write to for write access
f.write(myListJson) #Write the JSON String to the file that we have currently open
f.close() #Close the file
PHP:
exec(python3 /path/to/file/script.py); //Will execute the python script, ensure the needed packages are installed on the **SERVER**.
$fileContents = file_get_contents("fileName.txt");
$decodedJson = json_decode($fileContents); //This will now contain your Array like any other PHP Array.
Thanks for the help!
I want to pass a text as a argument from a bash file to a php script like this:
bash script
#!/bin/sh
php /var/www/html/assets/sms/get_sms.php $SMS_1_NUMBER $SMS_1_TEXT
php script
<?php
$url = "http://localhost/user/user/get_sms/".$argv[1];
$postdata = array('number' => $argv[1],'text'=>$argv[2]);
do_post_request($url,$postdata);
function do_post_request($url, $postdata)
{
//My function
}
?>
The problem is that, the first argument to the bash file is a number but the second argument is text. The Php file which receives the arguments just takes the first string of the text. For example, if the text of the $SMS_1_TEXT variable is "How can I make it work" , the php file will receive only "How".
How can I make it woks better?
Thank you very much
Quoting. Replace $SMS_1_TEXT by "$SMS_1_TEXT".
I am trying to call a simple python script from a php script. The result I am getting is just a single word while my actual input is a long text/sentence. The php script should return the entire sentence; it currently outputs only "The"
Python script
import sys
print sys.argv[1]
Php script
$var1 = "The extra sleep will help your body wash out stress hormones.";
$output = exec("C:\Python27\python.exe example.py $var1");
echo $output;
Because command line parameters are space-delimited, you have to add some quotes:
$output = exec("C:\Python27\python.exe example.py \"$var1\"");
Your Python script is printing the first parameter that it receives. That first parameter is "The".
I understand there are questions like mine already asked, but I can't figure this out even with the answers in those questions.
PHP:
<?php
$var1 = "hi";
$result = shell_exec('TestingStuff.py'.$var1);
?>
Python:
import sys
print(sys.argv[1])
Error received when running in Python:
IndexError: list index out of range
Both scripts are in the same folder.
Could someone please provide an answer with the code changes?
Error
If the Python script runs with no arguments at all, then that sys.argv[1] index is out of range.
Scripts
ExecPython.php
<?php
$var1 = "hi";
$result = shell_exec('TestingStuff.py ' . $var1);
echo "<pre>$result</pre>";
TestingStuff.py
import sys
if len(sys.argv) > 1:
print(sys.argv[1])
Demo
Explanation
We will start with the Python script. The goal is, that the script prints the first argument passed to it - without running into the "IndexError: list index out of range" error.
python TestingStuff.py 123 we want the output 123.
In Python the arguments passed to the script reside in sys.argv. It's a list. sys.argv[0] is always the script name itself (here TestingStuff.py). Using the example from above sys.argv[1] is now 123.
Handling the edge cases: "no argument" given.
python TestingStuff.py
This will result in an "IndexError: list index out of range" error, because you are trying to access a list element, which is not there. sys.argv[0] is the script name and sys.argv[1] is not set, but you are trying to print it and BAM goes the error. To avoid the error and only print the first argument, we need to make sure, that the list sys.argv contains more than one element (more than the script name). That's why i've added if len(sys.argv) > 1:.
That means: print the first argument only, if the list has more than 1 argument.
Now we can test the Python script standalone - with and without arguments.
And switch over to the PHP script.
The goal is to execute the Python script from PHP.
PHP provides several ways to execute a script, there are for instance exec(), passthru(), shell_exec(), system(). Here we are using shell_exec(). shell_exec() returns the output of the script or command we run with it.
In other words: if you run $result = shell_exec('php -v');, you'll get the PHP version lines in $result.
Here we are executing the Python script TestingStuff.py and add an argument, which is $var1. It's a string and added via concatenation to the string given to shell_exec(). The $result is echoed. I wrapped pre-tags around it, because i thought this is executed in the web/browser context. If you are using the scripts only on the CLI, you might drop the pre-tags.
Execution flow
the PHP script is executed
shell_exec() executes the Python script
shell_exec() returns the output of the Python script as $result
$result is printed by PHP via echo
I'd like to hash a file using php's hash_file(), but obfuscate it so it is not easily detected by a text string search in a text editor. Any advice? Possible?
You could use base64_encode/base64_decode to mask the name of the command being executed.
$command = "hash_file";
$encodedcommand = base64_encode($command); //aGFzaF9maWxl
Now you know that the base64 encoding of 'hash_file' is aGFzaF9maWxl.
So in your real script, just decode and execute that string:
$maskedcommand = base64_decode("aGFzaF9maWxl");
print $maskedcommand("md5",$filename);
So the string 'hash_file' isn't in the two lines of code above, but it still executes the 'hash_file' command.