Find and replace text in whole DOM - javascript

I am making a chrome extension to find a string if text in DOM and replace it with something else.
What is the best way to traverse the whole DOM element wise and replace the text in DOM. I Thought of placing document.body in a variable and then process it as a qeue but I am confused that how to do so
This is my Code:
flag = true;
var word = 'word',//word to replace
queue = [document.body],
curr;
try {
while ((curr = queue.pop()) || flag) {
if (!(curr.textContent.match(word))
continue;
for (var i = 0; i < curr.childNodes.length; ++i) {
if (!flag) break;
switch (curr.childNodes[i].nodeType) {
case Node.TEXT_NODE: // 3
if (curr.childNodes[i].textContent.match(word)) {
curr.childNodes[i].textContent("xxx");//replacing the word
console.log('Found!');
flag = false;
break;
}
break;
case Node.ELEMENT_NODE: // 1
queue.push(curr.childNodes[i]);
break;
}
}
}
} catch (e) {
//
}

you can do it I think with
function replaceAll(recherche, remplacement, chaineAModifier)
{
return chaineAModifier.split(recherche).join(remplacement);
}
str = $('body').html()
replaceAll(search_word,replacement,str)
$('body').html(str)
but that will replace everything including html nodes attribute and name

Related

Using switch case in javascript

This is the variable i am having right now
[
{
"_id":"63773059c3160f782c087e33",
"nfrid":"637328ebf5c4b2558b064809",
"nfrname":"azuread",
"fileName":"package.json",
"isImport":false,
"isConst":false,
"isComponent":false,
"isNewFile":false,
"landmark":"\"react\"",
"isAfter":false,
"fileContent":"\"#azure/msal-react\": \"^1.4.9\",",
"filePath":"package.json",
"isPackage":true,
"isIndexHtml":false,
"projecttypeid":"6372366d1b568e00d8af2e44",
"projecttypetitle":"PWA React",
"nfrGitIo":[
{
"_id":"637328ebf5c4b2558b064809",
"iconpath":"https://cdnerapidxdevportal.azureedge.net/webdesignerimages/azure-active-directory-aad-icon-488x512-3d71nrtk.png",
"title":"Azure AD",
"description":"Azure Active Directory (Azure AD), part of Microsoft Entra, is an enterprise identity service that provides single sign-on, multifactor authentication, and conditional access to guard against 99.9 percent of cybersecurity attacks."
}
]
},
{
"_id":"63773144c3160f782c087e35",
"nfrid":"637328ebf5c4b2558b064809",
"nfrname":"azuread",
"fileName":"index.js",
"isImport":true,
"isConst":false,
"isComponent":false,
"isNewFile":false,
"isPackage":false,
"landmark":null,
"isAfter":null,
"fileContent":"import { MsalProvider } from '#azure/msal-react';import { msalConfig } from './authConfig';import {PublicClientApplication } from '#azure/msal-browser';",
"filePath":"src/index.js",
"isIndexHtml":false,
"projecttypeid":"6372366d1b568e00d8af2e44",
"projecttypetitle":"PWA React",
"nfrGitIo":[
{
"_id":"637328ebf5c4b2558b064809",
"iconpath":"https://cdnerapidxdevportal.azureedge.net/webdesignerimages/azure-active-directory-aad-icon-488x512-3d71nrtk.png",
"title":"Azure AD",
"description":"Azure Active Directory (Azure AD), part of Microsoft Entra, is an enterprise identity service that provides single sign-on, multifactor authentication, and conditional access to guard against 99.9 percent of cybersecurity attacks."
}
]
},
]
I am having many flags like isImport, isPackage, isIndexHtml like that. I am trying to put those flags in a switch case and call individual function when each flag is true.Something like this,
for (let i = 0; i < cosmos.length; i++) {
console.log(cosmos[0].isPackage);
switch (cosmos[i]) {
case `${cosmos[i].isImport === true}`:
const statusImport = common.updateImport(cosmos[i]);
console.log(statusImport);
break;
// case `${cosmos[i].isConst === true}`:
// console.log("I own a dog");
// break;
case `${cosmos[i].isPackage === true}`:
const statusPackage = common.updatePackage(cosmos[i]);
console.log(statusPackage);
break;
case `${cosmos[i].isIndexHtml === true}`:
const statusIndexHtml = common.updateIndexHTML(cosmos[i]);
console.log(statusIndexHtml);
break;
// case `${cosmos[i].isNewFile === true}`:
// const statusNewFile = common.addNewFile(cosmos[i]);
// console.log(statusNewFile);
// break;
default:
console.log("Nothing to add/update");
break;
}
}
But when I run this i am always getting the default console log. I dont know what i am missing
This is my first switch case implementation. Can someone point me in the right direction?
Don't convert them to strings and in switch condition add just true:
for (let i = 0; i < cosmos.length; i++) {
console.log(cosmos[0].isPackage);
switch (true) {
case cosmos[i].isImport:
const statusImport = common.updateImport(cosmos[i]);
console.log(statusImport);
break;
case cosmos[i].isPackage:
const statusPackage = common.updatePackage(cosmos[i]);
console.log(statusPackage);
break;
case cosmos[i].isIndexHtml:
const statusIndexHtml = common.updateIndexHTML(cosmos[i]);
console.log(statusIndexHtml);
break;
default:
console.log("Nothing to add/update");
break;
}
}
switch is not the right construct to use in this case.
Simply use if/else here.
Since you're testing several different values from cosmos[i], not testing a single value against multiple possible matches, switch isn't the right tool here. (You can use it, just like you can use a wrench to bang in a nail, but it's not the right tool.) Instead, use an if/else if/else chain:
for (let i = 0; i < cosmos.length; i++) {
if (cosmos[i].isImport) {
const statusImport = common.updateImport(cosmos[i]);
console.log(statusImport);
} else if (cosmos[i].isPackage) {
const statusPackage = common.updatePackage(cosmos[i]);
console.log(statusPackage);
} else if (cosmos[i].isIndexHtml) {
const statusIndexHtml = common.updateIndexHTML(cosmos[i]);
console.log(statusIndexHtml);
} else {
console.log("Nothing to add/update");
}
}
Separately, in new code, I'd suggest using a for-of instead of a for when you don't need the index:
for (const entry of cosmos) {
if (entry.isImport) {
const statusImport = common.updateImport(entry);
console.log(statusImport);
} else if (entry.isPackage) {
const statusPackage = common.updatePackage(entry);
console.log(statusPackage);
} else if (entry.isIndexHtml) {
const statusIndexHtml = common.updateIndexHTML(entry);
console.log(statusIndexHtml);
} else {
console.log("Nothing to add/update");
}
}
A switch statement can only interrogate one variable. In your case the correct solution is an if statement for each member variable. Replace the switch statement with this snippet:
if (cosmos[i].isImport === true) {
const statusImport = common.updateImport(cosmos[i]);
console.log(statusImport);
}
if (cosmos[i].isPackage === true) {
const statusPackage = common.updatePackage(cosmos[i]);
console.log(statusPackage);
}
if (cosmos[i].isIndexHtml === true) {
const statusIndexHtml = common.updateIndexHTML(cosmos[i]);
console.log(statusIndexHtml);
}
I note that your data structure does not mutually exclude the isImport isPackage and isIndexHtml - so in principle any combination of them could be true and my proposed code would execute accordingly.

How to go to an a Specific HTML when a word is detected (Java)

Java I made an HTML called hello.html and now I want to use the replace() function in Java to go to the HTML page when the word "Covid" is detected on Google, I tried but it doesn't work for some reason, can you see where I am going wrong, or do I have to change my entire code?
function redirectURL() {
var specWord = getSpecificWord();
switch(specWord)
{
case 'corona':
window.location.replace('hello.html');
break;
case 'covid':
window.location.replace('hello.html');
break;
case 'covid-19':
window.location.replace('hello.html');
break;
default:
return true;
break;
}
return false; // don't let the form submit
}
function getSpecificWord(Element) {
var specificWord = "corona";
return specificWord;
}
The code does not work since you are not calling the redirectURL function.
Append redirectURL() to your code or use this instead:
(function redirectURL() {
var specWord = getSpecificWord();
switch (specWord) {
case 'corona':
window.location.replace('hello.html');
break;
case 'covid':
window.location.replace('hello.html');
break;
case 'covid-19':
window.location.replace('hello.html');
break;
default:
return true;
break;
}
return false; //don't let the form submit
})();
function getSpecificWord(Element) {
var specificWord = 'corona';
return specificWord;
}

Calling a function within a for loop - JavaScirpt

Hi I am trying to call a function within a for loop but It isn't working...This is how my code currently looks like:
bot.on('message', data => {
if (data.type !== 'message' || data.subtype === 'bot_message') {
return;
}
findClassroomMention(data,text);
});
var classrooms =
{
L108: ["lokaal 108","L108","108"],
L208: ["lokaal 208","L208","208"]
};
function findClassroomMention(message) {
var found = false
for(var ClassroomId in classrooms) {
for(var term of classrooms[ClassroomId]) {
if(message.includes(term)) {
found = ClassroomId;
notifyProblemSolver();
break;
}
}
if (found) notifyProblemSolver(); break;
}
return found
};
function notifyProblemSolver(ClassroomId) {
const params = {
icon_emoji: ':smiley:'
}
bot.postMessageToChannel('caris','We have a problem in' + ClassroomId, params);
};
I want the function notifyProblemSolver() to be called in the for loop...But if I run the code it isn't working. Any tips? Thanks in advance!
I think if (found) notifyProblemSolver; break; is the issue. That break will be called regardless of if (found) so for(var ClassroomId in classrooms) { will only run once.
I think you meant
if (found) {
notifyProblemSolver();
break;
}
I've seen some unnecessary semicolons at the end of functions. Also the part:
if (found) notifyProblemSolver; break;
Should be replaced with:
if (found) notifyProblemSolver(); break;
Because you are calling a function here, instead it was an expression.
Let me know if this works.
Full code modification here:
https://jsfiddle.net/terza_terza/ms9xLrzu/3/

How to get my loop to start from the beginning after error detected

I am trying to get my loop to restart when it comes across an user input error. I need it to restart at the very beginning and not just the last question.
So below when it says validImput = false this is where I am trying to get it to restart.
{
var validInput = true;
var start = confirm('Add item to shoping cart');
if (start == true) {
// ask first question
var orderProductCodeArr = parseInt(prompt('Enter input: '), 10);
if (isNaN(orderProductCodeArr)) {
alert("input is not a valid number");
validImput = false
} else if (orderProductCodeArr < 0 || orderProductCodeArr >= PRODUCT_LIST.length) {
alert("code does not match any item");
validInput = false;
}
// ask second question
else if(validInput == true) {
var item = PRODUCT_LIST[orderProductCodeArr];
alert("item is: " + item);
}
// get quantity input
var quanityArr = parseInt (prompt('Enter quality amount'),10);
if (isNaN(quanityArr)) {
alert("input is not a valid number");
validInput = false;
}
} else {
document.writeln('still to come')
}
}
The usual method of starting something over is some sort of loop construct, often using while like this:
while (true) {
// your loop code here
// you can use break; to break out of the while loop
// anywhere to stop repeating
// you can use continue; to jump to the next iteration immediately
}
Or, sometimes you use a loop condition like this:
var doAgain = true;
while (doAgain) {
// within the loop, you set doAgain to false when you are done
// and don't want to repeat the loop again
}
try
function test()
{
for(var s=0;s<5;s++)
{
try
{
//body of the for loop
}catch(e){s=0;}
}
}

Simple JavaScript Selector

Using pure JavaScript without any library like jQuery, how could I detect if a variable holds a DOM Class or ID?
For example if I pass into a function a value that could be...
var mySelector = ".class-name";
or
var mySelector = "#id-name";
Then based on if mySelector holds a Class or ID I would run
document.getElementsByClassName
or
document.getElementsById
What would be the best way to do this without the use of a library like jQuery or another library?
Take a look at document.querySelector or document.querySelectorAll, instead. Both of those can find elements by ID or class (as well as other selectors). querySelector will return 1 element, querySelectorAll will return all elements.
var mySelector = ".class-name", // "#id-name" will also work fine.
elements = document.querySelectorAll(mySelector);
Note that this doesn't work in IE < 8 (see http://caniuse.com/#search=querySelectorAll). A polyfill would be the best way to handle it to add IE7 support.
You can use this simple if/else statement to differentiate. This would also allow you to run other code based on whether it's a class or an ID you are referencing.
var mySelector = ".class-name";
if(mySelector.charAt(0) == ".")
{
document.getElementsByClassName(mySelector.substring(1));
}
else if(mySelector.charAt(0) == "#")
{
document.getElementsById(mySelector.substring(1));
}
The first way I think is check a first symbol of stroke.
Something like:
var $ = function( string ) {
var result;
switch (string.substr(0,1)) {
case '.': result = document.getElementsByClassName(string); break;
case '#': result = document.getElementById(string); break;
default: result = document.getElementsByTagName(string); break;
}
return result;
}
var mySelector = ".class-name";
console.log( $(mySelector) );
Just because you only want a selector and not the entire jQuery library, doesn't mean you have to roll your own own. jQuery uses the Sizzle selector engine, and you could just as easily use it yourself without the overhead of full jQuery:
http://sizzlejs.com/
I'm not an advanced user, but some time ago I created this little script:
https://gist.github.com/caiotarifa/cc7d486292f39157d763
var __;
__ = function(selector, filter) {
'use strict';
var response;
function filtering(selectors, filter) {
switch (filter) {
case "first":
return selectors[0];
break;
case "last":
return selectors[selectors.length - 1];
break;
default:
return selectors[filter];
break;
}
}
selector = selector.trim();
if (typeof filter === "string") { filter = filter.trim(); }
if (selector.indexOf(' ') < 0 && selector.indexOf('.', 1) < 0 && selector.indexOf('#', 1) < 0) {
switch (selector.substr(0, 1)) {
case '.':
response = document.getElementsByClassName(selector.substr(1));
if (response.length === 1) { filter = "first"; }
if (typeof filter !== "undefined") { response = filtering(response, filter) }
break;
case '#':
response = document.getElementById(selector.substr(1));
break;
default:
response = document.getElementsByTagName(selector);
if (response.length === 1) { filter = "first"; }
if (typeof filter !== "undefined") { response = filtering(response, filter) }
break;
}
} else {
if (typeof filter !== "undefined") {
switch (filter) {
case "first":
response = document.querySelector(selector);
break;
case "last":
response = document.querySelectorAll(selector);
response = response[response.length - 1];
break;
default:
response = document.querySelectorAll(selector);
response = response[filter];
break;
}
} else {
response = document.querySelectorAll(selector);
if (response.length === 1) { response = response[0]; }
else if (response.length < 1) { response = false; }
}
}
return response;
};
It's simple to use it:
__("div")
Or passing some filter like:
__("div", "first")
I didn't make a benchmark test with it. I hope it can help you.

Categories

Resources