Can I append an Ajax requestXML object to my document tree all in one go? - dom

Greetings.
Here is an XML object returned by my server in the responseXML object:
<tableRoot>
<table>
<caption>howdy!</caption>
<tr>
<td>hello</td>
<td>world</td>
</tr>
<tr>
<td>another</td>
<td>line</td>
</tr>
</table>
Now I attach this fragment to my document tree like so:
getElementById('entryPoint').appendChild(responseXML.firstChild.firstChild);
But instead of being rendered as a table, I get the following text:
howdy! helloworldanotherline
The same result occurs of I replace firstChild.firstChild with just firstChild.
It seems like I'm just getting the nodeValues, and all of the tags are stripped out?!
Am I fundamentally misunderstanding what the responseXML object is supposed to represent?
This works, BTW, if I take out the 'root' tags, and set innerHTML to responseText.
Can someone please enlighten me on the correct way to use responseXML?

You get the text instead of a table, because you use pure DOM for manipulations and your response XML doesn't have the namespaces declarations. So when appending an XML element browser doesn't know whether your "table" tag is from HTML, XUL, SVG or else from.
1) Add namespace declaration:
<table xmlns="http://www.w3.org/1999/xhtml">
2) Instead of directly inserting a reffered XML DOM Element, you should first import that node into your HTML DOM Document:
var element = document.importNode(responseXML.firstChild.firstChild, true);
document.getElementById('entryPoint').appendChild(element);
Hope this helps!

You can create an element at the position you want to insert and than do
element.innerHTML = request.responseText

Related

Meteor: How to return a Template from a Template Helper?

n00b here. I'm trying to "inject" an arbitrary template into another. But it seems like I'm doing it wrong :)
whatever.html:
<template name="parent">
{{child}}
</template>
<template name="child1">
I'm child 1
</template>
<template name="child2">
I'm child 2
</template>
whatever.coffee
x = "child1"
Template.parent.child = -> Template[x](#)
This will create "annotated HTML" (http://docs.meteor.com/#template_call) as the result, but the output of the {{child}} helper is html-encoded and thus is not interpreted.
I'm aware that I could use the Template.myTemplate.rendered event to add the template directly to the DOM using jQuery. But that seems like quite a hack imho. I'd rather have a helper generate that if possible.
What is the "right" way to do this? Is it possible to unescape the result in the template? Will reactivity work?
Thanks in advance!!1
Regards
A {{doubleBrace}} escapes HTML while a {{{tripleBrace}}} does not escape HTML and renders it as is.
EDIT: I mentioned it other way around.
From Handlebars docs - "Handlebars HTML-escapes values returned by a {{expression}}. If you don't want Handlebars to escape a value, use the 'triple-stash'."

Trouble pinpointing child elements while using Mojo::DOM

I'm trying to extract text from an old vBulletin forum using WWW::Mechanize and Mojo::DOM.
vBulletin doesn't use HTML and CSS for semantic markup, and I'm having trouble using Mojo::DOM->children to get at certain elements.
These vBulletin posts are structured differently depending on their content.
Single message:
<div id="postid_12345">The quick brown fox jumps over the lazy dog.<div>
Single message quoting another user:
<div id="postid_12345">
<div>
<table>
<tr>
<td>
<div>Quote originally posted by Bob</div>
<div>Everyone knows the sky is blue.</div>
</td>
</tr>
</table>
</div>
I disagree with you, Bob. It's obviously green.
</div>
Single message with spoilers:
<div id="postid_12345">
<div class="spoiler">Yoda is Luke's father!</div>
</div>
Single message quoting another user, with spoilers:
<div id="postid_12345">
<div>
<table>
<tr>
<td>
<div>Quote originally posted by Fred</div>
<div class="spoiler">Yoda is Luke's father!</div>
</td>
</tr>
</table>
</div>
<div class="spoiler">No waaaaay!</div>
</div>
Assuming the above HTML and an array packed with the necessary post IDs:
for (#post_ids) {
$mech->get($full_url_of_specific_forum_post);
my $dom = Mojo::DOM->new($mech->content);
my $div_id = 'postid_' . $_;
say $dom->at($div_id)->children('div')->first;
say $dom->at($div_id)->text;
}
Using $dom->at($div_id)->all_text gives me everything in an unbroken line, which makes it difficult to tell what's quoted and what's original in the post.
Using $dom->at($div_id)->text skips all of the child elements, so quoted text and spoilers are not picked up.
I've tried variations of $dom->at($div_id)->children('div')->first, but this gives me everything, including the HTML.
Ideally, I'd like to be able to pick up all the text in each post, with each child element on its own line, e.g.
POSTID12345:
+ Quote originally posted by Bob
+ Everyone knows the sky is blue.
I disagree with you, Bob. It's obviously green.
I'm new to Mojo and rusty with Perl. I wanted to solve this on my own, but after looking over the documentation and fiddling with it for a few hours, my brain is mush and I'm at a loss. I'm just not getting how Mojo::DOM and Mojo::Collections work.
Any help will be greatly appreciated.
Looking at the source of Mojo::DOM, basically the all_text method recursively walks the DOM and extracts all text. Use that source to write your own walking the DOM function. Its recursive function depends on returning a single string, in yours you might have it return an array with whatever context you need.
EDIT:
After some discussion on IRC, the web scraping example has been updated, it might help you guide you. http://mojolicio.us/perldoc/Mojolicious/Guides/Cookbook#Web_scraping
There is a module to flattern HTML tree, HTML::Linear.
The explanation of purpose for flatterning HTML tree is a bit long and boring, so here's a picture showing the output of the xpathify tool, bound with that module:
As you see, HTML tree nodes become single key/value list, where the key is the XPath for that node, and the value is the node's text attribute.
In a few keystrokes, this is how you use HTML::Linear:
#!/usr/bin/env perl
use strict;
use utf8;
use warnings;
use Data::Printer;
use HTML::Linear;
my $hl = HTML::Linear->new;
$hl->parse_file(q(vboard.html));
for my $el ($hl->as_list) {
my $hash = $el->as_hash;
next unless keys %{$hash};
p $hash;
}

How to access a session ArrayList by index in a form?

I have a session variable which is of type ArrayList.
In the jsp page I need to access it by index to create a form dynamically, but after I submit the form I found out that the session ArrayList's elements values didn't change.
Here it is what I've tried on my JSP page (I use struts2 Framework):
<s:iterator value="anotherArray" status="RowsIterator">
<tr>
<td>
<s:iterator value="actionOptionsArray" status="iter">
<s:radio
name="#session.chosenActionsArray[%{#RowsIterator.index}]" <!-- The concerned line -->
list="%{actionOptionsArray[#iter.index]}"
value="#{actionOptionsArray[0]}"
theme="simple" />
<br>
</s:iterator>
</td>
<!-- other fields-->
</tr>
</s:iterator>
anotherArray and #session.chosenActionsArray have the same size.
I guess I iterate it wrongly, but in my case iterating it by index is an obligation.
Thank you a lot in advance :)
You need to access the session via an action, the session is accessible from the jsp but not directly from the outside world in this way.
Have the action you are submitting the form to implement SessionAware. I would create a getter/setter for an ArrayList along with proper validation and then move those values into into the session via the execute method. I'm not a fan of exposing your session directly to the outside world (providing a setter for the session in your action)... if you do this you need to be aware that you may have given a malicious user access to things you might not have expected.
Edit
Suppose you have an ArrayList of ArrayList of String called "matrix" in your action... you can iterate the properties via:
<s:iterator value="matrix">
<s:iterator>
<s:property/>
</s:iterator>
</s:iterator>
The outer iterator, iterates over "matrix" which pushes each instance to the top of the value stack. The inner iterator will use what is at the top of the stack by default same with the property tag. Placing tr's and td elements in the right place an you could render a table.
To generate the right name attribute for input elements (possibly hidden ones) you would want them in the form matrix[i][j] where i and j are integers and would define an appropriate matrix. Using status attribute of iterator as you've done would be a good way to generate the indexes.

Why are some of my tags being removed (GWT)?

I'm adding an element to a document with the following:
Element parent = getParentElement(); // Returns the right thing.
HTML html = new HTML();
html.setHTML( "<td>BLAH</td>" );
parent.appendChild( html.getElement() );
When I view the resulting document with FireBug though, the parent's child looks like this:
<div class="gwt-HTML"> BLAH </div>
I can use FireBug to add in the <td> elements manually, and all my formatting applies, etc. Does anyone know why the HTML element seems to be removing my <td> tags?
It turns out that it's FireFox that's stripping it out. If I just use plain old javascript to create a div, or a tr, and set innerHTML to be <td>BLAH</td>, it still gets stripped. A couple of others have noticed this as well: http://www.jtanium.com/2009/10/28/firefox-gotcha-innerhtml-strips-td-tags/
If I use javascript to create a <table> tag, and add it to the DOM, I can then place the <td> in that. Of course, it helpfully creates a <tbody><tr> for me as well, so I'm not really getting back what I put in....

php - splitting a string with HTML by the first instance of a table cell

I am checking on HTML content on my page, and I've got the split down to have the variable left with this content:
">
<td>Oklahoma City</td>
<td>Oklahoma</td>
<td>OK</td>
<td>405</td>
<td>CST</td>
</tr>
</table>
<div id="
Those are dynamic pages I'm checking, so the data will always be different, but the layout the same...
How can I get the value out of the second <td> if that html is in 1 variable(string)?
It was a full page, I've used explode twice to remove everything above a div field and everything below the last dive field id... so it has some open html tags left because I did not know how to get rid of that along the way to be left with just this:
<td>Oklahoma City</td>
<td>Oklahoma</td>
<td>OK</td>
<td>405</td>
<td>CST</td>
</tr>
</table>
Can you tell me how to get that out? I just need the second one because it is the county and that is what I'm checking on...