CheerioJS, looping through <ul> with same class name - node.js

I'm trying to loop through each <ul> and get the value of each <li>. The thing is, it only takes the first <ul> and skips the rest.
HTML
<div id="browse-results">
<ul class="tips cf">
<li>tip11</li>
<li>tip12</li>
<li>tip13</li>
</ul>
<ul class="tips cf">
<li>tip21</li>
<li>tip22</li>
<li>tip23</li>
</ul>
<ul class="tips cf">
<li>tip31</li>
<li>tip32</li>
<li>tip33</li>
</ul>
<ul class="tips cf">
<li>tip41</li>
<li>tip42</li>
<li>tip43</li>
</ul>
</div>
Cheerio Parsing
$('#browse-results').find('.tips.cf').each(function(i, elm) {
console.log($(this).text()) // for testing do text()
});
$('#browse-results').children().find('.tips').each(function(i, elm) {
console.log($(this).text())
});
I've tried many more
The output is just the values of the first <ul>.
tip11
tip12
tip13
Please note guys that this is just a snippet example with the same structure of what I'm trying to parse.
I spent nearly 2 hours on this, and I can't find a way to do it.

Try this:
var html = '<div id="browse-results"> \
<ul class="tips cf"> \
<li>tip11</li> \
<li>tip12</li> \
<li>tip13</li> \
</ul> \
<ul class="tips cf"> \
<li>tip21</li> \
<li>tip22</li> \
<li>tip23</li> \
</ul> \
<ul class="tips cf"> \
<li>tip31</li> \
<li>tip32</li> \
<li>tip33</li> \
</ul> \
<ul class="tips cf"> \
<li>tip41</li> \
<li>tip42</li> \
<li>tip43</li> \
</ul> \
</div>';
var $ = cheerio.load(html);
$('#browse-results li').each(function(i, elm) {
console.log($(this).text()) // for testing do text()
});
This will select all li elements which are descendants of #browse-results.

Related

bootstrap5 navbar justify content between doesnt work

Hi im trying to make a navbar with 3 link in container class.I tried justify content between on navbar but it doesnt work justify content center works but between class doesnt work on navbar links displays like block.
<nav class="navbar navbar-expand-lg navbar-dark bg-dark d-flex ">
<div class="container justify-content-between ">
<ul class="navbar-nav">
<li class="nav-item">
About
</li>
<li class="nav-item">
Contact
</li>
<li class="nav-item">
About
</li>
</ul>
</div>
</nav>
<nav class="navbar navbar-expand-lg navbar-dark bg-dark">
<div class="container">
<ul class="navbar-nav d-flex flex-row align-items-center justify-content-between w-100">
<li class="nav-item">
About
</li>
<li class="nav-item">
Contact
</li>
<li class="nav-item">
About
</li>
</ul>
</div>
</nav>
You can try this.
that is because you are using flex on different element and justify-content in different element,
my suggestion is to use this
<nav class="navbar navbar-expand-lg navbar-dark bg-dark">
<div class="container d-flex justify-content-between ">
<ul class="navbar-nav">
<li class="nav-item">
About
</li>
<li class="nav-item">
Contact
</li>
<li class="nav-item">
About
</li>
</ul>
</div>
</nav>
also as a bonus suggestion use header instead of nav and replace the first div with nav for SEO purpose by using right semantic elements

CheerioJS get specific <li> where header text 'What I Want'

I'm trying to get li elements where the header is 'What I want'
This is my Code:
let wants = []
$$('li').each((wantIdx, wantElement) => {
const want= $(relatedArticleElement).text()
wants.push(want)
})
and this is the HTML i'm trying to parse from:
<div class="side-list-panel">
<h4 class="panel-header">What I Want</h4>
<ul class="panel-items-list">
<li>
1
</li>
<li>
2
</li>
<li>
3
</li>
<li>
4
</li>
<li>
5
</li>
</ul>
</div>
<div class="side-list-panel">
<h4 class="panel-header">What I don't want</h4>
<ul class="panel-items-list">
<li>
a
</li>
<li>
b
</li>
<li>
c
</li>
<li>
d
</li>
<li>
e
</li>
</ul>
</div>
this code gets me every single li elements in the page obviously, is there any way i can only get the lis under the 'What I Want' panel-header?
You can get those with:
$('h4:contains("What I Want") + ul li').get().map(li => $(li).text())
You can try JQuery's contains if Cheerio supports it Example $('td:contains("male")')

jQuery QueryBuilder doT.js template syntax inside twig file

I try to rewrite the rule template like this:
$(queryBuilderId).queryBuilder({
templates: {
rule: '\
<div id="{{= it.rule_id }}" class="rule-container"> \
<div class="rule-header"> \
<div class="btn-group pull-right rule-actions"> \
<button type="button" class="btn btn-xs btn-danger" data-delete="rule"> \
<i class="{{= it.icons.remove_rule }}"></i> {{= it.translate("delete_rule") }} \
</button> \
</div> \
</div> \
{{? it.settings.display_errors }} \
<div class="error-container"><i class="{{= it.icons.error }}"></i></div> \
{{?}} \
<div class="rule-filter-container"></div> \
<div class="rule-operator-container"></div> \
<div class="rule-value-container"></div> \
</div>'
}
})
I have included the doT.js in my header, but twig throws me this error:
Unexpected token "operator" of value "=".
Does somebody knows how I can use doT.js template syntax inside my twig file?

How to add menu link wrapper in drupal 7?

I have a menu, one menu item looking like this:
<li>
LINK TITLE
</li>
And I want this:
<li>
<a href="aaa">
<div class="custom">LINK TITLE</div>
</a>
</li>
Or this:
<li>
<div class="custom">
LINK TITLE
</div>
</li>
How can I do this?
This works:
function theme_menu_link(array $variables) {
$variables['element']['#localized_options']['html'] = true;
$variables['element']['#title'] = '<div class="custom">' . $variables['element']['#original_link']['link_title'] . '</div>';
return theme_menu_link($variables);
}

Unable to extract an html fragment using cheerio

I am using cheerio to perfom some html manipulation on node js server .I have an html string like this
var htmlString =" <ol>
<li>
<p>item1</p>
</li>
<li>
<p>item2</p>
</li>
<li>
<p>item 3</p>
</li>
<li>
<p>item 4</p>
</li>
</ol>
<p>First paragraph</p>
<p>second paragraph</p>
<p>Third paragraph</p>
"
var $ = cheerio.load(htmlString);
var dummy = $("<div></div>")
var item = dummy.append($("*").slice(0,3).clone()).html();
The output returned is
<ol>
<li>
<p>item1</p>
</li>
<li>
<p>item2</p>
</li>
<li>
<p>item 3</p>
</li>
<li>
<p>item 4</p>
</li>
</ol>
<li>item1</li>
<p>item1</p>
The output that I expect is the ordered list followed byparagraph1 followed by paragraph2
Am I doing something wrong or is this a bug in cheerio?
After fiddling with the code for the entire day I finally got the solution. Apparently I was loading the html fragment incorrectly. This worked for me
var $ = cheerio.load();
var dummy = $("<div></div>")
var item = dummy.append($(htmlString).slice(0,3)).html();

Resources