i'm working on setting up a page that uses PHP to layout the page, but i also need this PHP HTML code inserted into the PHP page for a search function. The search is done on a different page, and then the action is sent to the results page. I'm trying to get the PHP and HTML to mix together. I've tried using echo to no success. Basically i need the PHP HTML code to put the results into the $layout->content("");
<?php
require_once($_SERVER["DOCUMENT_ROOT"].'/layout/layout.inc.php');
require_once($_SERVER["DOCUMENT_ROOT"].'/functions/general.inc.php');
$layout = new default_layout();
$layout->title('IT KB Search');
$layout->content("<div class='border'>");
$layout->content('<h1>IT Support Knowledge Base - Search Results</h1>');
if (isset($_GET['q'])) {
$query = rawurlencode( strip_tags($_GET['q']));
$timestamp = time();
$baseUrl = 'https://oursite.atlassian.net/wiki';
$url = $baseUrl.'/rest/api/content/search?cql=space=KB%20AND%20type=page%20AND%20title~'.$query;
// To enable authenticated search:
// $url .= "&os_username=$username&os_password=$password";
$response = file_get_contents($url);
$response = json_decode($response);
$results = $response->results;
Echo '<div>';
Echo ' <ol>';
foreach($results as $item) {
Echo ' <li><strong><a href="';
$baseUrl. $item-> _links-> webui
Echo ' " target='_blank'>';
$item->title
Echo ' </a></strong></li>';
}
Echo ' </ol></div><hr>';
}
$layout->content("</div>");
$layout->render();
?>
You can to store the HTML to a string and then pass it to the $layout->content() function, like this...
<?php
require_once($_SERVER["DOCUMENT_ROOT"].'/layout/layout.inc.php');
require_once($_SERVER["DOCUMENT_ROOT"].'/functions/general.inc.php');
$layout = new default_layout();
$layout->title('IT KB Search');
$layout->content("<div class='border'>");
$layout->content('<h1>IT Support Knowledge Base - Search Results</h1>');
if (isset($_GET['q'])) {
$query = rawurlencode( strip_tags($_GET['q']));
$timestamp = time();
$baseUrl = 'https://oursite.atlassian.net/wiki';
$url = $baseUrl.'/rest/api/content/search?cql=space=KB%20AND%20type=page%20AND%20title~'.$query;
// To enable authenticated search:
// $url .= "&os_username=$username&os_password=$password";
$response = file_get_contents($url);
$response = json_decode($response);
$results = $response->results;
# Change Starts
$html = '<div>';
$html .= '<ol>';
foreach($results as $item) {
$html .= '<li><strong><a href="';
$html .= $baseUrl. $item-> _links-> webui;
$html .= '" target="_blank">';
$html .= $item->title;
$html .= '</a></strong></li>';
}
$html .= '</ol></div><hr>';
$html .= '</div>';
$layout->content($html);
# Change Ends
}
$layout->content('</div>');
$layout->render();
Related
I cannot find my second level node, the object is empty
include_once("simple_html_dom.php");
$simple = new simple_html_dom();
$simple->load("<div id='base'>divbase</div>");
$base = $simple->find("#base",0);
echo $simple->outertext."<br>";
echo "base=".$base->innertext."<br>";
$base->innertext .= "<div id='div_1_'>div1</div>";
$ch = $simple->save();
echo $ch."<br>";
$trouv = $simple->find('#div_1_',0);
$trouv->innertext .= "<div id='div_1_0_'>some text</div>";
$ch = $simple->save();
echo $ch."<br>";
the var $trouv is empty why?
I think that is because you add <div id='div_1_0_'>some text</div> to the innertext but that is not being parsed as html.
What you might do is load the modified html again using $simple->load($simple->save());
You code could look like:
$simple = new simple_html_dom();
$simple->load("<div id='base'>divbase</div>");
$base = $simple->find("#base",0);
echo $simple->outertext."<br>";
echo "base=".$base->innertext."<br>";
$base->innertext .= "<div id='div_1_'>div1</div>";
$simple->load($simple->save());
$ch = $simple->save();
echo $ch."<br>";
$trouv = $simple->find('#div_1_',0);
$trouv->innertext .= "<div id='div_1_0_'>some text</div>";
$ch = $simple->save();
echo $ch."<br>";
I have a site grabbing Confluence blogpost data. The API im using doesn't appear to have a sort feature. Can anyone help me get PHP sorting the posts on the page by the JSON date, i need the most recent first. Thanks!
<?php
require_once($_SERVER["DOCUMENT_ROOT"].'/layout/layout.inc.php');
require_once($_SERVER["DOCUMENT_ROOT"].'/functions/general.inc.php');
$layout = new my_layout();
$layout->title('IT KB Search');
$layout->content("<div class='border'>");
$layout->content('<h1>IT Support Knowledge Base - Search Results</h1>');
$baseUrl = 'https://website.atlassian.net/wiki';
$url = $baseUrl.'/rest/api/content?spaceKey=KB&type=blogpost&start=0&limit=10&expand=space,history,body.view,metadata.labels';
// To enable authenticated search:
// $url .= "&os_username=$username&os_password=$password";
$response = file_get_contents($url);
$response = json_decode($response);
$results = $response->results;
$html .= '<dl style=list-style: none;>';
foreach($results as $item) {
$date = $item-> history-> createdDate;
$html .= '<strong><a href="';
$html .= $baseUrl. $item-> _links-> webui;
$html .= '" target="_blank">';
$html .= $item->title;
$html .= ' - ';
$html .= date("d/m/Y",strtotime($date));
$html .= '</a></strong><br>';
$html .= $item->body-> view-> value;
$html .= '<br>';
}
$html .= '</dl>';
$layout->content($html);
$layout->content('</div>');
$layout->render();
Before foreach loop, you can use usort like this
usort($results, function ($a, $b) {
return strtotime($a->history->createdDate) - strtotime($b->history-> createdDate);
});
Once done, $result will have data in sorted order $a-$b will give you data in ascending order and $b-$a will give you data in descending order
You can try something like :-
function date_compare($a, $b)
{
$t1 = strtotime($a['datetime']);
$t2 = strtotime($b['datetime']);
return $t1 - $t2;
}
usort($results, 'date_compare');
You can declare the function date_compare in your php file and use the statement:-
usort($results, 'date_compare');
just before the for each loop
I've found a great tutorial on how to accomplish most of the work at:
https://www.developphp.com/video/PHP/simpleXML-Tutorial-Learn-to-Parse-XML-Files-and-RSS-Feeds
but I can't understand how to extract media:content images from the feeds. I've read as much info as i can find, but i'm still stuck.
ie: How to get media:content with SimpleXML
this suggests using:
foreach ($xml->channel->item as $news){
$ns_media = $news->children('http://search.yahoo.com/mrss/');
echo $ns_media->content; // displays "<media:content>"}
but i can't get it to work.
Here's my script and feed i'm trying to parse:
<?php
$html = "";
$url = "http://rssfeeds.webmd.com/rss/rss.aspx?RSSSource=RSS_PUBLIC";
$xml = simplexml_load_file($url);
for($i = 0; $i < 10; $i++){
$title = $xml->channel->item[$i]->title;
$link = $xml->channel->item[$i]->link;
$description = $xml->channel->item[$i]->description;
$pubDate = $xml->channel->item[$i]->pubDate;
$html .= "<a href='$link'><h3>$title</h3></a>";
$html .= "$description";
$html .= "<br />$pubDate<hr />";
}
echo $html;
?>
I don't know where to add this code into the script to make it work. Honestly, i've browsed for hours, but couldn't find working script that would parse media:content.
Can someone help with this?
========================
UPDATE:
Thanx to fusion3k, i got the final code working:
<?php
$html = "";
$url = "http://rssfeeds.webmd.com/rss/rss.aspx?RSSSource=RSS_PUBLIC";
$xml = simplexml_load_file($url);
for($i = 0; $i < 5; $i++){
$image = $xml->channel->item[$i]->children('media', True)->content->attributes();
$title = $xml->channel->item[$i]->title;
$link = $xml->channel->item[$i]->link;
$description = $xml->channel->item[$i]->description;
$pubDate = $xml->channel->item[$i]->pubDate;
$html .= "<img src='$image' alt='$title'>";
$html .= "<a href='$link'><h3>$title</h3></a>";
$html .= "$description";
$html .= "<br />$pubDate<hr />";
}
echo $html;
?>
Basically all i needed was this simple line:
$image = $xml->channel->item[$i]->children('media', True)->content->attributes();
Can't believe it was so hard for non techie to find this info online after reading dozens of posts and articles. Well, hope this will serve well for other folks like me :)
To get 'url' attribute, use ->attribute() syntax:
$ns_media = $news->children('http://search.yahoo.com/mrss/');
/* Echoes 'url' attribute: */
echo $ns_media->content->attributes()['url'];
// in php < 5.5: $attr = $ns_media->content->attributes(); echo $attr['url'];
/* Catches 'url' attribute: */
$url = $ns_media->content->attributes()['url']->__toString();
// in php < 5.5: $attr = $ns_media->content->attributes(); $url = $attr['url']->__toString();
Namespaces explanation:
The ->children() arguments is not the URL of your XML, it is a Namespace URI.
XML namespaces are used for providing uniquely named elements and attributes in an XML document:
<xxx> Standard XML tag
<yyy:zzz> Namespaced tag
└┬┘ └┬┘
│ └──── Element Name
└──────── Element Prefix (Namespace Identifier)
So, in your case, <media:content> is the “content” element of Namespace “media”. Namespaced elements must be have an associated Namespace URI, as attribute of a parent node or — most commonly — of the root element: this attribute has the form xmlns:yyy="NamespaceURI" (in your case xmlns:media="http://search.yahoo.com/mrss/" as attribute of root node <rss>).
Ultimately, the above $news->children( 'http://search.yahoo.com/mrss/' ) means “retrieve all children elements with http://search.yahoo.com/mrss/ as Namespace URI; an alternative — most intelligible — syntax is: $news->children( 'media', True ) (True means “regarded as a prefix”).
Returning to the code in example, the generic syntax to retrieve all first item's children with prefix media is:
$xml = simplexml_load_file( 'http://rssfeeds.webmd.com/rss/rss.aspx?RSSSource=RSS_PUBLIC' );
$xml->channel->item[0]->children( 'http://search.yahoo.com/mrss/' );
or (identical result):
$xml = simplexml_load_file( 'http://rssfeeds.webmd.com/rss/rss.aspx?RSSSource=RSS_PUBLIC' );
$xml->channel->item[0]->children( 'media', True );
Your new code:
If you want to show the <media:content url> thumbnail for each element in your page, modify the original code in this way:
(...)
$pubDate = $xml->channel->item[$i]->pubDate;
$image = $xml->channel->item[$i]->children( 'media', True )->content->attributes()['url'];
// in php < 5.5:
// $attr = $xml->channel->item[$i]->children( 'media', True )->content->attributes();
// $image = $attr['url'];
$html .= "<a href='$link'><h3>$title</h3></a>";
$html .= "<img src='$image' alt='$title'>";
(...)
Simple example for newbs like me:
$url = "https://www.youtube.com/feeds/videos.xml?channel_id=UCwNPPl_oX8oUtKVMLxL13jg";
$rss = simplexml_load_file($url);
foreach($rss->entry as $item) {
$time = $item->published;
$time = date('Y-m-d \ H:i', strtotime($time));
$media_group = $item->children( 'media', true );
$title = $media_group->group->title;
$description = $media_group->group->description;
$views = $media_group->group->community->statistics->attributes()['views'];
}
echo $time . ' :: ' . $title . '<br>' . $description . '<br>' . $views . '<br>';
I have a class that is building some HTML using data stored in an array. There are around 100 items in this array. Each item includes information like company name, a description, and flags for the different programming languages the company supports. I am doing string concatenation as I build the HTML for each item.
I have noticed that performance suddenly takes a huge hit when I append the programming language data. I see the page rendering timer jump from 0.15 secs to ~0.60 secs. This time includes grabbing the same data from the database each time. I can consistently get the performance to jump between these 2 times but commenting/uncommenting the following line of code:
$html .= '<div class="programmingLanguages"><strong>Programming Languages</strong> '.implode(', ', $progLanguagesArray).'</div>';
I've also been able to get the same performance drop by appending a long test string, something like this:
$html .= 'testtesttesttesttesttesttesttesttesttesttesttesttesttesttesttesttest';
What's especially bizarre is that I have another line of code that uses the same 'implode' function and does NOT make any significant difference in performance:
$html .= '<div class="integrationMethods"><strong>Integration Methods:</strong> '.implode(', ', $intMethodsArray).'</div>';
Does anybody have any insight into what might be going on here? I am doing tons of concatenation like this elsewhere in my code and haven't seen anything like this before. At this point, I'm stumped.
Here's the full class:
class DeveloperView {
public static function getHtml($developers) {
$html = '';
$html .= '<div>';
$html .= '<div>';
$count = 0;
foreach ($developers as $developer) {
$url = $developer['attributes']['url'];
$phone = $developer['attributes']['phone'];
$company = $developer['attributes']['desc'];
$active = $developer['attributes']['active'];
$desc = $developer['object_value'];
$intMethodsArray = array();
if ($developer['attributes']['m1']) { $intMethodsArray[] = 'method 1'; }
if ($developer['attributes']['m2']) { $intMethodsArray[] = 'method 2'; }
if ($developer['attributes']['m3']) { $intMethodsArray[] = 'method 3'; }
if ($developer['attributes']['m4']) { $intMethodsArray[] = 'method 4'; }
if ($developer['attributes']['m5']) { $intMethodsArray[] = 'method 5'; }
$progLanguagesArray = array();
if ($developer['attributes']['dotnet']) { $progLanguagesArray[] = '.Net (C# or VB.Net)'; }
if ($developer['attributes']['asp']) { $progLanguagesArray[] = 'Classic ASP'; }
if ($developer['attributes']['cf']) { $progLanguagesArray[] = 'Cold Fusion'; }
if ($developer['attributes']['java']) { $progLanguagesArray[] = 'Java'; }
if ($developer['attributes']['php']) { $progLanguagesArray[] = 'PHP'; }
if ($developer['attributes']['perl']) { $progLanguagesArray[] = 'Perl'; }
if ($developer['attributes']['other']) { $progLanguagesArray[] = 'Other'; }
$html .= '<div class="';
if ($count % 2 == 0) {
$html .= 'listingalt';
} else {
$html .= 'listing';
}
$html .= '">';
$html .= '<div class="developerPhone">'.$phone.'</div>';
$html .= '<a class="ext_link" target="_blank" href="'.$url.'">'.$company.'</a>';
$html .= '<div>';
if (!empty($intMethodsArray)) {
$html .= '<div class="integrationMethods"><strong>Integration Methods:</strong> '.implode(', ', $intMethodsArray).'</div>';
}
if (!empty($progLanguagesArray)) {
$html .= '<div class="programmingLanguages"><strong>Programming Languages</strong> '.implode(', ', $progLanguagesArray).'</div>';
}
$html .= '</div>';
$html .= '<p>'.$desc.'</p>';
$html .= '</div>'."\n";
$count++;
}
$html .= '</div></div>';
return $html;
}
}
Now that I can provide an answer, I'll just post my follow-up comment as the 'answer'...
I did indeed have a 'bug' in my timer, in that it was calculating the end processing time AFTER the echo of the HTML. So the amount of data being sent to the browser was effecting the processing time, where I was expecting to see the time spent processing BEFORE transmitting any data.
Thanks for taking the time to read my post... I'm trying to extract some information from my website using Simple HTML Dom...
I have it reading from the HTML source ok, now I'm just trying to extract the information that I need. I have a feeling I'm going about this in the wrong way... Here's my script...
<?php
include_once('simple_html_dom.php');
// create doctype
$dom = new DOMDocument("1.0");
// display document in browser as plain text
// for readability purposes
//header("Content-Type: text/plain");
// create root element
$xmlProducts = $dom->createElement("products");
$dom->appendChild($xmlProducts);
$html = file_get_html('http://myshop.com/small_houses.html');
$html .= file_get_html('http://myshop.com/medium_houses.html');
$html .= file_get_html('http://myshop.com/large_houses.html');
//Define my variable for later
$product['image'] = '';
$product['title'] = '';
$product['description'] = '';
foreach($html->find('img') as $src){
if (strpos($src->src,"http://myshop.com") === false) {
$src->src = "http://myshop.com/$src->src";
}
$product['image'] = $src->src;
}
foreach($html->find('p[class*=imAlign_left]') as $description){
$product['description'] = $description->innertext;
}
foreach($html->find('span[class*=fc3]') as $title){
$product['title'] = $title->innertext;
}
echo $product['img'];
echo $product['description'];
echo $product['title'];
?>
I put echo's on the end for sake of testing...but I'm not getting anything... Any pointers would be a great HELP!
Thanks
Charles
file_get_html() returns a HTMLDom Object, and you cannot concatenate Objects, although HTMLDom have __toString methods when there concatenated there more then lilly corrupt in some way, try the following:
<?php
include_once('simple_html_dom.php');
// create doctype
$dom = new DOMDocument("1.0");
// display document in browser as plain text
// for readability purposes
//header("Content-Type: text/plain");
// create root element
$xmlProducts = $dom->createElement("products");
$dom->appendChild($xmlProducts);
$pages = array(
'http://myshop.com/small_houses.html',
'http://myshop.com/medium_houses.html',
'http://myshop.com/large_houses.html'
)
foreach($pages as $page)
{
$product = array();
$source = file_get_html($page);
foreach($source->find('img') as $src)
{
if (strpos($src->src,"http://myshop.com") === false)
{
$product['image'] = "http://myshop.com/$src->src";
}
}
foreach($source->find('p[class*=imAlign_left]') as $description)
{
$product['description'] = $description->innertext;
}
foreach($source->find('span[class*=fc3]') as $title)
{
$product['title'] = $title->innertext;
}
//debug perposes!
echo "Current Page: " . $page . "\n";
print_r($product);
echo "\n\n\n"; //Clear seperator
}
?>