'ignore if constant not found (where constant is regex)
I hit a snag. This code snippet works great to get film ratings, when they exist. It errors out when it gets to a record that doesn't include the regex. "TypeError: Cannot read property '0' of null"
const ratingPass1 = /<span class="rating rated-([\s\S]*?)">/g;
const ratingPass2 = /(?<=<span class="rating rated-).*?(?=\">)/g;
for(var i = 0; i < 18; i++)
{ var rating1String = results[i].match(ratingPass1);
Logger.log('content: ' + rating1String[0]);
var rating2String = rating1String[0].match(ratingPass2);
--> error is here Logger.log('content: ' + rating2String[0]);
I'm too new to javascript to know how to implement an 'includes' or 'contains' or something of that ilk in this code. But I'm getting not too bad with Regex, and figured I might be able to turn the regex into one large excluded group with the included group within it, so I tried:
const ratingPass1 = /(?:<span class="rating rated-([\s\S]*?)">)/g;
var rating1String = results[i].match(ratingPass1);
Logger.log('content: ' + rating1String[0]);
but I keep getting the error, and I should, I guess because I'm still saying "find it, but it exclude it", where I need a "if you don't find it, just ignore it". Maybe it's the "match" in
var rating1String = results[i].match(ratingPass1);
Logger.log('content: ' + rating1String[0]);
that could be changed to say something like match OR ignore if null?
Update: It took quite a few hours, but I figured something out. Might just work by some fluke, but at least it works!
I replaced the variables and logging info with the following:
var rating0String = "";
var rating1String = results[i].match(ratingPass1);
if(!ratingPass1){
Logger.log('content: ' + rating0String);
}else{
Logger.log('content: ' + rating1String);
};
var rating2String = results[i].match(ratingPass2);
if(!ratingPass2){
Logger.log('content: ' + rating0String);
}else{
Logger.log('content: ' + rating2String);
};
Solution 1:[1]
It can be done effectively using Cheerio library, check self-explanatory comments in code:
function matchRating()
{
// TODO replace html with your data
const html = '<div><span class="rating rated-one"></span><span class="rating rated-two"></span><span class="rating rated-three"></span></div>';
// create Cheerio object
const $ = Cheerio.load(html);
const ratingPrefixForClass = 'rated-';
// select all spans with `rating` class
$(".rating").each((i, el) => {
let classAttr = $(el).attr('class');
// split class attribute to get list of class names, find one with needed prefix
let ratingClassSearch = classAttr.split(' ').find(cls => cls.indexOf(ratingPrefixForClass) === 0);
// if needed class with prefix found, log its name, and its name without prefix
if (ratingClassSearch)
{
console.log(ratingClassSearch, ratingClassSearch.substring(ratingPrefixForClass.length));
}
});
}
Main points:
- Do not use regex for parsing HTML.
- Uses Cheerio JS library ported for Google Apps Script. To install it, you need add it as a dependency.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | Kos |
