I’ve written a script to enable me to edit a simple TSV file and it seems to work except that having updated the file I get a PHP warning when it displays the data for editing.
First time through there is no warning; second and subsequent times I get the warning. If I press update without making any changes the “before” and “after” versions of the TSV file look identical in Notepad++ - but there is clearly some difference.
Here is my code:
function readtsvfile($file) {
// Read tsv file into array
$handle = fopen($file, 'r');
while ( !feof($handle) )
$array[] = fgetcsv($handle, 1024, "\t");
fclose($handle);
return $array;
}
$file = '../accounts-copy.tsv';
// values may have been modified - write updated file
if ( $_SERVER['REQUEST_METHOD'] == 'POST' ) {
$data = readtsvfile($file);
$handle = fopen($file, 'w');
foreach ( $_POST['cell'] as $k1 => $row ) {
$line = $data[$k1][0] . "\t";
foreach ( $row as $k2 => $val )
$line .= $val . "\t";
fwrite($handle, rtrim($line).PHP_EOL);
}
fclose($handle);
echo 'File updated', "\n";
}
// display file contents for editing
$data = readtsvfile($file);
echo '<form method="post">', "\n";
echo '<table>', "\n";
foreach ( $data as $k1 => $row ) {
echo ' <tr>', "\n"; # line 34
foreach ( $row as $k2 => $val ) {
if ( $k2 == 0 )
$val = htmlentities($val);
if ( $k2>0 )
echo ' <td><input type="text" name="cell[', $k1, '][', $k2, ']" value="', $val, '"></td>', "\n";
else
echo ' <td>', $val, '</td>', "\n";
}
echo ' </tr>', "\n";
}
echo '</table>', "\n";
echo '<input type="submit" value="Update">', "\n";
echo '</form>', "\n";
The warning is: Warning: Invalid argument supplied for foreach() in editcsv.php on line 34.
My unadulterated TSV file is attached (although I have had to change the extension to csv to upload).
accounts-copy.csv (490 Bytes)
Well, the obvious thing to do is logging (resp. looking, if you have remote debugging) what the variable in question actually contains.
1 Like
Thanks @Dormilich . I had been var_dumping $data and noticed no difference between “before” and “after”. Now when I var_dump $row AND look in the right place I see my edited file has an end of line at the end which the original doesn’t have.
The problem was an extra blank line being added to the end of the CSV file when it was updated
Try this:
<?php
# ERRORS VERBOSE
declare(strict_types=1);
$tmp = 'ERROR_LOG.php';
ini_set('error_log', $tmp );
ini_set('log_errors', 'true');
ini_set('html_errors', 'true');
ini_set('track_errors', 'true');
ini_set('display_errors', 'true');
ini_set('display_startup_errors', 'true');
error_reporting(-1);
# File Name
$file = 'accounts-copy.tsv';
$file = 'accounts-copy.csv'; //
# values may have been modified - write updated file
if ( $_SERVER['REQUEST_METHOD'] == 'POST' )
{
# fred($_POST, 'Just Posted');
$data = readtsvfile($file);
$handle = fopen($file, 'w');
foreach ( $_POST['cell'] as $k1 => $row )
{
$line = $data[$k1][0] . "\t";
foreach ( $row as $k2 => $val )
{
$line .= $val . "\t";
}
fwrite($handle, rtrim($line).PHP_EOL);
}
fclose($handle);
echo 'File updated', "\n";
}
# display file contents for editing
$data = readtsvfile($file);
echo '<form method="post">', "\n";
echo '<table>', "\n";
foreach ( $data as $k1 => $row )
{
echo ' <tr>', "\n"; # line 34
foreach ( $row as $k2 => $val )
{
if ( $k2 === 0 )
{
$val = htmlentities($val);
echo '<td>', $val, '</td>', "\n";
}else{
echo '<td><input type="text" name="cell[', $k1, '][', $k2, ']" value="', $val, '"></td>', "\n";
}
}#endif
echo ' </tr>', "\n";
}#endforeach
echo '</table>', "\n";
echo '<input type="submit" value="Update">', "\n";
echo '</form>', "\n";
//===============================================
function readtsvfile($file)
{
$array = [];
// Read tsv file into array
$handle = fopen($file, 'r');
while ( !feof($handle) )
{
$tmp = fgetcsv($handle, 1024, "\t");
if( $tmp ):
$array[] = $tmp;
else:
echo '<h1> Yes we have NO fgetcsv(...) <br>' ; // fred($tmp)';
echo 'line: ' .__line__;
echo '<br>';
echo '</h1>';
endif;
}
fclose($handle);
return $array;
}
//===============================================
function fred($val, $title='')
{
echo '<pre>'; echo $title .'<br>';
print_r($val);
echo '</pre>';
}
1 Like
Gandalf
Closed
September 11, 2017, 4:45pm
5
This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.