I'm a noob, is there someone could help me with this?
I have a local SQL database using Xampp thru phpMyAdmin and i want to mirror it to online MySQL in my website.
When I'm making changes to my local database, I want my online database to be updated (Realtime) with the changes made.
Is this possible? Can I have a sample php code or whatever that can do this? Thanks!!
Many times ago I wrote some script for this problem. As said above - replication it's really good solution but in my case I could not use it. So.. if you need some like replication by master->slave maybe this script will be useffull :
dumps.sh :
while getopts "c:l:" opt; do
case $opt in
c)
if [ -r "$OPTARG" ]; then
source "$OPTARG"
else
echo "Unreadable config file \"$OPTARG\""
exit 1
fi
;;
l) LOG_FILE="$OPTARG"
if [ ! -f "$LOG_FILE" ]; then
`touch $LOG_FILE`
fi
;;
\?) echo "Invalid options. -$OPTARG. USE -c config_file"
exit 1
;;
:) "Option -$OPTARG requires an argument."
;;
esac
done
logIt()
{
date_now=`date '+%D %T'`
if [ $LOG_FILE != "" ]; then
echo "$date_now : $*" >> $LOG_FILE
else
echo "$date_now : $*"
fi
}
build_tables()
{
TAB=""
logIt $#
for table in $TABLES
do
TAB="$TAB ${1}${table}"
done
echo $TAB
}
MYSQLDUMP="$(which mysqldump)"
CHOWN="$(which chown)"
CHMOD="$(which chmod)"
GZIP="$(which gzip)"
RM="$(which rm)"
DEST="."
MBD="$DEST/mysql"
eval $RM -fv "$MBD/*"
FILE=""
[ ! -d $MBD ] && mkdir -p $MBD || :
$CHOWN 0.0 -R $DEST
$CHMOD 0600 $DEST
TAB=`build_tables $DB_PREFIX`
FILE="$MBD/$DB_NAME.sql";
($MYSQLDUMP -u $MyUSER -h $MyHOST -p$MyPASS $DB_NAME $TAB 2>> $LOG_FILE) > $FILE
input_to_mysql()
{
###############################3
CP="$(which cp)"
SED="$(which sed)"
len=${#INSERT_DB_NAME[*]}
i=0
while [ $i -lt $len ]; do
NEW_FILE="$MBD/${INSERT_DB_NAME[$i]}.sql"
eval $CP $FILE $NEW_FILE
eval $SED -i "s/$DB_PREFIX/${INSERT_DB_PREFIX[$i]}/g" $NEW_FILE
eval $SED -i "s/^.\*!.*$//g" $NEW_FILE
let i++
done
i=0
while [ $i -lt $len ]; do
NAME="$MBD/${INSERT_DB_NAME[$i]}.sql"
if [ -e $NAME ]; then
$MYSQL -u${INSERT_DB_USER[$i]} -p${INSERT_DB_PASS[$i]} -h${INSERT_DB_HOST[$i]} ${INSERT_DB_NAME[$i]} < $NAME 2>> $LOG_FILE
#echo "$MYSQL -u${INSERT_DB_USER[$i]} -p${INSERT_DB_PASS[$i]} -h${INSERT_DB_HOST[$i]} ${INSERT_DB_NAME[$i]} < $NAME"
logIt "IMPORT TO ${INSERT_DB_NAME[$i]}"
else
logIt "File $NAME not exist";
fi
let i++
done
}
check_dump()
{
FILE_TMP_DUMP="$MBD/tmp_dump_${INSERT_DB_NAME[0]}.sql";
FILE_DIFF_RESS="$MBD/diff_res.diff"
tmp_tables=`build_tables ${INSERT_DB_PREFIX[0]}`
($MYSQLDUMP -u ${INSERT_DB_USER[0]} -h ${INSERT_DB_HOST[0]} -p${INSERT_DB_PASS[0]} ${INSERT_DB_NAME[0]} $tmp_tables 2>>$LOG_FILE) > $FILE_TMP_DUMP
DIFF="$(which diff)"
$DIFF $FILE $FILE_TMP_DUMP > FILE_DIFF_RESS
[ -s "$SMB/diff_res.diff" ];
SUCCESS=$?
eval $RM -f $FILE_TMP_DUMP $FILE_DIFF_RESS
return $SUCCESS
}
if check_dump; then
input_to_mysql
else
logIt "No need to dump"
fi
so run like dump.sh -c config -l log.file
Where config like this:
MyHOST="master_host"
MyUSER="master_user"
MyPASS="master_password"
DB_NAME="master_db_name"
DB_PREFIX="master_db_prefix_" # leave empty if you haven't table prefix
TABLES="table1 table2 table3" // list of tables - leave empty for all tables
###############################
INSERT_DB_NAME=(slave_dbname1 slave_dbname2)
INSERT_DB_HOST=(slave_host1 slave_host2)
INSERT_DB_USER=(slave_user1 slave_user2)
INSERT_DB_PASS=(slave_pass1 slave_pass2)
INSERT_DB_PREFIX=(slave_db_prefix1 slave_db_prefix1) //
I putted it to cron and all works fine for me.
Of course you can do all this manually ...
The word you are looking for, is Replication. It's not real time, but almost.
Related
I have available 2 packages with name:
package1
package2
Currently I have bash script set for one package:
if [[ $package1 == 'OFF' ]]; then
exit 0;
else
.......
......
......
do something
......
.....
.....
EOF
chown $username. /home/$username/domains/$domain/public_html/.htaccess
fi
Now when this package is OFF then we this script exit. Correct.
ok, but I want to run the code now depending on which option is enabled.
I try somelike this:
### START THIS CODE RUN ONLY WHEN PACKAKGE1 IS ON
if [[ $package1 == 'ON' ]]; then
.......
......
......
do something
......
.....
.....
EOF
chown $username. /home/$username/domains/$domain/public_html/.htaccess
fi
### END
### START THIS CODE RUN ONLY WHEN PACKAKGE2 IS ON
elseif [[ $package2 == 'ON' ]]; then
.......
......
......
do something
......
.....
.....
EOF
chown $username. /home/$username/domains/$domain/public_html/.htaccess
fi
But I guess I'm doing something wrong. Can someone please help me to do this. If the given option is enabled, it only wants to execute the code for the given option and skip the other codes.
When pkg 1 and 2 are ON, only 1 will executed:
if [ "$package1" = "ON" ]; then
chown...
elif [ "$package2" = "ON" ]; then
chown...
fi
When pkg 1 and 2 are ON, both will executed:
if [ "$package1" = "ON" ]; then
chown...
fi
if [ "$package2" = "ON" ]; then
chown...
fi
I've got a PHP script that calls the system shell with a piped command. In this case we're talking about a backup script (but it could be anything, I'm asking specifically about the exit status!):
exec(
"mysqldump --user=$u --password=$p --host=$h --port=$p $db | gzip -9 > backup.sql.gz",
$out,
$status
);
Now I want to know if the mysqldump command yielded an error, but the $status variable always seems to contain 0, even if I force an error. It appears to be the exit code of the second command (gzip in this case). I want to be able to see the exit status of the first command in PHP.
You'll need a little help from the Bash internal array PIPESTATUS. This holds the exit status of each command in the pipe. Since you're looking for the first command's exit status you would be addressing PIPESTATUS[0]. So you're code would look like:
exec(
"bash -c 'mysqldump --user=$u --password=$p --host=$h --port=$p $db | gzip -9 > backup.sql.gz; exit \${PIPESTATUS[0]}'",
$out,
$status
);
Note, this changes the overall exit status of the exec() call and you'll need additional code if you want to catch a failure in a longer chain of commands.
I've managed to think of a more generic solution that makes the exit status of each command in the pipe available to PHP. Of course it requires a shell with $PIPESTATUS (this excludes plain sh).
// The command with pipes.
$command = 'command1 | command2 | echo Test | gzip -9 -f';
// Execute the command. The overall exit code is in $exitStatus.
exec(
$command . '; echo -e "\n"${PIPESTATUS[*]}',
$out,
$exitStatus
);
// Get the exit statuses and remove them from the output.
$pipeStatus = explode(' ', array_pop($out));
print_r([$pipeStatus, $out]);
// [
// [
// "127",
// "127",
// "0",
// "0",
// ],
// [
// b"\x1F‹\x089fÙW\x02I-.á\x02Â\x1Axú\x05",
// ],
// ]
Slightly simpler variant if you're sure the piped commands will end with a newline (notice the echo part in the command is different):
// The command with pipes.
$command = 'command1 | command2 | echo Testing things | sed s/things/stuff/';
// Execute the command. The overall exit code is in $exitStatus.
exec(
$command . '; echo ${PIPESTATUS[*]}',
$out,
$exitStatus
);
// Get the exit statuses and remove them from the output.
$pipeStatus = explode(' ', array_pop($out));
print_r([$pipeStatus, $out]);
// [
// [
// "127",
// "127",
// "0",
// "0",
// ],
// [
// "Testing stuff",
// ],
// ]
I have 3 scripts (I have removed the help_page function from the networkstats.sh script when I pasted here to save some space):
api3.php
<?php
output = shell_exec('/bin/bash /usr/share/nginx/status/getnetworkstatsin.sh');
echo $output;
?>
getnetworkstatsin.sh
#!/bin/bash
ssh -i /tmp/id_rsa1 root#centos7clone bash -s -- -I < ./networkstats.sh
networkstats.sh
#!/bin/bash
interface=enp0s3
read -r inbytesold outbytesold < <(awk -v dev="^$interface:" '$1 ~ dev {
sub(/[^:]*:/,""); print $1, $9; exit }' /proc/net/dev)
sleep 1
read -r inbytesnew outbytesnew < <(awk -v dev="^$interface:" '$1 ~ dev {
sub(/[^:]*:/,""); print $1, $9; exit }' /proc/net/dev)
kilobitsin=$(( ( ( inbytesnew - inbytesold ) * 8 ) / 1024 ))
kilobitsout=$(( ( ( outbytesnew - outbytesold ) * 8 ) / 1024 ))
show_outgoing() {
echo $kilobitsout
}
show_all() {
echo "kilobits in: $kilobitsin"
echo "kilobits out: $kilobitsout"
}
if [[ $# -eq 0 ]];
then
help_page
exit 1
fi
for arg in "$#"
do
case $arg in
-h|--help)
help_page
;;
-I)
show_incoming
;;
-O)
show_outgoing
;;
-A|--all)
show_all
;;
esac
done
The problem I have is that when I execute the api3.php script from console, it is able to execute and return a value.
However when I try and execute from a webpage it fails to return anything.
I believe it is not even executing when I load it via the webpage by navigating to localhost/api3.php. Can someone help, what is the reason behind this? I have added
nginx ALL=NOPASSWD: /usr/share/nginx/status/getnetworkstatsin.sh
To my visudo section, I have tried to change permissions of all files involved to 777 (temporally) without success.
EDIT: I should also mention that all these scripts are located inside /usr/share/nginx/status which nginx has access to.
I can't find the error, the scripts runs fine from console, I thought it was PHP thing but couldn't fine anything.
Maybe permissions things? Exec things? I really don't know much, hope someone can help me. Thanks!
BASH Script (SIMPLY SENDS A JOB TO A PRINTER, but I put it enterely just in case):
#!/bin/bash
PBOX_DIR_TMP="/tmp"
DESDE=$1
HASTA=$2
FORMULARIO=$3
COLA=$4
FECHA=$(date +%F)
SPOOL="/spool.$$.txt"
ARCHIVOSALIDA="${PBOX_DIR_TMP}"/salida.$$.txt
RETURNCODE=0
echo "$DESDE"
echo "$HASTA"
echo "#PBSSFORM ${FORMULARIO}" > "${SPOOL}"
for ((i = ${DESDE};i <= ${HASTA};i++))
do
if [ $i > ${DESDE} ]
then
echo -e "\f${FECHA}" >> "${SPOOL}"
echo "${i}" >> "${SPOOL}"
else
echo "${FECHA}" >> "${SPOOL}"
echo "${i}" >> "${SPOOL}"
fi
done
cat "${SPOOL}" | pboxsvc ${PBOX_DIR_BIN}/pboxlib.bin AplicarHostForm > "${ARCHIVOSALIDA}"
lp -d "${COLA}" "${ARCHIVOSALIDA}"
RETURNCODE=$?
rm "${ARCHIVOSALIDA}"
rm "${SPOOL}"
if [ ${RETURNCODE} -eq 0 ]
then
exit 1
else
exit 0
fi
PHP call:
$cmd = "/printb/imprimirFormPlano.bin 1 2 FILE.PS Cola1";
Apache Log:
/printb/imprimirFormPlano.bin 1: Syntax error: ")" unexpected
sh: 2: not found.
The scripts works if I call it from shell like this: ./printb/imprimirFormPlano.bin 1 2 FILE.PS Cola1
It looks like your apache's default shell is sh rather than bash. Try changing your command to
$cmd = '/bin/bash /printb/imprimirFormPlano.bin 1 2 FILE.PS Cola1';
I have a PHP script that gets passed the MySQL connection details of a remote server and I want it to execute a mysqldump command. To do this I'm using the php exec() function:
<?php
exec("/usr/bin/mysqldump -u mysql-user -h 123.145.167.189 -pmysql-pass database_name > /path-to-export/file.sql", $output);
?>
When the right login details are passed to it, it'll work absolutely fine.
However, I'm having trouble checking if it executes as expected and if it doesn't finding out why not.
The $output array returns as empty, whereas if I run the command directly on the command line a message is printed out telling me the login failed. I want to capture such error messages and display them. Any ideas on how to do that?
You should check the third parameter of exec function: &$return_var.
$return_var = NULL;
$output = NULL;
$command = "/usr/bin/mysqldump -u mysql-user -h 123.145.167.189 -pmysql-pass database_name > /path-to-export/file.sql";
exec($command, $output, $return_var);
By convention in Unix a process returns anything other than 0 when something goes wrong.
And so you can:
if($return_var) { /* there was an error code: $return_var, see the $output */ }
The solution I found is to run the command in a sub-shell and then output the stderr to stdout (2>&1). This way, the $output variable is populated with the error message (if any).
i.e. :
exec("(mysqldump -uroot -p123456 my_database table_name > /path/to/dump.sql) 2>&1", $output, $exit_status);
var_dump($exit_status); // (int) The exit status of the command (0 for success, > 0 for errors)
echo "<br />";
var_dump($output); // (array) If exit status != 0 this will handle the error message.
Results :
int(6)
array(1) { [0]=> string(46) "mysqldump: Couldn't find table: "table_name"" }
Hope it helps !
Because this line redirect the stdout output > /path-to-export/file.sql
try this,
<?php
exec("/usr/bin/mysqldump -u mysql-user -h 123.145.167.189 -pmysql-pass database_name", $output);
/* $output will have sql backup, then save file with these codes */
$h=fopen("/path-to-export/file.sql", "w+");
fputs($h, $output);
fclose($h);
?>
I was looking for the exact same solution, and I remembered I'd already solved this a couple of years ago, but forgotten about it.
As this page is high in Google for the question, here's how I did it:
<?php
define("BACKUP_PATH", "/full/path/to/backup/folder/with/trailing/slash/");
$server_name = "your.server.here";
$username = "your_username";
$password = "your_password";
$database_name = "your_database_name";
$date_string = date("Ymd");
$cmd = "mysqldump --hex-blob --routines --skip-lock-tables --log-error=mysqldump_error.log -h {$server_name} -u {$username} -p{$password} {$database_name} > " . BACKUP_PATH . "{$date_string}_{$database_name}.sql";
$arr_out = array();
unset($return);
exec($cmd, $arr_out, $return);
if($return !== 0) {
echo "mysqldump for {$server_name} : {$database_name} failed with a return code of {$return}\n\n";
echo "Error message was:\n";
$file = escapeshellarg("mysqldump_error.log");
$message = `tail -n 1 $file`;
echo "- $message\n\n";
}
?>
It's the --log-error=[/path/to/error/log/file] part of mysqldump that I always forget about!
As exec() is fetching just stdout which is redirected to the file, we have partial or missing result in the file and we don't know why. We have to get message from stderr and exec() can't do that. There are several solutions, all has been already found so this is just a summary.
Solution from Jon: log errors from mysqldump and handle them separately (can't apply for every command).
Redirect outputs to separate files, i.e. mysqldump ... 2> error.log 1> dump.sql and read the error log separately as in previous solution.
Solution from JazZ: write the dump as a subshell and redirect stderr of the subshell to stdout which can php exec() put in the $output variable.
Solution from Pascal: better be using proc_open() instead of exec() because we can get stdout and stderr separately (directly from pipes).
write below code to get the database export in .sql file.
<?php exec('mysqldump --user=name_user --password=password_enter --host=localhost database_name > filenameofsql.sql'); ?>