We have a a supplier that each Monday sends a list of new Devices/Parts these are then manually entered into a database.
I'd like to use PHP to read this file and update the appropriate datebase records. The database I can do, but how do I read the data from the file ?
System: Avro
Supplier: ABC Inc
Quantity: 1
Device: ICD
ID: PA-658_ao8uY
For Clarity: PA-658_AO8UY
Quantity: 10
Device: PSTHG
ID: tg675_0O09i8
For Clarity: TG675_0O09I8
The above is an example of what we get. The System is us, the supplier is them. There can be hundreds for Quantity, device ID, and clarity lines in the file we receive.
How do I take the system / supplier names to variables, then loop through each of the Quantity, Device, ID and Clarity entries ???
-
So your problem is reading the file, rather than parsing its contents?Álvaro González– Álvaro González2013年02月11日 09:38:19 +00:00Commented Feb 11, 2013 at 9:38
-
You could parse the file with RegEx, but I wouldn't call it reliable, since if the markup changes you might end up with malformed data in your database. I'd suggest contacting them and asking them to send the second file with data in better suitable format for parsing, say XML or JSON.Ranty– Ranty2013年02月11日 09:49:11 +00:00Commented Feb 11, 2013 at 9:49
-
Hi. sorry if I've worded this badly. The issue is getting the data out of the file so I can write it to a database.MacMan– MacMan2013年02月11日 09:49:30 +00:00Commented Feb 11, 2013 at 9:49
-
I suppose that problem lies in reading AND parsing the file. Could you ask your supplier to change this format? For example to CSV, XML, JSON? It would be much easier and better with some standard format to extract data from this.sebast26– sebast262013年02月11日 09:50:23 +00:00Commented Feb 11, 2013 at 9:50
-
is this format a stable one? liable to changes? because you cannot have a generic approach to this, you need a totally customized soloution.Kris– Kris2013年02月11日 09:53:26 +00:00Commented Feb 11, 2013 at 9:53
3 Answers 3
For this simple task you don't need regular expressions, the following code will do it.
$content = file_get_contents("file.txt");
$content = str_replace(Array("\r\n", "\r"), "\n", $content); // we only want unix linebreaks
$data = explode("\n\n", $content);
foreach($data as &$section) {
$lines = explode("\n", $section);
$section = Array();
foreach($lines as $line) {
$colon = strpos($line, ":");
$section[substr($line, 0, $colon)] = trim(substr($line, $colon + 1));
}
}
print_r($data);
Sample Output Data:
Array
(
[0] => Array
(
[System] => Avro
[Supplier] => ABC Inc
)
[1] => Array
(
[Quantity] => 1
[Device] => ICD
[ID] => PA-658_ao8uY
[For Clarity] => PA-658_AO8UY
)
[2] => Array
(
[Quantity] => 10
[Device] => PSTHG
[ID] => tg675_0O09i8
[For Clarity] => TG675_0O09I8
)
)
3 Comments
[0] => Array ( [System] => Avro [Supplier] => ABC Inc [Quantity] => 1 [Device] => ICD [ID] => PA-658_ao8uY [For Clarity] => PA-658_AO8UY ) $handle = fopen("your file ");
//counter
$i=0;
$rowContentPrec=array();
while (!feof($handle)) {
$rowContent=explode(':',fread($handle, 8192));
//get the system and provider
if($i==0){
$sytem=$rowContent[1];
}elseif($i==1){
$provider=$rowContent[1];
}elseif(isset($rowContent)){
//product
$rowContent=explode(':',fread($handle, 8192));
if($rowContentPrec[0]=='For Clarity'){
//save your product to database here and initialize the array with informations about one product
$contentArr=array();
}else{
$contentArr[$rowContent[0]]=$rowContent[1];
}
$rowContentPrec=$rowContent;
$i++;
}
}
fclose($handle);
Comments
If you can redefine the format of this file to something like this..
[Core]
System=Avro
Supplier=ABC Inc
[line1]
Quantity= 1
Device=ICD
ID=PA-658_ao8uY
For Clarity=PA-658_AO8UY
[line2]
Quantity=10
Device=PSTHG
ID=tg675_0O09i8
For Clarity: TG675_0O09I8
You can use parse_ini_file(file,true,INI_SCANNER_NORMAL) can give you a multi-dimensional array of all the data.
This is one alternate highly subjective solution you can use. I'm just assuming the format is stable one, and will hold for long.
<?php
$newStock = new NewStockUpdate($itemListFile);
//do anything with $newStock Object
class NewStockUpdate
{
private $System;
private $Supplier;
private $allUpdates;
function __construct($listFile)
{
$fileHandle = fopen( $listFile, "r" ) or die("Couldn't open Update file $listFile");
$lineSystem = explode(":",getLineData($fileHandle));
$lineSupplier = explode(":",getLineData($fileHandle));
$i=0;
while(true)
{
$allUpdates[$i] = new ItemData($fileHandle);
$i++;
}
}
function getSystem()
{
return $this->System;
}
function getSupplier()
{
return $this->Supplier;
}
function getUpdateList()
{
return $this->allUpdates;
}
}
class ItemData
{
public $Quantity;
public $Device;
public $ID;
public $ForClarity;
public $lastObject;
function __construct($filePointer)
{
try
{
$lineQuantity = explode(":",getLineData($filePointer));
$lineDevice = explode(":",getLineData($filePointer));
$lineID = explode(":",getLineData($filePointer));
$lineForClarity = explode(":",getLineData($filePointer));
$this->Quantity = $lineQuantity[1];
$this->Device = $lineDevice[1];
$this->ID = $lineID[1];
$this->ForClarity = $lineForClarity[1];
}
catch(Exception $e)
{
//log something
}
if(feof($filePointer))
{
$this->lastObject = true;
}
else
{
$this->lastObject=false;
}
function isLastRecord()
{
return $this->lastObject;
}
}
}
function getLineData($filePointer)
{
while(!feof($filePointer))
{
$data = fgets($filePointer);
if(empty($data)|| $data=='\n')
{
$data = fgets($filePointer);
}
else
{
return $data;
}
}
}
?>
I think the rest you can manage with thie class object. Adding these entries to db and all. You can create multiple NewStock object for various Suppliers. Hopes this helps