Capture SQL output in PHP script as timestamped file - php

I have a mysql query that runs in a php file that outputs a page of data. I need to somehow output that data to a file, to allow me to perform client side functions on that data as needed before exporting it for download.
I need the temporary file named as a timestamp. Im wondering if i should use the fopen to create the file with the name being something like echo date(), then fwrite = $mysql, then fclose?
Is this the correct way to do this?

The SELECT ... INTO OUTFILE statement is intended primarily to let you very quickly dump a table to a text file on the server machine.
Read the documentaiton here...
http://dev.mysql.com/doc/refman/5.0/en/select.html

You could definitely do it that way. If it works for your purposes, then I would consider it correct. Sounds like you've got a good handle on it.
$filename = time() . '.txt';
$fp = fopen($filename,'w');
fputs($fp,$mysql);
fclose($fp);
If you want the filename with actual date numbering instead of a UNIX timestamp, use this instead:
$filename = date('YmdHis').'.txt';
You'll have to get your data into an exportable format of course... the code above assumes that $mysql contains your data and not just a query resource.

Related

how to convert the file content to byte array with php

I want to save (insert) a uploaded file to a database with PHP, which the type of the database filed is varbinary.
Finally I want to have the content of VarBinary (output) like when file is read in C# and then is stored in byte array and array is inserted to VarBinary.
Also my connection to the database is with sqlsrv.
The type of my files are just PDF and images.
I try this code but my output is different with the output of C#:
$handle=#fopen($_FILES["my_file"]["tmp_name"], 'rb');
$content= file_get_contents($_FILES["my_file"]["tmp_name"]);
$content = unpack("N*",$content);
$content= implode($content);
$sql = "INSERT INTO files (file_data) VALUES (CONVERT(varbinary(MAX)?)";
$params=array();
array_push($params,$content);
$table=sqlsrv_query( $conn, $sql, $params);
"$conn" is the name of my connection that works correctly.
PHP doesn't have a "byte array" data type. What it has is a string type, which is a byte array for all intents and purposes. To read the binary content of a file into a variable which is as close to a byte array as you'll ever get in PHP, do:
$content = file_get_contents($_FILES['my_file']['tmp_name']);
Yup, that's it. Nothing more to do.
I'm not particular familiar with the sqlsrv API, but perusing its documentation it appears that you can (need to?) set a flag this way to flag the data as being binary:
sqlsrv_query($conn, 'INSERT INTO files (file_data) VALUES (?)', array(
array($content, SQLSRV_PARAM_IN, SQLSRV_PHPTYPE_STRING, SQLSRV_SQLTYPE_BINARY)
));
I propose to always convert your binary data to base64.
So it can be stored in database easily and also it can be transfered from somewhere to anywhere with minimum headache!
$handle=#fopen($_FILES["my_file"]["tmp_name"], 'rb');
$elephantContent = file_get_contents($_FILES["my_file"]["tmp_name"]);
$rabbitContent = base64_encode($elephantContent);
//Now ...
$sql = "INSERT INTO files (file_data) VALUES (?)";
sqlsrv_query($conn , $sql , array($rabbitContent) );
file_data field in files table can be varchar, varbinary, blob, text ! :)
Now it can be invoked from database and be packed into a img tag directly.
<img src="data:image/jpeg;base64,PUT `file_data` CONTENTS HERE!" alt="..." />
You can store file type and alt properties in database and put them in tag.
You even can convert it to binary in database (if you insist on seeing binary data in db) (mysql 5.6+)
SELECT FROM_BASE64(`file_data`) as elephant_content from `files` WHERE ...
... And I'm pretty sure that there is equivalent method to do it so in SQL.
For example read this:
https://social.technet.microsoft.com/wiki/contents/articles/36388.transact-sql-convert-varbinary-to-base64-string-and-vice-versa.aspx

PHP/mySQL get_file_contents and update the column

I have a mySQL db table. One of the table columns contains URLs which point to different xml files on a remote server.
My goal is to read each URLs info and write the xml content into another column on the same record (line) respectively.
In my PHP code, I am able to get the URL correctly from mySQL database and I am able to get the XML content on remote server into a variable correctly.
But the issue is while I write the content to my table line by line. Some XML columns got update correctly and some XML columns are empty.
I am pretty sure each time the variable got content correctly because I am able to print out each individual content on screen.
Why are some content updating the column and some don't. All the XML strings have the same format. If I copied that content and updated the mysql table manually, it successfully wrote into the table.
At beginning I thought it was time issue so I add enough sleep time for my PHP code. it does't help. then I suspected my db datatype, so I changed the XML
column data type from VCHAR to TEXT and even LONGTEXT. it does't help either. Does any one have a clue?
part of my php code below...
$result = mysqli_query($con,"SELECT url_txt FROM mytable ");
//work with result line by line:
while($row = mysqli_fetch_array($result)) {
echo $url_content = file_get_contents($row['url_txt']);
//debug line below *******************************/
echo $URL=$row[url_txt];
//debug line above********************************/
mysqli_query($con,"UPDATE mytable SET xml_info='$url_content' where url_txt = '$URL' ");
}
Maybe try converting your XML to a native array and working with it that way:
$array = json_decode(json_encode(simplexml_load_string($url_content)),TRUE);

Get server time and date as string and pass it to txt file

I'm trying to get server date and time and send it to email or write to txt file from simple php form.
here is a sample of code
date_default_timezone_set('Europe/Zagreb');
$datum=date("y-m-d");
$upisufajl = ("\"{$_POST['firstName']}\",\"{$_POST['lastName']}\",\"{$_POST['email']}\",\"{$_POST['company']}\",\"{$_POST['datum']}\",\"{$_POST['oblik']}\",\"{$_POST['kategorija']}\",\"{$_POST['podkategorija']}\",\"{$_POST['message']}\"\n");
when do I need to write insted of {$_POST['datum']} to write date in txt file. everything elese works fine, but it doesnt show date.
echo date("r"); shows date and time correctly. do I need to convert it to string to be able to write it in txt file?
This is because $_POST['datum'] doesn't exist (at least that we can see in this code). It's just $datum.
$upisufajl = ("\"{$_POST['firstName']}\",\"{$_POST['lastName']}\",\"{$_POST['email']}\",\"{$_POST['company']}\",\"{$datum}\",\"{$_POST['oblik']}\",\"{$_POST['kategorija']}\",\"{$_POST['podkategorija']}\",\"{$_POST['message']}\"\n");
$datum has not been added to your variable $upisufajl. I assume $upisufajl is what you are writing to a text file.

Store BLOB-like data in PostgreSQL

I recently switched from MySQL to PostgreSQL. I have one problem left however.
Previously, I would store small images in the BLOB format in MySQL.
PostgreSQL doesn't know such thing as a BLOB.
I tried using BYTEA field type instead. This actually inserts an large (hexadecimal?) string I guess, but now I'm stuck trying to get this string back to displaying an actual image in PHP..
Any ideas? Thanks in advance.
Here is a piece of code I use to save the image in the database:
$data = bin2hex(file_get_contents('php://input'));
if (!empty($data)) {
$sql = "UPDATE asset SET data = X'%s' WHERE uuid = '%s'";
$args = array($data, $asset_uuid);
}
psql (9.1.3) and php 5.3.6 are used
Bytea is a byte array. It's not a bit pattern. See section 4.2.1.5 of PostgreSQL Lexical Structure.
The correct way to enter bytea is '\x...' with hex values. So what you want is SET data = '\x%s'.
You might also want to look into prepared statements with pg_prepare.
Edit: I was able to insert a (text) file into a bytea with this:
$source = file_get_contents( 'hello.php' );
$insert = pg_prepare( $conn, '', 'insert into t (name, data) values($1,$2)' );
pg_execute( $conn, '', array( 'hello.php', $source ) );
3rd Edit: This works fine to insert the file into the database. However, the pgsql driver in PHP is quite impolite. The only way to retrieve the actual data back is using the old bytea escape mechanism, as detailed here: pg_unescape_bytea.
pg_query('SET bytea_output = "escape";');
$result = pg_query( 'select data from t' );
while ( $row = pg_fetch_row( $result ) ) {
echo pg_unescape_bytea( $row[0] );
}
I'm sorry about how annoying this is. The PostgreSQL interface in PHP can do with some major overhaul for binary values.
To insert bytea contents with the pg_* API, the binary value should always be run through the pg_escape_bytea() function, even if it's passed to the pg_execute or pg_query_params functions.
This is because the pg_* layer doesn't "know" that a particular parameter has binary contents, and it does not implement any real support for parameter types anyway. So the text representation must be used. It can either be in the escape form or the hex form, it doesn't matter to the PG server, and it's independant of the value of bytea_output, which is meaningful only for values read from the server.
Example:
$esc=pg_escape_bytea("\000\001\002");
pg_query_params('INSERT INTO some_table(some_col) VALUES($1)', array($esc));
To read bytea contents with the pg_* API, the value must be run through pg_unescape_bytea() after the fetch. Assuming the client library is not older than 9.0 (libq.so.5.3 or higher), it can decode the contents whether it's in hex form or escape form and it will autodetect it. Only with an older library would it be necessary to force bytea_output to escape for it to decode properly, either dynamically with SET or statically for the whole database (ALTER DATABASE SET bytea_output=escape) or in postgresql.conf for the whole instance.
Example:
$p=pg_query("SELECT some_col FROM some_table WHERE...");
$r=pg_fetch_array($p);
$contents = pg_unescape_bytea($r[0]);
Both answers posted here gave me some thoughts, but none were 100% of the answer.
So, I will explain in this answer what I did to get it to work.
When displaying the image, I used this:
header('Content-Type: image/jpeg');
$data = pack("H*", pg_unescape_bytea($data));
echo $data;
I'm running PHP 5.3.8, in PHP 5.4.0 it turns out you can use hex2bin instead of pack.
When adding the image to the database, I used this:
$data = pg_escape_bytea($data); // Escape input for PostgreSQL
$sql = "UPDATE asset SET data = '%s'WHERE uuid = '%s'";
I'm glad it is working now. Thank you both Daniel and Johann!

How to current snapshot of MySQL Table and store it into CSV file(after creating it)?

I have large database table, approximately 5GB, now I wan to getCurrentSnapshot of Database using "Select * from MyTableName", am using PDO in PHP to interact with Database. So preparing a query and then executing it
// Execute the prepared query
$result->execute();
$resultCollection = $result->fetchAll(PDO::FETCH_ASSOC);
is not an efficient way as lots of memory is being user for storing into the associative array data which is approximately, 5GB.
My final goal is to collect data returned by Select query into an CSV file and put CSV file at an FTP Location from where Client can get it.
Other Option I thought was to do:
SELECT * INTO OUTFILE "c:/mydata.csv"
FIELDS TERMINATED BY ',' OPTIONALLY ENCLOSED BY '"'
LINES TERMINATED BY "\n"
FROM my_table;
But I am not sure if this would work as I have cron that initiates the complete process and we do not have an csv file, so basically for this approach,
PHP Scripts will have to create an CSV file.
Do a Select query on the database.
Store the select query result into the CSV file.
What would be the best or efficient way to do this kind of task ?
Any Suggestions !!!
You can use the php function fputcsv (see the PHP Manual) to write single lines of csv into a file. In order not to run into the memory problem, instead of fetching the whole result set at once, just select it and then iterate over the result:
$fp = fopen('file.csv', 'w');
$result->execute();
while ($row = $result->fetch(PDO::FETCH_ASSOC)) {
// and here you can simply export every row to a file:
fputcsv($fp, $row);
}
fclose($fp);

Categories