This is a discussion on Blank line at beginning of XML Doc within the PHP Language forums, part of the PHP Programming Forums category; Hi. First I apologise if there is a better place to post this. Please let me know. I also apologise ...
|
|||||||
| FAQ | Members List | Calendar | Search | Today's Posts | Mark Forums Read |
|
|||
|
Hi.
First I apologise if there is a better place to post this. Please let me know. I also apologise in advance if this is a really stupid mistake, but now seem to be bashing head against wall. I have some code that is creating an xml doc $dom = new DOMDocument(); $xmlDoc = $dom->appendChild($dom->createElement('root')); etc. that is then echo d $dom->formatOutput = true; ob_clean(); $dom->save('php://output'); also tried echo $dom->saveXML(); and it results in (inside the -----) ---------------------------------------------------------------------------------------------------- <?xml version="1.0" encoding="utf-8"?> <root> <user id="9"> <firstname>Tim</firstname> <lastname>D</lastname> <email></email> <houseName>The Station</houseName> <houseNo>259</houseNo> <street>Waterloo Rd</street> <village>Waterloo</village> <town>London</town> <county>London</county> <postcode>SE1 8RW</postcode> </user> </root> ----------------------------------------------------------------------- Which looks a bit odd - in Firefox there is a blank line before the xml and I get the message (By the time it gets back to login.php it has gone back through a HTTPResponse body. Warning: DOMDocument::loadXML() [function.DOMDocument-loadXML]: XML declaration allowed only at the start of the document in Entity, line: 2 in /web/zzz/login.php on line 40 Which makes me think the newline at the beginning is causing the problem Any ideas ? Thanks for any help |
|
|||
|
djaekimaar@googlemail.com wrote:
> Hi. > First I apologise if there is a better place to post this. Please let > me know. I also apologise in advance if this is a really stupid > mistake, but now seem to be bashing head against wall. > I have some code that is creating an xml doc > > $dom = new DOMDocument(); > $xmlDoc = $dom->appendChild($dom->createElement('root')); > etc. > > that is then echo d > > $dom->formatOutput = true; > ob_clean(); > $dom->save('php://output'); > > also tried > echo $dom->saveXML(); > > and it results in (inside the -----) > ---------------------------------------------------------------------------------------------------- > <?xml version="1.0" encoding="utf-8"?> > <root> > <user id="9"> > <firstname>Tim</firstname> > <lastname>D</lastname> > <email></email> > <houseName>The Station</houseName> > > <houseNo>259</houseNo> > <street>Waterloo Rd</street> > <village>Waterloo</village> > <town>London</town> > <county>London</county> > <postcode>SE1 8RW</postcode> > > </user> > </root> > > ----------------------------------------------------------------------- > Which looks a bit odd - in Firefox there is a blank line before the > xml > and I get the message (By the time it gets back to login.php it has > gone back through a HTTPResponse body. > > Warning: DOMDocument::loadXML() [function.DOMDocument-loadXML]: XML > declaration allowed only at the start of the document in Entity, line: > 2 in /web/zzz/login.php on line 40 > Which makes me think the newline at the beginning is causing the > problem > > Any ideas ? > Thanks for any help > It's impossible to tell from just limited excerpts of your code that you posted. It could be almost anything. First thing I would suggest is look for any white space outside of the <?php ... ?> tags - this includes new lines, etc. For instance, if you include another php file, do you have a newline after the php end tag? Otherwise, please put together a *small* example which shows the problem and post it here so we can look at it more closely. -- ================== Remove the "x" from my email address Jerry Stuckle JDS Computer Training Corp. jstucklex@attglobal.net ================== |
|
|||
|
Hi - sorry its taken a while to get back. Combination of a short hol
and trying to solve it myself. The set up I have is as follows (Its complicated due to trying to use a sort of MVC and REST) A Link from a homepage to login.php Logon.php then creates a verification class that takes the email address and checks against a db. This returns a userid that is then used in a call to UserProfile. In UserProfile I am trying to use REST so I have the following code public function exec($u) { //print 'In user profile'; $req =& new HTTP_Request("http://localhost/sbc/dbCaller/user/$u"); $req->addHeader('HTTP_ACCEPT', 'application/xml,application/xhtml +xml,application/xml;q=0.9,*/*;q=0.8'); if (!PEAR::isError($req->sendRequest())) { req->getResponseBody(); Using apache readback this gets caught by dbCaller dbCaller is just a handler that at the moment just creates a test class (see below) Test uses the rest of the url to work out what it needs to return and creates a DOM object of the xml. The creation seems to work ok, no exceptions. and the return to dbCaller results in a DOMDocument object in dbCaller. But it then falls down . I dont seem to be able to get the DOMDocument object back through the http response. (In UserProfile) Have tried creating a DOMDocument object and loading the responsebody into it - doesnt work. In fact I dont seem to be able to send a DOMDocument back through the response, and am begining to think its not possible. Am new to this and may be missing something v obvious. Any comments of any sort welcome :-) test class <?php /* * Created on 4 Aug 2008 * * To change the template for this generated file go to * Window - Preferences - PHPeclipse - PHP - Code Templates */ require_once ('Database.php'); // Standard functions. class test { function exec() { $conn = new dbConnection; $c = $conn->getConn(); //print 'In test'; $urlString = substr($_SERVER['REQUEST_URI'], strlen('/sbc/ dbCaller')); $urlParts = explode('/', $urlString); //create an array of the parts after the base url $lastPart = array_pop($urlParts); //get the last one $dotPosition = strpos($lastPart, '.'); // figure out what extension is required if ($dotPosition !== FALSE) { $this->extension = substr($lastPart, $dotPosition + 1); $lastPart = substr($lastPart, 0, $dotPosition); } array_push($urlParts, $lastPart); if (isset($urlParts[0]) && $urlParts[0] == '') { array_shift($urlParts); } if (isset($urlParts[0])) $this->table = $urlParts[0]; $sql = 'SELECT * FROM '. $this->table; $row = $c->query($sql); $res = $row->fetch(PDO::FETCH_ASSOC); $arr = array_keys($res); $cols = $row->columnCount(); if (count($urlParts) > 1 && $urlParts[1] != '') { array_shift($urlParts); $arrCount = count($urlParts); foreach ($urlParts as $uid) { if ($uid != '') { //print $uid; $this->uid[] = $uid; } } } //build the query $sql2 = 'SELECT * FROM '. $this->table; //print 'Arr' . $arrCount; if ($arrCount >= 1) { $sql2 .= ' WHERE ' . $arr[0] . ' = ' . $this->uid[0]; if ($arrCount >= 2) { for ($f=1; $f<=($arrCount-1); $f++) { $sql2 .= ' AND ' . $arr[$f] . ' = ' . $this->uid[$f]; } } } //print 'SQL' . $sql2; $dom = new DOMDocument(); $xmlDoc = $dom->appendChild($dom->createElement('root')); foreach ($c->query($sql2) as $row2) { $rec = $xmlDoc->appendChild($dom->createElement($this->table)); $rec->setAttribute($arr[0], $row2[$arr[0]]); for ($i= 1; $i< $cols; $i++) { if ($arr[$i] != 'password') { $rec->appendChild($dom->createElement($arr[$i], $row2[$arr[$i]])); } } } $dom->formatOutput = true; //ob_clean(); //$dom->save('php://output'); //$p = $dom->saveXML(); return $dom; //print $p; } } ?> |
|
|||
|
djaekimaar@googlemail.com wrote:
> Hi - sorry its taken a while to get back. Combination of a short hol > and trying to solve it myself. > The set up I have is as follows (Its complicated due to trying to use > a sort of MVC and REST) > A Link from a homepage to login.php > > Logon.php then creates a verification class that takes the email > address and checks against a db. This returns a userid that is then > used in a call to UserProfile. > > In UserProfile I am trying to use REST so I have the following code > > public function exec($u) { > > //print 'In user profile'; > $req =& new HTTP_Request("http://localhost/sbc/dbCaller/user/$u"); > $req->addHeader('HTTP_ACCEPT', 'application/xml,application/xhtml > +xml,application/xml;q=0.9,*/*;q=0.8'); > > > if (!PEAR::isError($req->sendRequest())) { > req->getResponseBody(); > > Using apache readback this gets caught by dbCaller > dbCaller is just a handler that at the moment just creates a test > class (see below) > Test uses the rest of the url to work out what it needs to return and > creates a DOM object of the xml. > The creation seems to work ok, no exceptions. and the return to > dbCaller results in a DOMDocument object in dbCaller. > But it then falls down . I dont seem to be able to get the > DOMDocument object back through the http response. (In UserProfile) > Have tried creating a DOMDocument object and loading the responsebody > into it - doesnt work. In fact I dont seem to be able to send a > DOMDocument back through the response, and > am begining to think its not possible. Am new to this and may be > missing something v obvious. > > Any comments of any sort welcome :-) > > test class > > <?php > /* > * Created on 4 Aug 2008 > * > * To change the template for this generated file go to > * Window - Preferences - PHPeclipse - PHP - Code Templates > */ > require_once ('Database.php'); // Standard functions. > > class test { > function exec() { > $conn = new dbConnection; > $c = $conn->getConn(); > //print 'In test'; > > $urlString = substr($_SERVER['REQUEST_URI'], strlen('/sbc/ > dbCaller')); > > $urlParts = explode('/', $urlString); //create an array of the parts > after the base url > > > $lastPart = array_pop($urlParts); //get the last one > > $dotPosition = strpos($lastPart, '.'); // figure out what > extension is required > if ($dotPosition !== FALSE) { > $this->extension = substr($lastPart, $dotPosition + 1); > $lastPart = substr($lastPart, 0, $dotPosition); > } > array_push($urlParts, $lastPart); > > if (isset($urlParts[0]) && $urlParts[0] == '') { > array_shift($urlParts); > } > > if (isset($urlParts[0])) $this->table = $urlParts[0]; > $sql = 'SELECT * FROM '. $this->table; > $row = $c->query($sql); > $res = $row->fetch(PDO::FETCH_ASSOC); > $arr = array_keys($res); > $cols = $row->columnCount(); > > if (count($urlParts) > 1 && $urlParts[1] != '') { > array_shift($urlParts); > $arrCount = count($urlParts); > foreach ($urlParts as $uid) { > if ($uid != '') { > //print $uid; > $this->uid[] = $uid; > } > } > } > //build the query > $sql2 = 'SELECT * FROM '. $this->table; > //print 'Arr' . $arrCount; > if ($arrCount >= 1) { > $sql2 .= ' WHERE ' . $arr[0] . ' = ' . $this->uid[0]; > if ($arrCount >= 2) { > for ($f=1; $f<=($arrCount-1); $f++) { > $sql2 .= ' AND ' . $arr[$f] . ' = ' . $this->uid[$f]; > } > } > } > //print 'SQL' . $sql2; > $dom = new DOMDocument(); > $xmlDoc = $dom->appendChild($dom->createElement('root')); > foreach ($c->query($sql2) as $row2) { > $rec = $xmlDoc->appendChild($dom->createElement($this->table)); > $rec->setAttribute($arr[0], $row2[$arr[0]]); > for ($i= 1; $i< $cols; $i++) { > if ($arr[$i] != 'password') { > $rec->appendChild($dom->createElement($arr[$i], $row2[$arr[$i]])); > } > } > } > $dom->formatOutput = true; > //ob_clean(); > //$dom->save('php://output'); > //$p = $dom->saveXML(); > return $dom; > //print $p; > > } > } > ?> > > > Well, you showed your class Test, which you indicate is working properly. But you never showed how you're calling Test->exec() and trying to return the document back to the caller. But I'm wondering why you're using an HTTP_Request object here to fetch the document, when it's on your own server. You're just creating an additional load on the server. It would be more efficient to just create the object of Test and create the dom document right there. As it is, you have a huge security hole - what happens, for instance, if someone enters on their browser "http://www.example.com//sbc/dbCaller/user/joeblow"? But if you insist on doing it this way, you have to handle it just like you would a browser request. You need to echo (or print) the document. But you can't do that directly, i.e. you can't just say echo $dom; because it's not a simple object. You need to either serialize it (not recommended) or convert to xml and print the resulting xml. Then you can get the xml and convert it back to a DomDocument. -- ================== Remove the "x" from my email address Jerry Stuckle JDS Computer Training Corp. jstucklex@attglobal.net ================== |
|
|||
|
Thanks a lot for replying Jerry. You are right on all counts.
The idea was to use REST between MVC layers as well as externaly. Have trashed that idea for the reasons you mentioned, and I hope a better understanding of REST. You were also right about the security hole. Though I was aware of that and was planning to pass the headers from the originating request through and then have the lower classes verify by the digest in the same way. So thanks for that and thanks for bearing with me as I worked it out. I solved the problem by using dom->saveHTML() instead of dom- >saveXML() and then printing that. thanks again |